github.com/hxx258456/ccgo@v0.0.5-0.20230213014102-48b35f46f66f/gmtls/common.go (about) 1 // Copyright 2022 s1ren@github.com/hxx258456. 2 3 /* 4 gmtls是基于`golang/go`的`tls`包实现的国密改造版本。 5 对应版权声明: thrid_licenses/github.com/golang/go/LICENSE 6 */ 7 8 package gmtls 9 10 import ( 11 "bytes" 12 "container/list" 13 "context" 14 "crypto" 15 "crypto/ecdsa" 16 "crypto/ed25519" 17 "crypto/elliptic" 18 "crypto/rand" 19 "crypto/rsa" 20 "crypto/sha512" 21 "errors" 22 "fmt" 23 "io" 24 "net" 25 "strings" 26 "sync" 27 "time" 28 29 "github.com/hxx258456/ccgo/sm2" 30 "github.com/hxx258456/ccgo/x509" 31 ) 32 33 //goland:noinspection GoCommentStart 34 const ( 35 // 国密SSL版本定义 GM/T 0024-2014 36 VersionGMSSL = 0x0101 37 VersionTLS10 = 0x0301 38 VersionTLS11 = 0x0302 39 VersionTLS12 = 0x0303 40 VersionTLS13 = 0x0304 41 42 // TO Deprecated: SSLv3 is cryptographically broken, and is no longer 43 // supported by this package. See golang.org/issue/32716. 44 VersionSSL30 = 0x0300 45 ) 46 47 func ShowTLSVersion(version int) string { 48 switch version { 49 case VersionGMSSL: 50 return "VersionGMSSL" 51 case VersionTLS10: 52 return "VersionTLS10" 53 case VersionTLS11: 54 return "VersionTLS11" 55 case VersionTLS12: 56 return "VersionTLS12" 57 case VersionTLS13: 58 return "VersionTLS13" 59 case VersionSSL30: 60 return "VersionSSL30" 61 default: 62 return "unknown" 63 } 64 } 65 66 const ( 67 maxPlaintext = 16384 // maximum plaintext payload length 68 maxCiphertext = 16384 + 2048 // maximum ciphertext payload length 69 maxCiphertextTLS13 = 16384 + 256 // maximum ciphertext length in TLS 1.3 70 recordHeaderLen = 5 // record header length 71 maxHandshake = 65536 // maximum handshake we support (protocol max is 16 MB) 72 maxUselessRecords = 16 // maximum number of consecutive non-advancing records 73 74 // minVersion = VersionGMSSL 75 // maxVersion = VersionTLS13 76 ) 77 78 // TLS record types. 79 type recordType uint8 80 81 // tls记录类型 82 const ( 83 recordTypeChangeCipherSpec recordType = 20 84 recordTypeAlert recordType = 21 85 recordTypeHandshake recordType = 22 86 recordTypeApplicationData recordType = 23 87 ) 88 89 // TLS handshake message types. 90 // 91 //goland:noinspection GoUnusedConst 92 const ( 93 typeHelloRequest uint8 = 0 94 typeClientHello uint8 = 1 95 typeServerHello uint8 = 2 96 typeNewSessionTicket uint8 = 4 97 typeEndOfEarlyData uint8 = 5 98 typeEncryptedExtensions uint8 = 8 99 typeCertificate uint8 = 11 100 typeServerKeyExchange uint8 = 12 101 typeCertificateRequest uint8 = 13 102 typeServerHelloDone uint8 = 14 103 typeCertificateVerify uint8 = 15 104 typeClientKeyExchange uint8 = 16 105 typeFinished uint8 = 20 106 typeCertificateStatus uint8 = 22 107 typeKeyUpdate uint8 = 24 108 typeNextProtocol uint8 = 67 // Not IANA assigned 109 typeMessageHash uint8 = 254 // synthetic message 110 ) 111 112 // TLS compression types. 113 const ( 114 compressionNone uint8 = 0 115 ) 116 117 // TLS extension numbers 118 const ( 119 extensionServerName uint16 = 0 120 extensionStatusRequest uint16 = 5 121 extensionSupportedCurves uint16 = 10 // supported_groups in TLS 1.3, see RFC 8446, Section 4.2.7 122 extensionSupportedPoints uint16 = 11 123 extensionSignatureAlgorithms uint16 = 13 124 extensionALPN uint16 = 16 125 extensionSCT uint16 = 18 126 extensionSessionTicket uint16 = 35 127 extensionPreSharedKey uint16 = 41 128 extensionEarlyData uint16 = 42 129 extensionSupportedVersions uint16 = 43 130 extensionCookie uint16 = 44 131 extensionPSKModes uint16 = 45 132 extensionCertificateAuthorities uint16 = 47 133 extensionSignatureAlgorithmsCert uint16 = 50 134 extensionKeyShare uint16 = 51 135 extensionRenegotiationInfo uint16 = 0xff01 136 ) 137 138 // TLS signaling cipher suite values 139 const ( 140 scsvRenegotiation uint16 = 0x00ff 141 ) 142 143 // CurveID is the type of a TLS identifier for an elliptic curve. See 144 // https://www.iana.org/assignments/tls-parameters/tls-parameters.xml#tls-parameters-8. 145 // 146 // In TLS 1.3, this type is called NamedGroup, but at this time this library 147 // only supports Elliptic Curve based groups. See RFC 8446, Section 4.2.7. 148 type CurveID uint16 149 150 // 支持的椭圆曲线ID 151 const ( 152 CurveP256 CurveID = 23 153 CurveP384 CurveID = 24 154 CurveP521 CurveID = 25 155 Curve256Sm2 CurveID = 26 // 添加国密SM2曲线ID 156 X25519 CurveID = 29 157 ) 158 159 // tls1.3的密钥交换算法参数,或者说共享密钥计算用参数。 160 // TLS 1.3 Key Share. See RFC 8446, Section 4.2.8. 161 type keyShare struct { 162 group CurveID // 椭圆曲线ID 163 data []byte // 公钥 164 } 165 166 // tls1.3的 PSK密钥交换模式 167 // TLS 1.3 PSK Key Exchange Modes. See RFC 8446, Section 4.2.9. 168 const ( 169 pskModePlain uint8 = 0 // 平文模式 170 pskModeDHE uint8 = 1 // DHE模式, 动态笛福赫尔曼密钥交换算法 171 ) 172 173 // tls1.3支持的psk身份,用作会话票据,或已保存的会话的引用。 174 // TLS 1.3 PSK Identity. Can be a Session Ticket, or a reference to a saved 175 // session. See RFC 8446, Section 4.2.11. 176 type pskIdentity struct { 177 label []byte 178 obfuscatedTicketAge uint32 179 } 180 181 // TLS Elliptic Curve Point Formats 182 // https://www.iana.org/assignments/tls-parameters/tls-parameters.xml#tls-parameters-9 183 const ( 184 // 椭圆曲线上的点坐标的序列化格式 185 // 该格式是不压缩存储, 即将x,y坐标完整序列化 186 pointFormatUncompressed uint8 = 0 187 ) 188 189 // TLS CertificateStatusType (RFC 3546) 190 const ( 191 statusTypeOCSP uint8 = 1 192 ) 193 194 // Certificate types (for certificateRequestMsg) 195 const ( 196 certTypeRSASign = 1 197 certTypeECDSASign = 64 // ECDSA or EdDSA keys, see RFC 8422, Section 3. 198 // 是否添加SM2Type 用于tls1.2及更老版本,暂时不做国密对应 199 // certTypeSM2Sign = 128 200 ) 201 202 // Signature algorithms (for internal signaling use). Starting at 225 to avoid overlap with 203 // TLS 1.2 codepoints (RFC 5246, Appendix A.4.1), with which these have nothing to do. 204 const ( 205 signaturePKCS1v15 uint8 = iota + 225 206 signatureRSAPSS 207 signatureECDSA 208 signatureEd25519 209 signatureSM2 210 ) 211 212 // directSigning is a standard Hash value that signals that no pre-hashing 213 // should be performed, and that the input should be signed directly. It is the 214 // hash function associated with the Ed25519 signature scheme. 215 var directSigning x509.Hash = 0 216 217 // supportedSignatureAlgorithms contains the signature and hash algorithms that 218 // the code advertises as supported in a TLS 1.2+ ClientHello and in a TLS 1.2+ 219 // CertificateRequest. The two fields are merged to match with TLS 1.3. 220 // Note that in TLS 1.2, the ECDSA algorithms are not constrained to P-256, etc. 221 var supportedSignatureAlgorithms = []SignatureScheme{ 222 PSSWithSHA256, 223 ECDSAWithP256AndSHA256, 224 SM2WITHSM3, // 增加SM2WithSM3 225 Ed25519, 226 PSSWithSHA384, 227 PSSWithSHA512, 228 PKCS1WithSHA256, 229 PKCS1WithSHA384, 230 PKCS1WithSHA512, 231 ECDSAWithP384AndSHA384, 232 ECDSAWithP521AndSHA512, 233 PKCS1WithSHA1, 234 ECDSAWithSHA1, 235 } 236 237 // 服务端未能获取到客户端公钥时,会发送HelloRetryRequest,请求客户端重新发送ClientHello。 238 // 此时需要将HelloRetryRequest中的random字段设置为该字段。 239 // helloRetryRequestRandom is set as the Random value of a ServerHello 240 // to signal that the message is actually a HelloRetryRequest. 241 var helloRetryRequestRandom = []byte{ // See RFC 8446, Section 4.1.3. 242 0xCF, 0x21, 0xAD, 0x74, 0xE5, 0x9A, 0x61, 0x11, 243 0xBE, 0x1D, 0x8C, 0x02, 0x1E, 0x65, 0xB8, 0x91, 244 0xC2, 0xA2, 0x11, 0x16, 0x7A, 0xBB, 0x8C, 0x5E, 245 0x07, 0x9E, 0x09, 0xE2, 0xC8, 0xA8, 0x33, 0x9C, 246 } 247 248 const ( 249 // downgradeCanaryTLS12 or downgradeCanaryTLS11 is embedded in the server 250 // random as a downgrade protection if the server would be capable of 251 // negotiating a higher version. See RFC 8446, Section 4.1.3. 252 downgradeCanaryTLS12 = "DOWNGRD\x01" 253 downgradeCanaryTLS11 = "DOWNGRD\x00" 254 ) 255 256 // testingOnlyForceDowngradeCanary is set in tests to force the server side to 257 // include downgrade canaries even if it's using its highers supported version. 258 var testingOnlyForceDowngradeCanary bool 259 260 // ConnectionState TLS握手过程中的连接状态管理用 261 // ConnectionState records basic TLS details about the connection. 262 type ConnectionState struct { 263 // Version is the TLS version used by the connection (e.g. VersionTLS12). 264 Version uint16 265 266 // HandshakeComplete is true if the handshake has concluded. 267 HandshakeComplete bool 268 269 // DidResume is true if this connection was successfully resumed from a 270 // previous session with a session ticket or similar mechanism. 271 DidResume bool 272 273 // CipherSuite is the cipher suite negotiated for the connection (e.g. 274 // TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, TLS_AES_128_GCM_SHA256). 275 CipherSuite uint16 276 277 // NegotiatedProtocol is the application protocol negotiated with ALPN. 278 NegotiatedProtocol string 279 280 // NegotiatedProtocolIsMutual used to indicate a mutual NPN negotiation. 281 // 282 // ToDeprecated: this value is always true. 283 NegotiatedProtocolIsMutual bool 284 285 // ServerName is the value of the Server Name Indication extension sent by 286 // the client. It's available both on the server and on the client side. 287 ServerName string 288 289 // PeerCertificates are the parsed certificates sent by the peer, in the 290 // order in which they were sent. The first element is the leaf certificate 291 // that the connection is verified against. 292 // 293 // On the client side, it can't be empty. On the server side, it can be 294 // empty if Config.ClientAuth is not RequireAnyClientCert or 295 // RequireAndVerifyClientCert. 296 PeerCertificates []*x509.Certificate 297 298 // VerifiedChains is a list of one or more chains where the first element is 299 // PeerCertificates[0] and the last element is from Config.RootCAs (on the 300 // client side) or Config.ClientCAs (on the server side). 301 // 302 // On the client side, it's set if Config.InsecureSkipVerify is false. On 303 // the server side, it's set if Config.ClientAuth is VerifyClientCertIfGiven 304 // (and the peer provided a certificate) or RequireAndVerifyClientCert. 305 VerifiedChains [][]*x509.Certificate 306 307 // SignedCertificateTimestamps is a list of SCTs provided by the peer 308 // through the TLS handshake for the leaf certificate, if any. 309 SignedCertificateTimestamps [][]byte 310 311 // OCSPResponse is a stapled Online Certificate Status Protocol (OCSP) 312 // response provided by the peer for the leaf certificate, if any. 313 OCSPResponse []byte 314 315 // TLSUnique contains the "tls-unique" channel binding value (see RFC 5929, 316 // Section 3). This value will be nil for TLS 1.3 connections and for all 317 // resumed connections. 318 // 319 // ToDeprecated: there are conditions in which this value might not be unique 320 // to a connection. See the Security Considerations sections of RFC 5705 and 321 // RFC 7627, and https://mitls.org/pages/attacks/3SHAKE#channelbindings. 322 TLSUnique []byte 323 324 // ekm is a closure exposed via ExportKeyingMaterial. 325 ekm func(label string, context []byte, length int) ([]byte, error) 326 } 327 328 // ExportKeyingMaterial returns length bytes of exported key material in a new 329 // slice as defined in RFC 5705. If context is nil, it is not used as part of 330 // the seed. If the connection was set to allow renegotiation via 331 // Config.Renegotiation, this function will return an error. 332 func (cs *ConnectionState) ExportKeyingMaterial(label string, context []byte, length int) ([]byte, error) { 333 return cs.ekm(label, context, length) 334 } 335 336 // ClientAuthType declares the policy the server will follow for 337 // TLS Client Authentication. 338 type ClientAuthType int 339 340 const ( 341 // NoClientCert indicates that no client certificate should be requested 342 // during the handshake, and if any certificates are sent they will not 343 // be verified. 344 NoClientCert ClientAuthType = iota 345 // RequestClientCert indicates that a client certificate should be requested 346 // during the handshake, but does not require that the client send any 347 // certificates. 348 RequestClientCert 349 // RequireAnyClientCert indicates that a client certificate should be requested 350 // during the handshake, and that at least one certificate is required to be 351 // sent by the client, but that certificate is not required to be valid. 352 RequireAnyClientCert 353 // VerifyClientCertIfGiven indicates that a client certificate should be requested 354 // during the handshake, but does not require that the client sends a 355 // certificate. If the client does send a certificate it is required to be 356 // valid. 357 VerifyClientCertIfGiven 358 // RequireAndVerifyClientCert indicates that a client certificate should be requested 359 // during the handshake, and that at least one valid certificate is required 360 // to be sent by the client. 361 RequireAndVerifyClientCert 362 ) 363 364 // requiresClientCert reports whether the ClientAuthType requires a client 365 // certificate to be provided. 366 func requiresClientCert(c ClientAuthType) bool { 367 switch c { 368 case RequireAnyClientCert, RequireAndVerifyClientCert: 369 return true 370 default: 371 return false 372 } 373 } 374 375 // ClientSessionState contains the state needed by clients to resume TLS 376 // sessions. 377 type ClientSessionState struct { 378 sessionTicket []uint8 // Encrypted ticket used for session resumption with server 379 vers uint16 // TLS version negotiated for the session 380 cipherSuite uint16 // Ciphersuite negotiated for the session 381 masterSecret []byte // Full handshake MasterSecret, or TLS 1.3 resumption_master_secret 382 serverCertificates []*x509.Certificate // Certificate chain presented by the server 383 verifiedChains [][]*x509.Certificate // Certificate chains we built for verification 384 receivedAt time.Time // When the session ticket was received from the server 385 ocspResponse []byte // Stapled OCSP response presented by the server 386 scts [][]byte // SCTs presented by the server 387 388 // TLS 1.3 fields. 389 nonce []byte // Ticket nonce sent by the server, to derive PSK 390 useBy time.Time // Expiration of the ticket lifetime as set by the server 391 ageAdd uint32 // Random obfuscation factor for sending the ticket age 392 } 393 394 // ClientSessionCache is a cache of ClientSessionState objects that can be used 395 // by a client to resume a TLS session with a given server. ClientSessionCache 396 // implementations should expect to be called concurrently from different 397 // goroutines. Up to TLS 1.2, only ticket-based resumption is supported, not 398 // SessionID-based resumption. In TLS 1.3 they were merged into PSK modes, which 399 // are supported via this interface. 400 type ClientSessionCache interface { 401 // Get searches for a ClientSessionState associated with the given key. 402 // On return, ok is true if one was found. 403 Get(sessionKey string) (session *ClientSessionState, ok bool) 404 405 // Put adds the ClientSessionState to the cache with the given key. It might 406 // get called multiple times in a connection if a TLS 1.3 server provides 407 // more than one session ticket. If called with a nil *ClientSessionState, 408 // it should remove the cache entry. 409 Put(sessionKey string, cs *ClientSessionState) 410 } 411 412 //go:generate stringer -type=SignatureScheme,CurveID,ClientAuthType -output=common_string.go 413 414 // SignatureScheme identifies a signature algorithm supported by TLS. See 415 // RFC 8446, Section 4.2.3. 416 type SignatureScheme uint16 417 418 //goland:noinspection GoCommentStart 419 const ( 420 // RSASSA-PKCS1-v1_5 algorithms. 421 PKCS1WithSHA256 SignatureScheme = 0x0401 422 PKCS1WithSHA384 SignatureScheme = 0x0501 423 PKCS1WithSHA512 SignatureScheme = 0x0601 424 425 // RSASSA-PSS algorithms with public key OID rsaEncryption. 426 PSSWithSHA256 SignatureScheme = 0x0804 427 PSSWithSHA384 SignatureScheme = 0x0805 428 PSSWithSHA512 SignatureScheme = 0x0806 429 430 // ECDSA algorithms. Only constrained to a specific curve in TLS 1.3. 431 ECDSAWithP256AndSHA256 SignatureScheme = 0x0403 432 ECDSAWithP384AndSHA384 SignatureScheme = 0x0503 433 ECDSAWithP521AndSHA512 SignatureScheme = 0x0603 434 435 // EdDSA algorithms. 436 Ed25519 SignatureScheme = 0x0807 437 438 // Legacy signature and hash algorithms for TLS 1.2. 439 PKCS1WithSHA1 SignatureScheme = 0x0201 440 ECDSAWithSHA1 SignatureScheme = 0x0203 441 442 // 国密签名算法 443 SM2WITHSM3 SignatureScheme = 0x0204 444 ) 445 446 // ClientHelloInfo contains information from a ClientHello message in order to 447 // guide application logic in the GetCertificate and GetConfigForClient callbacks. 448 type ClientHelloInfo struct { 449 // CipherSuites lists the CipherSuites supported by the client (e.g. 450 // TLS_AES_128_GCM_SHA256, TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256). 451 CipherSuites []uint16 452 453 // ServerName indicates the name of the server requested by the client 454 // in order to support virtual hosting. ServerName is only set if the 455 // client is using SNI (see RFC 4366, Section 3.1). 456 ServerName string 457 458 // SupportedCurves lists the elliptic curves supported by the client. 459 // SupportedCurves is set only if the Supported Elliptic Curves 460 // Extension is being used (see RFC 4492, Section 5.1.1). 461 SupportedCurves []CurveID 462 463 // SupportedPoints lists the point formats supported by the client. 464 // SupportedPoints is set only if the Supported Point Formats Extension 465 // is being used (see RFC 4492, Section 5.1.2). 466 SupportedPoints []uint8 467 468 // SignatureSchemes lists the signature and hash schemes that the client 469 // is willing to verify. SignatureSchemes is set only if the Signature 470 // Algorithms Extension is being used (see RFC 5246, Section 7.4.1.4.1). 471 SignatureSchemes []SignatureScheme 472 473 // SupportedProtos lists the application protocols supported by the client. 474 // SupportedProtos is set only if the Application-Layer Protocol 475 // Negotiation Extension is being used (see RFC 7301, Section 3.1). 476 // 477 // Servers can select a protocol by setting Config.NextProtos in a 478 // GetConfigForClient return value. 479 SupportedProtos []string 480 481 // SupportedVersions lists the TLS versions supported by the client. 482 // For TLS versions less than 1.3, this is extrapolated from the max 483 // version advertised by the client, so values other than the greatest 484 // might be rejected if used. 485 SupportedVersions []uint16 486 487 // Conn is the underlying net.Conn for the connection. Do not read 488 // from, or write to, this connection; that will cause the TLS 489 // connection to fail. 490 Conn net.Conn 491 492 // config is embedded by the GetCertificate or GetConfigForClient caller, 493 // for use with SupportsCertificate. 494 config *Config 495 496 // ctx is the context of the handshake that is in progress. 497 ctx context.Context 498 } 499 500 // Context returns the context of the handshake that is in progress. 501 // This context is a child of the context passed to HandshakeContext, 502 // if any, and is canceled when the handshake concludes. 503 func (chi *ClientHelloInfo) Context() context.Context { 504 return chi.ctx 505 } 506 507 // CertificateRequestInfo contains information from a server's 508 // CertificateRequest message, which is used to demand a certificate and proof 509 // of control from a client. 510 type CertificateRequestInfo struct { 511 // AcceptableCAs contains zero or more, DER-encoded, X.501 512 // Distinguished Names. These are the names of root or intermediate CAs 513 // that the server wishes the returned certificate to be signed by. An 514 // empty slice indicates that the server has no preference. 515 AcceptableCAs [][]byte 516 517 // SignatureSchemes lists the signature schemes that the server is 518 // willing to verify. 519 SignatureSchemes []SignatureScheme 520 521 // Version is the TLS version that was negotiated for this connection. 522 Version uint16 523 524 // ctx is the context of the handshake that is in progress. 525 ctx context.Context 526 } 527 528 // Context returns the context of the handshake that is in progress. 529 // This context is a child of the context passed to HandshakeContext, 530 // if any, and is canceled when the handshake concludes. 531 func (cri *CertificateRequestInfo) Context() context.Context { 532 return cri.ctx 533 } 534 535 // RenegotiationSupport enumerates the different levels of support for TLS 536 // renegotiation. TLS renegotiation is the act of performing subsequent 537 // handshakes on a connection after the first. This significantly complicates 538 // the state machine and has been the source of numerous, subtle security 539 // issues. Initiating a renegotiation is not supported, but support for 540 // accepting renegotiation requests may be enabled. 541 // 542 // Even when enabled, the server may not change its identity between handshakes 543 // (i.e. the leaf certificate must be the same). Additionally, concurrent 544 // handshake and application data flow is not permitted so renegotiation can 545 // only be used with protocols that synchronise with the renegotiation, such as 546 // HTTPS. 547 // 548 // Renegotiation is not defined in TLS 1.3. 549 type RenegotiationSupport int 550 551 const ( 552 // RenegotiateNever disables renegotiation. 553 RenegotiateNever RenegotiationSupport = iota 554 555 // RenegotiateOnceAsClient allows a remote server to request 556 // renegotiation once per connection. 557 RenegotiateOnceAsClient 558 559 // RenegotiateFreelyAsClient allows a remote server to repeatedly 560 // request renegotiation. 561 RenegotiateFreelyAsClient 562 ) 563 564 // Config TLS通信配置 565 // A Config structure is used to configure a TLS client or server. 566 // After one has been passed to a TLS function it must not be 567 // modified. A Config may be reused; the tls package will also not 568 // modify it. 569 type Config struct { 570 // 是否支持国密,默认支持 571 // if not nil, will support GMT0024 572 // GMSupport *GMSupport 573 // GMSupport bool 574 575 // Rand provides the source of entropy for nonces and RSA blinding. 576 // If Rand is nil, TLS uses the cryptographic random reader in package 577 // crypto/rand. 578 // The Reader must be safe for use by multiple goroutines. 579 Rand io.Reader 580 581 // 当前时间 582 // Time returns the current time as the number of seconds since the epoch. 583 // If Time is nil, TLS uses time.Now. 584 Time func() time.Time 585 586 // 向通信对方展示的证书链 587 // Certificates contains one or more certificate chains to present to the 588 // other side of the connection. The first certificate compatible with the 589 // peer's requirements is selected automatically. 590 // 591 // Server configurations must set one of Certificates, GetCertificate or 592 // GetConfigForClient. Clients doing client-authentication may set either 593 // Certificates or GetClientCertificate. 594 // 595 // Note: if there are multiple Certificates, and they don't have the 596 // optional field Leaf set, certificate selection will incur a significant 597 // per-handshake performance cost. 598 Certificates []Certificate 599 600 // NameToCertificate maps from a certificate name to an element of 601 // Certificates. Note that a certificate name can be of the form 602 // '*.example.com' and so doesn't have to be a domain name as such. 603 // 604 // ToDeprecated: NameToCertificate only allows associating a single 605 // certificate with a given name. Leave this field nil to let the library 606 // select the first compatible chain from Certificates. 607 NameToCertificate map[string]*Certificate 608 609 // 根据ClientHelloInfo返回证书,只在客户端提供了SNI或Certificates为空时调用。 610 // GetCertificate returns a Certificate based on the given 611 // ClientHelloInfo. It will only be called if the client supplies SNI 612 // information or if Certificates is empty. 613 // 614 // If GetCertificate is nil or returns nil, then the certificate is 615 // retrieved from NameToCertificate. If NameToCertificate is nil, the 616 // best element of Certificates will be used. 617 GetCertificate func(*ClientHelloInfo) (*Certificate, error) 618 619 // GetKECertificate 获取密钥交换证书(加密证书) 620 // 这个方法只有在使用Config中Certificates为空或长度小于2时,才会被调用。 621 // 如果该方法为空,则默认从证书列表中 Certificates 取出第二个位置的证书,也就是加密证书。 622 // 该方法只有GMSSL流程中才会调用。 623 // GetKECertificate func(*ClientHelloInfo) (*Certificate, error) 624 625 // 当服务端向客户端请求证书时调用,用于获取客户端证书。该函数被设置时比Certificates优先。 626 // GetClientCertificate, if not nil, is called when a server requests a 627 // certificate from a client. If set, the contents of Certificates will 628 // be ignored. 629 // 630 // If GetClientCertificate returns an error, the handshake will be 631 // aborted and that error will be returned. Otherwise 632 // GetClientCertificate must return a non-nil Certificate. If 633 // Certificate.Certificate is empty then no certificate will be sent to 634 // the server. If this is unacceptable to the server then it may abort 635 // the handshake. 636 // 637 // GetClientCertificate may be called multiple times for the same 638 // connection if renegotiation occurs or if TLS 1.3 is in use. 639 GetClientCertificate func(*CertificateRequestInfo) (*Certificate, error) 640 641 // 当服务端收到一个ClientHello后调用,用于获取客户端的TLS通信配置。 642 // GetConfigForClient, if not nil, is called after a ClientHello is 643 // received from a client. It may return a non-nil Config in order to 644 // change the Config that will be used to handle this connection. If 645 // the returned Config is nil, the original Config will be used. The 646 // Config returned by this callback may not be subsequently modified. 647 // 648 // If GetConfigForClient is nil, the Config passed to Server() will be 649 // used for all connections. 650 // 651 // If SessionTicketKey was explicitly set on the returned Config, or if 652 // SetSessionTicketKeys was called on the returned Config, those keys will 653 // be used. Otherwise, the original Config keys will be used (and possibly 654 // rotated if they are automatically managed). 655 GetConfigForClient func(*ClientHelloInfo) (*Config, error) 656 657 // 预先定义好的额外的证书验证。 658 // 客户端或服务端进行正常的证书验证后调用,接收对方提供的ASN1格式证书或经过验证的证书链。 659 // VerifyPeerCertificate, if not nil, is called after normal 660 // certificate verification by either a TLS client or server. It 661 // receives the raw ASN.1 certificates provided by the peer and also 662 // any verified chains that normal processing found. If it returns a 663 // non-nil error, the handshake is aborted and that error results. 664 // 665 // If normal verification fails then the handshake will abort before 666 // considering this callback. If normal verification is disabled by 667 // setting InsecureSkipVerify, or (for a server) when ClientAuth is 668 // RequestClientCert or RequireAnyClientCert, then this callback will 669 // be considered but the verifiedChains argument will always be nil. 670 VerifyPeerCertificate func(rawCerts [][]byte, verifiedChains [][]*x509.Certificate) error 671 672 // 预先定义好的额外的连接验证。 673 // 在正常的证书验证以及VerifyPeerCertificate之后调用。 674 // VerifyConnection, if not nil, is called after normal certificate 675 // verification and after VerifyPeerCertificate by either a TLS client 676 // or server. If it returns a non-nil error, the handshake is aborted 677 // and that error results. 678 // 679 // If normal verification fails then the handshake will abort before 680 // considering this callback. This callback will run for all connections 681 // regardless of InsecureSkipVerify or ClientAuth settings. 682 VerifyConnection func(ConnectionState) error 683 684 // 客户端用来验证服务端证书的CA根证书池 685 // RootCAs defines the set of root certificate authorities 686 // that clients use when verifying server certificates. 687 // If RootCAs is nil, TLS uses the host's root CA set. 688 RootCAs *x509.CertPool 689 690 // 应用层协议列表 691 // 如果双方都支持应用层协议协商(Application-Layer Protocol Negotiation,简称ALPN), 692 // 则从该列表中选择。 693 // NextProtos is a list of supported application level protocols, in 694 // order of preference. If both peers support ALPN, the selected 695 // protocol will be one from this list, and the connection will fail 696 // if there is no mutually supported protocol. If NextProtos is empty 697 // or the peer doesn't support ALPN, the connection will succeed and 698 // ConnectionState.NegotiatedProtocol will be empty. 699 NextProtos []string 700 701 // InsecureSkipVerify为设置时,根据ServerName检查收到的证书中的hostname。 702 // ServerName is used to verify the hostname on the returned 703 // certificates unless InsecureSkipVerify is given. It is also included 704 // in the client's handshake to support virtual hosting unless it is 705 // an IP address. 706 ServerName string 707 708 // 服务端对客户端认证的策略,默认NoClientCert,不需要客户端证书。 709 // ClientAuth determines the server's policy for 710 // TLS Client Authentication. The default is NoClientCert. 711 ClientAuth ClientAuthType 712 713 // 客户端CA根证书池, 当服务端需要客户端提供证书时验证这些证书用。 714 // ClientCAs defines the set of root certificate authorities 715 // that servers use if required to verify a client certificate 716 // by the policy in ClientAuth. 717 ClientCAs *x509.CertPool 718 719 // InsecureSkipVerify 控制客户端是否验证服务器的证书链和主机名。 720 // 如果 InsecureSkipVerify 为真,crypto/tls 接受服务器提供的任何证书以及该证书中的任何主机名。 721 // 在这种模式下,除非使用自定义验证,否则 TLS 容易受到中间机攻击。 722 // 这应该仅用于测试或与 VerifyConnection 或 VerifyPeerCertificate 结合使用。 723 // InsecureSkipVerify controls whether a client verifies the server's 724 // certificate chain and host name. If InsecureSkipVerify is true, crypto/tls 725 // accepts any certificate presented by the server and any host name in that 726 // certificate. In this mode, TLS is susceptible to machine-in-the-middle 727 // attacks unless custom verification is used. This should be used only for 728 // testing or in combination with VerifyConnection or VerifyPeerCertificate. 729 InsecureSkipVerify bool 730 731 // CipherSuites 是启用的 TLS 1.0–1.2 密码套件的列表。 列表的顺序被忽略。 732 // 请注意,TLS 1.3 密码套件不可配置。 733 // CipherSuites is a list of enabled TLS 1.0–1.2 cipher suites. The order of 734 // the list is ignored. Note that TLS 1.3 ciphersuites are not configurable. 735 // 736 // If CipherSuites is nil, a safe default list is used. The default cipher 737 // suites might change over time. 738 CipherSuites []uint16 739 740 // PreferServerCipherSuites is a legacy field and has no effect. 741 // 742 // It used to control whether the server would follow the client's or the 743 // server's preference. Servers now select the best mutually supported 744 // cipher suite based on logic that takes into account inferred client 745 // hardware, server hardware, and security. 746 // 747 // Deprected: PreferServerCipherSuites is ignored. 748 PreferServerCipherSuites bool 749 750 // SessionTicketsDisabled 可以设置为 true 以禁用会话票证和 PSK(恢复)支持。 751 // 请注意,在客户端上,如果 ClientSessionCache 为 nil,会话票证支持也会被禁用。 752 // SessionTicketsDisabled may be set to true to disable session ticket and 753 // PSK (resumption) support. Note that on clients, session ticket support is 754 // also disabled if ClientSessionCache is nil. 755 SessionTicketsDisabled bool 756 757 // TLS 服务器使用 SessionTicketKey 来提供会话恢复。 758 // SessionTicketKey is used by TLS servers to provide session resumption. 759 // See RFC 5077 and the PSK mode of RFC 8446. If zero, it will be filled 760 // with random data before the first server handshake. 761 // 762 // ToDeprecated: if this field is left at zero, session ticket keys will be 763 // automatically rotated every day and dropped after seven days. For 764 // customizing the rotation schedule or synchronizing servers that are 765 // terminating connections for the same host, use SetSessionTicketKeys. 766 SessionTicketKey [32]byte 767 768 // ClientSessionCache 是用于 TLS 会话恢复的 ClientSessionState 条目的缓存。 769 // 它仅供客户使用。 770 // ClientSessionCache is a cache of ClientSessionState entries for TLS 771 // session resumption. It is only used by clients. 772 ClientSessionCache ClientSessionCache 773 774 // 支持的最低的TLS协议版本,默认 TLS 1.0 775 // 国密改造后默认是 GMSSL 776 // MinVersion contains the minimum TLS version that is acceptable. 777 // If zero, TLS 1.0 is currently taken as the minimum. 778 MinVersion uint16 779 780 // 支持的最高的TLS协议版本,默认 TLS 1.3 781 // MaxVersion contains the maximum TLS version that is acceptable. 782 // If zero, the maximum version supported by this package is used, 783 // which is currently TLS 1.3. 784 MaxVersion uint16 785 786 // ECDHE握手支持的椭圆曲线ID 787 // CurvePreferences contains the elliptic curves that will be used in 788 // an ECDHE handshake, in preference order. If empty, the default will 789 // be used. The client will use the first preference as the type for 790 // its key share in TLS 1.3. This may change in the future. 791 CurvePreferences []CurveID 792 793 // DynamicRecordSizingDisabled 禁用 TLS 记录的自适应大小。 794 // 如果为 true,则始终使用最大可能的 TLS 记录大小。 795 // 如果为 false,则可能会调整 TLS 记录的大小以尝试改善延迟。 796 // DynamicRecordSizingDisabled disables adaptive sizing of TLS records. 797 // When true, the largest possible TLS record size is always used. When 798 // false, the size of TLS records may be adjusted in an attempt to 799 // improve latency. 800 DynamicRecordSizingDisabled bool 801 802 // 重新协商控制支持哪些类型的重新协商。 默认值 none 对于绝大多数应用程序都是正确的。 803 // Renegotiation controls what types of renegotiation are supported. 804 // The default, none, is correct for the vast majority of applications. 805 Renegotiation RenegotiationSupport 806 807 // KeyLogWriter 可以选择以 NSS 密钥日志格式指定 TLS 主密钥的存储目标。 808 // 该目标可用于允许 Wireshark 等外部程序解密 TLS 连接。 809 // KeyLogWriter optionally specifies a destination for TLS master secrets 810 // in NSS key log format that can be used to allow external programs 811 // such as Wireshark to decrypt TLS connections. 812 // See https://developer.mozilla.org/en-US/docs/Mozilla/Projects/NSS/Key_Log_Format. 813 // Use of KeyLogWriter compromises security and should only be 814 // used for debugging. 815 KeyLogWriter io.Writer 816 817 // mutex protects sessionTicketKeys and autoSessionTicketKeys. 818 mutex sync.RWMutex 819 // sessionTicketKeys contains zero or more ticket keys. If set, it means the 820 // the keys were set with SessionTicketKey or SetSessionTicketKeys. The 821 // first key is used for new tickets and any subsequent keys can be used to 822 // decrypt old tickets. The slice contents are not protected by the mutex 823 // and are immutable. 824 sessionTicketKeys []ticketKey 825 // autoSessionTicketKeys is like sessionTicketKeys but is owned by the 826 // auto-rotation logic. See Config.ticketKeys. 827 autoSessionTicketKeys []ticketKey 828 } 829 830 const ( 831 // ticketKeyNameLen is the number of bytes of identifier that is prepended to 832 // an encrypted session ticket in order to identify the key used to encrypt it. 833 ticketKeyNameLen = 16 834 835 // ticketKeyLifetime is how long a ticket key remains valid and can be used to 836 // resume a client connection. 837 ticketKeyLifetime = 7 * 24 * time.Hour // 7 days 838 839 // ticketKeyRotation is how often the server should rotate the session ticket key 840 // that is used for new tickets. 841 ticketKeyRotation = 24 * time.Hour 842 ) 843 844 // ticketKey is the internal representation of a session ticket key. 845 type ticketKey struct { 846 // keyName is an opaque byte string that serves to identify the session 847 // ticket key. It's exposed as plaintext in every session ticket. 848 keyName [ticketKeyNameLen]byte 849 // 原先是aesKey,国密改造改为sm4 850 sm4Key [16]byte 851 hmacKey [16]byte 852 // created is the time at which this ticket key was created. See Config.ticketKeys. 853 created time.Time 854 } 855 856 // ticketKeyFromBytes converts from the external representation of a session 857 // ticket key to a ticketKey. Externally, session ticket keys are 32 random 858 // bytes and this function expands that into sufficient name and key material. 859 func (c *Config) ticketKeyFromBytes(b [32]byte) (key ticketKey) { 860 // 目前只能继续采用sha512,因为sm3校验和长度只有32个字节,不够用。 861 hashed := sha512.Sum512(b[:]) 862 // 1~16字节作为 keyName 863 copy(key.keyName[:], hashed[:ticketKeyNameLen]) 864 // 17~32字节作为aesKey 865 copy(key.sm4Key[:], hashed[ticketKeyNameLen:ticketKeyNameLen+16]) 866 // 33~64字节作为hmacKey 867 copy(key.hmacKey[:], hashed[ticketKeyNameLen+16:ticketKeyNameLen+32]) 868 key.created = c.time() 869 return key 870 } 871 872 // maxSessionTicketLifetime is the maximum allowed lifetime of a TLS 1.3 session 873 // ticket, and the lifetime we set for tickets we send. 874 const maxSessionTicketLifetime = 7 * 24 * time.Hour 875 876 // Clone returns a shallow clone of c or nil if c is nil. It is safe to clone a Config that is 877 // being used concurrently by a TLS client or server. 878 func (c *Config) Clone() *Config { 879 if c == nil { 880 return nil 881 } 882 c.mutex.RLock() 883 defer c.mutex.RUnlock() 884 return &Config{ 885 // GMSupport: c.GMSupport, 886 Rand: c.Rand, 887 Time: c.Time, 888 Certificates: c.Certificates, 889 NameToCertificate: c.NameToCertificate, 890 GetCertificate: c.GetCertificate, 891 // GetKECertificate: c.GetKECertificate, 892 GetClientCertificate: c.GetClientCertificate, 893 GetConfigForClient: c.GetConfigForClient, 894 VerifyPeerCertificate: c.VerifyPeerCertificate, 895 VerifyConnection: c.VerifyConnection, 896 RootCAs: c.RootCAs, 897 NextProtos: c.NextProtos, 898 ServerName: c.ServerName, 899 ClientAuth: c.ClientAuth, 900 ClientCAs: c.ClientCAs, 901 InsecureSkipVerify: c.InsecureSkipVerify, 902 CipherSuites: c.CipherSuites, 903 PreferServerCipherSuites: c.PreferServerCipherSuites, 904 SessionTicketsDisabled: c.SessionTicketsDisabled, 905 SessionTicketKey: c.SessionTicketKey, 906 ClientSessionCache: c.ClientSessionCache, 907 MinVersion: c.MinVersion, 908 MaxVersion: c.MaxVersion, 909 CurvePreferences: c.CurvePreferences, 910 DynamicRecordSizingDisabled: c.DynamicRecordSizingDisabled, 911 Renegotiation: c.Renegotiation, 912 KeyLogWriter: c.KeyLogWriter, 913 sessionTicketKeys: c.sessionTicketKeys, 914 autoSessionTicketKeys: c.autoSessionTicketKeys, 915 } 916 } 917 918 // deprecatedSessionTicketKey is set as the prefix of SessionTicketKey if it was 919 // randomized for backwards compatibility but is not in use. 920 var deprecatedSessionTicketKey = []byte("DEPRECATED") 921 922 // initLegacySessionTicketKeyRLocked ensures the legacy SessionTicketKey field is 923 // randomized if empty, and that sessionTicketKeys is populated from it otherwise. 924 func (c *Config) initLegacySessionTicketKeyRLocked() { 925 // Don't write if SessionTicketKey is already defined as our deprecated string, 926 // or if it is defined by the user but sessionTicketKeys is already set. 927 if c.SessionTicketKey != [32]byte{} && 928 (bytes.HasPrefix(c.SessionTicketKey[:], deprecatedSessionTicketKey) || len(c.sessionTicketKeys) > 0) { 929 return 930 } 931 932 // We need to write some data, so get an exclusive lock and re-check any conditions. 933 c.mutex.RUnlock() 934 defer c.mutex.RLock() 935 c.mutex.Lock() 936 defer c.mutex.Unlock() 937 if c.SessionTicketKey == [32]byte{} { 938 // 生成一个长度32的随机SessionTicketKey 939 if _, err := io.ReadFull(c.rand(), c.SessionTicketKey[:]); err != nil { 940 panic(fmt.Sprintf("gmtls: unable to generate random session ticket key: %v", err)) 941 } 942 // Write the deprecated prefix at the beginning so we know we created 943 // it. This key with the DEPRECATED prefix isn't used as an actual 944 // session ticket key, and is only randomized in case the application 945 // reuses it for some reason. 946 copy(c.SessionTicketKey[:], deprecatedSessionTicketKey) 947 } else if !bytes.HasPrefix(c.SessionTicketKey[:], deprecatedSessionTicketKey) && len(c.sessionTicketKeys) == 0 { 948 c.sessionTicketKeys = []ticketKey{c.ticketKeyFromBytes(c.SessionTicketKey)} 949 } 950 951 } 952 953 // 为当前连接获取ticketKeys。 954 // ticketKeys returns the ticketKeys for this connection. 955 // If configForClient has explicitly set keys, those will 956 // be returned. Otherwise, the keys on c will be used and 957 // may be rotated if auto-managed. 958 // During rotation, any expired session ticket keys are deleted from 959 // c.sessionTicketKeys. If the session ticket key that is currently 960 // encrypting tickets (ie. the first ticketKey in c.sessionTicketKeys) 961 // is not fresh, then a new session ticket key will be 962 // created and prepended to c.sessionTicketKeys. 963 func (c *Config) ticketKeys(configForClient *Config) []ticketKey { 964 // If the ConfigForClient callback returned a Config with explicitly set 965 // keys, use those, otherwise just use the original Config. 966 if configForClient != nil { 967 configForClient.mutex.RLock() 968 if configForClient.SessionTicketsDisabled { 969 return nil 970 } 971 configForClient.initLegacySessionTicketKeyRLocked() 972 if len(configForClient.sessionTicketKeys) != 0 { 973 ret := configForClient.sessionTicketKeys 974 configForClient.mutex.RUnlock() 975 return ret 976 } 977 configForClient.mutex.RUnlock() 978 } 979 980 c.mutex.RLock() 981 defer c.mutex.RUnlock() 982 if c.SessionTicketsDisabled { 983 return nil 984 } 985 c.initLegacySessionTicketKeyRLocked() 986 if len(c.sessionTicketKeys) != 0 { 987 return c.sessionTicketKeys 988 } 989 // Fast path for the common case where the key is fresh enough. 990 if len(c.autoSessionTicketKeys) > 0 && c.time().Sub(c.autoSessionTicketKeys[0].created) < ticketKeyRotation { 991 return c.autoSessionTicketKeys 992 } 993 994 // autoSessionTicketKeys are managed by auto-rotation. 995 c.mutex.RUnlock() 996 defer c.mutex.RLock() 997 c.mutex.Lock() 998 defer c.mutex.Unlock() 999 // Re-check the condition in case it changed since obtaining the new lock. 1000 if len(c.autoSessionTicketKeys) == 0 || c.time().Sub(c.autoSessionTicketKeys[0].created) >= ticketKeyRotation { 1001 var newKey [32]byte 1002 if _, err := io.ReadFull(c.rand(), newKey[:]); err != nil { 1003 panic(fmt.Sprintf("unable to generate random session ticket key: %v", err)) 1004 } 1005 valid := make([]ticketKey, 0, len(c.autoSessionTicketKeys)+1) 1006 valid = append(valid, c.ticketKeyFromBytes(newKey)) 1007 for _, k := range c.autoSessionTicketKeys { 1008 // While rotating the current key, also remove any expired ones. 1009 if c.time().Sub(k.created) < ticketKeyLifetime { 1010 valid = append(valid, k) 1011 } 1012 } 1013 c.autoSessionTicketKeys = valid 1014 } 1015 return c.autoSessionTicketKeys 1016 } 1017 1018 // SetSessionTicketKeys updates the session ticket keys for a server. 1019 // 1020 // The first key will be used when creating new tickets, while all keys can be 1021 // used for decrypting tickets. It is safe to call this function while the 1022 // server is running in order to rotate the session ticket keys. The function 1023 // will panic if keys is empty. 1024 // 1025 // Calling this function will turn off automatic session ticket key rotation. 1026 // 1027 // If multiple servers are terminating connections for the same host they should 1028 // all have the same session ticket keys. If the session ticket keys leaks, 1029 // previously recorded and future TLS connections using those keys might be 1030 // compromised. 1031 func (c *Config) SetSessionTicketKeys(keys [][32]byte) { 1032 if len(keys) == 0 { 1033 panic("gmtls: keys must have at least one key") 1034 } 1035 1036 newKeys := make([]ticketKey, len(keys)) 1037 for i, key := range keys { 1038 newKeys[i] = c.ticketKeyFromBytes(key) 1039 } 1040 1041 c.mutex.Lock() 1042 c.sessionTicketKeys = newKeys 1043 c.mutex.Unlock() 1044 } 1045 1046 func (c *Config) rand() io.Reader { 1047 r := c.Rand 1048 if r == nil { 1049 return rand.Reader 1050 } 1051 return r 1052 } 1053 1054 func (c *Config) time() time.Time { 1055 t := c.Time 1056 if t == nil { 1057 t = time.Now 1058 } 1059 return t() 1060 } 1061 1062 func (c *Config) cipherSuites() []uint16 { 1063 if c.CipherSuites != nil { 1064 return c.CipherSuites 1065 } 1066 return defaultCipherSuites 1067 } 1068 1069 // TODO: 可能需要调整 VersionGMSSL 的位置 1070 var supportedVersions = []uint16{ 1071 VersionTLS13, 1072 VersionTLS12, 1073 VersionTLS11, 1074 VersionTLS10, 1075 VersionGMSSL, 1076 } 1077 1078 // 获取目标Config支持的TLS协议 1079 // 1080 // 协议版本需要位于[c.MinVersion, c.MaxVersion]之间 1081 func (c *Config) supportedVersions() []uint16 { 1082 versions := make([]uint16, 0, len(supportedVersions)) 1083 for _, v := range supportedVersions { 1084 if c != nil && c.MinVersion != 0 && v < c.MinVersion { 1085 continue 1086 } 1087 if c != nil && c.MaxVersion != 0 && v > c.MaxVersion { 1088 continue 1089 } 1090 versions = append(versions, v) 1091 } 1092 return versions 1093 } 1094 1095 // 获取支持的最高TLS协议版本 1096 func (c *Config) maxSupportedVersion() uint16 { 1097 supportedVersions := c.supportedVersions() 1098 if len(supportedVersions) == 0 { 1099 return 0 1100 } 1101 // supportedVersions列表中,越高的版本越靠前 1102 return supportedVersions[0] 1103 } 1104 1105 // supportedVersionsFromMax returns a list of supported versions derived from a 1106 // legacy maximum version value. Note that only versions supported by this 1107 // library are returned. Any newer peer will use supportedVersions anyway. 1108 func supportedVersionsFromMax(maxVersion uint16) []uint16 { 1109 versions := make([]uint16, 0, len(supportedVersions)) 1110 for _, v := range supportedVersions { 1111 if v > maxVersion { 1112 continue 1113 } 1114 versions = append(versions, v) 1115 } 1116 return versions 1117 } 1118 1119 // 将sm2p256列为默认曲线首位 1120 var defaultCurvePreferences = []CurveID{Curve256Sm2, X25519, CurveP256, CurveP384, CurveP521} 1121 1122 func (c *Config) curvePreferences() []CurveID { 1123 if c == nil || len(c.CurvePreferences) == 0 { 1124 return defaultCurvePreferences 1125 } 1126 return c.CurvePreferences 1127 } 1128 1129 func (c *Config) supportsCurve(curve CurveID) bool { 1130 for _, cc := range c.curvePreferences() { 1131 if cc == curve { 1132 return true 1133 } 1134 } 1135 return false 1136 } 1137 1138 // 协商tls协议 1139 // 1140 // 根据对方传来的tls版本信息,从己方支持的版本列表中从前往后选取第一个匹配的版本。 1141 // 目前优先匹配顺序是 tls1.3 -> gmssl -> tls1.2 ... 1142 // 1143 // mutualVersion returns the protocol version to use given the advertised 1144 // versions of the peer. Priority is given to the peer preference order. 1145 func (c *Config) mutualVersion(peerVersions []uint16) (uint16, bool) { 1146 supportedVersions := c.supportedVersions() 1147 for _, peerVersion := range peerVersions { 1148 for _, v := range supportedVersions { 1149 if v == peerVersion { 1150 return v, true 1151 } 1152 } 1153 } 1154 return 0, false 1155 } 1156 1157 // getCertificate 返回密钥交换使用的证书及密钥 1158 // 该方法只有GMSSL会调用 1159 // 如果 Certificates 长度大于等于2时,默认返回第2个证书密钥 1160 // 如果 Certificates 为空或不足2时,调用 GetEKCertificate 方法获取。 1161 // func (c *Config) getEKCertificate(clientHello *ClientHelloInfo) (*Certificate, error) { 1162 // if c.GetKECertificate != nil && (len(c.Certificates) < 2) { 1163 // cert, err := c.GetKECertificate(clientHello) 1164 // if cert != nil || err != nil { 1165 // return cert, err 1166 // } 1167 // } 1168 // if len(c.Certificates) >= 2 { 1169 // return &c.Certificates[1], nil 1170 // } 1171 // return nil, errors.New("gmtls: no key exchange (encrypt) certificate configured") 1172 // } 1173 1174 var errNoCertificates = errors.New("gmtls: no certificates configured") 1175 1176 // getCertificate returns the best certificate for the given ClientHelloInfo, 1177 // defaulting to the first element of c.Certificates. 1178 func (c *Config) getCertificate(clientHello *ClientHelloInfo) (*Certificate, error) { 1179 if c.GetCertificate != nil && 1180 (len(c.Certificates) == 0 || len(clientHello.ServerName) > 0) { 1181 cert, err := c.GetCertificate(clientHello) 1182 if cert != nil || err != nil { 1183 return cert, err 1184 } 1185 } 1186 1187 if len(c.Certificates) == 0 { 1188 return nil, errNoCertificates 1189 } 1190 1191 if len(c.Certificates) == 1 { 1192 // There's only one choice, so no point doing any work. 1193 return &c.Certificates[0], nil 1194 } 1195 1196 if c.NameToCertificate != nil { 1197 name := strings.ToLower(clientHello.ServerName) 1198 if cert, ok := c.NameToCertificate[name]; ok { 1199 return cert, nil 1200 } 1201 if len(name) > 0 { 1202 labels := strings.Split(name, ".") 1203 labels[0] = "*" 1204 wildcardName := strings.Join(labels, ".") 1205 if cert, ok := c.NameToCertificate[wildcardName]; ok { 1206 return cert, nil 1207 } 1208 } 1209 } 1210 1211 for _, cert := range c.Certificates { 1212 if err := clientHello.SupportsCertificate(&cert); err == nil { 1213 return &cert, nil 1214 } 1215 } 1216 1217 // If nothing matches, return the first certificate. 1218 return &c.Certificates[0], nil 1219 } 1220 1221 // SupportsCertificate returns nil if the provided certificate is supported by 1222 // the client that sent the ClientHello. Otherwise, it returns an error 1223 // describing the reason for the incompatibility. 1224 // 1225 // If this ClientHelloInfo was passed to a GetConfigForClient or GetCertificate 1226 // callback, this method will take into account the associated Config. Note that 1227 // if GetConfigForClient returns a different Config, the change can't be 1228 // accounted for by this method. 1229 // 1230 // This function will call x509.ParseCertificate unless c.Leaf is set, which can 1231 // incur a significant performance cost. 1232 func (chi *ClientHelloInfo) SupportsCertificate(c *Certificate) error { 1233 // Note we don't currently support certificate_authorities nor 1234 // signature_algorithms_cert, and don't check the algorithms of the 1235 // signatures on the chain (which anyway are a SHOULD, see RFC 8446, 1236 // Section 4.4.2.2). 1237 1238 config := chi.config 1239 if config == nil { 1240 config = &Config{} 1241 } 1242 vers, ok := config.mutualVersion(chi.SupportedVersions) 1243 if !ok { 1244 return errors.New("no mutually supported protocol versions") 1245 } 1246 1247 // If the client specified the name they are trying to connect to, the 1248 // certificate needs to be valid for it. 1249 if chi.ServerName != "" { 1250 x509Cert, err := c.leaf() 1251 if err != nil { 1252 return fmt.Errorf("failed to parse certificate: %w", err) 1253 } 1254 if err := x509Cert.VerifyHostname(chi.ServerName); err != nil { 1255 return fmt.Errorf("certificate is not valid for requested server name: %w", err) 1256 } 1257 } 1258 1259 // supportsRSAFallback returns nil if the certificate and connection support 1260 // the static RSA key exchange, and unsupported otherwise. The logic for 1261 // supporting static RSA is completely disjoint from the logic for 1262 // supporting signed key exchanges, so we just check it as a fallback. 1263 supportsRSAFallback := func(unsupported error) error { 1264 // TLS 1.3 dropped support for the static RSA key exchange. 1265 if vers == VersionTLS13 || vers == VersionGMSSL { 1266 return unsupported 1267 } 1268 // The static RSA key exchange works by decrypting a challenge with the 1269 // RSA private key, not by signing, so check the PrivateKey implements 1270 // crypto.Decrypter, like *rsa.PrivateKey does. 1271 if priv, ok := c.PrivateKey.(crypto.Decrypter); ok { 1272 if _, ok := priv.Public().(*rsa.PublicKey); !ok { 1273 return unsupported 1274 } 1275 } else { 1276 return unsupported 1277 } 1278 // Finally, there needs to be a mutual cipher suite that uses the static 1279 // RSA key exchange instead of ECDHE. 1280 rsaCipherSuite := selectCipherSuite(chi.CipherSuites, config.cipherSuites(), func(c *cipherSuite) bool { 1281 if c.flags&suiteECDHE != 0 { 1282 return false 1283 } 1284 if vers < VersionTLS12 && c.flags&suiteTLS12 != 0 { 1285 return false 1286 } 1287 return true 1288 }) 1289 if rsaCipherSuite == nil { 1290 return unsupported 1291 } 1292 return nil 1293 } 1294 1295 // If the client sent the signature_algorithms extension, ensure it supports 1296 // schemes we can use with this certificate and TLS version. 1297 if len(chi.SignatureSchemes) > 0 { 1298 if _, err := selectSignatureScheme(vers, c, chi.SignatureSchemes); err != nil { 1299 return supportsRSAFallback(err) 1300 } 1301 } 1302 1303 // In TLS 1.3 we are done because supported_groups is only relevant to the 1304 // ECDHE computation, point format negotiation is removed, cipher suites are 1305 // only relevant to the AEAD choice, and static RSA does not exist. 1306 if vers == VersionTLS13 || vers == VersionGMSSL { 1307 return nil 1308 } 1309 1310 // The only signed key exchange we support is ECDHE. 1311 if !supportsECDHE(config, chi.SupportedCurves, chi.SupportedPoints) { 1312 return supportsRSAFallback(errors.New("client doesn't support ECDHE, can only use legacy RSA key exchange")) 1313 } 1314 1315 var ecdsaCipherSuite bool 1316 if priv, ok := c.PrivateKey.(crypto.Signer); ok { 1317 switch pub := priv.Public().(type) { 1318 // 添加sm2分支 1319 case *sm2.PublicKey: 1320 var curve CurveID 1321 switch pub.Curve { 1322 case sm2.P256Sm2(): 1323 curve = Curve256Sm2 1324 default: 1325 return supportsRSAFallback(unsupportedCertificateError(c)) 1326 } 1327 var curveOk bool 1328 for _, c := range chi.SupportedCurves { 1329 if c == curve && config.supportsCurve(c) { 1330 curveOk = true 1331 break 1332 } 1333 } 1334 if !curveOk { 1335 return errors.New("client doesn't support certificate curve") 1336 } 1337 ecdsaCipherSuite = true 1338 case *ecdsa.PublicKey: 1339 var curve CurveID 1340 switch pub.Curve { 1341 case elliptic.P256(): 1342 curve = CurveP256 1343 case elliptic.P384(): 1344 curve = CurveP384 1345 case elliptic.P521(): 1346 curve = CurveP521 1347 default: 1348 return supportsRSAFallback(unsupportedCertificateError(c)) 1349 } 1350 var curveOk bool 1351 for _, c := range chi.SupportedCurves { 1352 if c == curve && config.supportsCurve(c) { 1353 curveOk = true 1354 break 1355 } 1356 } 1357 if !curveOk { 1358 return errors.New("client doesn't support certificate curve") 1359 } 1360 ecdsaCipherSuite = true 1361 case ed25519.PublicKey: 1362 if vers < VersionTLS12 || len(chi.SignatureSchemes) == 0 { 1363 return errors.New("connection doesn't support Ed25519") 1364 } 1365 ecdsaCipherSuite = true 1366 case *rsa.PublicKey: 1367 default: 1368 return supportsRSAFallback(unsupportedCertificateError(c)) 1369 } 1370 } else { 1371 return supportsRSAFallback(unsupportedCertificateError(c)) 1372 } 1373 1374 // Make sure that there is a mutually supported cipher suite that works with 1375 // this certificate. Cipher suite selection will then apply the logic in 1376 // reverse to pick it. See also serverHandshakeState.cipherSuiteOk. 1377 cipherSuite := selectCipherSuite(chi.CipherSuites, config.cipherSuites(), func(c *cipherSuite) bool { 1378 if c.flags&suiteECDHE == 0 { 1379 return false 1380 } 1381 if c.flags&suiteECSign != 0 { 1382 if !ecdsaCipherSuite { 1383 return false 1384 } 1385 } else { 1386 if ecdsaCipherSuite { 1387 return false 1388 } 1389 } 1390 if vers < VersionTLS12 && c.flags&suiteTLS12 != 0 { 1391 return false 1392 } 1393 return true 1394 }) 1395 if cipherSuite == nil { 1396 return supportsRSAFallback(errors.New("client doesn't support any cipher suites compatible with the certificate")) 1397 } 1398 1399 return nil 1400 } 1401 1402 // SupportsCertificate returns nil if the provided certificate is supported by 1403 // the server that sent the CertificateRequest. Otherwise, it returns an error 1404 // describing the reason for the incompatibility. 1405 func (cri *CertificateRequestInfo) SupportsCertificate(c *Certificate) error { 1406 if _, err := selectSignatureScheme(cri.Version, c, cri.SignatureSchemes); err != nil { 1407 return err 1408 } 1409 1410 if len(cri.AcceptableCAs) == 0 { 1411 return nil 1412 } 1413 1414 for j, cert := range c.Certificate { 1415 x509Cert := c.Leaf 1416 // Parse the certificate if this isn't the leaf node, or if 1417 // chain.Leaf was nil. 1418 if j != 0 || x509Cert == nil { 1419 var err error 1420 if x509Cert, err = x509.ParseCertificate(cert); err != nil { 1421 return fmt.Errorf("failed to parse certificate #%d in the chain: %w", j, err) 1422 } 1423 } 1424 1425 for _, ca := range cri.AcceptableCAs { 1426 if bytes.Equal(x509Cert.RawIssuer, ca) { 1427 return nil 1428 } 1429 } 1430 } 1431 return errors.New("chain is not signed by an acceptable CA") 1432 } 1433 1434 // BuildNameToCertificate parses c.Certificates and builds c.NameToCertificate 1435 // from the CommonName and SubjectAlternateName fields of each of the leaf 1436 // certificates. 1437 // 1438 // ToDeprecated: NameToCertificate only allows associating a single certificate 1439 // with a given name. Leave that field nil to let the library select the first 1440 // compatible chain from Certificates. 1441 func (c *Config) BuildNameToCertificate() { 1442 c.NameToCertificate = make(map[string]*Certificate) 1443 for i := range c.Certificates { 1444 cert := &c.Certificates[i] 1445 x509Cert, err := cert.leaf() 1446 if err != nil { 1447 continue 1448 } 1449 // If SANs are *not* present, some clients will consider the certificate 1450 // valid for the name in the Common Name. 1451 if x509Cert.Subject.CommonName != "" && len(x509Cert.DNSNames) == 0 { 1452 c.NameToCertificate[x509Cert.Subject.CommonName] = cert 1453 } 1454 for _, san := range x509Cert.DNSNames { 1455 c.NameToCertificate[san] = cert 1456 } 1457 } 1458 } 1459 1460 const ( 1461 keyLogLabelTLS12 = "CLIENT_RANDOM" 1462 keyLogLabelClientHandshake = "CLIENT_HANDSHAKE_TRAFFIC_SECRET" 1463 keyLogLabelServerHandshake = "SERVER_HANDSHAKE_TRAFFIC_SECRET" 1464 keyLogLabelClientTraffic = "CLIENT_TRAFFIC_SECRET_0" 1465 keyLogLabelServerTraffic = "SERVER_TRAFFIC_SECRET_0" 1466 ) 1467 1468 func (c *Config) writeKeyLog(label string, clientRandom, secret []byte) error { 1469 if c.KeyLogWriter == nil { 1470 return nil 1471 } 1472 1473 logLine := []byte(fmt.Sprintf("%s %x %x\n", label, clientRandom, secret)) 1474 1475 writerMutex.Lock() 1476 _, err := c.KeyLogWriter.Write(logLine) 1477 writerMutex.Unlock() 1478 1479 return err 1480 } 1481 1482 // writerMutex protects all KeyLogWriters globally. It is rarely enabled, 1483 // and is only for debugging, so a global mutex saves space. 1484 var writerMutex sync.Mutex 1485 1486 // Certificate 证书链, 子证书在前 1487 // A Certificate is a chain of one or more certificates, leaf first. 1488 type Certificate struct { 1489 // 证书列表 1490 Certificate [][]byte 1491 // 子证书公钥对应的私钥 1492 // PrivateKey contains the private key corresponding to the public key in 1493 // Leaf. This must implement crypto.Signer with an RSA, ECDSA or Ed25519 PublicKey. 1494 // For a server up to TLS 1.2, it can also implement crypto.Decrypter with 1495 // an RSA PublicKey. 1496 PrivateKey crypto.PrivateKey 1497 // 子证书私钥支持的签名算法列表 1498 // SupportedSignatureAlgorithms is an optional list restricting what 1499 // signature algorithms the PrivateKey can be used for. 1500 SupportedSignatureAlgorithms []SignatureScheme 1501 // 供客户端请求的OCSP响应 1502 // OCSPStaple contains an optional OCSP response which will be served 1503 // to clients that request it. 1504 OCSPStaple []byte 1505 // 供客户端请求的证书签名时间列表 1506 // SignedCertificateTimestamps contains an optional list of Signed 1507 // Certificate Timestamps which will be served to clients that request it. 1508 SignedCertificateTimestamps [][]byte 1509 // 子证书 1510 // Leaf is the parsed form of the leaf certificate, which may be initialized 1511 // using x509.ParseCertificate to reduce per-handshake processing. If nil, 1512 // the leaf certificate will be parsed as needed. 1513 Leaf *x509.Certificate 1514 } 1515 1516 // leaf returns the parsed leaf certificate, either from c.Leaf or by parsing 1517 // the corresponding c.Certificate[0]. 1518 func (c *Certificate) leaf() (*x509.Certificate, error) { 1519 if c.Leaf != nil { 1520 return c.Leaf, nil 1521 } 1522 return x509.ParseCertificate(c.Certificate[0]) 1523 } 1524 1525 type handshakeMessage interface { 1526 marshal() []byte 1527 unmarshal([]byte) bool 1528 } 1529 1530 // 使用LRU(近期最少使用)算法实现的客户端会话缓存。 1531 // lruSessionCache is a ClientSessionCache implementation that uses an LRU 1532 // caching strategy. 1533 type lruSessionCache struct { 1534 sync.Mutex 1535 1536 m map[string]*list.Element 1537 q *list.List 1538 capacity int 1539 } 1540 1541 type lruSessionCacheEntry struct { 1542 sessionKey string 1543 state *ClientSessionState 1544 } 1545 1546 // NewLRUClientSessionCache returns a ClientSessionCache with the given 1547 // capacity that uses an LRU strategy. If capacity is < 1, a default capacity 1548 // is used instead. 1549 func NewLRUClientSessionCache(capacity int) ClientSessionCache { 1550 const defaultSessionCacheCapacity = 64 1551 1552 if capacity < 1 { 1553 capacity = defaultSessionCacheCapacity 1554 } 1555 return &lruSessionCache{ 1556 m: make(map[string]*list.Element), 1557 q: list.New(), 1558 capacity: capacity, 1559 } 1560 } 1561 1562 // Put 存储会话到缓存, 实现了 ClientSessionCache 接口 1563 // Put adds the provided (sessionKey, cs) pair to the cache. If cs is nil, the entry 1564 // corresponding to sessionKey is removed from the cache instead. 1565 func (c *lruSessionCache) Put(sessionKey string, cs *ClientSessionState) { 1566 c.Lock() 1567 defer c.Unlock() 1568 1569 if elem, ok := c.m[sessionKey]; ok { 1570 if cs == nil { 1571 c.q.Remove(elem) 1572 delete(c.m, sessionKey) 1573 } else { 1574 entry := elem.Value.(*lruSessionCacheEntry) 1575 entry.state = cs 1576 c.q.MoveToFront(elem) 1577 } 1578 return 1579 } 1580 1581 if c.q.Len() < c.capacity { 1582 entry := &lruSessionCacheEntry{sessionKey, cs} 1583 c.m[sessionKey] = c.q.PushFront(entry) 1584 return 1585 } 1586 1587 elem := c.q.Back() 1588 entry := elem.Value.(*lruSessionCacheEntry) 1589 delete(c.m, entry.sessionKey) 1590 entry.sessionKey = sessionKey 1591 entry.state = cs 1592 c.q.MoveToFront(elem) 1593 c.m[sessionKey] = elem 1594 } 1595 1596 // Get 从缓存获取会话, 实现了 ClientSessionCache 接口 1597 // Get returns the ClientSessionState value associated with a given key. It 1598 // returns (nil, false) if no value is found. 1599 func (c *lruSessionCache) Get(sessionKey string) (*ClientSessionState, bool) { 1600 c.Lock() 1601 defer c.Unlock() 1602 1603 if elem, ok := c.m[sessionKey]; ok { 1604 c.q.MoveToFront(elem) 1605 return elem.Value.(*lruSessionCacheEntry).state, true 1606 } 1607 return nil, false 1608 } 1609 1610 var emptyConfig Config 1611 1612 func defaultConfig() *Config { 1613 return &emptyConfig 1614 } 1615 1616 func unexpectedMessageError(wanted, got interface{}) error { 1617 return fmt.Errorf("gmtls: received unexpected handshake message of type %T when waiting for %T", got, wanted) 1618 } 1619 1620 // 判断是否支持目标签名算法 1621 // - sigAlg : 目标签名算法 1622 // - supportedSignatureAlgorithms : 支持的签名算法集合 1623 func isSupportedSignatureAlgorithm(sigAlg SignatureScheme, supportedSignatureAlgorithms []SignatureScheme) bool { 1624 for _, s := range supportedSignatureAlgorithms { 1625 if s == sigAlg { 1626 return true 1627 } 1628 } 1629 return false 1630 }