1
16
17 package jose
18
19 import (
20 "crypto"
21 "crypto/aes"
22 "crypto/ecdsa"
23 "crypto/rand"
24 "crypto/rsa"
25 "crypto/sha1"
26 "crypto/sha256"
27 "errors"
28 "fmt"
29 "math/big"
30
31 "golang.org/x/crypto/ed25519"
32 josecipher "gopkg.in/go-jose/go-jose.v2/cipher"
33 "gopkg.in/go-jose/go-jose.v2/json"
34 )
35
36
37 type rsaEncrypterVerifier struct {
38 publicKey *rsa.PublicKey
39 }
40
41
42 type rsaDecrypterSigner struct {
43 privateKey *rsa.PrivateKey
44 }
45
46
47 type ecEncrypterVerifier struct {
48 publicKey *ecdsa.PublicKey
49 }
50
51 type edEncrypterVerifier struct {
52 publicKey ed25519.PublicKey
53 }
54
55
56 type ecKeyGenerator struct {
57 size int
58 algID string
59 publicKey *ecdsa.PublicKey
60 }
61
62
63 type ecDecrypterSigner struct {
64 privateKey *ecdsa.PrivateKey
65 }
66
67 type edDecrypterSigner struct {
68 privateKey ed25519.PrivateKey
69 }
70
71
72 func newRSARecipient(keyAlg KeyAlgorithm, publicKey *rsa.PublicKey) (recipientKeyInfo, error) {
73
74 switch keyAlg {
75 case RSA1_5, RSA_OAEP, RSA_OAEP_256:
76 default:
77 return recipientKeyInfo{}, ErrUnsupportedAlgorithm
78 }
79
80 if publicKey == nil {
81 return recipientKeyInfo{}, errors.New("invalid public key")
82 }
83
84 return recipientKeyInfo{
85 keyAlg: keyAlg,
86 keyEncrypter: &rsaEncrypterVerifier{
87 publicKey: publicKey,
88 },
89 }, nil
90 }
91
92
93 func newRSASigner(sigAlg SignatureAlgorithm, privateKey *rsa.PrivateKey) (recipientSigInfo, error) {
94
95 switch sigAlg {
96 case RS256, RS384, RS512, PS256, PS384, PS512:
97 default:
98 return recipientSigInfo{}, ErrUnsupportedAlgorithm
99 }
100
101 if privateKey == nil {
102 return recipientSigInfo{}, errors.New("invalid private key")
103 }
104
105 return recipientSigInfo{
106 sigAlg: sigAlg,
107 publicKey: staticPublicKey(&JSONWebKey{
108 Key: privateKey.Public(),
109 }),
110 signer: &rsaDecrypterSigner{
111 privateKey: privateKey,
112 },
113 }, nil
114 }
115
116 func newEd25519Signer(sigAlg SignatureAlgorithm, privateKey ed25519.PrivateKey) (recipientSigInfo, error) {
117 if sigAlg != EdDSA {
118 return recipientSigInfo{}, ErrUnsupportedAlgorithm
119 }
120
121 if privateKey == nil {
122 return recipientSigInfo{}, errors.New("invalid private key")
123 }
124 return recipientSigInfo{
125 sigAlg: sigAlg,
126 publicKey: staticPublicKey(&JSONWebKey{
127 Key: privateKey.Public(),
128 }),
129 signer: &edDecrypterSigner{
130 privateKey: privateKey,
131 },
132 }, nil
133 }
134
135
136 func newECDHRecipient(keyAlg KeyAlgorithm, publicKey *ecdsa.PublicKey) (recipientKeyInfo, error) {
137
138 switch keyAlg {
139 case ECDH_ES, ECDH_ES_A128KW, ECDH_ES_A192KW, ECDH_ES_A256KW:
140 default:
141 return recipientKeyInfo{}, ErrUnsupportedAlgorithm
142 }
143
144 if publicKey == nil || !publicKey.Curve.IsOnCurve(publicKey.X, publicKey.Y) {
145 return recipientKeyInfo{}, errors.New("invalid public key")
146 }
147
148 return recipientKeyInfo{
149 keyAlg: keyAlg,
150 keyEncrypter: &ecEncrypterVerifier{
151 publicKey: publicKey,
152 },
153 }, nil
154 }
155
156
157 func newECDSASigner(sigAlg SignatureAlgorithm, privateKey *ecdsa.PrivateKey) (recipientSigInfo, error) {
158
159 switch sigAlg {
160 case ES256, ES384, ES512:
161 default:
162 return recipientSigInfo{}, ErrUnsupportedAlgorithm
163 }
164
165 if privateKey == nil {
166 return recipientSigInfo{}, errors.New("invalid private key")
167 }
168
169 return recipientSigInfo{
170 sigAlg: sigAlg,
171 publicKey: staticPublicKey(&JSONWebKey{
172 Key: privateKey.Public(),
173 }),
174 signer: &ecDecrypterSigner{
175 privateKey: privateKey,
176 },
177 }, nil
178 }
179
180
181 func (ctx rsaEncrypterVerifier) encryptKey(cek []byte, alg KeyAlgorithm) (recipientInfo, error) {
182 encryptedKey, err := ctx.encrypt(cek, alg)
183 if err != nil {
184 return recipientInfo{}, err
185 }
186
187 return recipientInfo{
188 encryptedKey: encryptedKey,
189 header: &rawHeader{},
190 }, nil
191 }
192
193
194
195 func (ctx rsaEncrypterVerifier) encrypt(cek []byte, alg KeyAlgorithm) ([]byte, error) {
196 switch alg {
197 case RSA1_5:
198 return rsa.EncryptPKCS1v15(RandReader, ctx.publicKey, cek)
199 case RSA_OAEP:
200 return rsa.EncryptOAEP(sha1.New(), RandReader, ctx.publicKey, cek, []byte{})
201 case RSA_OAEP_256:
202 return rsa.EncryptOAEP(sha256.New(), RandReader, ctx.publicKey, cek, []byte{})
203 }
204
205 return nil, ErrUnsupportedAlgorithm
206 }
207
208
209 func (ctx rsaDecrypterSigner) decryptKey(headers rawHeader, recipient *recipientInfo, generator keyGenerator) ([]byte, error) {
210 return ctx.decrypt(recipient.encryptedKey, headers.getAlgorithm(), generator)
211 }
212
213
214
215 func (ctx rsaDecrypterSigner) decrypt(jek []byte, alg KeyAlgorithm, generator keyGenerator) ([]byte, error) {
216
217
218 switch alg {
219 case RSA1_5:
220 defer func() {
221
222
223
224
225
226
227 _ = recover()
228 }()
229
230
231 keyBytes := ctx.privateKey.PublicKey.N.BitLen() / 8
232 if keyBytes != len(jek) {
233
234
235
236 return nil, ErrCryptoFailure
237 }
238
239 cek, _, err := generator.genKey()
240 if err != nil {
241 return nil, ErrCryptoFailure
242 }
243
244
245
246
247
248 _ = rsa.DecryptPKCS1v15SessionKey(rand.Reader, ctx.privateKey, jek, cek)
249
250 return cek, nil
251 case RSA_OAEP:
252
253 return rsa.DecryptOAEP(sha1.New(), rand.Reader, ctx.privateKey, jek, []byte{})
254 case RSA_OAEP_256:
255
256 return rsa.DecryptOAEP(sha256.New(), rand.Reader, ctx.privateKey, jek, []byte{})
257 }
258
259 return nil, ErrUnsupportedAlgorithm
260 }
261
262
263 func (ctx rsaDecrypterSigner) signPayload(payload []byte, alg SignatureAlgorithm) (Signature, error) {
264 var hash crypto.Hash
265
266 switch alg {
267 case RS256, PS256:
268 hash = crypto.SHA256
269 case RS384, PS384:
270 hash = crypto.SHA384
271 case RS512, PS512:
272 hash = crypto.SHA512
273 default:
274 return Signature{}, ErrUnsupportedAlgorithm
275 }
276
277 hasher := hash.New()
278
279
280 _, _ = hasher.Write(payload)
281 hashed := hasher.Sum(nil)
282
283 var out []byte
284 var err error
285
286 switch alg {
287 case RS256, RS384, RS512:
288
289
290
291 out, err = rsa.SignPKCS1v15(RandReader, ctx.privateKey, hash, hashed)
292 case PS256, PS384, PS512:
293 out, err = rsa.SignPSS(RandReader, ctx.privateKey, hash, hashed, &rsa.PSSOptions{
294 SaltLength: rsa.PSSSaltLengthEqualsHash,
295 })
296 }
297
298 if err != nil {
299 return Signature{}, err
300 }
301
302 return Signature{
303 Signature: out,
304 protected: &rawHeader{},
305 }, nil
306 }
307
308
309 func (ctx rsaEncrypterVerifier) verifyPayload(payload []byte, signature []byte, alg SignatureAlgorithm) error {
310 var hash crypto.Hash
311
312 switch alg {
313 case RS256, PS256:
314 hash = crypto.SHA256
315 case RS384, PS384:
316 hash = crypto.SHA384
317 case RS512, PS512:
318 hash = crypto.SHA512
319 default:
320 return ErrUnsupportedAlgorithm
321 }
322
323 hasher := hash.New()
324
325
326 _, _ = hasher.Write(payload)
327 hashed := hasher.Sum(nil)
328
329 switch alg {
330 case RS256, RS384, RS512:
331 return rsa.VerifyPKCS1v15(ctx.publicKey, hash, hashed, signature)
332 case PS256, PS384, PS512:
333 return rsa.VerifyPSS(ctx.publicKey, hash, hashed, signature, nil)
334 }
335
336 return ErrUnsupportedAlgorithm
337 }
338
339
340 func (ctx ecEncrypterVerifier) encryptKey(cek []byte, alg KeyAlgorithm) (recipientInfo, error) {
341 switch alg {
342 case ECDH_ES:
343
344 return recipientInfo{
345 header: &rawHeader{},
346 }, nil
347 case ECDH_ES_A128KW, ECDH_ES_A192KW, ECDH_ES_A256KW:
348 default:
349 return recipientInfo{}, ErrUnsupportedAlgorithm
350 }
351
352 generator := ecKeyGenerator{
353 algID: string(alg),
354 publicKey: ctx.publicKey,
355 }
356
357 switch alg {
358 case ECDH_ES_A128KW:
359 generator.size = 16
360 case ECDH_ES_A192KW:
361 generator.size = 24
362 case ECDH_ES_A256KW:
363 generator.size = 32
364 }
365
366 kek, header, err := generator.genKey()
367 if err != nil {
368 return recipientInfo{}, err
369 }
370
371 block, err := aes.NewCipher(kek)
372 if err != nil {
373 return recipientInfo{}, err
374 }
375
376 jek, err := josecipher.KeyWrap(block, cek)
377 if err != nil {
378 return recipientInfo{}, err
379 }
380
381 return recipientInfo{
382 encryptedKey: jek,
383 header: &header,
384 }, nil
385 }
386
387
388 func (ctx ecKeyGenerator) keySize() int {
389 return ctx.size
390 }
391
392
393 func (ctx ecKeyGenerator) genKey() ([]byte, rawHeader, error) {
394 priv, err := ecdsa.GenerateKey(ctx.publicKey.Curve, RandReader)
395 if err != nil {
396 return nil, rawHeader{}, err
397 }
398
399 out := josecipher.DeriveECDHES(ctx.algID, []byte{}, []byte{}, priv, ctx.publicKey, ctx.size)
400
401 b, err := json.Marshal(&JSONWebKey{
402 Key: &priv.PublicKey,
403 })
404 if err != nil {
405 return nil, nil, err
406 }
407
408 headers := rawHeader{
409 headerEPK: makeRawMessage(b),
410 }
411
412 return out, headers, nil
413 }
414
415
416 func (ctx ecDecrypterSigner) decryptKey(headers rawHeader, recipient *recipientInfo, generator keyGenerator) ([]byte, error) {
417 epk, err := headers.getEPK()
418 if err != nil {
419 return nil, errors.New("go-jose/go-jose: invalid epk header")
420 }
421 if epk == nil {
422 return nil, errors.New("go-jose/go-jose: missing epk header")
423 }
424
425 publicKey, ok := epk.Key.(*ecdsa.PublicKey)
426 if publicKey == nil || !ok {
427 return nil, errors.New("go-jose/go-jose: invalid epk header")
428 }
429
430 if !ctx.privateKey.Curve.IsOnCurve(publicKey.X, publicKey.Y) {
431 return nil, errors.New("go-jose/go-jose: invalid public key in epk header")
432 }
433
434 apuData, err := headers.getAPU()
435 if err != nil {
436 return nil, errors.New("go-jose/go-jose: invalid apu header")
437 }
438 apvData, err := headers.getAPV()
439 if err != nil {
440 return nil, errors.New("go-jose/go-jose: invalid apv header")
441 }
442
443 deriveKey := func(algID string, size int) []byte {
444 return josecipher.DeriveECDHES(algID, apuData.bytes(), apvData.bytes(), ctx.privateKey, publicKey, size)
445 }
446
447 var keySize int
448
449 algorithm := headers.getAlgorithm()
450 switch algorithm {
451 case ECDH_ES:
452
453 return deriveKey(string(headers.getEncryption()), generator.keySize()), nil
454 case ECDH_ES_A128KW:
455 keySize = 16
456 case ECDH_ES_A192KW:
457 keySize = 24
458 case ECDH_ES_A256KW:
459 keySize = 32
460 default:
461 return nil, ErrUnsupportedAlgorithm
462 }
463
464 key := deriveKey(string(algorithm), keySize)
465 block, err := aes.NewCipher(key)
466 if err != nil {
467 return nil, err
468 }
469
470 return josecipher.KeyUnwrap(block, recipient.encryptedKey)
471 }
472
473 func (ctx edDecrypterSigner) signPayload(payload []byte, alg SignatureAlgorithm) (Signature, error) {
474 if alg != EdDSA {
475 return Signature{}, ErrUnsupportedAlgorithm
476 }
477
478 sig, err := ctx.privateKey.Sign(RandReader, payload, crypto.Hash(0))
479 if err != nil {
480 return Signature{}, err
481 }
482
483 return Signature{
484 Signature: sig,
485 protected: &rawHeader{},
486 }, nil
487 }
488
489 func (ctx edEncrypterVerifier) verifyPayload(payload []byte, signature []byte, alg SignatureAlgorithm) error {
490 if alg != EdDSA {
491 return ErrUnsupportedAlgorithm
492 }
493 ok := ed25519.Verify(ctx.publicKey, payload, signature)
494 if !ok {
495 return errors.New("go-jose/go-jose: ed25519 signature failed to verify")
496 }
497 return nil
498 }
499
500
501 func (ctx ecDecrypterSigner) signPayload(payload []byte, alg SignatureAlgorithm) (Signature, error) {
502 var expectedBitSize int
503 var hash crypto.Hash
504
505 switch alg {
506 case ES256:
507 expectedBitSize = 256
508 hash = crypto.SHA256
509 case ES384:
510 expectedBitSize = 384
511 hash = crypto.SHA384
512 case ES512:
513 expectedBitSize = 521
514 hash = crypto.SHA512
515 }
516
517 curveBits := ctx.privateKey.Curve.Params().BitSize
518 if expectedBitSize != curveBits {
519 return Signature{}, fmt.Errorf("go-jose/go-jose: expected %d bit key, got %d bits instead", expectedBitSize, curveBits)
520 }
521
522 hasher := hash.New()
523
524
525 _, _ = hasher.Write(payload)
526 hashed := hasher.Sum(nil)
527
528 r, s, err := ecdsa.Sign(RandReader, ctx.privateKey, hashed)
529 if err != nil {
530 return Signature{}, err
531 }
532
533 keyBytes := curveBits / 8
534 if curveBits%8 > 0 {
535 keyBytes++
536 }
537
538
539
540
541 rBytes := r.Bytes()
542 rBytesPadded := make([]byte, keyBytes)
543 copy(rBytesPadded[keyBytes-len(rBytes):], rBytes)
544
545 sBytes := s.Bytes()
546 sBytesPadded := make([]byte, keyBytes)
547 copy(sBytesPadded[keyBytes-len(sBytes):], sBytes)
548
549 out := append(rBytesPadded, sBytesPadded...)
550
551 return Signature{
552 Signature: out,
553 protected: &rawHeader{},
554 }, nil
555 }
556
557
558 func (ctx ecEncrypterVerifier) verifyPayload(payload []byte, signature []byte, alg SignatureAlgorithm) error {
559 var keySize int
560 var hash crypto.Hash
561
562 switch alg {
563 case ES256:
564 keySize = 32
565 hash = crypto.SHA256
566 case ES384:
567 keySize = 48
568 hash = crypto.SHA384
569 case ES512:
570 keySize = 66
571 hash = crypto.SHA512
572 default:
573 return ErrUnsupportedAlgorithm
574 }
575
576 if len(signature) != 2*keySize {
577 return fmt.Errorf("go-jose/go-jose: invalid signature size, have %d bytes, wanted %d", len(signature), 2*keySize)
578 }
579
580 hasher := hash.New()
581
582
583 _, _ = hasher.Write(payload)
584 hashed := hasher.Sum(nil)
585
586 r := big.NewInt(0).SetBytes(signature[:keySize])
587 s := big.NewInt(0).SetBytes(signature[keySize:])
588
589 match := ecdsa.Verify(ctx.publicKey, hashed, r, s)
590 if !match {
591 return errors.New("go-jose/go-jose: ecdsa signature failed to verify")
592 }
593
594 return nil
595 }
596
View as plain text