...
1
2
3
4 package jwt
5
6 import (
7 "crypto"
8 "crypto/rand"
9 "crypto/rsa"
10 )
11
12
13 type SigningMethodRSAPSS struct {
14 *SigningMethodRSA
15 Options *rsa.PSSOptions
16
17
18
19
20 VerifyOptions *rsa.PSSOptions
21 }
22
23
24 var (
25 SigningMethodPS256 *SigningMethodRSAPSS
26 SigningMethodPS384 *SigningMethodRSAPSS
27 SigningMethodPS512 *SigningMethodRSAPSS
28 )
29
30 func init() {
31
32 SigningMethodPS256 = &SigningMethodRSAPSS{
33 SigningMethodRSA: &SigningMethodRSA{
34 Name: "PS256",
35 Hash: crypto.SHA256,
36 },
37 Options: &rsa.PSSOptions{
38 SaltLength: rsa.PSSSaltLengthEqualsHash,
39 },
40 VerifyOptions: &rsa.PSSOptions{
41 SaltLength: rsa.PSSSaltLengthAuto,
42 },
43 }
44 RegisterSigningMethod(SigningMethodPS256.Alg(), func() SigningMethod {
45 return SigningMethodPS256
46 })
47
48
49 SigningMethodPS384 = &SigningMethodRSAPSS{
50 SigningMethodRSA: &SigningMethodRSA{
51 Name: "PS384",
52 Hash: crypto.SHA384,
53 },
54 Options: &rsa.PSSOptions{
55 SaltLength: rsa.PSSSaltLengthEqualsHash,
56 },
57 VerifyOptions: &rsa.PSSOptions{
58 SaltLength: rsa.PSSSaltLengthAuto,
59 },
60 }
61 RegisterSigningMethod(SigningMethodPS384.Alg(), func() SigningMethod {
62 return SigningMethodPS384
63 })
64
65
66 SigningMethodPS512 = &SigningMethodRSAPSS{
67 SigningMethodRSA: &SigningMethodRSA{
68 Name: "PS512",
69 Hash: crypto.SHA512,
70 },
71 Options: &rsa.PSSOptions{
72 SaltLength: rsa.PSSSaltLengthEqualsHash,
73 },
74 VerifyOptions: &rsa.PSSOptions{
75 SaltLength: rsa.PSSSaltLengthAuto,
76 },
77 }
78 RegisterSigningMethod(SigningMethodPS512.Alg(), func() SigningMethod {
79 return SigningMethodPS512
80 })
81 }
82
83
84
85 func (m *SigningMethodRSAPSS) Verify(signingString, signature string, key interface{}) error {
86 var err error
87
88
89 var sig []byte
90 if sig, err = DecodeSegment(signature); err != nil {
91 return err
92 }
93
94 var rsaKey *rsa.PublicKey
95 switch k := key.(type) {
96 case *rsa.PublicKey:
97 rsaKey = k
98 default:
99 return ErrInvalidKey
100 }
101
102
103 if !m.Hash.Available() {
104 return ErrHashUnavailable
105 }
106 hasher := m.Hash.New()
107 hasher.Write([]byte(signingString))
108
109 opts := m.Options
110 if m.VerifyOptions != nil {
111 opts = m.VerifyOptions
112 }
113
114 return rsa.VerifyPSS(rsaKey, m.Hash, hasher.Sum(nil), sig, opts)
115 }
116
117
118
119 func (m *SigningMethodRSAPSS) Sign(signingString string, key interface{}) (string, error) {
120 var rsaKey *rsa.PrivateKey
121
122 switch k := key.(type) {
123 case *rsa.PrivateKey:
124 rsaKey = k
125 default:
126 return "", ErrInvalidKeyType
127 }
128
129
130 if !m.Hash.Available() {
131 return "", ErrHashUnavailable
132 }
133
134 hasher := m.Hash.New()
135 hasher.Write([]byte(signingString))
136
137
138 if sigBytes, err := rsa.SignPSS(rand.Reader, rsaKey, m.Hash, hasher.Sum(nil), m.Options); err == nil {
139 return EncodeSegment(sigBytes), nil
140 } else {
141 return "", err
142 }
143 }
144
View as plain text