OCSP bypass with tryLater in responseStatus

RESOLVED INVALID

Status

()

Core
Security: PSM
RESOLVED INVALID
9 years ago
a year ago

People

(Reporter: bsterne, Unassigned)

Tracking

(Blocks: 1 bug, {sec-low})

1.9.1 Branch
sec-low
Points:
---

Firefox Tracking Flags

(blocking2.0 -, status1.9.1 wanted)

Details

(Whiteboard: [sg:low] spec issue?, URL)

(Reporter)

Description

9 years ago
Moxie Marlinspike reported this issue to Mozilla via the security@mozilla.org email alias.  Here are the full contents of the email:

-----


Since this is all on its way out anyway, I'll report another bug in an attempt to up my tshirt count.

I was always a little worried that my null-prefix certificates were going to be discovered and revoked by CAs (of course, being CAs, that never happened).  When my null-prefix certs started being issued with OCSP URLs in them, that made me even more nervous.

Looking at the OCSP protocol, though, I was surprised.  The most simple attack I found is as follows.  If you look at the basic response structure:

   OCSPResponse ::= SEQUENCE {
      responseStatus         OCSPResponseStatus,
      responseBytes          [0] EXPLICIT ResponseBytes OPTIONAL
   }

...only some of the data in "responseBytes" is signed.  "responseStatus" itself is unsigned, and the "responseBytes" field itself is optional depending on the status value.

If we look at OCSPResponseStatus for possible values:

   OCSPResponseStatus ::= ENUMERATED {
       successful            (0),  --Response has valid confirmations
       malformedRequest      (1),  --Illegal confirmation request
       internalError         (2),  --Internal error in issuer
       tryLater              (3),  --Try again later
                                   --(4) is not used
       sigRequired           (5),  --Must sign the request
       unauthorized          (6)   --Request unauthorized
   }

...we can't use "successful," because then we'd have to include responseBytes (which might require a signature we don't have).  But we can use the value "tryLater" without including any signed data, and hey, "tryLater" doesn't sound so bad.

In my testing, I've found that almost all implementations agree it doesn't sound so bad.  Firefox, for instance, does not consider a certificate that gets a "tryLater" OCSP response to be suspicious.

So my MITM tool watches for OCSP requests for the OCSP urls in the certificates it's using, intercepts them, and responds with "tryLater" (literally the single ASCII byte 0x33).

I'm not sure that you guys are doing anything "wrong" as far as the RFC is concerned, since the behavior of how one is supposed to react in this case isn't clearly defined.  The protocol is problematic for even allowing this case to exist.

But I would say that it is a security vulnerability to not take some implementation liberty here.  If I am capable of intercepting your communication and redirecting it to my stolen/forged/whatever certificate, I am also almost certainly capable of intercepting your OCSP request and responding with 0x33.  In the case of LAN-based MITM attacks, it's guaranteed.

- moxie
(Reporter)

Updated

9 years ago
Whiteboard: [sg:critical]
This is not an NSS bug.  It may or may not be a browser bug.  It's a matter 
of policy and choice.  This bug is either not a bug, or is a PSM bug, IMO.

I'll be the first to agree that it's truly bizarre that the OCSP response's 
first and most fundamental result is not part of the signed data.  Of course,
that's a vulnerability with the protocol definition itself, and not with any
particular implementation of it.  

In the case of OCSP (or any other revocation protocol) there are basically 
3 possible outcomes:
1) clear unambiguous authorized valid response saying "that cert is good".
2) clear unambiguous authorized valid response saying "that cert is bad".
3) anything else, including
   - no response
   - syntactically invalid response 
   - unauthorized response 
     - signature not valid or 
     - signature not verifiable from an authorized responder
   - vague response (there are several, "tryLater" being just one)

The caller of NSS tells NSS how to handle all those "anything else" cases. 
It can tell us to require a response of case 1 or case 2 above, and treat 
anything else as a revoked cert.  There are further levels of nuance in how
it can choose to interpret various odd responses.  

IIRC, Firefox gives the user a preference choice about what to do with 
"anything else" responses.  The default setting is to treat the "anything 
else" case as "give the cert the benefit of a doubt and honor it".  But the
user can also choose to "reject the cert for anything other than case 1". 
The UI for this preference varies by product or version, but the preference is
   security.OCSP.require   default   boolean   false

The browser defaults to NOT requiring a positive ("cert is good") response,
because historically the probability of getting ANY OCSP response hasn't 
been all that high.  Maybe Mozilla should reconsider that default.  That is
purely a browser (PSM) matter and changing it requires no NSS change.

Moxie, I would be interested in knowing 
a) what version(s) of the Firefox browser did you test?
b) Did you try setting the preference to require a positive OCSP response?
c) If so, how did Firefox treat the cert when the response said "tryLater"?
Assignee: nobody → kaie
Component: Libraries → Security: PSM
Product: NSS → Core
QA Contact: libraries → psm
Version: unspecified → 1.9.1 Branch
Whiteboard: [sg:critical] → [sg:high] spec issue?
blocking1.9.1: needed → ---
blocking2.0: --- → ?
status1.9.1: --- → wanted
Is there any reason to keep this bug hidden? Moxie revealed this at his BlackHat talk two months ago.
Whiteboard: [sg:high] spec issue? → [sg:moderate] spec issue?

Comment 3

8 years ago
What happens if OCSP strict mode is enabled, and server responds try-later? Do we accept the cert?

If we are in strict mode, is there any way to cause the client to accept an unsigned OCSP response and accept the subject cert?

If yes, that's a vulnerability.


(In reply to comment #2)
> Is there any reason to keep this bug hidden? Moxie revealed this at his
> BlackHat talk two months ago.

If this has been published, I'm fine to open the bug.
Nelson, do you agree?
Assignee: kaie → nobody
Blocks: 157555
Agreed, not "security sensitive" any more.
Group: core-security

Comment 5

7 years ago
I don't think this blocks, although we should fix it.
blocking2.0: ? → -

Updated

6 years ago
Assignee: nobody → bsmith
If the attacker could send us tryLater, they can just filter out the response completely. So, while tryLater is totally bogus, it doesn't enable any attacks that aren't already possible when the strict OCSP checking pref isn't set. So, I think the only work on this bug is to add tests that tryLater and other unsigned response codes are accepted when strict mode is enabled.

I am reducing the severity of this particular issue. The real problem is that the OCSP revocation checking model is broken--there are too many reasons we can't be strict by default, and it only works if we are strict by default--and that's not this bug.
Keywords: sec-review-needed
Whiteboard: [sg:moderate] spec issue? → [sg:low] spec issue?
(Reporter)

Comment 7

6 years ago
I understand the spirit of the sec-review, request but there really isn't anything for us to review until there is a proposal on the table to address the issue in the spec.
Keywords: sec-review-needed
Assignee: bsmith → nobody
Keywords: sec-low
See comment 6.
Status: NEW → RESOLVED
Last Resolved: 2 years ago
Resolution: --- → INVALID
See Also: → bug 1323141
You need to log in before you can comment on or make changes to this bug.