While encrypting a string, it generates '\n' at end of the string.
This is how I'm doing encryption
public static String encrypt(String plainText) throws Exception {
byte[] tdesKeyData = Consts.getSecretKey().getBytes();
byte[] myIV = Consts.getInitializationVector().getBytes();
SecretKeySpec myKey = new SecretKeySpec(tdesKeyData, "DES");
IvParameterSpec ivspec = new IvParameterSpec(myIV);
Cipher cipher = Cipher.getInstance("DESede/CBC/PKCS7Padding");
cipher.init(Cipher.ENCRYPT_MODE, myKey, ivspec);
byte[] plainTextBytes = plainText.getBytes("UTF-8");
byte[] buf = cipher.doFinal(plainTextBytes);
byte[] base64Bytes = Base64.encode(buf, Base64.DEFAULT);
String base64EncryptedString = new String(base64Bytes);
return base64EncryptedString;
}
Please, somebody, guide me, what am I doing wrong here? Thanks in Advance.
Base64.NO_WRAP
Encoder flag bit to omit all line terminators (i.e., the output will be on one long line).
Related
Am trying to Decrypt an encrypted text from data power in Java using below code. Am using symmetric key mechanism. Thee below code is able to Decrypt the data but gives me a data with unwanted characters f
ollowed by plain text. I tried to substring the response for 16 characters, but I found not all the decrypted texts have the same unwanted characters. Can you please help me on this. Appreciate your response.
public String decrypt(String encryptedText, String basekey){
byte[] encryptedTextByte = DatatypeConverter.parseBase64Binary(encrypted text);
byte[] key = Base64.getDecoder().decode(base64Key.getBytes());
byte[] IV = new byte[16];
IvParameterSpec ivSpec = new IvParameterSpec(iv);
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding);
SecretKeySpec secret = new SecretKeySpec(key, "AES");
cipher.init(Cipher.DECRYPT_MODE, secret, ivSpec);
return new String(cipher.doFinal(encryptedTextByte));
}
Encryption logic in datapower
<xsl:variable name="ciphertext">
<xsl:value-of select="dp:encrypt-data($algorithm,$session-key,$node)"/>
</xsl:variable>
I found solution, am using substring of 16 to remove the padding. But ideally I should be removing the bytes. So before conversion to String I will remove the extra bytes and then convert it to String. So, I only have plain text.
public String decrypt(String encryptedText, String basekey){
byte[] encryptedTextByte = DatatypeConverter.parseBase64Binary(encrypted text);
byte[] key = Base64.getDecoder().decode(base64Key.getBytes());
byte[] IV = new byte[16];
IvParameterSpec ivSpec = new IvParameterSpec(iv);
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding);
SecretKeySpec secret = new SecretKeySpec(key, "AES");
cipher.init(Cipher.DECRYPT_MODE, secret, ivSpec);
byte[] decryptedBytes = cipher.doFinal(encryptedTextByte);
// Removing extra characters here
byte[] plainBytes = Arrays.copyOfRange(decryptedBytes, 16, decryptedBytes.length);
return new String(plainBytes);
}
I am developing an application, where I am encrypting and decrypting a text entered by the user.
But, I am getting the following error:
javax.crypto.IllegalBlockSizeException: last block incomplete in
decryption
below is my code for encryption and decryption. Encryption works perfectly, while I am getting this error while decrypting. Please refer the code below:
public static String fncEncrypt(String strClearText, String strKey) throws Exception{
String strData = "";
try {
SecretKeySpec sKeySpec = new SecretKeySpec(strKey.getBytes(), "Blowfish");
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.ENCRYPT_MODE, sKeySpec);
byte[] encrypted = cipher.doFinal(strClearText.getBytes());
strData = new String(encrypted);
}catch (Exception e){
e.printStackTrace();
}
return strData;
}
public static String fncDecrypt(String strEecrypted, String strKey) throws Exception {
String strData = "";
try {
SecretKeySpec skeySpec = new SecretKeySpec(strKey.getBytes(), "Blowfish");
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.DECRYPT_MODE, skeySpec);
byte[] decrypted = cipher.doFinal(strEecrypted.getBytes());
strData = new String(decrypted);
}catch (Exception e){
e.printStackTrace();
}
return strData;
}
Please respond if you have a solution for this.
You should decode the string instead of encoding the platform specific representation of the string, right at the start of your method.
byte[] base64TextToDecrypt = Base64.decodeBase64(textToDecrypt);
or more precisely:
byte[] bytesToDecrypt = Base64(base64TextToDecrypt);
if you name your variables correctly.
In general, each time you (feel like you have to) use the String.getBytes(): byte[] method or the String(byte[]) constructor you are likely doing something wrong. You should first think about what you are trying to do, and specify a character-encoding if you do need to use it.
In your case, the output in the converted variable is probably character-encoded. So you you could use the following fragment:
String plainText = new String(converted, Charset.forName("UTF8"));
System.out.println(plainText);
instead of what you have now.
Reference : https://stackoverflow.com/a/13274072/8416317
String class method getBytes() or new String(byte bytes[]) encode / decode with Charset.defaultCharset().name(), and some encrypted data would be ignored by encoding with special charset.
you could directly return byte[] by fncEncrypt and input byte[] to fncDecrypt. or encode result with BASE64.
public static byte[] fncEncrypt(String strClearText, String strKey) throws Exception{
byte[] encrypted = null;
try {
SecretKeySpec sKeySpec = new SecretKeySpec(strKey.getBytes(), "Blowfish");
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.ENCRYPT_MODE, sKeySpec);
encrypted = cipher.doFinal(strClearText.getBytes());
} catch (Exception e){
e.printStackTrace();
}
return encrypted;
}
public static String fncDecrypt(byte[] ecrypted, String strKey) throws Exception {
String strData = "";
try {
SecretKeySpec skeySpec = new SecretKeySpec(strKey.getBytes(), "Blowfish");
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.DECRYPT_MODE, skeySpec);
byte[] decrypted = cipher.doFinal(ecrypted);
strData = new String(decrypted);
}catch (Exception e){
e.printStackTrace();
}
return strData;
}
The reason is when you use new String(encrypted) it will not fully encode the bytes to string. Try the code below
public static byte[] fncEncrypt(String strClearText, String strKey) throws Exception{
SecretKeySpec sKeySpec = new SecretKeySpec(strKey.getBytes(), "Blowfish");
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.ENCRYPT_MODE, sKeySpec);
byte[] encrypted = cipher.doFinal(strClearText.getBytes());
return encrypted;
}
public static String fncDecrypt(byte[] encrypted, String strKey) throws Exception {
SecretKeySpec skeySpec = new SecretKeySpec(strKey.getBytes(), "Blowfish");
Cipher cipher = Cipher.getInstance("Blowfish");
cipher.init(Cipher.DECRYPT_MODE, skeySpec);
byte[] decrypted = cipher.doFinal(encrypted);
return new String(decrypted);
}
You can encrypt and decrypt using the code below
String message = "Hello!";
byte[] encrypted = fncEncrypt(message, "key");
String decrypted = fncDecrypt(encrypted, "key");
System.out.println(decrypted);
So at the moment I'm trying to write some encrypted text to a file and then be able to read that back in, decrypt it and display it to the user. I'm currently using AES-256 with PBKDF2 password derivation as I'd like to be able to use a user's password to encrypt/decrypt the files. The files are simple text files. The code I am currently using to encrypt some text and save it to a file is below. As far as I can tell, from having a look using adb, this works correctly.
FileOutputStream out = new FileOutputStream(mypath);
String defaultMessage = "Empty File";
int iterationCount = 1000;
int keyLength = 256;
int saltLength = keyLength / 8;
SecureRandom randomGenerator = new SecureRandom();
byte[] salt = new byte[saltLength];
randomGenerator.nextBytes(salt);
KeySpec keySpec = new PBEKeySpec(submittedPassword.toCharArray(), salt, iterationCount, keyLength);
SecretKeyFactory keyFactory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
byte[] keyBytes = keyFactory.generateSecret(keySpec).getEncoded();
SecretKey key = new SecretKeySpec(keyBytes, "AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
byte[] iv = new byte[cipher.getBlockSize()];
randomGenerator.nextBytes(iv);
IvParameterSpec ivParams = new IvParameterSpec(iv);
cipher.init(Cipher.ENCRYPT_MODE, key, ivParams);
byte[] ciphertext = cipher.doFinal(defaultMessage.getBytes("UTF-8"));
String finalMessage = ciphertext.toString() + "]" + iv.toString() + "]" + salt.toString();
out.write(finalMessage.getBytes());
out.close();
P.S The above is within a Try/Except.
The code below is what I'm currently trying to use to read in the file and then decrypt it, however, when I try to display the decrypted contents via the test view at the end, it does not show up.
FileInputStream fileInputStream = new FileInputStream(mypath);
InputStreamReader inputStreamReader = new InputStreamReader(fileInputStream);
BufferedReader bufferedReader = new BufferedReader(inputStreamReader);
StringBuffer stringBuffer = new StringBuffer();
while ((fileContents = bufferedReader.readLine()) != null) {
stringBuffer.append(fileContents + "\n");
}
String fileContentsString = stringBuffer.toString();
String[] fileContentsList = fileContentsString.split("]");
byte[] cipherText = fileContentsList[0].getBytes();
Toast.makeText(getApplicationContext(), fileContentsList[0], Toast.LENGTH_LONG).show();
byte[] iv = fileContentsList[1].getBytes();
byte[] salt = fileContentsList[2].getBytes();
KeySpec keySpec = new PBEKeySpec(submittedPassword.toCharArray(), salt, 1000, 256);
SecretKeyFactory keyFactory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
byte[] keyBytes = keyFactory.generateSecret(keySpec).getEncoded();
SecretKey key = new SecretKeySpec(keyBytes, "AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
IvParameterSpec ivParams = new IvParameterSpec(iv);
cipher.init(Cipher.DECRYPT_MODE, key, ivParams);
byte[] plaintext = cipher.doFinal(cipherText);
String plainrStr = new String(plaintext , "UTF-8");
textEdit.setText(plainrStr);
Hopefully someone can provide me with some assistance here. Again, the second code segment is within a Try/Except statement.
You have multiple problems with your code.
Encryption
This code
String finalMessage = ciphertext.toString() + "]" + iv.toString() + "]" + salt.toString();
does not produce a ciphertext. See here: Java: Syntax and meaning behind "[B#1ef9157"? Binary/Address?
The IV and salt have fixed sizes, so they can be placed in front of the ciphertext. After you've written the whole ciphertext, you need to use something like Base64 or Hex in order to get a String. Modern ciphers like AES produce ciphertexts that can contain bytes of any value which don't always constitute valid character encodings such as UTF-8. Strings are no containers for arbitrary byte[] contents.
ByteArrayOutputStream baos = new ByteArrayOutputStream();
baos.write(iv);
baos.write(salt);
baos.write(ciphertext);
String finalMessage = Base64.encodeToString(baos.toByteArray(), Base64.DEFAULT);
But you don't need that at all, because you can directly write your ciphertext into the file:
out.write(iv);
out.write(salt);
out.write(ciphertext);
Decryption
Don't use InputStreamReader, a BufferedReader and a StringBuffer for binary data. Otherwise, you'll corrupt your binary ciphertext.
You only need this:
byte[] iv = new byte[16];
byte[] salt = new byte[32];
byte[] ctChunk = new byte[8192]; // not for whole ciphertext, just a buffer
if (16 != fileInputStream.read(iv) || 32 != fileInputStream.read(salt)) {
throw new Exception("IV or salt too short");
}
KeySpec keySpec = new PBEKeySpec(submittedPassword.toCharArray(), salt, 1000, 256);
SecretKeyFactory keyFactory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
byte[] keyBytes = keyFactory.generateSecret(keySpec).getEncoded();
SecretKey key = new SecretKeySpec(keyBytes, "AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
IvParameterSpec ivParams = new IvParameterSpec(iv);
cipher.init(Cipher.DECRYPT_MODE, key, ivParams);
int read;
ByteArrayOutputStream ctBaos = new ByteArrayOutputStream();
while((read = fileInputStream.read(ctChunk)) > 0) {
ctBaos.write(cipher.update(cipherText, 0, read));
}
ctBaos.write(cipher.doFinal());
String plainrStr = new String(ctBaos.toByteArray(), "UTF-8");
textEdit.setText(plainrStr);
This handles randomization properly but doesn't provide integrity. If you want to detect (malicious) manipulations of your ciphertexts (and generally you'll want that to prevent some attacks), you'd need to use an authenticated mode like GCM or EAX, or employ an encrypt-then-MAC scheme with a strong MAC like HMAC-SHA256.
Use a library like tozny/java-aes-crypto in order to use good defaults.
How to write some encrypted text to a file and then be able to read that back in?
public static byte[] generateKey(String password) throws Exception
{
byte[] keyStart = password.getBytes("UTF-8");
KeyGenerator kgen = KeyGenerator.getInstance("AES");
SecureRandom sr = SecureRandom.getInstance("SHA1PRNG", "Crypto");
sr.setSeed(keyStart);
kgen.init(128, sr);
SecretKey skey = kgen.generateKey();
return skey.getEncoded();
}
public static byte[] encodeFile(byte[] key, byte[] fileData) throws Exception
{
SecretKeySpec skeySpec = new SecretKeySpec(key, "AES");
Cipher cipher = Cipher.getInstance("AES");
cipher.init(Cipher.ENCRYPT_MODE, skeySpec);
byte[] encrypted = cipher.doFinal(fileData);
return encrypted;
}
public static byte[] decodeFile(byte[] key, byte[] fileData) throws Exception
{
SecretKeySpec skeySpec = new SecretKeySpec(key, "AES");
Cipher cipher = Cipher.getInstance("AES");
cipher.init(Cipher.DECRYPT_MODE, skeySpec);
byte[] decrypted = cipher.doFinal(fileData);
return decrypted;
}
To save a encrypted file to sd do:
File file = new File(Environment.getExternalStorageDirectory() + File.separator + "your_folder_on_sd", "file_name");
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(file));
byte[] yourKey = generateKey("password");
byte[] filesBytes = encodeFile(yourKey, yourByteArrayContainigDataToEncrypt);
bos.write(fileBytes);
bos.flush();
bos.close();
To decode a file use:
byte[] yourKey = generateKey("password");
byte[] decodedData = decodeFile(yourKey, bytesOfYourFile);
For reading in a file to a byte Array there a different way out there. A Example: http://examples.javacodegeeks.com/core-java/io/fileinputstream/read-file-in-byte-array-with-fileinputstream/
I need to encode a string in Java and php where the result must be the same.
The following conditions are given:
algorithm: RIJNDAEL-128
key: 5P443m2Q1R9A7f5r3e1z08642
mode: ECB
initialization vector: N/A (Since we're using ECB, IV's are ignored)
String to encode: 201412181656005P443m2Q1R9A7f5r3e1z08642
PHP
<?php
class Cipher
{
private $securekey, $iv;
function __construct($textkey)
{
$this->securekey = $textkey;
$this->iv = mcrypt_create_iv(32);
}
function encryptR($input)
{
$enc = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $this->securekey, $input, MCRYPT_MODE_ECB, $this->iv);
return base64_encode($enc);
}
function decryptR($input)
{
return trim(mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $this->securekey, base64_decode($input), MCRYPT_MODE_ECB, $this->iv));
}
}
$raw_text = '201412181656005P443m2Q1R9A7f5r3e1z08642';
$secretKey = '5P443m2Q1R9A7f5r3e1z08642';
$cipher = new Cipher($secretKey);
$encrypted = $cipher->encryptR($raw_text);
?>
Output: MbDHhIanWgySlMTOX+ItgVKudVLXbtj7ig2GMQacVM9JhyAPvVQxLJnHpEj/vhqW
JAVA
encrypted = encrypt("201412181656005P443m2Q1R9A7f5r3e1z08642","5P443m2Q1R9A7f5r3e1z08642");
public class Crypt {
private final String characterEncoding = "UTF-8";
private final String cipherTransformation = "AES/ECB/PKCS5Padding";
private final String aesEncryptionAlgorithm = "AES";
public byte[] decrypt(byte[] cipherText, byte[] key) throws Exception
{
Cipher cipher = Cipher.getInstance(cipherTransformation);
SecretKeySpec secretKeySpecy = new SecretKeySpec(key, aesEncryptionAlgorithm);
cipher.init(Cipher.DECRYPT_MODE, secretKeySpecy);
cipherText = cipher.doFinal(cipherText);
return cipherText;
}
public byte[] encrypt(byte[] plainText, byte[] key) throws Exception
{
Cipher cipher = Cipher.getInstance(cipherTransformation);
SecretKeySpec secretKeySpec = new SecretKeySpec(key, aesEncryptionAlgorithm);
cipher.init(Cipher.ENCRYPT_MODE, secretKeySpec);
plainText = cipher.doFinal(plainText);
return plainText;
}
private byte[] getKeyBytes(String key) throws UnsupportedEncodingException{
byte[] keyBytes= new byte[16];
byte[] parameterKeyBytes= key.getBytes(characterEncoding);
System.arraycopy(parameterKeyBytes, 0, keyBytes, 0, Math.min(parameterKeyBytes.length, keyBytes.length));
return keyBytes;
}
#SuppressLint("NewApi")
public String encrypt(String plainText, String key) throws Exception {
byte[] plainTextbytes = plainText.getBytes(characterEncoding);
byte[] keyBytes = getKeyBytes(key);
// Log.i("iv", ""+keyBytesIV);
return Base64.encodeToString(encrypt(plainTextbytes,keyBytes), Base64.DEFAULT);
}
#SuppressLint("NewApi")
public String decrypt(String encryptedText, String key) throws Exception {
byte[] cipheredBytes = Base64.decode(encryptedText, Base64.DEFAULT);
byte[] keyBytes = getKeyBytes(key);
return new String(decrypt(cipheredBytes, keyBytes), characterEncoding);
}
}
Output: wd0FHYpLbgdpHhcSql7VVCiKWJWN5hvP0W9F4sgKWAWeDcSjvfKWTM5LHBCZJSRw
Updated:
I changed the padding from NoPadding to PKCS5Padding
Is this correct? I'm not sure, cause if you look at the PHP code. There wasn't any padding specified(my own assumption based on syntax).
Info on Mcrypt
Additional Insight:
Read this document regarding padding(No Padding). Must've been related to the issue.
Looks like your PHP version uses AES-128, which by definition, uses 128-bit (16-byte) keys. However looks like you passed in a 25-byte key (5P443m2Q1R9A7f5r3e1z08642), which I'm not sure what PHP does when that happens.
Your Java version's getKeyBytes() method only returns the first 16 bytes of the supplied key, so it encrypts with only that.
Try truncating the key in your PHP version to 5P443m2Q1R9A7f5r and you'd get the same result. Except the end part which may be different. At that point, the issue then would be the padding. You can apply the pkcs5_pad PHP function on your plaintext so it matches your Java version.
All that said, if this was just for learning purposes, it's ok. Otherwise, for actual use it's important that you do not use ECB cipher mode.
I changed byte[] keyBytes= new byte[16]; to byte[] keyBytes= new byte[32]; in getKeyBytes method then it worked fine.
I have a simple code here, the code uses the sun.misc.BASE64Encoder and sun.misc.BASE64Decoder, which are not available in Eclipse Java 7.0 , I wanted to make the code such that it uses the Apache commons base 64 and still do exactly the same thing,
The variables
private static final String ALGORITHM = "AES";
private static final byte[] keyValue = "2H5a1r5i6s3h8C1h".getBytes();
Original Code
public static String AESencrypt(String valueToEnc) throws Exception {
Key key = new SecretKeySpec(keyValue, ALGORITHM);
Cipher c = Cipher.getInstance(ALGORITHM);
c.init(Cipher.ENCRYPT_MODE, key);
byte[] encValue = c.doFinal(valueToEnc.getBytes());
String encryptedValue = new BASE64Encoder().encode(encValue);
return encryptedValue;
}
public static String AESdecrypt(String encryptedValue) throws Exception {
Key key = new SecretKeySpec(keyValue, ALGORITHM);
Cipher c = Cipher.getInstance(ALGORITHM);
c.init(Cipher.DECRYPT_MODE, key);
byte[] decordedValue = new BASE64Decoder().decodeBuffer(encryptedValue);
byte[] decValue = c.doFinal(decordedValue);
String decryptedValue = new String(decValue);
return decryptedValue;
}
Trying to modify to apache commons code
public static String AESencrypt(String valueToEnc) throws Exception {
Key key = new SecretKeySpec(keyValue, ALGORITHM);
Cipher c = Cipher.getInstance(ALGORITHM);
c.init(Cipher.ENCRYPT_MODE, key);
byte[] encValue = c.doFinal(valueToEnc.getBytes());
String encryptedValue = new Base64().encodeBase64(encValue).toString();
return encryptedValue;
}
public static String AESdecrypt(String encryptedValue) throws Exception {
Key key = new SecretKeySpec(keyValue, ALGORITHM);
Cipher c = Cipher.getInstance(ALGORITHM);
c.init(Cipher.DECRYPT_MODE, key);
byte[] decordedValue = new Base64().decodeBase64(encryptedValue);
byte[] decValue = c.doFinal(decordedValue);
String decryptedValue = new String(decValue);
return decryptedValue;
}
The original code works fine, the new code throws the following exception,
Exception in thread "main" javax.crypto.IllegalBlockSizeException:
Input length must be multiple of 16 when decrypting with padded cipher
at com.sun.crypto.provider.CipherCore.doFinal(CipherCore.java:750)
at com.sun.crypto.provider.CipherCore.doFinal(CipherCore.java:676)
at
com.sun.crypto.provider.AESCipher.engineDoFinal(AESCipher.java:313)
at javax.crypto.Cipher.doFinal(Cipher.java:2087) at
trial2.encrypt.AESdecrypt(encrypt.java:28) at
trial2.encrypt.main(encrypt.java:37)
Java Result: 1
How can I solve this problem without altering the initial code too much, a few lines here and there are OK. Is it possible to completely eliminate the Base64encoding step and make it work with only the ciphers like this:
public static String AESencrypt(String valueToEnc) throws Exception {
Key key = new SecretKeySpec(keyValue, ALGORITHM);
Cipher c = Cipher.getInstance(ALGORITHM);
c.init(Cipher.ENCRYPT_MODE, key);
byte[] encValue = c.doFinal(valueToEnc.getBytes());
return encValue.toString();
}
public static String AESdecrypt(String encryptedValue) throws Exception {
Key key = new SecretKeySpec(keyValue, ALGORITHM);
Cipher c = Cipher.getInstance(ALGORITHM);
c.init(Cipher.DECRYPT_MODE, key);
byte[] decValue = c.doFinal(encryptedValue.getBytes());
String decryptedValue = new String(decValue);
return decryptedValue;
}
The above code has similar exception like the second code:
Exception in thread "main" javax.crypto.IllegalBlockSizeException:
Input length must be multiple of 16 when decrypting with padded cipher
at com.sun.crypto.provider.CipherCore.doFinal(CipherCore.java:750)
at com.sun.crypto.provider.CipherCore.doFinal(CipherCore.java:676)
at
com.sun.crypto.provider.AESCipher.engineDoFinal(AESCipher.java:313)
at javax.crypto.Cipher.doFinal(Cipher.java:2087) at
trial2.encrypt.AESdecrypt(encrypt.java:26) at
trial2.encrypt.main(encrypt.java:35) Java Result: 1
Please help and TYVM
The error is in your encrypt method. The following code is wrong:
byte[] encValue = c.doFinal(valueToEnc.getBytes());
String encryptedValue = new Base64().encodeBase64(encValue).toString();
You are calling toString() on a byte array, which won't do what you want! Instead, try:
byte[] encValue = c.doFinal(valueToEnc.getBytes());
String encryptedValue = Base64.encodeBase64String(encValue);
This should then work correctly.