2012-04-20 4 views
6

私のアプリケーションが接続しようとしているサーバから認証チャレンジを受けているので、connection:didReceiveAuthenticationChallenge:メソッドを実装しました。 SecCertificateRefSecIdentityRefを送信する必要があります。 IDは機能していますが、証明書はNSArrayとして送信する必要があります。CFArrayRefNSArrayに変換する方法がわかりません。NSURLConnection認証チャレンジのSecCertificateRefの作成

// Returns an array containing the certificate 
- (CFArrayRef)getCertificate { 
    SecCertificateRef certificate = nil; 
    NSString *thePath = [[NSBundle mainBundle] pathForResource:@"CertificateName" ofType:@"p12"]; 
    NSData *PKCS12Data = [[NSData alloc] initWithContentsOfFile:thePath]; 
    CFDataRef inPKCS12Data = (__bridge CFDataRef)PKCS12Data; 
    certificate = SecCertificateCreateWithData(nil, inPKCS12Data); 
    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; 
} 

// Returns the identity 
- (SecIdentityRef)getClientCertificate { 
    SecIdentityRef identityApp = nil; 
    NSString *thePath = [[NSBundle mainBundle] pathForResource:@"CertificateName" ofType:@"p12"]; 
    NSData *PKCS12Data = [[NSData alloc] initWithContentsOfFile:thePath]; 
    CFDataRef inPKCS12Data = (__bridge CFDataRef)PKCS12Data; 
    CFStringRef password = CFSTR("password"); 
    const void *keys[] = { kSecImportExportPassphrase };//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); 
    identityApp = (SecIdentityRef)CFDictionaryGetValue(identityDict, kSecImportItemIdentity); 
    } else { 
    NSLog(@"Error opening Certificate."); 
    } 
    return identityApp; 
} 

そしてconnection:didReceiveAuthenticationChallenge:に私が持っている:

- (void)connection:(NSURLConnection *)connection didReceiveAuthenticationChallenge:(NSURLAuthenticationChallenge *)challenge { 
    if ([challenge previousFailureCount] == 0) { 
    SecIdentityRef identity = [self getClientCertificate]; // Go get a SecIdentityRef 
    CFArrayRef certs = [self getCertificate]; // Get an array of certificates 

    // Convert the CFArrayRef to a NSArray 
    NSArray *myArray = (__bridge NSArray *)certs; 

    // Create the NSURLCredential 
    NSURLCredential *newCredential = [NSURLCredential credentialWithIdentity:identity certificates:certs persistence:NSURLCredentialPersistenceNone]; 

    // Send 
    [challenge.sender useCredential:newCredential forAuthenticationChallenge:challenge]; 
    } else { 
    // Failed 
    [[challenge sender] cancelAuthenticationChallenge:challenge]; 
    } 
} 

アプリケーションがクラッシュNSURLCredentialが作成され

これはアイデンティティと証明書を作成するための私の方法です。さらに調べると、CFArrayRefNSArrayに変換すると、SecCertificateRefのデータが失われ、クラッシュの原因となるnullがアレイに含まれていると判断しました。

NSArraySecCertificateRefを配置するにはどうすればよいですか?私は一歩足りなかったのですか、それとも間違っていますか?

答えて

6

私はようやく答えを見つけました。私はSecCertificateCreateWithData(nil, inPKCS12Data);の代わりにSecIdentityCopyCertificate(identity, &certificateRef);を使用して証明書を作成することになっていました。

関連する問題