我正在尝试在Windows上为我的服务器应用程序编写IOS(MacOS)客户端,需要实现RSA(RSA 2048bit)加密。
我从服务器(在Windows端)获得模数和指数,并以BER格式将其解析为NSDATA。我已经拥有适用于Android的Java客户端,其工作非常棒。
但是当我尝试使用SecItemAdd时它返回错误-50(errSecParam传递给函数的一个或多个参数无效。),我在Delphi XE中的代码,在MacOS Yosemite上测试最后一个XCode
var
peerName: NSString;
peerTag, RSAKeyNS: NSDATA;
peerPublicKeyAttr: TNSMutableDictionary;
persistPeer, CFDictionaryRef1: Pointer;
begin
peerName := StrToNSStr('Test Public Key');
peerTag := peerName.dataUsingEncoding(NSUTF8StringEncoding);
RSAKeyStream.
RSAKeyNS := TNSData.Wrap(TNSData.Alloc.initWithBytes(RSAKeyStream.Memory,Cardinal(RSAKeyStream.Size)));
RSAKeyStream := TMemoryStream.Create;
b1 := 48; // SEQUENCE $30
RSAKeyStream.Write(b1, SizeOf(b1));
//...
//... write PublicKey data in BER code to stream
peerPublicKeyAttr := TNSMutableDictionary.Create;
kSecClass := StrToNSStr('kSecClass');
kSecClassKey := StrToNSStr('kSecClassKey');
kSecAttrKeyTypeRSA := StrToNSStr('kSecAttrKeyTypeRSA');
kSecAttrKeyType := StrToNSStr('kSecAttrKeyType');
kSecAttrApplicationTag := StrToNSStr('kSecAttrApplicationTag');
kSecValueData := StrToNSStr('kSecValueData');
kSecReturnPersistentRef := StrToNSStr('kSecReturnPersistentRef');
peerPublicKeyAttr.setValue((kSecClassKey as ILocalObject).GetObjectID, kSecClass);
peerPublicKeyAttr.setValue((kSecAttrKeyTypeRSA as ILocalObject).GetObjectID, kSecAttrKeyType);
peerPublicKeyAttr.setValue((peerTag as ILocalObject).GetObjectID, kSecAttrApplicationTag);
peerPublicKeyAttr.setValue((RSAKeyNS as ILocalObject).GetObjectID, kSecValueData);
peerPublicKeyAttr.setValue(TNSNumber.OCClass.numberWithBool(True), kSecReturnPersistentRef);
persistPeer := nil;
CFDictionaryRef1 := (peerPublicKeyAttr as ILocalObject).GetObjectID;
sanityCheck := SecItemAdd(CFDictionaryRef1, persistPeer);
sanityCheck - -50 /// error
end;
是的,我知道我可以在KeyData中出错,因此我在SecItemDelete函数上测试它,它更简单,我得到相同的错误-50。
peerPublicKeyAttr.setValue((kSecClassKey as ILocalObject).GetObjectID, kSecClass);
peerPublicKeyAttr.setValue((kSecAttrKeyTypeRSA as ILocalObject).GetObjectID, kSecAttrKeyType);
peerPublicKeyAttr.setValue((peerTag as ILocalObject).GetObjectID, kSecAttrApplicationTag);
CFDictionaryRef1 := (peerPublicKeyAttr as ILocalObject).GetObjectID;
sanityCheck := SecItemDelete(CFDictionaryRef1);
sanityCheck - -50 /// error
可能是NSData中的问题 - peerTag,我尝试将其作为指向Data peerTag.Bytes或@peerTag的指针传递给我,但我对这种情况有访问冲突。
Functions
const
libSecurity = '/System/Library/Frameworks/Security.framework/Security';
function SecItemAdd(ApeerPublicKeyAttr: Pointer; persistPeer: Pointer): OSStatus; cdecl; external libSecurity name _PU + 'SecItemAdd';
function SecItemDelete(ApeerPublicKeyAttr: Pointer): OSStatus; cdecl; external libSecurity name _PU + 'SecItemAdd';
我尝试搜索答案但没找到答案。 我在MacOS上使用IPhone模拟器。 请帮忙)