mirror of
https://github.com/lukaszraczylo/traefikoidc.git
synced 2026-11-08 08:34:07 +00:00
fix(jwt): bind ECDSA curve to the algorithm and require fixed signature length
ES256, ES384 and ES512 verified against any curve and any even-length signature. RFC 7518 fixes the curve per algorithm and the signature to R||S at the curve's octet length. Verification now enforces both.
This commit is contained in:
@@ -322,6 +322,9 @@ func verifyTimeClaims(claims map[string]interface{}) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
// ecdsaAlgBits maps an ES* algorithm to its curve size (RFC 7518 3.4).
|
||||
var ecdsaAlgBits = map[string]int{"ES256": 256, "ES384": 384, "ES512": 521}
|
||||
|
||||
// verifySignatureWithKey verifies a JWT signature using an already-parsed
|
||||
// public key, skipping the PEM-encode/decode round trip. This is the hot
|
||||
// path used by VerifyJWTSignatureAndClaims and verifyLogoutTokenSignature.
|
||||
@@ -369,7 +372,13 @@ func verifySignatureWithKey(tokenString string, pubKey crypto.PublicKey, alg str
|
||||
if strings.HasPrefix(alg, "ES") {
|
||||
var r, s big.Int
|
||||
sigLen := len(signature)
|
||||
if sigLen%2 != 0 {
|
||||
// RFC 7518 3.4: the curve is fixed by the algorithm and the
|
||||
// signature is R||S at exactly the curve's octet length.
|
||||
bits := ecdsaAlgBits[alg]
|
||||
if bits == 0 || pubKey.Curve.Params().BitSize != bits {
|
||||
return fmt.Errorf("ECDSA key curve does not match algorithm %s", alg)
|
||||
}
|
||||
if sigLen != 2*((bits+7)/8) {
|
||||
return fmt.Errorf("invalid ECDSA signature length")
|
||||
}
|
||||
r.SetBytes(signature[:sigLen/2])
|
||||
|
||||
Reference in New Issue
Block a user