Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

iPhone Custom CA certificate for an application which uses NSURLConnection?

I have an application which is communicating with many different sites and each site has its own SSL certificate signed by our own internal CA. Doing this prevents us the need from purchasing SSL certificates for each site (hundreds or thousands) and is more secure then using a wildcard certificate with a shared key on each of those sites. So, basically using a CA certificate is the only way.

Right now, I have a mobileprovision file which will install the CA certificate as a profile on the phone. When our iPhone application launches if it gets an SSL Certificate error it redirects to a this mobile provision file via Safari and the user will be prompted to install the CA.

The problem is that I am concerned that the Apple AppStore might deny my app for doing this (Just some feedback from other developers at this point), and I wanted to research other ways to accomplish this.

Basically what I need to accomplish is allow an SSL connection which will verify against a custom CA certificate which will be embedded in my application. This will make the CA certificate active for only the calls I make. I am using the standard NSURLConnection methods in order to communicate with the service.

Is this possible? Can someone show me how to load the CA (what form PEM?) and add it to the list of trusted CA certificates for my application? If that is not possible what other options do I have? Just trusting all certificates isn't really any option, we want to prevent man in the middle attacks and only trust our CA issued certificates.

Thanks!

like image 720
jr. Avatar asked Jun 11 '10 20:06

jr.


1 Answers

Use the below two delegate method of NSURLConnection to access any site with invalid certificate

   - (BOOL)connection:(NSURLConnection *)connection canAuthenticateAgainstProtectionSpace:(NSURLProtectionSpace *)protectionSpace
    {

            NSLog(@"canAuthenticateAgainstProtectionSpace");
        if([[protectionSpace authenticationMethod] isEqualToString:NSURLAuthenticationMethodServerTrust]) {
            // Note: this is presently only called once per server (or URL?) until
            //       you restart the app
                NSLog(@"Authentication checking is doing");
            return YES; // Self-signed cert will be accepted
            // Note: it doesn't seem to matter what you return for a proper SSL cert
            //       only self-signed certs
        }
        return NO;
    }

    - (void)connection:(NSURLConnection *)connection didReceiveAuthenticationChallenge:(NSURLAuthenticationChallenge *)challenge
    {
            NSLog(@"didReceiveAuthenticationChallenge");
        if ([challenge.protectionSpace.authenticationMethod isEqualToString:NSURLAuthenticationMethodServerTrust])
        {
            [challenge.sender useCredential:[NSURLCredential credentialForTrust:challenge.protectionSpace.serverTrust] forAuthenticationChallenge:challenge];
                NSLog(@"chalenging protection space authentication checking");
        }
    }
like image 74
RVN Avatar answered Nov 15 '22 20:11

RVN