> On Oct 13, 2023, at 3:52 PM, Orie Steele <orie@transmute.industries> wrote:
>
> Inline (and sorry for repeating points / rambling) :
>
> On Fri, Oct 13, 2023 at 1:25 PM Brian Campbell <bcampb...@pingidentity.com
> <mailto:bcampb...@pingidentity.com>> wrote:
>> That makes sense in principle but is maybe not particularly actionable or
>> helpful guidance. The need to do some JSON parsing/processing prior to
>> signature verification is kinda inherent to JWS itself.
>
> It's not when you have the verification keys, and you are still looking at
> base64url encoded strings.
> You can try all keys and trade off multiple verification attempts for
> exposing the parser to an attacker directly.
>
> But not all protocols work like this, sometimes you need to decode the JWS to
> discover the verification keys.
>
> In those cases, parsing is basically unavoidable... but you still have the
> choice of "parse as an object" vs "find me a string I need, from another
> string"... both approaches can have vulnerable implementations.
>
> Given the existing security considerations that say that discovery is out of
> scope,
> it's reasonable to assert that implementers SHOULD NOT "parse as json
> objects" the protected header or payload, prior to signature verification.
All of JOSE, as well as JWTs, define algorithms and representations for use in
higher level interoperable applications within protocols.
The “iss” claim is optional, as is its connotations around discovery (say, via
an OAuth Server Metadata endpoint).
I would tend to expect that the "JSON Object Signing and Encryption"
specifications expect the ability to parse and serialize JSON objects as part
of the security layer, such as what would be needed for creating and consuming
JSON serialization of signed/encrypted messages.
That doesn’t mean it has to be a fully formed JSON library; just as you don’t
need some generalized CBOR library with an object model to handle verification
of COSE signatures. However, there is a difference in established JSON parsers,
as well as JSON being used in less constrained environments and JSON Text
having complete/non-extensible set of data types. It is far more likely for
generalized JSON parsers and generators to be used.
An application can constrain things down to convey any requirements elsewhere
in the protocol (such as conveying a reference to the keys as a HTTP header or
query parameter), such that integrity of compact serialization could be
verified before JSON parsing of the protected header. I suppose they could also
constrain identifiers and JSON string escaping such that they could pull them
out via regular expressions. An application might also require a limited
character set (latin-1 code point range only with no unicode escaping in
strings) to allow consumers to reduce the risk of unicode-level vulnerabilities.
An example of text I would expect from a specification constraining
JSON-formatted input to be consumed without JSON parsing would be
https://www.w3.org/TR/webauthn-3/#clientdatajson-serialization. This is also
not dissimilar to additional effort CBOR specs make to reduce
optionality/variability in formats. That said, the vast majority of relying
parties (e.g. all but one implementation) will likely use off-the-shelf JSON
parsers for this data, which could very well be coming from a malicious client.
> Noting that the JWT RFC contains normative statements in security
> considerations that are already targeted at addressing security issues with
> JSON: https://datatracker.ietf.org/doc/html/rfc7515#section-10.12
>
>> At a minimum the algorithm is in the header.
>
> Sorta, "parsing" can mean many things... it's reasonable to assume the folks
> who worked on the original RFC had good reasons for distinguishing JWS
> parsers from JSON parsers.
>
> See : https://datatracker.ietf.org/doc/html/rfc7515#section-5.2
> <https://datatracker.ietf.org/doc/html/rfc7515#section-5.2>
A JWS parser converts compact and JSON serializations of a JWS into the
representative parts (protected header, signature, payload, unprotected
header). JSON parsers neither handle compact serialization input nor have
octet-string output (sans extensions like replacers).
<snip>
> In the case that you have a public key that is already restricted to a single
> fully specified algorithm,
> I'd argue it's safer to just use the algorithm specified for the public key,
> than it is to decode and parse the header, then match the alg to the public
> key,
> and then attempt to verify a potentially tampered / maliciously crafted
> message.
Generally, you want the algorithm chosen by the issuer to be externally
negotiated and authoritative. Whether you verify alg matches alg before or
after could then be a function of how plausible you think it is that there is
indeed a remote code execution vulnerability or DOS in your JSON parser.
> SD-JWT doesn't give guidance like this on restricting keys, it could say
> issuer and holder keys SHOULD be restricted to fully specified alg values,
> and still defer key discovery to other specs.
Wouldn’t signature and issuance claims verification be typically a function of
the JWT libraries and not the wrapping SD-JWT libraries?
Is this guidance specific for SD-JWT, or is it meant to provide JWT guidance in
general?
> Yep, but in this case, we are inheriting the specific text in
> https://datatracker.ietf.org/doc/html/rfc7515#section-5.2
>
> Which does not forbid or require JSON parsing... in other words, it does not
> provide clear guidance on if parsing the header as a JSON object is
> required... and even if it did... parsing is hard to define as I said above.
I don’t understand how step 3 (which takes in a protected header octet string,
validate it is proper JSON, and return the representative JSON object) would
not constitute a JSON parser, even if such a parser was not a generalized
implementation. Step 5 requires processing of the individual properties of this
JSON object which are required by the application space for support, including
`crit` validation, pre-signature validation (step 8).
<snip>
>
> The principle is: don't use parsers when you don't need to, minimize the code
> associated with processing untrusted data,
For SD-JWT, I would suspect this would mean that validation of issuance claims
MUST happen based on the JWT, e.g. not based on reconstitution of selectively
disclosed information. E.g., an “exp” claim in a disclosure is an invalid
SD-JWT.
> and treat all unverified messages as RCE payloads that are crafted to exploit
> a vulnerable parser if you are paranoid.
Once you have established the necessary parsers, this is an audit requirement
on paranoid implementations. For example, the certificates in protected headers
could be malformed ASN.1 and could contain invalid public keys, such as points
that are not in the subgroup. This might be a good reason to push back on using
a x509 certificate chain in a protected header to dynamically establish the
issuer and issuer trust. However, there will be applications which require
this, and if you need to interoperate your only choice will be to
harden/isolate that functionality.
> It's still true that an RCE in a parser that is only exploitable in a library
> after verification is a show stopper, but defense in depth requires us to
> address what we can address.
Worrying about malicious issuers is another application level concern. If your
authenticated messages could be coming from malicious parties, you have a much
harder time.
<snip>
-DW
_______________________________________________
OAuth mailing list
OAuth@ietf.org
https://www.ietf.org/mailman/listinfo/oauth