Rfc2898DeriveBytes in java

人走茶凉 提交于 2019-12-03 04:38:34

问题


I am trying to implement the following code in java:

var keyGenerator = new Rfc2898DeriveBytes(password, salt, 1000);
byte[] key = keyGenerator.GetBytes(32);
byte[] iv = keyGenerator.GetBytes(16);
using (AesManaged aes = new AesManaged())
{
    using (ICryptoTransform encryptor = aes.CreateEncryptor(key, iv)) 
    {
        byte[] result = encryptor.TransformFinalBlock(content, 0, content.Length);
    }
}

By using the following one:

SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
PBEKeySpec keyspec = new PBEKeySpec(password, salt, 1000, 256);
Key key = factory.generateSecret(keyspec);
SecretKeySpec secret = new SecretKeySpec(key.getEncoded(), "AES");
byte[] iv = "how_to_generate_in_java_as_in_c".getBytes();
AlgorithmParameterSpec ivSpec = new IvParameterSpec(iv);
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
cipher.init(Cipher.ENCRYPT_MODE, secret, ivSpec);
byte[] result = cipher.doFinal("asdfasdf".getBytes("UTF-8"));

I looked through a lot of examples and questions of SO and did not find a way to generate correctly iv[] (in the same value as in C). And it seems there is not way to do it, as java allow to create this value only as random (not pseudo random as available in C). Is this right? Could somebody please help with this issue?


回答1:


Got a prompt from crypt specialist and found the right solution:

SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
PBEKeySpec pbeKeySpec = new PBEKeySpec(password, salt, 1000, 384);
Key secretKey = factory.generateSecret(pbeKeySpec);
byte[] key = new byte[32];
byte[] iv = new byte[16];
System.arraycopy(secretKey.getEncoded(), 0, key, 0, 32);
System.arraycopy(secretKey.getEncoded(), 32, iv, 0, 16);



回答2:


I want to make sure people understand that the final code should be:

SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
PBEKeySpec pbeKeySpec = new PBEKeySpec(password, salt, 1000, 384);
Key secretKey = factory.generateSecret(pbeKeySpec);
byte[] key = new byte[32];
byte[] iv = new byte[16];
System.arraycopy(secretKey.getEncoded(), 0, key, 0, 32);
System.arraycopy(secretKey.getEncoded(), 32, iv, 0, 16);

SecretKeySpec secret = new SecretKeySpec(key, "AES");
AlgorithmParameterSpec ivSpec = new IvParameterSpec(iv);
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
cipher.init(Cipher.ENCRYPT_MODE, secret, ivSpec);
byte[] result = cipher.doFinal("asdfasdf".getBytes("UTF-8"));

if you want to turn result to a string using new String(result) is best if you use new String(result,Charset), if you don't you may get the string in formatted incorrectly.



来源:https://stackoverflow.com/questions/24405731/rfc2898derivebytes-in-java

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!