SecKeyEncrypt()
尝试使用with时,我遇到了一些挫败感kSecPaddingNone
。经过大量调查,我找到了一种解决方法,但我想知道发生了什么。目前,我没有可用的代码,但我可以在今天晚些时候发布它。不过,我真的不相信问题出在我的代码中:我倾向于相信我只是在做一些根本错误的事情。(也就是说,我相信我的代码是正确的,但我正在尝试做的是错误的。)
我的问题是:我想使用对称密钥加密一大块数据,然后使用不同的公钥加密该密钥。使用CryptoExercise
作为模板,我很容易得到一堆代码。我为 生成一个对称密钥AES128
,用它来加密我的大缓冲区。我的单元测试对此没有任何问题。
但是后来我的单元测试创建了一个公钥/私钥对,尝试用公钥加密对称密钥,用私钥解密,然后解密大缓冲区。请注意,我根据问题集的受限域做了一些简化假设:我总是AES128
用来加密大缓冲区,所以密钥总是 16 字节,我总是使用 1024 位公共/私钥对,所以我AES
通过创建一个 128 字节的缓冲区来加密密钥,用随机数据填充它,然后将AES
密钥嵌入到该缓冲区中。
最后,由于我有一组固定的缓冲区大小,我在kSecPaddingNone
调用 `SecKeyEncrypt() 时使用。我的假设是我可以依靠我填充缓冲区的方法和缓冲区大小的知识。
当我开始运行测试时,我看到的情况令人沮丧:大约 80% 的时间,它们运行良好。但另外 20%SecKeyEncrypt()
失败OSStatus
,参数错误为 -50。我花了很多时间寻找堆栈损坏、堆损坏、过早释放等,但没有结果。
然后我开始在普通的旧缓冲区上查看公钥/私钥对操作,即我做了一个新的单元测试,试图加密/解密我手动创建和填充的缓冲区。至此,我找到了线索:如果我发送了,例如,一个零缓冲区,然后SecKeyEncrypt
陷入了无限循环。如果我发送一个只填充一个的缓冲区,那么它工作得很好。如果我用 1 填充缓冲区,然后用零替换第一个字节,我又回到了无限循环。
各种其他模式使我找到了解决方法,目前是在第一个字节之后插入 AES 密钥并始终将第一个字节设置为一个,但我非常困惑。从文档中SecKeyEncrypt()
:
通常
kSecPaddingPKCS1
使用 ,它PKCS1
在加密之前添加填充。如果您指定kSecPaddingNone
,则数据按原样加密。
我读到的方式,明文缓冲区的内容不应该影响加密算法的执行,但是,我的单元测试似乎表明它正在发生,并且缓冲区的第一个字节对操作至关重要. 而且我的解决方法似乎 100% 的时间通过了我的单元测试。
这里有更多经验的人有什么可以帮助我理解发生了什么吗?我是否误解了文档?我是否正在尝试做一些我不应该做的事情?我是否过于简单化了?
我可以在今晚晚些时候发布代码,一旦我可以再次访问它,如果有人认为它会有所帮助。