1

私はしばらくの間暗号化に苦労していて、プロセスを完了しようとしていますが、IVでいくつかの問題が発生しています。これが私のコードです:

IV世代

public static byte[] createIV(int size) { 
 byte[] iv = new byte[size];
 SecureRandom random = new SecureRandom();
 random.nextBytes(iv);   

 return iv; 
}

AES-256暗号作成(キー)

public static Map<String, byte[]> cipherAES() throws NoSuchAlgorithmException {
     Map<String, byte[]> aes = new HashMap<String, byte[]>();
     aes.put("IV", ConversionUtil.toHex(createIV(16), 16).getBytes());
     KeyGenerator keyGen = KeyGenerator.getInstance("AES");
     keyGen.init(256);
     Key encryptionKey = keyGen.generateKey();
     aes.put("key", encryptionKey.getEncoded());

     return aes;
}

toHexメソッド

public static String toHex(byte[] data, int length) {
     StringBuffer buf = new StringBuffer();

     for (int i = 0; i != length; i++) {
        int v = data[i] & 0xff;

        buf.append(DIGITS.charAt(v >> 4));
        buf.append(DIGITS.charAt(v & 0xf));
     }

        return buf.toString();
}

暗号の初期化

  SecretKey key = new SecretKeySpec(map.get("key"), 0, map.get("key").length, "AES");
  Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
  cipher.init(Cipher.ENCRYPT_MODE, key, new IvParameterSpec(map.get("IV"), 0, 16));

この形式の16バイトのIVを暗号に提供する場合:

8E12399C07726F5A8E12399C07726F5A

暗号でgetIVメソッドを呼び出すと、次のようになります。

8E12399C07726F5A

これは、私がIVに提供したバイトのちょうど半分です。サーバーはメッセージの2番目の部分を復号化できますが、最初の部分は復号化できないため、これは現在いくつかの問題を引き起こしています。

私はJCEライブラリのみを使用しています:

import javax.crypto.Cipher;
import javax.crypto.SecretKey;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;

誰かがこれに光を当てることができますか?詳細が必要な場合はお知らせください。

4

1 に答える 1

1

CodesInChaosbimsapiのコメントで述べたように、エラーはIV値を16進数に変換することにあります。cipherAES()メソッドの簡単な修正は次のようになります。

public static Map<String, byte[]> cipherAES() throws NoSuchAlgorithmException {
     Map<String, byte[]> aes = new HashMap<String, byte[]>();
     aes.put("IV", createIV(16)); // <-- no need for conversion
     KeyGenerator keyGen = KeyGenerator.getInstance("AES");
     keyGen.init(256);
     Key encryptionKey = keyGen.generateKey();
     aes.put("key", encryptionKey.getEncoded());
     return aes;
}

メソッドの設計が少し変わっていることにも注意してください。文字列のマップをバイト配列に返すことは非常に脆弱であり、エラーが発生しやすくなります。代わりに、これらのアイテムを格納するオブジェクトを返すことを検討してください。そのオブジェクトでは、キーをKeyバイト配列ではなく、として格納します。

于 2012-12-12T18:52:37.897 に答える