【发布时间】:2011-02-01 13:17:25
【问题描述】:
我是密码学的新手,我正在构建一些测试应用程序来尝试了解它的基础知识。我不是试图从头开始构建算法,而是试图让两个不同的 AES-256 实现相互通信。
我有一个数据库,其中填充了this Javascript implementation,存储在 Base64 中。现在,我正在尝试使用 Objective-C 方法来解密其内容,但对于实现的差异在哪里我有点迷茫。我可以在 Javascript 中加密/解密,我可以在 Cocoa 中加密/解密,但不能在 Cocoa 中解密用 Javascript 加密的字符串,反之亦然。
我猜它与初始化向量、nonce、计数器操作模式或所有这些有关,坦率地说,目前对我没有任何影响。
这是我在Objective-C中使用的,主要改编自this和this:
@implementation NSString (Crypto)
- (NSString *)encryptAES256:(NSString *)key {
NSData *input = [self dataUsingEncoding: NSUTF8StringEncoding];
NSData *output = [NSString cryptoAES256:input key:key doEncrypt:TRUE];
return [Base64 encode:output];
}
- (NSString *)decryptAES256:(NSString *)key {
NSData *input = [Base64 decode:self];
NSData *output = [NSString cryptoAES256:input key:key doEncrypt:FALSE];
return [[[NSString alloc] initWithData:output encoding:NSUTF8StringEncoding] autorelease];
}
+ (NSData *)cryptoAES256:(NSData *)input key:(NSString *)key doEncrypt:(BOOL)doEncrypt {
// 'key' should be 32 bytes for AES256, will be null-padded otherwise
char keyPtr[kCCKeySizeAES256 + 1]; // room for terminator (unused)
bzero(keyPtr, sizeof(keyPtr)); // fill with zeroes (for padding)
// fetch key data
[key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSUTF8StringEncoding];
NSUInteger dataLength = [input length];
// See the doc: For block ciphers, the output size will always be less than or
// equal to the input size plus the size of one block.
// That's why we need to add the size of one block here
size_t bufferSize = dataLength + kCCBlockSizeAES128;
void* buffer = malloc(bufferSize);
size_t numBytesCrypted = 0;
CCCryptorStatus cryptStatus =
CCCrypt(doEncrypt ? kCCEncrypt : kCCDecrypt,
kCCAlgorithmAES128,
kCCOptionECBMode | kCCOptionPKCS7Padding,
keyPtr, kCCKeySizeAES256,
nil, // initialization vector (optional)
[input bytes], dataLength, // input
buffer, bufferSize, // output
&numBytesCrypted
);
if (cryptStatus == kCCSuccess) {
// the returned NSData takes ownership of the buffer and will free it on deallocation
return [NSData dataWithBytesNoCopy:buffer length:numBytesCrypted];
}
free(buffer); // free the buffer;
return nil;
}
@end
当然,输入是预先经过 Base64 解码的。
我看到在 Javascript 中使用相同密钥和相同内容的每次加密都会给出不同的加密字符串,而 Objective-C 实现的情况并非总是给出相同的加密字符串。我已经阅读了this post 的答案,这让我相信我对向量初始化方面的一些事情是正确的,但我需要你的帮助来确定到底发生了什么。
谢谢!
【问题讨论】:
-
你找到让两人说话的方法了吗?我面临着完全相同的问题,但我无法找到一种方法来完成这项工作。感谢任何帮助。谢谢。
-
@Ipfavreau,我遇到了和你一样的问题。你解决了吗?谢谢!
-
@AlexR,不,我没有解决它。 Accipitridae 说的是真的:两种实现方式存在差异,并没有走这条路线。
标签: javascript objective-c cocoa encryption aes