AES Encryption using JCE

I have taken the program for AES encrytion and decryption from the site

"http://java.sun.com/developer/technicalArticles/Security/AES/AES_v1.html"

It is working fine if i haven't change any pat of the program except the input to encrypt. I couldn't able to decrypt data of my own. that is i have to read a file and give that file content as the input for decryption.

String strDataToEncrypt =new String();

String strCipherText =new String();

String strDecryptedText =new String();

try{

KeyGenerator keyGen = KeyGenerator.getInstance("AES");

keyGen.init(128);

SecretKey secretKey = keyGen.generateKey();

Cipher aesCipher = Cipher.getInstance("AES");

aesCipher.init(Cipher.ENCRYPT_MODE,secretKey);

byte[] byteDataToEncrypt = CardDeatils.getBytes();

byte[] byteCipherText = aesCipher.doFinal(byteDataToEncrypt);

strCipherText =new BASE64Encoder().encode(byteCipherText);

System.out.println("Cipher Text generated using AES is " +strCipherText+"\n");

String sFilePath="c://CardDetails.txt";

String sFileContent=null,strToDecrypt="";

byte[] ByteToDecrypt=null;

try{

FileOutputStream fos=new FileOutputStream(sFilePath,true);

BufferedOutputStream bos =new BufferedOutputStream(fos);

DataOutputStream dos =new DataOutputStream(bos);

dos.writeBytes(strCipherText);

dos.close();

bos.close();

fos.close();

}catch (Exception e){

System.err.println("File input error");

}

try{

FileInputStream fstream =new FileInputStream(sFilePath);

BufferedInputStream bis =new BufferedInputStream(fstream);

DataInputStream dis =new DataInputStream(bis);

while (dis.available() !=0){

strToDecrypt=dis.readLine();

System.out.println("The data from file is"+strToDecrypt);

}

System.out.println("The data from file is"+strToDecrypt);

ByteToDecrypt=strToDecrypt.getBytes("utf-8");

aesCipher.init(Cipher.DECRYPT_MODE,secretKey);

byte[] byteDecryptedText = aesCipher.doFinal(ByteToDecrypt);

strDecryptedText =new String(byteDecryptedText);

System.out.println(" Decrypted Text message is " +strDecryptedText);

fstream.close();

bis.close();

dis.close();

}catch (IOException e){

System.err.println("File input error");

}

}

catch (NoSuchAlgorithmException noSuchAlgo){

System.out.println(" No Such Algorithm exists " + noSuchAlgo);

}

catch (NoSuchPaddingException noSuchPad){

System.out.println(" No Such Padding exists " + noSuchPad);

}

catch (InvalidKeyException invalidKey){

System.out.println(" Invalid Key " + invalidKey);

}

catch (BadPaddingException badPadding){

System.out.println(" Bad Padding " + badPadding);

}

catch (IllegalBlockSizeException illegalBlockSize){

System.out.println(" Illegal Block Size " + illegalBlockSize);

}

But if i do as above i'm getting error as "Illegal Block Size javax.crypto.IllegalBlockSizeException: Input length must be multiple of 16 when decrypting with padded cipher".

I don't know how to solve it. please help me on correcting this error.

Message was edited by:

jakuarvim

[5252 byte] By [jakuarvima] at [2007-11-27 7:01:38]
# 1

Looks to me like you encrypt-and-BASE64-encode, and then forget to BASE64-DEcode before trying to decrypt.

I hate your catch-blocks, by the way. You lost a lot of data with the external ones. At a minimum, you should dump the stack-trace in code like this - it'd tell you exactly which line is failing. And, if you're not going to do anything specific in your catch(), then having a bunch of them just makes your code harder to read and modify.

G

ggaineya at 2007-7-12 18:52:29 > top of Java-index,Security,Cryptography...
# 2

I don't understand

1) why you are appending the encrypted data to the file.

2) why you are ignoring all but the last line of the encrypted file.

3) why you are converting the last line of the file to bytes before decrypting it but not Base64 decoding it first.

4) why you handle exceptions like that.

You do realize that most Base64 encoders break the output into lines of about 68 characters so if you are trying to decrypt just the last encrypted data appended to the file you probably will only be working with a small fragment of the last encrypted data.

sabre150a at 2007-7-12 18:52:29 > top of Java-index,Security,Cryptography...
# 3

Wow, clearly I should've looked a little more closely at the posted code. I think my comment is still true - but irrelevant, given the other issues.

In penance - this code works:package javaforum;

import java.io.BufferedInputStream;

public class FileCrypto {

// arg0 = plaintext full path, ciphertext == arg0.enc, decrypted == arg0.dec

public static void main(String[] args) throws Exception {

String plaintextFileName = args[0];

String ciphertextFileName = args[0]+".enc";

String decrypttextFileName = args[0]+".dec";

// Generate a key to use

KeyGenerator keyGen = KeyGenerator.getInstance("AES");

keyGen.init(128);

SecretKey secretKey = keyGen.generateKey();

Cipher aesCipher = Cipher.getInstance("AES/ECB/PKCS5Padding");

InputStream bis = new BufferedInputStream(new FileInputStream(plaintextFileName));

OutputStream bos = new BufferedOutputStream(new FileOutputStream(ciphertextFileName));

// Read plaintext and encrypt

aesCipher.init(Cipher.ENCRYPT_MODE, secretKey);

byte[] buf = new byte[4096];

byte[] ciphertext;

int bytesRead = bis.read(buf);

while (bytesRead > -1) {

ciphertext = aesCipher.update(buf, 0, bytesRead);

bos.write(ciphertext, 0, ciphertext.length);

bytesRead = bis.read(buf);

}

bis.close();

ciphertext = aesCipher.doFinal();

bos.write(ciphertext, 0, ciphertext.length);

bos.flush();

bos.close();

// Read ciphertext and decrypt

aesCipher.init(Cipher.DECRYPT_MODE, secretKey);

bis = new BufferedInputStream(new FileInputStream(ciphertextFileName));

bos = new BufferedOutputStream(new FileOutputStream(decrypttextFileName));

buf = new byte[4096];

byte[] plaintext;

bytesRead = bis.read(buf);

while (bytesRead > -1) {

plaintext = aesCipher.update(buf, 0, bytesRead);

bos.write(plaintext, 0, plaintext.length);

bytesRead = bis.read(buf);

}

bis.close();

plaintext = aesCipher.doFinal();

bos.write(plaintext, 0, plaintext.length);

bos.flush();

bos.close();

}

}

Now, "works" is not the same as "the way I would do it" (look at CipherIn/OutputStream, for example). But it does address the issues sabre raises.

G

ggaineya at 2007-7-12 18:52:29 > top of Java-index,Security,Cryptography...