我有一个使用此方法从c#加密的字符串:
public static string KEY = "81736529";
public string EncryptString(string stringToEncrypt,string keyStr)
{
byte[] key = { };
byte[] IV = { 0x01, 0x12, 0x23, 0x34, 0x45, 0x56, 0x67, 0x78 };
try
{
key = Encoding.UTF8.GetBytes(keyStr);
DESCryptoServiceProvider desProvidr = new
DESCryptoServiceProvider();
byte[] inputByteArray = Encoding.UTF8.GetBytes(stringToEncrypt);
MemoryStream ms = new MemoryStream();
CryptoStream csstreamdata = new CryptoStream(ms,
desProvidr.CreateEncryptor(key, IV), CryptoStreamMode.Write);
csstreamdata.Write(inputByteArray, 0, inputByteArray.Length);
csstreamdata.FlushFinalBlock();
return Convert.ToBase64String(ms.ToArray());
}
catch (Exception ex)
{
throw ex;
}
}
我正在尝试通过在PHP中使用几种类型的方法对此字符串进行解密,但遗憾的是它无效! 这是我在php中的代码
$key = "81736529";
$data = "Ntl1xIjA1k3zn+uRxw8s+w==";
$ivSize = 8;
$iv = "1 18 35 52 69 86 103 120";
$data = substr ($data,0, 8);
$decrypted = rtrim(mcrypt_decrypt(MCRYPT_CRYPT, $key, $data, MCRYPT_MODE_CBC,$iv));
echo $decrypted;
答案 0 :(得分:0)
你有四个问题:
您的IV编码错误。使用类似的东西:
$iv = "\x01\x12\x23\x34\x45\x56\x67\x78";
或
$iv = hex2bin("0112233445566778");
实施适当的PKCS#5 padding。 DES和Triple DES的块大小为8字节,AES为16字节。
$data = substr ($data,0, 8);
会破坏您的密文。由于您的密文是Base64编码的,因此您必须先对其进行解码:
$data = base64_decode($data);
您需要使用MCRYPT_DES
代替MCRYPT_CRYPT
。
把它放在一起:
$iv = hex2bin("0112233445566778");
$key = "81736529";
$data = "Ntl1xIjA1k3zn+uRxw8s+w==";
$data = base64_decode($data);
$decrypted = pkcs7unpad(mcrypt_decrypt(MCRYPT_DES, $key, $data, MCRYPT_MODE_CBC, $iv), 8);
echo $decrypted;
应该从整个字节范围中随机选择键。如果你只使用数字,你可以在几秒钟内使你的密钥暴力破解。密钥中的每个字节应该在0x00 - 0xFF(0 - 255)范围内,而不是0x30 - 0x39(“0” - “9”)。查看ASCII表了解更多信息。
现在不要使用DES。它只提供56位安全性。 AES会更好,因为它的最低密钥大小为128位更安全。使用DES的最大密文大小也存在实际限制。请参阅Security comparison of 3DES and AES。
IV必须是不可预测的(读:随机)。不要使用静态IV,因为这会使密码具有确定性,因此在语义上不安全。观察密文的攻击者可以确定何时发送相同的消息前缀。 IV不是秘密,因此您可以将其与密文一起发送。通常,它只是在密文之前加上密码并在解密前切掉。