¿Cómo cifrar o descifrar con Rijndael y un tamaño de bloque de 256 bits?

Por ciertas razones, necesito implementar Rijndael de / compression con un tamaño de bloque de 256 bits en lugar de AES que usa un tamaño de bloque de 128 bits (razón: los datos se cifran en PHP usando Rijndael …).

¿Cómo puedo cambiar el tamaño de bloque para un cifrado?

Si solo obtengo un cifrado con "RIJNDAEL/CFB/PKCS5Padding" y trato de inicializar un IV con 256 bits obtengo una excepción, porque el tamaño del bloque es de solo 128 bits.

No existe soporte en ninguno de los proveedores de Sun JCE para nada más que Rijndael con el tamaño de bloques de 128 bits: este es el algoritmo AES. Para obtener rijndael con el tamaño de bloque de 256 bits, tendrá que ir a otro lugar. Sugiero la biblioteca de Bouncycastle java . La clase RijndaelEngine tiene un constructor que acepta un tamaño de bloque en bits. La mayoría de las personas considera que la clase PaddedBufferedBlockCipher es más conveniente cuando se usa con relleno adecuado, por ejemplo

 PaddedBufferedBlockCipher c = new PaddedBufferedBlockCipher(new RijndaelEngine(256), new PKCS7Padding()); 

Tenga en cuenta que PHP mcrypt utiliza el relleno Zero Byte para que se new ZeroBytePadding() lugar del new PKCS7Padding() .

A continuación una implementación completa utilizando CBC y RIJNDAEL 256 .

 import org.bouncycastle.crypto.CipherParameters; import org.bouncycastle.crypto.InvalidCipherTextException; import org.bouncycastle.crypto.engines.RijndaelEngine; import org.bouncycastle.crypto.modes.CBCBlockCipher; import org.bouncycastle.crypto.paddings.PaddedBufferedBlockCipher; import org.bouncycastle.crypto.paddings.ZeroBytePadding; import org.bouncycastle.crypto.params.KeyParameter; import org.bouncycastle.crypto.params.ParametersWithIV; import org.bouncycastle.util.encoders.Base64; public static String encryptWithAesCBC(String plaintext, String key, String iv) { try { PaddedBufferedBlockCipher cipher = new PaddedBufferedBlockCipher(new CBCBlockCipher(new RijndaelEngine(256)), new ZeroBytePadding()); CipherParameters ivAndKey = new ParametersWithIV(new KeyParameter(key.getBytes()), iv.getBytes()); cipher.init(true, ivAndKey); return new String(Base64.encode(cipherData(cipher, plaintext.getBytes()))); } catch (InvalidCipherTextException e) { throw new RuntimeException(e); } } public static String decryptWithAesCBC(String encrypted, String key, String iv) { try { byte[] ciphertext = Base64.decode(encrypted); PaddedBufferedBlockCipher aes = new PaddedBufferedBlockCipher(new CBCBlockCipher(new RijndaelEngine(256)), new ZeroBytePadding()); CipherParameters ivAndKey = new ParametersWithIV(new KeyParameter(key.getBytes()), iv.getBytes()); aes.init(false, ivAndKey); return new String(cipherData(aes, ciphertext)); } catch (InvalidCipherTextException e) { throw new RuntimeException(e); } } private static byte[] cipherData(PaddedBufferedBlockCipher cipher, byte[] data) throws InvalidCipherTextException { int minSize = cipher.getOutputSize(data.length); byte[] outBuf = new byte[minSize]; int length1 = cipher.processBytes(data, 0, data.length, outBuf, 0); int length2 = cipher.doFinal(outBuf, length1); int actualLength = length1 + length2; byte[] cipherArray = new byte[actualLength]; for (int x = 0; x < actualLength; x++) { cipherArray[x] = outBuf[x]; } return cipherArray; } private String md5(String string) { try { java.security.MessageDigest md = java.security.MessageDigest.getInstance("MD5"); byte[] array = md.digest(string.getBytes()); StringBuffer sb = new StringBuffer(); for (int i = 0; i < array.length; ++i) { sb.append(Integer.toHexString((array[i] & 0xFF) | 0x100).substring(1, 3)); } return sb.toString(); } catch (java.security.NoSuchAlgorithmException e) { throw new RuntimeException(e); } } 

Al utilizar CFB, PaddedBufferedBlockCipher debe reemplazar por lo siguiente:

 PaddedBufferedBlockCipher aes = new PaddedBufferedBlockCipher(new CFBBlockCipher(new RijndaelEngine(256),8), new ZeroBytePadding()); // PHP mcrypt uses a blocksize of 8 bit for CFB 

Uso:

 String salt = "fbhweui3497"; String key = md5(salt); String iv = md5(md5(salt)); String encrypted = encryptWithAesCBC("text to encript", key, iv); String decrypted = decryptWithAesCBC(encrypted, key, iv);