Hi folks, i need some help on how to get this code to work properly:
I have not had the time to fully commit to its intrinsics but i am sure there is someone
in the community who can get me some quick help.
Thanx.
package javaapplication1;
import java.io.ByteArrayOutputStream;
import javax.crypto.Cipher;
import javax.crypto.spec.SecretKeySpec;
/**
* @author dkawalya
*/
public class DataEncryptor {
protected DataEncryptor(){}
protected SecretKeySpec initialize() throws Exception {
byte[] mySecretKey = {
(byte)0xbb,(byte)0xbb,(byte)0xbb,(byte)0xbb,(byte)0xbb,(byte)0xbb,
(byte)0xbb,(byte)0xbb,(byte)0xbb,(byte)0xbb,(byte)0xbb,(byte)0xbb,
(byte)0xbb,(byte)0xdd,(byte)0xdd,(byte)0xcc };
SecretKeySpec myKeySpec = new SecretKeySpec(mySecretKey, "AES");
return myKeySpec;
}
protected byte[] encryptedDataBytes(String c) throws Exception{
if(c == null)
return null;
try{
SecretKeySpec keySpec = initialize();
if (keySpec == null)
return null;
Cipher myCipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
myCipher.init(Cipher.ENCRYPT_MODE, keySpec);
byte[] dataBytes = c.getBytes();
byte[] encryptedData = myCipher.doFinal(dataBytes);
return encryptedData;
}catch(Exception e){
e.printStackTrace();
return null;
}
//The rest of the throwables are not caught and it is up to the calling
//routine to catch them
}
protected String decryptDataBytes(byte[] encryptedBytes) throws Exception{
if (encryptedBytes == null)
return null;
try{
SecretKeySpec keySpec = initialize();//initialize is a method declared above and returns the SecretKeySpec
if (keySpec == null)
return null;
//Get an instance of the cipher
Cipher myCipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
myCipher.init(Cipher.ENCRYPT_MODE,keySpec);
myCipher.init(Cipher.DECRYPT_MODE, keySpec,myCipher.getParameters());
byte[] decryptedData = myCipher.doFinal(encryptedBytes);
return new String(decryptedData);
}catch(Exception e){
e.printStackTrace();
return null;
}
}
//The above two methods are byte based whereas the ones below are string based
protected String encryptData(String c) throws Exception{
if(c == null)
return null;
try{
SecretKeySpec keySpec = initialize();
if (keySpec == null)
return null;
Cipher myCipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
myCipher.init(Cipher.ENCRYPT_MODE, keySpec);
byte[] dataBytes = c.getBytes();
byte[] encryptedData = myCipher.doFinal(dataBytes);
return new String((encryptedData));
}catch(Exception e){
e.printStackTrace();
return null;
}
//The rest of the throwables are not caught and it is up to the calling
//routine to catch them
}
protected String decryptData(String c) throws Exception{
if (c == null)
return null;
try{
SecretKeySpec keySpec = initialize();
if (keySpec == null)
return null;
//Get an instance of the cipher
Cipher myCipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
myCipher.init(Cipher.ENCRYPT_MODE,keySpec);
myCipher.init(Cipher.DECRYPT_MODE, keySpec,myCipher.getParameters());
/*Try to implement the padding, described in http://www.faqs.org/rfcs/rfc2315.html, at line 63
which is 2. Some content-encryption algorithms assume the input length is a multiple of k octets, where k > 1, and let the application
define a method for handling inputs whose lengths are not a multiple of k octets. For such algorithms, the method shall be to pad the
input at the trailing end with k - (l mod k) octets all having value k -
(l mod k), where l is the length of the input. In other words, the input is padded at the trailing end with one of the following strings:
01 -- if l mod k = k-1
02 02 -- if l mod k = k-2
> .
k k ... k k -- if l mod k = 0 The padding can be removed unambiguously since all input is padded and no padding string is a suffix of another. This
padding method is well-defined if and only if k < 256; methods for larger k are an open issue for further study.*/
//Pad up the bytes as according to the convention above
ByteArrayOutputStream byteArray = new ByteArrayOutputStream();
byteArray.write(c.getBytes());
for(int i = ((c.length() == 16) ? 16 : (16 - c.length() % 16)); i>0; i--){
byteArray.write((byte)(16 -(c.length() % 16)));
}
byte[] bytesToDecrypt = byteArray.toByteArray(); //This should be the padded up array of //bytes
byte[] decryptedData = myCipher.doFinal(bytesToDecrypt);// i get this error on this line: javax.crypto.IllegalBlockSizeException:
//Input length must be multiple of 16 when decrypting with //padded cipher
return new String(decryptedData);
}catch(Exception e){
e.printStackTrace();
return null;
}
}
public static void main(String[] args){
try{
DataEncryptor davis = new DataEncryptor();
//Lets use the byte based routines first
byte[] encryptedBytes = davis.encryptedDataBytes("My brains seem to be in normal mode");
System.out.println(new String(encryptedBytes)); //print the string of encrypted bytes
String decrypt = davis.decryptDataBytes(encryptedBytes);//decrypt the data bytes returned by //the above routine
System.out.println(decrypt);// print the decrypted bytes as a string, but this is what i get(the //string is decrypted half way): #H�F��=���#]�Do be in normal mode
//Now lets use the string based routines
String encryptedString = davis.encryptData("My brains seem to be in normal mode");//encrypt //this string
System.out.println(encryptedString);//print the encrypted string
String decryptedString = davis.decryptData(encryptedString);//decrypt the above string
System.out.println(decryptedString);//print out the decrypted string and get this error:
}catch(Exception e){
System.out.println(e.getMessage());
e.printStackTrace();
}
}
}