github.com/Carcraftz/utls@v0.0.0-20220413235215-6b7c52fd78b6/u_public.go (about)

     1  // Copyright 2017 Google Inc. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package tls
     6  
     7  import (
     8  	"crypto"
     9  	"crypto/x509"
    10  	"hash"
    11  )
    12  
    13  // ClientHandshakeState includes both TLS 1.3-only and TLS 1.2-only states,
    14  // only one of them will be used, depending on negotiated version.
    15  //
    16  // ClientHandshakeState will be converted into and from either
    17  //   - clientHandshakeState      (TLS 1.2)
    18  //   - clientHandshakeStateTLS13 (TLS 1.3)
    19  // uTLS will call .handshake() on one of these private internal states,
    20  // to perform TLS handshake using standard crypto/tls implementation.
    21  type ClientHandshakeState struct {
    22  	C            *Conn
    23  	ServerHello  *ServerHelloMsg
    24  	Hello        *ClientHelloMsg
    25  	MasterSecret []byte
    26  	Session      *ClientSessionState
    27  
    28  	State12 TLS12OnlyState
    29  	State13 TLS13OnlyState
    30  
    31  	uconn *UConn
    32  }
    33  
    34  // TLS 1.3 only
    35  type TLS13OnlyState struct {
    36  	Suite         *CipherSuiteTLS13
    37  	EcdheParams   map[CurveID]EcdheParameters // XXX/yawning - annoying
    38  	EarlySecret   []byte
    39  	BinderKey     []byte
    40  	CertReq       *CertificateRequestMsgTLS13
    41  	UsingPSK      bool
    42  	SentDummyCCS  bool
    43  	Transcript    hash.Hash
    44  	TrafficSecret []byte // client_application_traffic_secret_0
    45  	CertCompAlgs  []CertCompressionAlgo
    46  }
    47  
    48  // TLS 1.2 and before only
    49  type TLS12OnlyState struct {
    50  	FinishedHash FinishedHash
    51  	Suite        CipherSuite
    52  }
    53  
    54  func (chs *ClientHandshakeState) toPrivate13() *clientHandshakeStateTLS13 {
    55  	if chs == nil {
    56  		return nil
    57  	} else {
    58  		return &clientHandshakeStateTLS13{
    59  			c:           chs.C,
    60  			serverHello: chs.ServerHello.getPrivatePtr(),
    61  			hello:       chs.Hello.getPrivatePtr(),
    62  			ecdheParams: ecdheParamMapToPrivate(chs.State13.EcdheParams),
    63  
    64  			session:     chs.Session,
    65  			earlySecret: chs.State13.EarlySecret,
    66  			binderKey:   chs.State13.BinderKey,
    67  
    68  			certReq:       chs.State13.CertReq.toPrivate(),
    69  			usingPSK:      chs.State13.UsingPSK,
    70  			sentDummyCCS:  chs.State13.SentDummyCCS,
    71  			suite:         chs.State13.Suite.toPrivate(),
    72  			transcript:    chs.State13.Transcript,
    73  			masterSecret:  chs.MasterSecret,
    74  			trafficSecret: chs.State13.TrafficSecret,
    75  			certCompAlgs:  chs.State13.CertCompAlgs,
    76  
    77  			uconn: chs.uconn,
    78  		}
    79  	}
    80  }
    81  
    82  func (chs13 *clientHandshakeStateTLS13) toPublic13() *ClientHandshakeState {
    83  	if chs13 == nil {
    84  		return nil
    85  	} else {
    86  		tls13State := TLS13OnlyState{
    87  			EcdheParams:   ecdheParamMapToPublic(chs13.ecdheParams),
    88  			EarlySecret:   chs13.earlySecret,
    89  			BinderKey:     chs13.binderKey,
    90  			CertReq:       chs13.certReq.toPublic(),
    91  			UsingPSK:      chs13.usingPSK,
    92  			SentDummyCCS:  chs13.sentDummyCCS,
    93  			Suite:         chs13.suite.toPublic(),
    94  			TrafficSecret: chs13.trafficSecret,
    95  			Transcript:    chs13.transcript,
    96  			CertCompAlgs:  chs13.certCompAlgs,
    97  		}
    98  		return &ClientHandshakeState{
    99  			C:           chs13.c,
   100  			ServerHello: chs13.serverHello.getPublicPtr(),
   101  			Hello:       chs13.hello.getPublicPtr(),
   102  
   103  			Session: chs13.session,
   104  
   105  			MasterSecret: chs13.masterSecret,
   106  
   107  			State13: tls13State,
   108  
   109  			uconn: chs13.uconn,
   110  		}
   111  	}
   112  }
   113  
   114  func (chs *ClientHandshakeState) toPrivate12() *clientHandshakeState {
   115  	if chs == nil {
   116  		return nil
   117  	} else {
   118  		return &clientHandshakeState{
   119  			c:           chs.C,
   120  			serverHello: chs.ServerHello.getPrivatePtr(),
   121  			hello:       chs.Hello.getPrivatePtr(),
   122  			suite:       chs.State12.Suite.getPrivatePtr(),
   123  			session:     chs.Session,
   124  
   125  			masterSecret: chs.MasterSecret,
   126  
   127  			finishedHash: chs.State12.FinishedHash.getPrivateObj(),
   128  
   129  			uconn: chs.uconn,
   130  		}
   131  	}
   132  }
   133  
   134  func (chs12 *clientHandshakeState) toPublic12() *ClientHandshakeState {
   135  	if chs12 == nil {
   136  		return nil
   137  	} else {
   138  		tls12State := TLS12OnlyState{
   139  			Suite:        chs12.suite.getPublicObj(),
   140  			FinishedHash: chs12.finishedHash.getPublicObj(),
   141  		}
   142  		return &ClientHandshakeState{
   143  			C:           chs12.c,
   144  			ServerHello: chs12.serverHello.getPublicPtr(),
   145  			Hello:       chs12.hello.getPublicPtr(),
   146  
   147  			Session: chs12.session,
   148  
   149  			MasterSecret: chs12.masterSecret,
   150  
   151  			State12: tls12State,
   152  
   153  			uconn: chs12.uconn,
   154  		}
   155  	}
   156  }
   157  
   158  type EcdheParameters interface {
   159  	ecdheParameters
   160  }
   161  
   162  func ecdheParamMapToPublic(src map[CurveID]ecdheParameters) map[CurveID]EcdheParameters {
   163  	dst := make(map[CurveID]EcdheParameters)
   164  	for curveID, param := range src {
   165  		dst[curveID] = EcdheParameters(param)
   166  	}
   167  	return dst
   168  }
   169  
   170  func ecdheParamMapToPrivate(src map[CurveID]EcdheParameters) map[CurveID]ecdheParameters {
   171  	dst := make(map[CurveID]ecdheParameters)
   172  	for curveID, param := range src {
   173  		dst[curveID] = ecdheParameters(param)
   174  	}
   175  	return dst
   176  }
   177  
   178  type CertificateRequestMsgTLS13 struct {
   179  	Raw                              []byte
   180  	OcspStapling                     bool
   181  	Scts                             bool
   182  	SupportedSignatureAlgorithms     []SignatureScheme
   183  	SupportedSignatureAlgorithmsCert []SignatureScheme
   184  	CertificateAuthorities           [][]byte
   185  }
   186  
   187  func (crm *certificateRequestMsgTLS13) toPublic() *CertificateRequestMsgTLS13 {
   188  	if crm == nil {
   189  		return nil
   190  	} else {
   191  		return &CertificateRequestMsgTLS13{
   192  			Raw:                              crm.raw,
   193  			OcspStapling:                     crm.ocspStapling,
   194  			Scts:                             crm.scts,
   195  			SupportedSignatureAlgorithms:     crm.supportedSignatureAlgorithms,
   196  			SupportedSignatureAlgorithmsCert: crm.supportedSignatureAlgorithmsCert,
   197  			CertificateAuthorities:           crm.certificateAuthorities,
   198  		}
   199  	}
   200  }
   201  
   202  func (crm *CertificateRequestMsgTLS13) toPrivate() *certificateRequestMsgTLS13 {
   203  	if crm == nil {
   204  		return nil
   205  	} else {
   206  		return &certificateRequestMsgTLS13{
   207  			raw:                              crm.Raw,
   208  			ocspStapling:                     crm.OcspStapling,
   209  			scts:                             crm.Scts,
   210  			supportedSignatureAlgorithms:     crm.SupportedSignatureAlgorithms,
   211  			supportedSignatureAlgorithmsCert: crm.SupportedSignatureAlgorithmsCert,
   212  			certificateAuthorities:           crm.CertificateAuthorities,
   213  		}
   214  	}
   215  }
   216  
   217  type CipherSuiteTLS13 struct {
   218  	Id     uint16
   219  	KeyLen int
   220  	Aead   func(key, fixedNonce []byte) aead
   221  	Hash   crypto.Hash
   222  }
   223  
   224  func (c *cipherSuiteTLS13) toPublic() *CipherSuiteTLS13 {
   225  	if c == nil {
   226  		return nil
   227  	} else {
   228  		return &CipherSuiteTLS13{
   229  			Id:     c.id,
   230  			KeyLen: c.keyLen,
   231  			Aead:   c.aead,
   232  			Hash:   c.hash,
   233  		}
   234  	}
   235  }
   236  
   237  func (c *CipherSuiteTLS13) toPrivate() *cipherSuiteTLS13 {
   238  	if c == nil {
   239  		return nil
   240  	} else {
   241  		return &cipherSuiteTLS13{
   242  			id:     c.Id,
   243  			keyLen: c.KeyLen,
   244  			aead:   c.Aead,
   245  			hash:   c.Hash,
   246  		}
   247  	}
   248  }
   249  
   250  type ServerHelloMsg struct {
   251  	Raw                          []byte
   252  	Vers                         uint16
   253  	Random                       []byte
   254  	SessionId                    []byte
   255  	CipherSuite                  uint16
   256  	CompressionMethod            uint8
   257  	NextProtoNeg                 bool
   258  	NextProtos                   []string
   259  	OcspStapling                 bool
   260  	Scts                         [][]byte
   261  	Ems                          bool
   262  	TicketSupported              bool
   263  	SecureRenegotiation          []byte
   264  	SecureRenegotiationSupported bool
   265  	AlpnProtocol                 string
   266  
   267  	// 1.3
   268  	SupportedVersion        uint16
   269  	ServerShare             keyShare
   270  	SelectedIdentityPresent bool
   271  	SelectedIdentity        uint16
   272  	Cookie                  []byte  // HelloRetryRequest extension
   273  	SelectedGroup           CurveID // HelloRetryRequest extension
   274  
   275  }
   276  
   277  func (shm *ServerHelloMsg) getPrivatePtr() *serverHelloMsg {
   278  	if shm == nil {
   279  		return nil
   280  	} else {
   281  		return &serverHelloMsg{
   282  			raw:                          shm.Raw,
   283  			vers:                         shm.Vers,
   284  			random:                       shm.Random,
   285  			sessionId:                    shm.SessionId,
   286  			cipherSuite:                  shm.CipherSuite,
   287  			compressionMethod:            shm.CompressionMethod,
   288  			nextProtoNeg:                 shm.NextProtoNeg,
   289  			nextProtos:                   shm.NextProtos,
   290  			ocspStapling:                 shm.OcspStapling,
   291  			scts:                         shm.Scts,
   292  			ems:                          shm.Ems,
   293  			ticketSupported:              shm.TicketSupported,
   294  			secureRenegotiation:          shm.SecureRenegotiation,
   295  			secureRenegotiationSupported: shm.SecureRenegotiationSupported,
   296  			alpnProtocol:                 shm.AlpnProtocol,
   297  			supportedVersion:             shm.SupportedVersion,
   298  			serverShare:                  shm.ServerShare,
   299  			selectedIdentityPresent:      shm.SelectedIdentityPresent,
   300  			selectedIdentity:             shm.SelectedIdentity,
   301  			cookie:                       shm.Cookie,
   302  			selectedGroup:                shm.SelectedGroup,
   303  		}
   304  	}
   305  }
   306  
   307  func (shm *serverHelloMsg) getPublicPtr() *ServerHelloMsg {
   308  	if shm == nil {
   309  		return nil
   310  	} else {
   311  		return &ServerHelloMsg{
   312  			Raw:                          shm.raw,
   313  			Vers:                         shm.vers,
   314  			Random:                       shm.random,
   315  			SessionId:                    shm.sessionId,
   316  			CipherSuite:                  shm.cipherSuite,
   317  			CompressionMethod:            shm.compressionMethod,
   318  			NextProtoNeg:                 shm.nextProtoNeg,
   319  			NextProtos:                   shm.nextProtos,
   320  			OcspStapling:                 shm.ocspStapling,
   321  			Scts:                         shm.scts,
   322  			Ems:                          shm.ems,
   323  			TicketSupported:              shm.ticketSupported,
   324  			SecureRenegotiation:          shm.secureRenegotiation,
   325  			SecureRenegotiationSupported: shm.secureRenegotiationSupported,
   326  			AlpnProtocol:                 shm.alpnProtocol,
   327  			SupportedVersion:             shm.supportedVersion,
   328  			ServerShare:                  shm.serverShare,
   329  			SelectedIdentityPresent:      shm.selectedIdentityPresent,
   330  			SelectedIdentity:             shm.selectedIdentity,
   331  			Cookie:                       shm.cookie,
   332  			SelectedGroup:                shm.selectedGroup,
   333  		}
   334  	}
   335  }
   336  
   337  type ClientHelloMsg struct {
   338  	Raw                          []byte
   339  	Vers                         uint16
   340  	Random                       []byte
   341  	SessionId                    []byte
   342  	CipherSuites                 []uint16
   343  	CompressionMethods           []uint8
   344  	NextProtoNeg                 bool
   345  	ServerName                   string
   346  	OcspStapling                 bool
   347  	Scts                         bool
   348  	Ems                          bool // [UTLS] actually implemented due to its prevalence
   349  	SupportedCurves              []CurveID
   350  	SupportedPoints              []uint8
   351  	TicketSupported              bool
   352  	SessionTicket                []uint8
   353  	SupportedSignatureAlgorithms []SignatureScheme
   354  	SecureRenegotiation          []byte
   355  	SecureRenegotiationSupported bool
   356  	AlpnProtocols                []string
   357  
   358  	// 1.3
   359  	SupportedSignatureAlgorithmsCert []SignatureScheme
   360  	SupportedVersions                []uint16
   361  	Cookie                           []byte
   362  	KeyShares                        []KeyShare
   363  	EarlyData                        bool
   364  	PskModes                         []uint8
   365  	PskIdentities                    []pskIdentity
   366  	PskBinders                       [][]byte
   367  }
   368  
   369  func (chm *ClientHelloMsg) getPrivatePtr() *clientHelloMsg {
   370  	if chm == nil {
   371  		return nil
   372  	} else {
   373  		return &clientHelloMsg{
   374  			raw:                          chm.Raw,
   375  			vers:                         chm.Vers,
   376  			random:                       chm.Random,
   377  			sessionId:                    chm.SessionId,
   378  			cipherSuites:                 chm.CipherSuites,
   379  			compressionMethods:           chm.CompressionMethods,
   380  			nextProtoNeg:                 chm.NextProtoNeg,
   381  			serverName:                   chm.ServerName,
   382  			ocspStapling:                 chm.OcspStapling,
   383  			scts:                         chm.Scts,
   384  			ems:                          chm.Ems,
   385  			supportedCurves:              chm.SupportedCurves,
   386  			supportedPoints:              chm.SupportedPoints,
   387  			ticketSupported:              chm.TicketSupported,
   388  			sessionTicket:                chm.SessionTicket,
   389  			supportedSignatureAlgorithms: chm.SupportedSignatureAlgorithms,
   390  			secureRenegotiation:          chm.SecureRenegotiation,
   391  			secureRenegotiationSupported: chm.SecureRenegotiationSupported,
   392  			alpnProtocols:                chm.AlpnProtocols,
   393  
   394  			supportedSignatureAlgorithmsCert: chm.SupportedSignatureAlgorithmsCert,
   395  			supportedVersions:                chm.SupportedVersions,
   396  			cookie:                           chm.Cookie,
   397  			keyShares:                        KeyShares(chm.KeyShares).ToPrivate(),
   398  			earlyData:                        chm.EarlyData,
   399  			pskModes:                         chm.PskModes,
   400  			pskIdentities:                    chm.PskIdentities,
   401  			pskBinders:                       chm.PskBinders,
   402  		}
   403  	}
   404  }
   405  
   406  func (chm *clientHelloMsg) getPublicPtr() *ClientHelloMsg {
   407  	if chm == nil {
   408  		return nil
   409  	} else {
   410  		return &ClientHelloMsg{
   411  			Raw:                          chm.raw,
   412  			Vers:                         chm.vers,
   413  			Random:                       chm.random,
   414  			SessionId:                    chm.sessionId,
   415  			CipherSuites:                 chm.cipherSuites,
   416  			CompressionMethods:           chm.compressionMethods,
   417  			NextProtoNeg:                 chm.nextProtoNeg,
   418  			ServerName:                   chm.serverName,
   419  			OcspStapling:                 chm.ocspStapling,
   420  			Scts:                         chm.scts,
   421  			Ems:                          chm.ems,
   422  			SupportedCurves:              chm.supportedCurves,
   423  			SupportedPoints:              chm.supportedPoints,
   424  			TicketSupported:              chm.ticketSupported,
   425  			SessionTicket:                chm.sessionTicket,
   426  			SupportedSignatureAlgorithms: chm.supportedSignatureAlgorithms,
   427  			SecureRenegotiation:          chm.secureRenegotiation,
   428  			SecureRenegotiationSupported: chm.secureRenegotiationSupported,
   429  			AlpnProtocols:                chm.alpnProtocols,
   430  
   431  			SupportedSignatureAlgorithmsCert: chm.supportedSignatureAlgorithmsCert,
   432  			SupportedVersions:                chm.supportedVersions,
   433  			Cookie:                           chm.cookie,
   434  			KeyShares:                        keyShares(chm.keyShares).ToPublic(),
   435  			EarlyData:                        chm.earlyData,
   436  			PskModes:                         chm.pskModes,
   437  			PskIdentities:                    chm.pskIdentities,
   438  			PskBinders:                       chm.pskBinders,
   439  		}
   440  	}
   441  }
   442  
   443  // A CipherSuite is a specific combination of key agreement, cipher and MAC
   444  // function. All cipher suites currently assume RSA key agreement.
   445  type CipherSuite struct {
   446  	Id uint16
   447  	// the lengths, in bytes, of the key material needed for each component.
   448  	KeyLen int
   449  	MacLen int
   450  	IvLen  int
   451  	Ka     func(version uint16) keyAgreement
   452  	// flags is a bitmask of the suite* values, above.
   453  	Flags  int
   454  	Cipher func(key, iv []byte, isRead bool) interface{}
   455  	Mac    func(version uint16, macKey []byte) macFunction
   456  	Aead   func(key, fixedNonce []byte) aead
   457  }
   458  
   459  func (cs *CipherSuite) getPrivatePtr() *cipherSuite {
   460  	if cs == nil {
   461  		return nil
   462  	} else {
   463  		return &cipherSuite{
   464  			id:     cs.Id,
   465  			keyLen: cs.KeyLen,
   466  			macLen: cs.MacLen,
   467  			ivLen:  cs.IvLen,
   468  			ka:     cs.Ka,
   469  			flags:  cs.Flags,
   470  			cipher: cs.Cipher,
   471  			mac:    cs.Mac,
   472  			aead:   cs.Aead,
   473  		}
   474  	}
   475  }
   476  
   477  func (cs *cipherSuite) getPublicObj() CipherSuite {
   478  	if cs == nil {
   479  		return CipherSuite{}
   480  	} else {
   481  		return CipherSuite{
   482  			Id:     cs.id,
   483  			KeyLen: cs.keyLen,
   484  			MacLen: cs.macLen,
   485  			IvLen:  cs.ivLen,
   486  			Ka:     cs.ka,
   487  			Flags:  cs.flags,
   488  			Cipher: cs.cipher,
   489  			Mac:    cs.mac,
   490  			Aead:   cs.aead,
   491  		}
   492  	}
   493  }
   494  
   495  // A FinishedHash calculates the hash of a set of handshake messages suitable
   496  // for including in a Finished message.
   497  type FinishedHash struct {
   498  	Client hash.Hash
   499  	Server hash.Hash
   500  
   501  	// Prior to TLS 1.2, an additional MD5 hash is required.
   502  	ClientMD5 hash.Hash
   503  	ServerMD5 hash.Hash
   504  
   505  	// In TLS 1.2, a full buffer is sadly required.
   506  	Buffer []byte
   507  
   508  	Version uint16
   509  	Prf     func(result, secret, label, seed []byte)
   510  }
   511  
   512  func (fh *FinishedHash) getPrivateObj() finishedHash {
   513  	if fh == nil {
   514  		return finishedHash{}
   515  	} else {
   516  		return finishedHash{
   517  			client:    fh.Client,
   518  			server:    fh.Server,
   519  			clientMD5: fh.ClientMD5,
   520  			serverMD5: fh.ServerMD5,
   521  			buffer:    fh.Buffer,
   522  			version:   fh.Version,
   523  			prf:       fh.Prf,
   524  		}
   525  	}
   526  }
   527  
   528  func (fh *finishedHash) getPublicObj() FinishedHash {
   529  	if fh == nil {
   530  		return FinishedHash{}
   531  	} else {
   532  		return FinishedHash{
   533  			Client:    fh.client,
   534  			Server:    fh.server,
   535  			ClientMD5: fh.clientMD5,
   536  			ServerMD5: fh.serverMD5,
   537  			Buffer:    fh.buffer,
   538  			Version:   fh.version,
   539  			Prf:       fh.prf}
   540  	}
   541  }
   542  
   543  // TLS 1.3 Key Share. See RFC 8446, Section 4.2.8.
   544  type KeyShare struct {
   545  	Group CurveID
   546  	Data  []byte
   547  }
   548  
   549  type KeyShares []KeyShare
   550  type keyShares []keyShare
   551  
   552  func (kss keyShares) ToPublic() []KeyShare {
   553  	var KSS []KeyShare
   554  	for _, ks := range kss {
   555  		KSS = append(KSS, KeyShare{Data: ks.data, Group: ks.group})
   556  	}
   557  	return KSS
   558  }
   559  func (KSS KeyShares) ToPrivate() []keyShare {
   560  	var kss []keyShare
   561  	for _, KS := range KSS {
   562  		kss = append(kss, keyShare{data: KS.Data, group: KS.Group})
   563  	}
   564  	return kss
   565  }
   566  
   567  // ClientSessionState is public, but all its fields are private. Let's add setters, getters and constructor
   568  
   569  // ClientSessionState contains the state needed by clients to resume TLS sessions.
   570  func MakeClientSessionState(
   571  	SessionTicket []uint8,
   572  	Vers uint16,
   573  	CipherSuite uint16,
   574  	MasterSecret []byte,
   575  	ServerCertificates []*x509.Certificate,
   576  	VerifiedChains [][]*x509.Certificate) *ClientSessionState {
   577  	css := ClientSessionState{sessionTicket: SessionTicket,
   578  		vers:               Vers,
   579  		cipherSuite:        CipherSuite,
   580  		masterSecret:       MasterSecret,
   581  		serverCertificates: ServerCertificates,
   582  		verifiedChains:     VerifiedChains}
   583  	return &css
   584  }
   585  
   586  // Encrypted ticket used for session resumption with server
   587  func (css *ClientSessionState) SessionTicket() []uint8 {
   588  	return css.sessionTicket
   589  }
   590  
   591  // SSL/TLS version negotiated for the session
   592  func (css *ClientSessionState) Vers() uint16 {
   593  	return css.vers
   594  }
   595  
   596  // Ciphersuite negotiated for the session
   597  func (css *ClientSessionState) CipherSuite() uint16 {
   598  	return css.cipherSuite
   599  }
   600  
   601  // MasterSecret generated by client on a full handshake
   602  func (css *ClientSessionState) MasterSecret() []byte {
   603  	return css.masterSecret
   604  }
   605  
   606  // Certificate chain presented by the server
   607  func (css *ClientSessionState) ServerCertificates() []*x509.Certificate {
   608  	return css.serverCertificates
   609  }
   610  
   611  // Certificate chains we built for verification
   612  func (css *ClientSessionState) VerifiedChains() [][]*x509.Certificate {
   613  	return css.verifiedChains
   614  }
   615  
   616  func (css *ClientSessionState) SetSessionTicket(SessionTicket []uint8) {
   617  	css.sessionTicket = SessionTicket
   618  }
   619  func (css *ClientSessionState) SetVers(Vers uint16) {
   620  	css.vers = Vers
   621  }
   622  func (css *ClientSessionState) SetCipherSuite(CipherSuite uint16) {
   623  	css.cipherSuite = CipherSuite
   624  }
   625  func (css *ClientSessionState) SetMasterSecret(MasterSecret []byte) {
   626  	css.masterSecret = MasterSecret
   627  }
   628  func (css *ClientSessionState) SetServerCertificates(ServerCertificates []*x509.Certificate) {
   629  	css.serverCertificates = ServerCertificates
   630  }
   631  func (css *ClientSessionState) SetVerifiedChains(VerifiedChains [][]*x509.Certificate) {
   632  	css.verifiedChains = VerifiedChains
   633  }