【发布时间】:2012-01-09 21:56:03
【问题描述】:
我正在开发一个使用 C# 服务器和 C++ 客户端的应用程序,许可数据在两个应用程序之间传输。出于安全原因,我显然想加密这些许可证,但是我在寻找适合我的 C++ 用途的库时遇到了一些麻烦。也就是说,我已经尝试过 Crypto++ 和 CryptoAPI。 Crypto++ 看起来是一个不错的、易于使用的库,但是 Crypto++ 的加密结果和 C# 的加密结果是不同的。 CryptoAPI 可以完成这项工作,因为它由 Microsoft 维护,但 API 令人困惑且难以理解。此外,奇怪的是,C# 在每次运行时都会生成相同的加密输出,即使我没有触及 IV 的随机生成。 Crypto++ 不这样做(输出随随机 IV 下的每个运行时而变化)。
有没有人有任何建议或指导?我对 Crypto++ 和 C# 都使用 CBC 模式,所以我认为这不是问题。我目前正在使用 TripleDES 让程序首先运行。我应该使用不同的算法吗(我肯定会在完成后使用)?
代码,按要求(抱歉):
public static string Encrypt(string ToEncrypt, string Key)
{
byte[] keyArray = UTF8Encoding.UTF8.GetBytes(Key);
byte[] toEncryptArray = UTF8Encoding.UTF8.GetBytes(ToEncrypt);
TripleDESCryptoServiceProvider tDes = new TripleDESCryptoServiceProvider();
tDes.Key = keyArray;
tDes.Mode = CipherMode.CBC;
tDes.Padding = PaddingMode.PKCS7;
ICryptoTransform cTransform = tDes.CreateEncryptor();
byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length);
tDes.Clear();
return Convert.ToBase64String(resultArray, 0, resultArray.Length);
}
和解密(C++):
std::string Decrypt(std::string ToDecrypt, string Key)
{
const byte *byteKey = (byte*) Key.c_str();
CryptoPP::SecByteBlock key(CryptoPP::DES_EDE2::DEFAULT_KEYLENGTH);
key.Assign(byteKey, Key.length());
byte iv[8] = { 1, 1, 1, 1, 1, 1, 1, 1 };
try {
std::string recovered, cipher;
CryptoPP::CBC_Mode<CryptoPP::DES_EDE2>::Decryption d;
d.SetKeyWithIV(key, key.size(), iv);
CryptoPP::StringSource(ToDecrypt, true, new CryptoPP::Base64Decoder(new CryptoPP::StringSink(cipher)));
CryptoPP::StringSource(cipher, true, new CryptoPP::StreamTransformationFilter(d, new CryptoPP::StringSink(recovered)));
std::cout << "Recovered: " << recovered << std::endl;
return recovered;
} catch (const CryptoPP::Exception &e) {
std::cout << e.what() << std::endl;
exit(1);
}
}
【问题讨论】:
-
我们需要代码和输出来查看 IV 部分哪里出错了。
-
刚刚添加了代码。对此感到抱歉。
-
@jForshee : 你的
Decrypt函数没有使用它传递的Key参数——这是故意的吗? -
为什么IV设置为全零?有人可以检查 CryptoPP 中的默认填充是否是 PKCS#5 和/或 PKCS#7?
-
在密文前添加随机 IV 是解决 IV 传输问题的正常方法(IV 始终与密码块具有相同的大小)。除了不相关的随机数据之外,使用 ECB 模式对于任何其他数据都是不安全的。再说一次,不执行完整性检查的客户端/服务器协议也是如此(例如,由于填充预言) - 您可能还想在密文上创建(H)MAC,并在解密之前验证(最后一个块)数据。
标签: c# c++ encryption cryptography