get SecKeyRef from base64 coded string

前端 未结 1 484
心在旅途
心在旅途 2020-12-15 08:59

I\'m working on an iOS app and I get a base64 coded public key such as:

MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC3gn+tJ1+PbP0GHa6hmM35WsVyibpypWAwRuBYY4

相关标签:
1条回答
  • 2020-12-15 09:30

    First, you must base64 decode your NSString to NSData: See this answer for solutions. If you are developing for iOS 7, you can use initWithBase64EncodedString::options.

    Once you have the string decoded as NSData, you can attempt to create a certificate from it. The format of the certificate you received matters - you can use DER (which is common) or PKCS12. You're likely to be getting it as DER, so that's what I'll assume you need guidance on.

    Create a certificate and policy:

    SecCertificateRef   cert    = NULL;
    SecPolicyRef        policy  = NULL;
    
    cert = SecCertificateCreateWithData(kCFAllocatorDefault, data);
    policy = SecPolicyCreateBasicX509();
    

    If the cerificate data was in an incorrect format when passed to SecCertificateCreateWithData you will get a NULL result.

    At this point you have the certificate, but not the public key. To obtain the public key you must create a trust reference and evaluate the trust of the certificate.

    OSStatus        status      = noErr;
    SecKeyRef       *publicKey  = NULL;
    SecTrustRef     trust       = NULL;
    SecTrustResultType  trustType   = kSecTrustResultInvalid;
    
    if (cert != NULL){
        SecCertificateRef   certArray[1] = {cert};
        certs = CFArrayCreate(kCFAllocatorDefault, (void *)certArray, 1, NULL);
        status = SecTrustCreateWithCertificates(certs, policy, &trust);
    
        if (status == errSecSuccess){
            status = SecTrustEvaluate(trust, &trustType);
    
            // Evaulate the trust.
            switch (trustType) {
                case kSecTrustResultInvalid:
                case kSecTrustResultConfirm:
                case kSecTrustResultDeny:
                case kSecTrustResultUnspecified:
                case kSecTrustResultFatalTrustFailure:
                case kSecTrustResultOtherError:
                    break;
                case kSecTrustResultRecoverableTrustFailure:
                    *publicKey = SecTrustCopyPublicKey(trust);
                    break;
                case kSecTrustResultProceed:
                    *publicKey = SecTrustCopyPublicKey(trust);
                    break;
            }
    
        }
    }
    

    If everything went well, you should now have a populated SecKeyRef with the public key. If it didn't go well, you will have a NULL SecKeyRef and an OSStatus indicating what went wrong. SecBase.h in the Security framework gives more detailed information on those error codes.

    Now that you have a SecKeyRef with a public key, using it to encrypt data with a corresponding private key is covered well by the programming guide.

    Note that you will have to release the things you allocated above (policy, certs) using ARC or CFRelease.

    0 讨论(0)
提交回复
热议问题