github.com/Hyperledger-TWGC/tjfoc-gm@v1.4.0/gmtls/cipher_suites.go (about) 1 /* 2 Copyright Suzhou Tongji Fintech Research Institute 2017 All Rights Reserved. 3 Licensed under the Apache License, Version 2.0 (the "License"); 4 you may not use this file except in compliance with the License. 5 You may obtain a copy of the License at 6 7 http://www.apache.org/licenses/LICENSE-2.0 8 9 Unless required by applicable law or agreed to in writing, software 10 distributed under the License is distributed on an "AS IS" BASIS, 11 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 See the License for the specific language governing permissions and 13 limitations under the License. 14 */ 15 16 package gmtls 17 18 import ( 19 "crypto/aes" 20 "crypto/cipher" 21 "crypto/des" 22 "crypto/hmac" 23 "crypto/rc4" 24 "crypto/sha1" 25 "crypto/sha256" 26 "hash" 27 28 "github.com/Hyperledger-TWGC/tjfoc-gm/x509" 29 30 "golang.org/x/crypto/chacha20poly1305" 31 ) 32 33 // a keyAgreement implements the client and server side of a TLS key agreement 34 // protocol by generating and processing key exchange messages. 35 type keyAgreement interface { 36 // On the server side, the first two methods are called in order. 37 38 // In the case that the key agreement protocol doesn't use a 39 // ServerKeyExchange message, generateServerKeyExchange can return nil, 40 // nil. 41 generateServerKeyExchange(*Config, *Certificate, *Certificate, *clientHelloMsg, *serverHelloMsg) (*serverKeyExchangeMsg, error) 42 processClientKeyExchange(*Config, *Certificate, *clientKeyExchangeMsg, uint16) ([]byte, error) 43 44 // On the client side, the next two methods are called in order. 45 46 // This method may not be called if the server doesn't send a 47 // ServerKeyExchange message. 48 processServerKeyExchange(*Config, *clientHelloMsg, *serverHelloMsg, *x509.Certificate, *serverKeyExchangeMsg) error 49 generateClientKeyExchange(*Config, *clientHelloMsg, *x509.Certificate) ([]byte, *clientKeyExchangeMsg, error) 50 } 51 52 const ( 53 // suiteECDH indicates that the cipher suite involves elliptic curve 54 // Diffie-Hellman. This means that it should only be selected when the 55 // client indicates that it supports ECC with a curve and point format 56 // that we're happy with. 57 suiteECDHE = 1 << iota 58 // suiteECDSA indicates that the cipher suite involves an ECDSA 59 // signature and therefore may only be selected when the server's 60 // certificate is ECDSA. If this is not set then the cipher suite is 61 // RSA based. 62 suiteECDSA 63 // suiteTLS12 indicates that the cipher suite should only be advertised 64 // and accepted when using TLS 1.2. 65 suiteTLS12 66 // suiteSHA384 indicates that the cipher suite uses SHA384 as the 67 // handshake hash. 68 suiteSHA384 69 // suiteDefaultOff indicates that this cipher suite is not included by 70 // default. 71 suiteDefaultOff 72 ) 73 74 // A cipherSuite is a specific combination of key agreement, cipher and MAC 75 // function. All cipher suites currently assume RSA key agreement. 76 type cipherSuite struct { 77 id uint16 78 // the lengths, in bytes, of the key material needed for each component. 79 keyLen int 80 macLen int 81 ivLen int 82 ka func(version uint16) keyAgreement 83 // flags is a bitmask of the suite* values, above. 84 flags int 85 cipher func(key, iv []byte, isRead bool) interface{} 86 mac func(version uint16, macKey []byte) macFunction 87 aead func(key, fixedNonce []byte) cipher.AEAD 88 } 89 90 var cipherSuites = []*cipherSuite{ 91 // Ciphersuite order is chosen so that ECDHE comes before plain RSA and 92 // AEADs are the top preference. 93 {TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305, 32, 0, 12, ecdheRSAKA, suiteECDHE | suiteTLS12, nil, nil, aeadChaCha20Poly1305}, 94 {TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305, 32, 0, 12, ecdheECDSAKA, suiteECDHE | suiteECDSA | suiteTLS12, nil, nil, aeadChaCha20Poly1305}, 95 {TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, 16, 0, 4, ecdheRSAKA, suiteECDHE | suiteTLS12, nil, nil, aeadAESGCM}, 96 {TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, 16, 0, 4, ecdheECDSAKA, suiteECDHE | suiteECDSA | suiteTLS12, nil, nil, aeadAESGCM}, 97 {TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384, 32, 0, 4, ecdheRSAKA, suiteECDHE | suiteTLS12 | suiteSHA384, nil, nil, aeadAESGCM}, 98 {TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384, 32, 0, 4, ecdheECDSAKA, suiteECDHE | suiteECDSA | suiteTLS12 | suiteSHA384, nil, nil, aeadAESGCM}, 99 {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256, 16, 32, 16, ecdheECDSAKA, suiteECDHE | suiteECDSA | suiteTLS12 | suiteDefaultOff, cipherAES, macSHA256, nil}, 100 {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA, 16, 20, 16, ecdheECDSAKA, suiteECDHE | suiteECDSA, cipherAES, macSHA1, nil}, 101 {TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA, 32, 20, 16, ecdheRSAKA, suiteECDHE, cipherAES, macSHA1, nil}, 102 {TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA, 32, 20, 16, ecdheECDSAKA, suiteECDHE | suiteECDSA, cipherAES, macSHA1, nil}, 103 {TLS_RSA_WITH_AES_128_GCM_SHA256, 16, 0, 4, rsaKA, suiteTLS12, nil, nil, aeadAESGCM}, 104 {TLS_RSA_WITH_AES_256_GCM_SHA384, 32, 0, 4, rsaKA, suiteTLS12 | suiteSHA384, nil, nil, aeadAESGCM}, 105 {TLS_RSA_WITH_AES_128_CBC_SHA256, 16, 32, 16, rsaKA, suiteTLS12 | suiteDefaultOff, cipherAES, macSHA256, nil}, 106 {TLS_RSA_WITH_AES_128_CBC_SHA, 16, 20, 16, rsaKA, 0, cipherAES, macSHA1, nil}, 107 {TLS_RSA_WITH_AES_256_CBC_SHA, 32, 20, 16, rsaKA, 0, cipherAES, macSHA1, nil}, 108 {TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA, 24, 20, 8, ecdheRSAKA, suiteECDHE, cipher3DES, macSHA1, nil}, 109 {TLS_RSA_WITH_3DES_EDE_CBC_SHA, 24, 20, 8, rsaKA, 0, cipher3DES, macSHA1, nil}, 110 111 // RC4-based cipher suites are disabled by default. 112 {TLS_RSA_WITH_RC4_128_SHA, 16, 20, 0, rsaKA, suiteDefaultOff, cipherRC4, macSHA1, nil}, 113 {TLS_ECDHE_RSA_WITH_RC4_128_SHA, 16, 20, 0, ecdheRSAKA, suiteECDHE | suiteDefaultOff, cipherRC4, macSHA1, nil}, 114 {TLS_ECDHE_ECDSA_WITH_RC4_128_SHA, 16, 20, 0, ecdheECDSAKA, suiteECDHE | suiteECDSA | suiteDefaultOff, cipherRC4, macSHA1, nil}, 115 } 116 117 func cipherRC4(key, iv []byte, isRead bool) interface{} { 118 cipher, _ := rc4.NewCipher(key) 119 return cipher 120 } 121 122 func cipher3DES(key, iv []byte, isRead bool) interface{} { 123 block, _ := des.NewTripleDESCipher(key) 124 if isRead { 125 return cipher.NewCBCDecrypter(block, iv) 126 } 127 return cipher.NewCBCEncrypter(block, iv) 128 } 129 130 func cipherAES(key, iv []byte, isRead bool) interface{} { 131 block, _ := aes.NewCipher(key) 132 if isRead { 133 return cipher.NewCBCDecrypter(block, iv) 134 } 135 return cipher.NewCBCEncrypter(block, iv) 136 } 137 138 // macSHA1 returns a macFunction for the given protocol version. 139 func macSHA1(version uint16, key []byte) macFunction { 140 if version == VersionSSL30 { 141 mac := ssl30MAC{ 142 h: sha1.New(), 143 key: make([]byte, len(key)), 144 } 145 copy(mac.key, key) 146 return mac 147 } 148 return tls10MAC{hmac.New(newConstantTimeHash(sha1.New), key)} 149 } 150 151 // macSHA256 returns a SHA-256 based MAC. These are only supported in TLS 1.2 152 // so the given version is ignored. 153 func macSHA256(version uint16, key []byte) macFunction { 154 return tls10MAC{hmac.New(sha256.New, key)} 155 } 156 157 type macFunction interface { 158 Size() int 159 MAC(digestBuf, seq, header, data, extra []byte) []byte 160 } 161 162 type aead interface { 163 cipher.AEAD 164 165 // explicitIVLen returns the number of bytes used by the explicit nonce 166 // that is included in the record. This is eight for older AEADs and 167 // zero for modern ones. 168 explicitNonceLen() int 169 } 170 171 // fixedNonceAEAD wraps an AEAD and prefixes a fixed portion of the nonce to 172 // each call. 173 type fixedNonceAEAD struct { 174 // nonce contains the fixed part of the nonce in the first four bytes. 175 nonce [12]byte 176 aead cipher.AEAD 177 } 178 179 func (f *fixedNonceAEAD) NonceSize() int { return 8 } 180 func (f *fixedNonceAEAD) Overhead() int { return f.aead.Overhead() } 181 func (f *fixedNonceAEAD) explicitNonceLen() int { return 8 } 182 183 func (f *fixedNonceAEAD) Seal(out, nonce, plaintext, additionalData []byte) []byte { 184 copy(f.nonce[4:], nonce) 185 return f.aead.Seal(out, f.nonce[:], plaintext, additionalData) 186 } 187 188 func (f *fixedNonceAEAD) Open(out, nonce, plaintext, additionalData []byte) ([]byte, error) { 189 copy(f.nonce[4:], nonce) 190 return f.aead.Open(out, f.nonce[:], plaintext, additionalData) 191 } 192 193 // xoredNonceAEAD wraps an AEAD by XORing in a fixed pattern to the nonce 194 // before each call. 195 type xorNonceAEAD struct { 196 nonceMask [12]byte 197 aead cipher.AEAD 198 } 199 200 func (f *xorNonceAEAD) NonceSize() int { return 8 } 201 func (f *xorNonceAEAD) Overhead() int { return f.aead.Overhead() } 202 func (f *xorNonceAEAD) explicitNonceLen() int { return 0 } 203 204 func (f *xorNonceAEAD) Seal(out, nonce, plaintext, additionalData []byte) []byte { 205 for i, b := range nonce { 206 f.nonceMask[4+i] ^= b 207 } 208 result := f.aead.Seal(out, f.nonceMask[:], plaintext, additionalData) 209 for i, b := range nonce { 210 f.nonceMask[4+i] ^= b 211 } 212 213 return result 214 } 215 216 func (f *xorNonceAEAD) Open(out, nonce, plaintext, additionalData []byte) ([]byte, error) { 217 for i, b := range nonce { 218 f.nonceMask[4+i] ^= b 219 } 220 result, err := f.aead.Open(out, f.nonceMask[:], plaintext, additionalData) 221 for i, b := range nonce { 222 f.nonceMask[4+i] ^= b 223 } 224 225 return result, err 226 } 227 228 func aeadAESGCM(key, fixedNonce []byte) cipher.AEAD { 229 aes, err := aes.NewCipher(key) 230 if err != nil { 231 panic(err) 232 } 233 aead, err := cipher.NewGCM(aes) 234 if err != nil { 235 panic(err) 236 } 237 238 ret := &fixedNonceAEAD{aead: aead} 239 copy(ret.nonce[:], fixedNonce) 240 return ret 241 } 242 243 func aeadChaCha20Poly1305(key, fixedNonce []byte) cipher.AEAD { 244 aead, err := chacha20poly1305.New(key) 245 if err != nil { 246 panic(err) 247 } 248 249 ret := &xorNonceAEAD{aead: aead} 250 copy(ret.nonceMask[:], fixedNonce) 251 return ret 252 } 253 254 // ssl30MAC implements the SSLv3 MAC function, as defined in 255 // www.mozilla.org/projects/security/pki/nss/ssl/draft302.txt section 5.2.3.1 256 type ssl30MAC struct { 257 h hash.Hash 258 key []byte 259 } 260 261 func (s ssl30MAC) Size() int { 262 return s.h.Size() 263 } 264 265 var ssl30Pad1 = [48]byte{0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36, 0x36} 266 267 var ssl30Pad2 = [48]byte{0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c, 0x5c} 268 269 // MAC does not offer constant timing guarantees for SSL v3.0, since it's deemed 270 // useless considering the similar, protocol-level POODLE vulnerability. 271 func (s ssl30MAC) MAC(digestBuf, seq, header, data, extra []byte) []byte { 272 padLength := 48 273 if s.h.Size() == 20 { 274 padLength = 40 275 } 276 277 s.h.Reset() 278 s.h.Write(s.key) 279 s.h.Write(ssl30Pad1[:padLength]) 280 s.h.Write(seq) 281 s.h.Write(header[:1]) 282 s.h.Write(header[3:5]) 283 s.h.Write(data) 284 digestBuf = s.h.Sum(digestBuf[:0]) 285 286 s.h.Reset() 287 s.h.Write(s.key) 288 s.h.Write(ssl30Pad2[:padLength]) 289 s.h.Write(digestBuf) 290 return s.h.Sum(digestBuf[:0]) 291 } 292 293 type constantTimeHash interface { 294 hash.Hash 295 ConstantTimeSum(b []byte) []byte 296 } 297 298 // cthWrapper wraps any hash.Hash that implements ConstantTimeSum, and replaces 299 // with that all calls to Sum. It's used to obtain a ConstantTimeSum-based HMAC. 300 type cthWrapper struct { 301 h constantTimeHash 302 } 303 304 func (c *cthWrapper) Size() int { return c.h.Size() } 305 func (c *cthWrapper) BlockSize() int { return c.h.BlockSize() } 306 func (c *cthWrapper) Reset() { c.h.Reset() } 307 func (c *cthWrapper) Write(p []byte) (int, error) { return c.h.Write(p) } 308 func (c *cthWrapper) Sum(b []byte) []byte { return c.h.ConstantTimeSum(b) } 309 310 func newConstantTimeHash(h func() hash.Hash) func() hash.Hash { 311 return func() hash.Hash { 312 return &cthWrapper{h().(constantTimeHash)} 313 } 314 } 315 316 // tls10MAC implements the TLS 1.0 MAC function. RFC 2246, section 6.2.3. 317 type tls10MAC struct { 318 h hash.Hash 319 } 320 321 func (s tls10MAC) Size() int { 322 return s.h.Size() 323 } 324 325 // MAC is guaranteed to take constant time, as long as 326 // len(seq)+len(header)+len(data)+len(extra) is constant. extra is not fed into 327 // the MAC, but is only provided to make the timing profile constant. 328 func (s tls10MAC) MAC(digestBuf, seq, header, data, extra []byte) []byte { 329 s.h.Reset() 330 s.h.Write(seq) 331 s.h.Write(header) 332 s.h.Write(data) 333 res := s.h.Sum(digestBuf[:0]) 334 if extra != nil { 335 s.h.Write(extra) 336 } 337 return res 338 } 339 340 func rsaKA(version uint16) keyAgreement { 341 return rsaKeyAgreement{} 342 } 343 344 func ecdheECDSAKA(version uint16) keyAgreement { 345 return &ecdheKeyAgreement{ 346 isRSA: false, 347 version: version, 348 } 349 } 350 351 func ecdheRSAKA(version uint16) keyAgreement { 352 return &ecdheKeyAgreement{ 353 isRSA: true, 354 version: version, 355 } 356 } 357 358 // mutualCipherSuite returns a cipherSuite given a list of supported 359 // ciphersuites and the id requested by the peer. 360 func mutualCipherSuite(have []uint16, want uint16) *cipherSuite { 361 for _, id := range have { 362 if id == want { 363 for _, suite := range cipherSuites { 364 if suite.id == want { 365 return suite 366 } 367 } 368 return nil 369 } 370 } 371 return nil 372 } 373 374 // A list of cipher suite IDs that are, or have been, implemented by this 375 // package. 376 // 377 // Taken from https://www.iana.org/assignments/tls-parameters/tls-parameters.xml 378 const ( 379 TLS_RSA_WITH_RC4_128_SHA uint16 = 0x0005 380 TLS_RSA_WITH_3DES_EDE_CBC_SHA uint16 = 0x000a 381 TLS_RSA_WITH_AES_128_CBC_SHA uint16 = 0x002f 382 TLS_RSA_WITH_AES_256_CBC_SHA uint16 = 0x0035 383 TLS_RSA_WITH_AES_128_CBC_SHA256 uint16 = 0x003c 384 TLS_RSA_WITH_AES_128_GCM_SHA256 uint16 = 0x009c 385 TLS_RSA_WITH_AES_256_GCM_SHA384 uint16 = 0x009d 386 TLS_ECDHE_ECDSA_WITH_RC4_128_SHA uint16 = 0xc007 387 TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA uint16 = 0xc009 388 TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA uint16 = 0xc00a 389 TLS_ECDHE_RSA_WITH_RC4_128_SHA uint16 = 0xc011 390 TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA uint16 = 0xc012 391 TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA uint16 = 0xc013 392 TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA uint16 = 0xc014 393 TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256 uint16 = 0xc023 394 TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256 uint16 = 0xc027 395 TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 uint16 = 0xc02f 396 TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 uint16 = 0xc02b 397 TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 uint16 = 0xc030 398 TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 uint16 = 0xc02c 399 TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305 uint16 = 0xcca8 400 TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305 uint16 = 0xcca9 401 402 // TLS_FALLBACK_SCSV isn't a standard cipher suite but an indicator 403 // that the client is doing version fallback. See 404 // https://tools.ietf.org/html/rfc7507. 405 TLS_FALLBACK_SCSV uint16 = 0x5600 406 )