aes encryption and openssl descryption (interoperable)
hi all,
I am a new to encryption using AES, actually it is an adhoc task.
also new to the jce library.
I need to encrypt a text file from java program using bouncycastle jce as provider.
i create both encrypt and decrypt program. They work fine(the decrypt can store the original text from encrypted on). but it got corrupt when use openssl (0.98) under command prompt on win32 platform. i am seeking help why openssl can't decrypt the file correct
after encrypted the text using java program and try using the openssl command to restore the original text.
D:\fts\aes>openssl enc -d -aes-128-cbc -k 1234567890123456 -in encrypt.aes -out
test.des -nosalt
it shows the folllowing error
bad decrypt
3860:error:06065064:digital envelope routines:EVP_DecryptFinal:bad decrypt:.\cry
pto\evp\evp_enc.c:450:
what happen to my java code. do i provide the wrong key to openssl
or i miss any components in openssl.?
I understand there it need IV, but i just ignore it, it works fine in decrypted code. does openssl to provide iv explicitly?
I also taked alook of the post threadid=739626. but its code seems not compatiable in my version. it will be appreciated if the complete code is provided. i just a beginner in java ce with some theory/concept from books.
thx
here is my encrypt code.
import java.io.*;
import javax.crypto.*;
import javax.crypto.spec.*;
import java.security.*;
import java.security.cert.*;
import org.bouncycastle.jce.provider.BouncyCastleProvider;
import org.bouncycastle.util.encoders.Hex;
public class EncryptFile3 {
public static void main(String args[]) {
if (args.length < 1) {
System.out.println("Usage: java EncryptFile <file name>");
System.exit(-1);
}
try {
File desFile = new File("encrypt.aes");
FileInputStream fis = null;
FileOutputStream fos;
CipherInputStream cis;
//String xform = "AES/CBC/PKCS5Padding";
String xform = "AES/CBC/NoPadding";
// Creation of Secret key
byte[] keyBytes = "1234567890123456".getBytes(); //AES 128bit
Security.addProvider(new org.bouncycastle.jce.provider.BouncyCastleProvider());
System.out.println("Generate key for AES at "+keyBytes.length +" bits");
Key key = new SecretKeySpec(keyBytes, "AES");
// Creation of Cipher objects
Cipher encrypt = Cipher.getInstance(xform);
System.out.println("Get Provider Info."+encrypt.getProvider().getInfo());
encrypt.init(Cipher.ENCRYPT_MODE, key);
// Open the Plaintext file
try {
fis = new FileInputStream(args[0]);
} catch(IOException err) {
System.out.println("Cannot open file!");
System.exit(-1);
}
cis = new CipherInputStream(fis, encrypt);
// Write to the Encrypted file
fos = new FileOutputStream(desFile);
byte[] b = new byte[8];
//fos.write("Salted__".getBytes());
int i = cis.read(b);
while (i != -1) {
fos.write(b, 0, i);
i = cis.read(b);
}
fos.flush();
fos.close();
cis.close();
fis.close();
} catch(Exception e){
e.printStackTrace();
}
}
}
[3314 byte] By [
kyhoa] at [2007-10-3 2:59:23]

I have just modified my AES file encryption example to generate the openssl command to decrypt based on the keys and iv used. The result is
openssl enc -d -aes-128-cbc -K 30313233343536373839414243444546 -iv 30313233343536373031323334353637 -in /home/sabre/user.sql.enc -out abc.sql
which decrypts successfully.
Notice that I have used an 'iv' and that I have specified the key and 'iv' on the command line in hex. The -k parameter that you use is inappropriate when using an explicit key rather than a passphrase.
hi sabre,thx ur reply, i understand there is a IV parameter. but in my code there is no IV parameter to set. would you mind show me how to set the parameter in java program?or show me ur encrypt java program?appreciateky
kyhoa at 2007-7-14 20:48:59 >

byte[] iv = your 16 iv bytescipher.init(mode, key, new IvParameterSpec(iv));
just a question , so in ur caseit is byte[] iv= "30313233343536373031323334353637".getBytes();?
kyhoa at 2007-7-14 20:48:59 >

> just a question , so in ur case
> it is
> byte[] iv=
> "30313233343536373031323334353637".getBytes();
>
No ! I have to hex decode "30313233343536373031323334353637" to get the iv bytes int the JCE.
For AES the iv is 16 bytes which in the JCE is specifed as 16 bytes in an array. In openssl the -iv parameter needs 16 bytes but HEX encoded as 32 hex characters. For example if the JCE iv bytes were specified as
byte[] iv = {0x12, 0x34, 0x56 ... 13 more bytes
then the openssl iv would be
-iv 123456 ... 26 more hex chars
Message was edited by:
sabre150
hi sabre150,
thx ur advice, i have successfully encrypt the file from java program
and decrypt using the openssl..
but the key, is it only allowed numeric ?
can i use string as key e.g. "p2123k12232321...."
and also any functions can convert (hex decode) the string to hex presentation?
currently for the key , i am using that kind of style
bytes key[] = {0x1,0x2....}
can i present alphabetic charactor too ? e.g. a, b ,c...
kyhoa at 2007-7-14 20:48:59 >

> thx ur advice, i have successfully encrypt the file
> from java program
> and decrypt using the openssl..
Well done.
>
> but the key, is it only allowed numeric ?
> can i use string as key e.g. "p2123k12232321...."
Of course you can as long as you convert your String to bytes - the key is bytes. String characters can be converted to bytes any number of ways. Examples -
1) byte[] keyBytes = keyString.getBytes("utf-8"); // poor - use any coding you wish.
2) byte[] keybytes = selectRequiredNumberOfBytesFrom(hash(keySring)); //MD5, SHA-1, SHA256 etc hash
3) PKCS5 - http://www.rsasecurity.com/rsalabs/node.asp?id=2127
In my view the best apprach is PKCS5 but whatever you do the key bytes for both the JCE and open SSL must be the same.
>
> and also any functions can convert (hex decode) the
> string to hex presentation?
Don't you mean 'hex encode the bytes'? Check out 'Jakarta Commons Codec'.
> currently for the key , i am using that kind of
> style
> bytes key[] = {0x1,0x2....}
> can i present alphabetic charactor too ? e.g. a, b
> ,c...
See above list.
hi,
i need to do aes encryption and descryption in separate files like for client / server.
i am passing data to be encrypted as arguments.
i am able to encrypt the data and disply.
but to decrypt the data is a problem.
i have 3-files:
--for key generation--
public class blow_key {
public static SecretKeySpec Key_gen()
KeyGenerator kgen = KeyGenerator.getInstance("AES");
kgen.init(128);
SecretKey skey = kgen.generateKey();
byte[] raw = skey.getEncoded();
SecretKeySpec skeySpec = new SecretKeySpec(raw, "AES");
System.out.println("SecretKeySpec skeySpec: " + skeySpec );
return skeySpec;
}
data encryption-
public class blow_enc {
public static byte[] encrypt(byte[] inpBytes, SecretKeySpec key)
throws Exception {
Cipher cipher = Cipher.getInstance("AES");
cipher.init(Cipher.ENCRYPT_MODE, key);
return cipher.doFinal(inpBytes);
}
public static void main(String[] args) throws Exception {
byte[] encryptionBytes = null ;
blow_key my_encrypt = new blow_key();
SecretKeySpec ksp = my_encrypt.Key_gen() ;
encryptionBytes = encrypt(input, ksp);
System.out.println("Encrypted as:" + encryptionBytes);
}
}
--execution:::
java blow_enc sam
Entered: sam
SecretKeySpec skeySpec: javax.crypto.spec.SecretKeySpec@366a3592
Encrypted as:[B@64b1c8
for dec exec
java blow_dec [B@64b1c8
Entered: [B@64b1c8
SecretKeySpec skeySpec: javax.crypto.spec.SecretKeySpec@366a3592
Exception in thread "main" javax.crypto.IllegalBlockSizeException: last block incomplete in decryption
at org.bouncycastle.jce.provider.JCEBlockCipher.engineDoFinal (bcprov-1.31.jar.so)
at javax.crypto.Cipher.doFinal (libgcj.so.7)
at javax.crypto.Cipher.doFinal (libgcj.so.7)
at blow_dec.decrypt (blow_dec.java:18)
at blow_dec.main (blow_dec.java:46)
--data decryption progtam
public class blow_dec {
public static byte[] decrypt(byte[] inpBytes, SecretKeySpec key)
throws Exception {
Cipher cipher = Cipher.getInstance("AES");
cipher.init(Cipher.DECRYPT_MODE, key);
return cipher.doFinal(inpBytes);
}
public static void main(String[] args) throws Exception {
byte[] encryptionBytes = null ;
byte[] input = args[0].getBytes();
blow_key my_encrypt = new blow_key();
SecretKeySpec ksp = my_encrypt.Key_gen() ;
encryptionBytes = decrypt(input, ksp);
System.out.println("Encrypted as:" + encryptionBytes);
}
}
> i need to do aes encryption and descryption in> separate files like for client / server.> i am passing data to be encrypted as arguments.> Since this has little or nothing to do with the topic from original thread you should create a new thread.
hi,
i need to do aes encryption and descryption in separate files like for client / server.
i am passing data to be encrypted as arguments.
i am able to encrypt the data and disply.
but to decrypt the data is a problem.
i have 3-files:
--for key generation--
public class blow_key {
public static SecretKeySpec Key_gen()
KeyGenerator kgen = KeyGenerator.getInstance("AES");
kgen.init(128);
SecretKey skey = kgen.generateKey();
byte[] raw = skey.getEncoded();
SecretKeySpec skeySpec = new SecretKeySpec(raw, "AES");
System.out.println("SecretKeySpec skeySpec: " + skeySpec );
return skeySpec;
}
data encryption-
public class blow_enc {
public static byte[] encrypt(byte[] inpBytes, SecretKeySpec key)
throws Exception {
Cipher cipher = Cipher.getInstance("AES");
cipher.init(Cipher.ENCRYPT_MODE, key);
return cipher.doFinal(inpBytes);
}
public static void main(String[] args) throws Exception {
byte[] encryptionBytes = null ;
blow_key my_encrypt = new blow_key();
SecretKeySpec ksp = my_encrypt.Key_gen() ;
encryptionBytes = encrypt(input, ksp);
System.out.println("Encrypted as:" + encryptionBytes);
}
}
--execution:::
java blow_enc sam
Entered: sam
SecretKeySpec skeySpec: javax.crypto.spec.SecretKeySpec@366a3592
Encrypted as:[B@64b1c8
for dec exec
java blow_dec [B@64b1c8
Entered: [B@64b1c8
SecretKeySpec skeySpec: javax.crypto.spec.SecretKeySpec@366a3592
Exception in thread "main" javax.crypto.IllegalBlockSizeException: last block incomplete in decryption
at org.bouncycastle.jce.provider.JCEBlockCipher.engineDoFinal (bcprov-1.31.jar.so)
at javax.crypto.Cipher.doFinal (libgcj.so.7)
at javax.crypto.Cipher.doFinal (libgcj.so.7)
at blow_dec.decrypt (blow_dec.java:18)
at blow_dec.main (blow_dec.java:46)
--data decryption progtam
public class blow_dec {
public static byte[] decrypt(byte[] inpBytes, SecretKeySpec key)
throws Exception {
Cipher cipher = Cipher.getInstance("AES");
cipher.init(Cipher.DECRYPT_MODE, key);
return cipher.doFinal(inpBytes);
}
public static void main(String[] args) throws Exception {
byte[] encryptionBytes = null ;
byte[] input = args[0].getBytes();
blow_key my_encrypt = new blow_key();
SecretKeySpec ksp = my_encrypt.Key_gen() ;
encryptionBytes = decrypt(input, ksp);
System.out.println("Encrypted as:" + encryptionBytes);
}
}
--
its not complete client server programs.
i just want to pass the encrypted data to another program adn decrypt it.
I thought using arguments is better.
or can just suggest anything else. how to pass the encrypted data like in byte format or String format.
only thing is the encryption and decryption programs should be in differet files.
please do reply soon.
thanks in advance.
can u please help me.
Don't just repeat yourself please. Take the advice above.
ejpa at 2007-7-14 20:48:59 >

Hi. I'm very interested in this interoperability. Do you have the C/C++ code for the openssl library? I'm trying to get it workign via api but without any result.Thanks in advance,Eduardo.
Sorry, it worked at the end if we use Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");and EVP_CipherInit_ex(&ctx, EVP_aes_128_cbc(), NULL,key, iv, 0);Thanks for your help.