Как я могу сохранить открытый ключ NSString в цепочке ключей, а затем получить его SecKeyRef? - PullRequest
2 голосов
/ 18 февраля 2012

У меня есть NSString, который должен быть открытым ключом . Я хочу сохранить его в цепочке для ключей, а затем получить SecKeyRef, чтобы использовать его в других функциях безопасности, таких как SecKeyEncrypt и т. Д.

Для хранения я использую SecItemAdd, предполагая, что у меня также есть идентификатор для открытого ключа. Я попытался получить постоянный реф, а затем с этим получить SecKeyRef с SecItemCopyMatching. Я использую следующие две функции. Прежде чем передать строку ключа в putKey, я преобразовал ее в NSData.

-(SecKeyRef)putKey:(NSData *)key withIdentifier:(NSString *)identifier 
{
    OSStatus status = noErr;
    SecKeyRef keyRef = nil;
    CFTypeRef persKey = nil;

    NSData * identifierTag = [[NSData alloc] initWithBytes:(const void *)[identifier UTF8String] length:[identifier length]];
    NSMutableDictionary *queryKey = [[NSMutableDictionary alloc] init];

    [queryKey setObject:(__bridge id)kSecClassKey forKey:(__bridge id)kSecClass];
    [queryKey setObject:(__bridge id)kSecAttrKeyTypeRSA forKey:(__bridge id)kSecAttrKeyType];
    [queryKey setObject:identifierTag forKey:(__bridge id)kSecAttrApplicationTag];
    [queryKey setObject:key forKey:(__bridge id)kSecValueData];
    [queryKey setObject:[NSNumber numberWithBool:YES] forKey:(__bridge id)kSecReturnPersistentRef];

    status = SecItemAdd((__bridge CFDictionaryRef)queryKey, (CFTypeRef *)&persKey);

    if (status == errSecDuplicateItem) NSLog(@"Key %@ already exists in the KeyStore, OSStatus = %ld.", identifier, status);
    else if (status != noErr) NSLog(@"Error putting key %@ in KeyStore, OSStatus = %ld.", identifier, status);

    keyRef = [self getKeyRefWithPersistentKeyRef:persKey];

    return keyRef;
}

- (SecKeyRef)getKeyRefWithPersistentKeyRef:(CFTypeRef)persistentRef
{
    OSStatus sanityCheck = noErr;
    SecKeyRef keyRef = NULL;

    if (persistentRef == NULL) NSLog(@"persistentRef object cannot be NULL.");

    NSMutableDictionary * queryKey = [[NSMutableDictionary alloc] init];

    // Set the SecKeyRef query dictionary.
    [queryKey setObject:(__bridge id)persistentRef forKey:(__bridge id)kSecValuePersistentRef];
    [queryKey setObject:[NSNumber numberWithBool:YES] forKey:(__bridge id)kSecReturnRef];

    // Get the key reference.
    sanityCheck = SecItemCopyMatching((__bridge CFDictionaryRef)queryKey, (CFTypeRef *)&keyRef);

    return keyRef;
 }

SecItemAdd успешно возвращает постоянный ключ ref.

Но SecItemCopyMatching возвращает 0x0. Кто-нибудь знает почему?

1 Ответ

0 голосов
/ 03 апреля 2012

Оформление Apple Crypto Exercise . Чтобы добавить открытый ключ в KeyChain, необходимо удалить заголовок, который к нему прикреплен. Пример Apple показывает, что именно это и делает код простым в использовании.

...