【问题标题】:Using . bks keystores certificate in iPhone app使用 。 iPhone应用程序中的bks密钥库证书
【发布时间】:2012-09-10 06:47:09
【问题描述】:

我正在构建一个需要 .bks 密钥库进行身份验证的 iPhone 应用程序。我没有找到任何关于 iOS 应用程序的信息。

我想知道苹果是否允许在他们的应用程序中使用密钥库以及如何开始使用 iOS。证书是使用 BouncyCastle 创建的。我确实为 android 找到了有关它的信息,但对于 iOS,我没有运气。任何帮助将不胜感激。

【问题讨论】:

    标签: iphone objective-c ios bouncycastle


    【解决方案1】:

    您可以像这样从密钥库中导出所需的证书

    keytool -exportcert -keystore <keystore> -file some.cer
    

    您可能需要告诉 keytool 商店类型和商店提供商 look here

    您可以使用以下代码将该 .cer 文件读入 iOS 钥匙串:

    - (void) importCertToKeyChain: (NSData *) data
    {
        // Delete the old certificate, otherwise SecItemAdd complains.
        OSStatus oss = SecItemDelete((__bridge CFDictionaryRef)([self clientCertificateQuery]));
    
        // Import the certificate
        SecCertificateRef certRef = NULL;
        certRef = SecCertificateCreateWithData(NULL, (__bridge CFDataRef)(data));
    
        NSDictionary *att = [NSDictionary dictionaryWithObjectsAndKeys: (__bridge id)(kSecClassCertificate), kSecClass, (__bridge id) certRef, kSecValueRef, nil];
    
        oss = SecItemAdd((__bridge CFDictionaryRef)(att), NULL);
    }
    

    当您需要证书时,您可以像这样从钥匙串中获取:

    - (SecCertificateRef) getCertFromKeyChain
    {
        CFTypeRef ref = NULL;
        SecItemCopyMatching((__bridge CFDictionaryRef)([self clientCertificateQuery]), &ref);
    
        return (SecCertificateRef) ref;
    }
    

    clientCertificateQuery 如下所示。

    static NSString *clientCertSubject = @"TestSubjectClient";
    
    -(NSMutableDictionary *) clientCertificateQuery
    {
        NSMutableDictionary *query = [[NSMutableDictionary alloc] init];
        [query setObject:(__bridge id) kSecClassCertificate forKey:(__bridge id)kSecClass];
        [query setObject:clientCertSubject forKey:(__bridge id<NSCopying>)(kSecMatchSubjectContains)];
        [query setObject:[NSNumber numberWithBool:YES] forKey:(__bridge id)kSecReturnRef];
     id)kSecAttrKeyType];
        return query;
    }
    

    还有一个读取 PCKS12 存储的功能(您仍然需要将 BKS 存储转换为该格式)。它被称为SecPKCS12Import,有了它,您无需将证书导入您的 iOS 钥匙串。我运气不好,无论如何都需要钥匙串中的证书,但这里是something about this

    更新:

    正如 camdaochemgio 在 cmets 中指出的那样,在应用程序中包含包含机密信息(如私钥)的证书时,不建议使用上述方法。因为 .cer 文件不受保护,可以很容易地从 .ipa 中提取出来。

    PKCS#P12 支持密码保护,所以最好使用这个。

    您可以像这样将您的密钥库转换为 PKCS#P12(采用 from here):

     keytool -importkeystore -srckeystore KEYSTORE.jks -destkeystore KEYSTORE.p12 -srcstoretype BKS -deststoretype PKCS12 -srcstorepass mysecret -deststorepass mysecret -srcalias myalias -destalias myalias -srckeypass mykeypass -destkeypass mykeypass -noprompt
    

    然后你可以像这样加载 .p12 文件(学分去here

    // Load Certificate
    NSString *path = [[NSBundle mainBundle] pathForResource:@"cert" ofType:@"p12"];
    NSData *p12data = [NSData dataWithContentsOfFile:path];
    CFDataRef inP12data = (__bridge CFDataRef)p12data;
    
    // Only password based PKCS#12 blobs are supported
    CFStringRef password = CFSTR("Password");
    const void *keys[] = { kSecImportExportPassphrase };
    const void *values[] = { password };
    CFDictionaryRef options = CFDictionaryCreate(NULL, keys, values, 1, NULL, NULL);
    
    // The import
    CFArrayRef items = CFArrayCreate(NULL, 0, 0, NULL);
    OSStatus securityError = SecPKCS12Import(inP12data, options, &items);
    
    if (securityError == 0)
    {
        // Exploring the content
        CFDictionaryRef myIdentityAndTrust = CFArrayGetValueAtIndex(items, 0);
        const void *tempIdentity = NULL;
        tempIdentity = CFDictionaryGetValue(myIdentityAndTrust, kSecImportItemIdentity);
        *identity = (SecIdentityRef)tempIdentity;
        const void *tempTrust = NULL;
        tempTrust = CFDictionaryGetValue(myIdentityAndTrust, kSecImportItemTrust);
        *trust = (SecTrustRef)tempTrust;
    }
    
    if (options) {
        CFRelease(options);
    }
    

    最后但并非最不重要的一些关于此主题的链接:

    【讨论】:

    • 这种方式不安全,因为证书文件存储在主包中。有些人可能会提取捆绑包,然后在没有密码的情况下获取文件。密钥库作为 android 更好,但我不知道在 iOS 中做密钥库。有什么想法吗?
    • @camdaochemgio 对,我更新了关于如何使用 PCKS12 商店的帖子。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-02-06
    • 2014-11-20
    • 2011-12-09
    • 2022-06-10
    • 1970-01-01
    • 2012-04-24
    相关资源
    最近更新 更多