VB6 で AES を使用してデータを暗号化し、Java で同じ暗号化に一致させようとしています。Microsoft から基本的な VB6 コードを取得しました: http://support.microsoft.com/kb/821762
VB6:
strProvider = "Microsoft Enhanced RSA and AES Cryptographic Provider (Prototype)" & vbNullChar
lngHashType = CALG_MD5
lngAlgoType = CALG_AES_128
strPassword = "secretPassphrase"
If CBool(CryptAcquireContext(g_lngCryptoContext, ByVal strTemp, _
ByVal strProvider, PROV_RSA_AES, CRYPT_VERIFYCONTEXT)) Then
GetProvider = True
else
GoTo CleanUp
End If
If Not CBool(CryptCreateHash(g_lngCryptoContext, lngHashType, ByVal 0&, _
ByVal 0&, lngHashHnd)) Then
MsgBox "Error: " & CStr(GetLastError) & " during CryptCreateHash!", _
vbExclamation Or vbOKOnly, "Encryption Errors"
GoTo CleanUp
End If
If Not CBool(CryptHashData(lngHashHnd, strPassword, Len(strPassword), ByVal 0&)) Then
MsgBox "Error: " & CStr(GetLastError) & " during CryptHashData!", _
vbExclamation Or vbOKOnly, "Encryption Errors"
GoTo CleanUp
End If
If Not CBool(CryptDeriveKey(g_lngCryptoContext, lngAlgoType, _
lngHashHnd, ByVal CRYPT_NO_SALT, lngkey)) Then
MsgBox "Error: " & CStr(GetLastError) & " during CryptDeriveKey!", _
vbExclamation Or vbOKOnly, "Encryption Errors"
GoTo CleanUp
End If
If lngHashHnd <> 0 Then
lngRetCode = CryptDestroyHash(lngHashHnd)
End If
lngHashHnd = 0
lngEncDataLength = Len(g_strInData)
lngEnctBuffLen = lngEncDataLength * 2
strEncBuffer = String$(lngEnctBuffLen, vbNullChar)
LSet strEncBuffer = g_strInData
If Not CBool(CryptEncrypt(lngkey, ByVal 0&, ByVal 1&, ByVal 0&, _
strEncBuffer, lngEncDataLength, lngEnctBuffLen)) Then
MsgBox "Bytes required:" & CStr(lngEnctBuffLen) & vbCrLf & vbCrLf & _
"Error: " & CStr(GetLastError) & " during CryptEncrypt!", _
vbExclamation Or vbOKOnly, "Encryption Errors"
GoTo CleanUp
End If
strOutData = Mid$(strEncBuffer, 1, lngEncDataLength)
g_abytOutData = StringToByteArray(strOutData)
モード、パディング、iv、およびブロック長は明示的に設定されていませんが、CBC、PKCS5、{0、0、0、0、0、0、0、0、0、0、0、0、0、0、0 です。 、0}、および 128 がそれぞれデフォルトであり、GetKeyParam 関数を使用して確認しました。
ジャワ:
String password = "secretPassphrase";
String text = "text to encrypt";
MessageDigest md = MessageDigest.getInstance("MD5");
md.update(password.getBytes("UTF-8"), 0, password.length());
byte[] rawKey = md.digest();
byte[] iv = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
IvParameterSpec ivSpec = new IvParameterSpec(iv);
SecretKeySpec skeySpec = new SecretKeySpec(rawKey, "AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding", "SunJCE");
cipher.init(Cipher.ENCRYPT_MODE, skeySpec, ivSpec);
byte[] encrypted = cipher.doFinal(text.getBytes("UTF-8"));
System.out.println(toHex(encrypted));
暗号化設定を両側で同じに設定しても、暗号化を 16 進数として出力すると異なる結果が得られます。2 つの異なる CSP が AES を使用して互換性があるかどうか疑問に思っていますか?
AES の代わりに RC2 を使用するように両端でコードを少し変更すると、暗号化は一致します。
どんな考えでも大歓迎です。私はこれで髪を引っ張っています。