3

我試圖按照蘋果文檔的處理客戶端P12的證書在此:在鑰匙串中存儲一個的.p12證書使用後

https://developer.apple.com/library/ios/documentation/Security/Conceptual/CertKeyTrustProgGuide/iPhone_Tasks/iPhone_Tasks.html#//apple_ref/doc/uid/TP40001358-CH208-SW13

我已成功加載從文件系統中的.p12證書:

- (SecIdentityRef)getClientCertificate:(NSString *) certificatePath { 
    SecIdentityRef identity = nil; 
    NSData *PKCS12Data = [NSData dataWithContentsOfFile:certificatePath]; 

    CFDataRef inPKCS12Data = (__bridge CFDataRef)PKCS12Data; 
    CFStringRef password = CFSTR("password"); 
    const void *keys[] = { kSecImportExportPassphrase }; 
    const void *values[] = { password }; 
    CFDictionaryRef options = CFDictionaryCreate(NULL, keys, values, 1, NULL, NULL); 
    CFArrayRef items = CFArrayCreate(NULL, 0, 0, NULL); 
    OSStatus securityError = SecPKCS12Import(inPKCS12Data, options, &items); 
    CFRelease(options); 
    CFRelease(password); 
    if (securityError == errSecSuccess) { 
     NSLog(@"Success opening p12 certificate. Items: %ld", CFArrayGetCount(items)); 
     CFDictionaryRef identityDict = CFArrayGetValueAtIndex(items, 0); 
     identity = (SecIdentityRef) CFDictionaryGetValue(identityDict, kSecImportItemIdentity); 
    } else { 
     NSLog(@"Error opening Certificate."); 
    } 

    return identity; 
} 

然後我得到該身份證書:

- (CFArrayRef)getCertificate:(SecIdentityRef) identity { 
    SecCertificateRef certificate = nil; 

    SecIdentityCopyCertificate(identity, &certificate); 
    SecCertificateRef certs[1] = { certificate }; 



    CFArrayRef array = CFArrayCreate(NULL, (const void **) certs, 1, NULL); 

    SecPolicyRef myPolicy = SecPolicyCreateBasicX509(); 
    SecTrustRef myTrust; 

    OSStatus status = SecTrustCreateWithCertificates(array, myPolicy, &myTrust); 
    if (status == noErr) { 
     NSLog(@"No Err creating certificate"); 
    } else { 
     NSLog(@"Possible Err Creating certificate"); 
    } 
    return array; 
} 

但我真正想做的是將證書(或身份)存儲在我的應用程序鑰匙串中,所以我沒有從文件系統讀取它。

幾個問題:

  1. 我應該來存儲?證書或身份?
  2. 如何存儲並檢索它?

上面的鏈接是關於'獲取和使用持久性鑰匙串引用',這對我來說非常混亂。

它還談論'在鑰匙串中查找證書',但它提到使用證書的名稱來查找它。我不確定'姓名'的來源。

回答

2

我想不出一個很好的理由將證書存儲在鑰匙串中,儘管我確信可能會有一些。我只在鑰匙串中存儲身份(這是私鑰部分)。爲了更容易地找到鑰匙串中的身份,您生成一個持久性引用(見鏈接中的清單2-3),然後將該持久引用保存在您的應用程序的文件系統中。持久性引用只是一個CFDataRef,你可以免費橋接到一個NSData對象,然後輕鬆保存/加載。當你想要私鑰用於加密/無論什麼時,你使用該持久化引用來加載鑰匙鏈中的身份(參見鏈接中的清單2-4)。我會爲你發佈一些代碼,但是我現在正在重建我的開發機器,並且還沒有安裝Xcode。

+0

謝謝!我一直試圖保存/檢索持久的引用/從NSUserDefaults沒有運氣。想知道如果我可以寫到NSUserDefaults,如果是的話,如果我做得正確。 – lostintranslation

+0

我會建議不要在NSUserDefaults中存儲該引用,它只是不適合它的地方,並且可能很挑剔。只需使用[-writeToFile:atomically:](https://developer.apple.com/library/mac/documentation/Cocoa/Reference/Foundation/Classes/NSData_Class/index.html#//apple_ref/occ/instm/NSData/writeToFile:原子:)方法 – RyanR