ATS Certificate Revocation Check

I have made my own public key infrastructure that my app uses and I want to support certificate revocation on it. From what I have gather through documentation and forum posts, there is not too much support for that. I have seen mentions of using OCSP stapling, which is probably the direction I want to take. However, I did not see anything showing how to use it. Is it even possible to do so with a custom OCSP authority? If so, how would it be enabled/configured? Thanks

Replies

I have made my own public key infrastructure that my app uses

I’d like to clarify what you mean by that. It sounds like:

  • You’re working with HTTPS.

  • You have created a custom certificate authority (CA).

  • It issues certificates for your HTTPS servers.

  • And those servers are on the public Internet.

  • You have an app that talks to those servers using URLSession.

Is that right?

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

Yes that is all correct.

Why are you doing this?

My general advice is that, if your server is available on the public Internet, you should give it a certificate from a trusted CA. That avoids a whole world of grief.

If you want to impose security beyond that, that’s fine. We even have some explicit support for that, namely NSPinnedDomains.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

We want to use a custom PKI for both client/server authentication in a sensitive application where we want to control the processes (we don't want an externally hosted CA). We are developing in-house all the parts of the PKI, including an OCSP responder, and we have gotten our custom certificates to work on our iOS app. The only part we don't have is getting the iOS app to check for certificate revocation.

You realise that you’re actually reducing security, right? In order to support a custom CA you must disable ATS, which means you miss out on the security enhancements that it provides.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

Sorry, I'm a little confused. We have been using our custom CA for a while and in our plist file, in NSAppTransportSecurity, we do not have an exceptions enabled and have NSAllowsArbitraryLoads as false. Is that not enough to have ATS considered enabled? Because SSL verification is definitely happening: when an incorrectly configured server certificate is presented, we have SSL verification errors. We're only encountering issues now when we want certificate revocation.

We have been using our custom CA for a while and in our plist file, in NSAppTransportSecurity, we do not have an exceptions enabled and have NSAllowsArbitraryLoads as false.

This is using URLSession, right?

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

Yes, that is correct

OK. So, with respect to this:

We have been using our custom CA for a while and in our plist file, in NSAppTransportSecurity, we do not have an exceptions enabled and have NSAllowsArbitraryLoads as false.

does that mean you have no NSAppTransportSecurity property? I mean, the default value for NSAllowsArbitraryLoads is false, so setting it to false is redundant, so if that’s the only thing in there then you don’t need the property at all.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

We have NSAppTransportSecurity, since we have NSPinnedDomains and NSPinnedCAIdentities for our server domain and our custom CA certificate.

Regardless, is your recommended solution to this to have the server bear a certificate signed by a trusted CA like Digicert, and then we can have our own custom PKI for our client auth scheme, since we want to at least control the client CA.

is your recommended solution to this to have the server bear a certificate signed by a trusted CA

Yes.

You are absolutely free to do your own additional trust evaluation if you like — using NSPinnedDomains or something custom with authentication challenges — but using a ‘base’ certificate issued by a trusted CA will save you a lot of grief.

and then we can have our own custom PKI for our client auth scheme

By “client auth scheme” you’re referring to the certificates you issue to your users (or perhaps your app) to support mTLS [1], right?

If so, I have no specific advice on that front. iOS doesn’t perform trust evaluation on client certificates, so it doesn’t care where you get them from.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

[1] See TLS for App Developers.

Thank you for your response! I would like to inquire further about what you meant by ATS being disabled when we use a custom CA. When we use our server certificate signed by our custom CA, TLS is definitely in use (invalidly signed or configured server certificates cause TLS errors, while valid certificates work fine). Besides TLS, what other security features are provided by ATS that we would have to forgo if we use a custom CA for our server certificate?

All Apple’s TLS APIs perform default TLS server trust evaluation [1]. ATS applies a series of security checks in addition to that default. In order to use a custom CA you must:

  1. Disable ATS for your domain.

  2. Override HTTPS server trust evaluation to treat your CA’s root as a trusted anchor.

Step 1 means that you lose all of ATS’s additional security checks. In most cases, maybe even all, it’s possible to add them back in step 2. However, there are issues with that:

  • A minor bug can introduce a security vulnerability. So, if you decide to do this, you need a test environment to check that you’ve done it correctly. Such a test environment must test both the successful and the failed cases, so you need a test server that exhibits all of the attacks that you’re trying to detect. That’s not impossible to set up, but it’s a pain.

  • You lose the declarative nature of ATS. One nice thing about ATS is that, by looking at your ATS dictionary, an outside observer [2] can tell which of your connections are secured by the platform. If you disable ATS, the observer has to audit your step 2 code.

The approach I recommend is to configure your servers to use certificates issued by a CA that’s trusted by default. This gets rid of step 1 entirely. If you want, you can retain step 2 to implement your own additional security checks [3]. However, those are strictly in addition to the default TLS server trust evaluation and the checks done by ATS. So, no matter what bugs you have in your code, you still get those protections, which is a pretty solid foundation.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

[1] I generally call this RFC 2818-style trust evaluation, but that’s increasingly inaccurate these days.

[2] Outside observers include App Review, and they have their own policy about this. However, that’s not my primary concern here. Rather, I’m imagining you presenting your app to your own security auditors.

[3] Or, better yet, implement them declaratively using NSPinnedDomains.