Alternative TLS implementation in Go
您最多选择25个主题 主题必须以字母或数字开头,可以包含连字符 (-),并且长度不得超过35个字符

406 行
12 KiB

  1. // Copyright 2010 The Go Authors. 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. package tls
  5. import (
  6. "crypto"
  7. "crypto/ecdsa"
  8. "crypto/elliptic"
  9. "crypto/md5"
  10. "crypto/rsa"
  11. "crypto/sha1"
  12. "crypto/x509"
  13. "encoding/asn1"
  14. "errors"
  15. "io"
  16. "math/big"
  17. )
  18. var errClientKeyExchange = errors.New("tls: invalid ClientKeyExchange message")
  19. var errServerKeyExchange = errors.New("tls: invalid ServerKeyExchange message")
  20. // rsaKeyAgreement implements the standard TLS key agreement where the client
  21. // encrypts the pre-master secret to the server's public key.
  22. type rsaKeyAgreement struct{}
  23. func (ka rsaKeyAgreement) generateServerKeyExchange(config *Config, cert *Certificate, clientHello *clientHelloMsg, hello *serverHelloMsg) (*serverKeyExchangeMsg, error) {
  24. return nil, nil
  25. }
  26. func (ka rsaKeyAgreement) processClientKeyExchange(config *Config, cert *Certificate, ckx *clientKeyExchangeMsg, version uint16) ([]byte, error) {
  27. if len(ckx.ciphertext) < 2 {
  28. return nil, errClientKeyExchange
  29. }
  30. ciphertext := ckx.ciphertext
  31. if version != VersionSSL30 {
  32. ciphertextLen := int(ckx.ciphertext[0])<<8 | int(ckx.ciphertext[1])
  33. if ciphertextLen != len(ckx.ciphertext)-2 {
  34. return nil, errClientKeyExchange
  35. }
  36. ciphertext = ckx.ciphertext[2:]
  37. }
  38. priv, ok := cert.PrivateKey.(crypto.Decrypter)
  39. if !ok {
  40. return nil, errors.New("tls: certificate private key does not implement crypto.Decrypter")
  41. }
  42. // Perform constant time RSA PKCS#1 v1.5 decryption
  43. preMasterSecret, err := priv.Decrypt(config.rand(), ciphertext, &rsa.PKCS1v15DecryptOptions{SessionKeyLen: 48})
  44. if err != nil {
  45. return nil, err
  46. }
  47. // We don't check the version number in the premaster secret. For one,
  48. // by checking it, we would leak information about the validity of the
  49. // encrypted pre-master secret. Secondly, it provides only a small
  50. // benefit against a downgrade attack and some implementations send the
  51. // wrong version anyway. See the discussion at the end of section
  52. // 7.4.7.1 of RFC 4346.
  53. return preMasterSecret, nil
  54. }
  55. func (ka rsaKeyAgreement) processServerKeyExchange(config *Config, clientHello *clientHelloMsg, serverHello *serverHelloMsg, cert *x509.Certificate, skx *serverKeyExchangeMsg) error {
  56. return errors.New("tls: unexpected ServerKeyExchange")
  57. }
  58. func (ka rsaKeyAgreement) generateClientKeyExchange(config *Config, clientHello *clientHelloMsg, cert *x509.Certificate) ([]byte, *clientKeyExchangeMsg, error) {
  59. preMasterSecret := make([]byte, 48)
  60. preMasterSecret[0] = byte(clientHello.vers >> 8)
  61. preMasterSecret[1] = byte(clientHello.vers)
  62. _, err := io.ReadFull(config.rand(), preMasterSecret[2:])
  63. if err != nil {
  64. return nil, nil, err
  65. }
  66. encrypted, err := rsa.EncryptPKCS1v15(config.rand(), cert.PublicKey.(*rsa.PublicKey), preMasterSecret)
  67. if err != nil {
  68. return nil, nil, err
  69. }
  70. ckx := new(clientKeyExchangeMsg)
  71. ckx.ciphertext = make([]byte, len(encrypted)+2)
  72. ckx.ciphertext[0] = byte(len(encrypted) >> 8)
  73. ckx.ciphertext[1] = byte(len(encrypted))
  74. copy(ckx.ciphertext[2:], encrypted)
  75. return preMasterSecret, ckx, nil
  76. }
  77. // sha1Hash calculates a SHA1 hash over the given byte slices.
  78. func sha1Hash(slices [][]byte) []byte {
  79. hsha1 := sha1.New()
  80. for _, slice := range slices {
  81. hsha1.Write(slice)
  82. }
  83. return hsha1.Sum(nil)
  84. }
  85. // md5SHA1Hash implements TLS 1.0's hybrid hash function which consists of the
  86. // concatenation of an MD5 and SHA1 hash.
  87. func md5SHA1Hash(slices [][]byte) []byte {
  88. md5sha1 := make([]byte, md5.Size+sha1.Size)
  89. hmd5 := md5.New()
  90. for _, slice := range slices {
  91. hmd5.Write(slice)
  92. }
  93. copy(md5sha1, hmd5.Sum(nil))
  94. copy(md5sha1[md5.Size:], sha1Hash(slices))
  95. return md5sha1
  96. }
  97. // hashForServerKeyExchange hashes the given slices and returns their digest
  98. // and the identifier of the hash function used. The sigAndHash argument is
  99. // only used for >= TLS 1.2 and precisely identifies the hash function to use.
  100. func hashForServerKeyExchange(sigAndHash signatureAndHash, version uint16, slices ...[]byte) ([]byte, crypto.Hash, error) {
  101. if version >= VersionTLS12 {
  102. if !isSupportedSignatureAndHash(sigAndHash, supportedSignatureAlgorithms) {
  103. return nil, crypto.Hash(0), errors.New("tls: unsupported hash function used by peer")
  104. }
  105. hashFunc, err := lookupTLSHash(sigAndHash.hash)
  106. if err != nil {
  107. return nil, crypto.Hash(0), err
  108. }
  109. h := hashFunc.New()
  110. for _, slice := range slices {
  111. h.Write(slice)
  112. }
  113. digest := h.Sum(nil)
  114. return digest, hashFunc, nil
  115. }
  116. if sigAndHash.signature == signatureECDSA {
  117. return sha1Hash(slices), crypto.SHA1, nil
  118. }
  119. return md5SHA1Hash(slices), crypto.MD5SHA1, nil
  120. }
  121. // pickTLS12HashForSignature returns a TLS 1.2 hash identifier for signing a
  122. // ServerKeyExchange given the signature type being used and the client's
  123. // advertised list of supported signature and hash combinations.
  124. func pickTLS12HashForSignature(sigType uint8, clientList []signatureAndHash) (uint8, error) {
  125. if len(clientList) == 0 {
  126. // If the client didn't specify any signature_algorithms
  127. // extension then we can assume that it supports SHA1. See
  128. // http://tools.ietf.org/html/rfc5246#section-7.4.1.4.1
  129. return hashSHA1, nil
  130. }
  131. for _, sigAndHash := range clientList {
  132. if sigAndHash.signature != sigType {
  133. continue
  134. }
  135. if isSupportedSignatureAndHash(sigAndHash, supportedSignatureAlgorithms) {
  136. return sigAndHash.hash, nil
  137. }
  138. }
  139. return 0, errors.New("tls: client doesn't support any common hash functions")
  140. }
  141. func curveForCurveID(id CurveID) (elliptic.Curve, bool) {
  142. switch id {
  143. case CurveP256:
  144. return elliptic.P256(), true
  145. case CurveP384:
  146. return elliptic.P384(), true
  147. case CurveP521:
  148. return elliptic.P521(), true
  149. default:
  150. return nil, false
  151. }
  152. }
  153. // ecdheRSAKeyAgreement implements a TLS key agreement where the server
  154. // generates a ephemeral EC public/private key pair and signs it. The
  155. // pre-master secret is then calculated using ECDH. The signature may
  156. // either be ECDSA or RSA.
  157. type ecdheKeyAgreement struct {
  158. version uint16
  159. sigType uint8
  160. privateKey []byte
  161. curve elliptic.Curve
  162. x, y *big.Int
  163. }
  164. func (ka *ecdheKeyAgreement) generateServerKeyExchange(config *Config, cert *Certificate, clientHello *clientHelloMsg, hello *serverHelloMsg) (*serverKeyExchangeMsg, error) {
  165. var curveid CurveID
  166. preferredCurves := config.curvePreferences()
  167. NextCandidate:
  168. for _, candidate := range preferredCurves {
  169. for _, c := range clientHello.supportedCurves {
  170. if candidate == c {
  171. curveid = c
  172. break NextCandidate
  173. }
  174. }
  175. }
  176. if curveid == 0 {
  177. return nil, errors.New("tls: no supported elliptic curves offered")
  178. }
  179. var ok bool
  180. if ka.curve, ok = curveForCurveID(curveid); !ok {
  181. return nil, errors.New("tls: preferredCurves includes unsupported curve")
  182. }
  183. var x, y *big.Int
  184. var err error
  185. ka.privateKey, x, y, err = elliptic.GenerateKey(ka.curve, config.rand())
  186. if err != nil {
  187. return nil, err
  188. }
  189. ecdhePublic := elliptic.Marshal(ka.curve, x, y)
  190. // http://tools.ietf.org/html/rfc4492#section-5.4
  191. serverECDHParams := make([]byte, 1+2+1+len(ecdhePublic))
  192. serverECDHParams[0] = 3 // named curve
  193. serverECDHParams[1] = byte(curveid >> 8)
  194. serverECDHParams[2] = byte(curveid)
  195. serverECDHParams[3] = byte(len(ecdhePublic))
  196. copy(serverECDHParams[4:], ecdhePublic)
  197. sigAndHash := signatureAndHash{signature: ka.sigType}
  198. if ka.version >= VersionTLS12 {
  199. if sigAndHash.hash, err = pickTLS12HashForSignature(ka.sigType, clientHello.signatureAndHashes); err != nil {
  200. return nil, err
  201. }
  202. }
  203. digest, hashFunc, err := hashForServerKeyExchange(sigAndHash, ka.version, clientHello.random, hello.random, serverECDHParams)
  204. if err != nil {
  205. return nil, err
  206. }
  207. priv, ok := cert.PrivateKey.(crypto.Signer)
  208. if !ok {
  209. return nil, errors.New("tls: certificate private key does not implement crypto.Signer")
  210. }
  211. var sig []byte
  212. switch ka.sigType {
  213. case signatureECDSA:
  214. _, ok := priv.Public().(*ecdsa.PublicKey)
  215. if !ok {
  216. return nil, errors.New("ECDHE ECDSA requires an ECDSA server key")
  217. }
  218. case signatureRSA:
  219. _, ok := priv.Public().(*rsa.PublicKey)
  220. if !ok {
  221. return nil, errors.New("ECDHE RSA requires a RSA server key")
  222. }
  223. default:
  224. return nil, errors.New("unknown ECDHE signature algorithm")
  225. }
  226. sig, err = priv.Sign(config.rand(), digest, hashFunc)
  227. if err != nil {
  228. return nil, errors.New("failed to sign ECDHE parameters: " + err.Error())
  229. }
  230. skx := new(serverKeyExchangeMsg)
  231. sigAndHashLen := 0
  232. if ka.version >= VersionTLS12 {
  233. sigAndHashLen = 2
  234. }
  235. skx.key = make([]byte, len(serverECDHParams)+sigAndHashLen+2+len(sig))
  236. copy(skx.key, serverECDHParams)
  237. k := skx.key[len(serverECDHParams):]
  238. if ka.version >= VersionTLS12 {
  239. k[0] = sigAndHash.hash
  240. k[1] = sigAndHash.signature
  241. k = k[2:]
  242. }
  243. k[0] = byte(len(sig) >> 8)
  244. k[1] = byte(len(sig))
  245. copy(k[2:], sig)
  246. return skx, nil
  247. }
  248. func (ka *ecdheKeyAgreement) processClientKeyExchange(config *Config, cert *Certificate, ckx *clientKeyExchangeMsg, version uint16) ([]byte, error) {
  249. if len(ckx.ciphertext) == 0 || int(ckx.ciphertext[0]) != len(ckx.ciphertext)-1 {
  250. return nil, errClientKeyExchange
  251. }
  252. x, y := elliptic.Unmarshal(ka.curve, ckx.ciphertext[1:])
  253. if x == nil {
  254. return nil, errClientKeyExchange
  255. }
  256. if !ka.curve.IsOnCurve(x, y) {
  257. return nil, errClientKeyExchange
  258. }
  259. x, _ = ka.curve.ScalarMult(x, y, ka.privateKey)
  260. preMasterSecret := make([]byte, (ka.curve.Params().BitSize+7)>>3)
  261. xBytes := x.Bytes()
  262. copy(preMasterSecret[len(preMasterSecret)-len(xBytes):], xBytes)
  263. return preMasterSecret, nil
  264. }
  265. func (ka *ecdheKeyAgreement) processServerKeyExchange(config *Config, clientHello *clientHelloMsg, serverHello *serverHelloMsg, cert *x509.Certificate, skx *serverKeyExchangeMsg) error {
  266. if len(skx.key) < 4 {
  267. return errServerKeyExchange
  268. }
  269. if skx.key[0] != 3 { // named curve
  270. return errors.New("tls: server selected unsupported curve")
  271. }
  272. curveid := CurveID(skx.key[1])<<8 | CurveID(skx.key[2])
  273. var ok bool
  274. if ka.curve, ok = curveForCurveID(curveid); !ok {
  275. return errors.New("tls: server selected unsupported curve")
  276. }
  277. publicLen := int(skx.key[3])
  278. if publicLen+4 > len(skx.key) {
  279. return errServerKeyExchange
  280. }
  281. ka.x, ka.y = elliptic.Unmarshal(ka.curve, skx.key[4:4+publicLen])
  282. if ka.x == nil {
  283. return errServerKeyExchange
  284. }
  285. if !ka.curve.IsOnCurve(ka.x, ka.y) {
  286. return errServerKeyExchange
  287. }
  288. serverECDHParams := skx.key[:4+publicLen]
  289. sig := skx.key[4+publicLen:]
  290. if len(sig) < 2 {
  291. return errServerKeyExchange
  292. }
  293. sigAndHash := signatureAndHash{signature: ka.sigType}
  294. if ka.version >= VersionTLS12 {
  295. // handle SignatureAndHashAlgorithm
  296. sigAndHash = signatureAndHash{hash: sig[0], signature: sig[1]}
  297. if sigAndHash.signature != ka.sigType {
  298. return errServerKeyExchange
  299. }
  300. sig = sig[2:]
  301. if len(sig) < 2 {
  302. return errServerKeyExchange
  303. }
  304. }
  305. sigLen := int(sig[0])<<8 | int(sig[1])
  306. if sigLen+2 != len(sig) {
  307. return errServerKeyExchange
  308. }
  309. sig = sig[2:]
  310. digest, hashFunc, err := hashForServerKeyExchange(sigAndHash, ka.version, clientHello.random, serverHello.random, serverECDHParams)
  311. if err != nil {
  312. return err
  313. }
  314. switch ka.sigType {
  315. case signatureECDSA:
  316. pubKey, ok := cert.PublicKey.(*ecdsa.PublicKey)
  317. if !ok {
  318. return errors.New("ECDHE ECDSA requires a ECDSA server public key")
  319. }
  320. ecdsaSig := new(ecdsaSignature)
  321. if _, err := asn1.Unmarshal(sig, ecdsaSig); err != nil {
  322. return err
  323. }
  324. if ecdsaSig.R.Sign() <= 0 || ecdsaSig.S.Sign() <= 0 {
  325. return errors.New("ECDSA signature contained zero or negative values")
  326. }
  327. if !ecdsa.Verify(pubKey, digest, ecdsaSig.R, ecdsaSig.S) {
  328. return errors.New("ECDSA verification failure")
  329. }
  330. case signatureRSA:
  331. pubKey, ok := cert.PublicKey.(*rsa.PublicKey)
  332. if !ok {
  333. return errors.New("ECDHE RSA requires a RSA server public key")
  334. }
  335. if err := rsa.VerifyPKCS1v15(pubKey, hashFunc, digest, sig); err != nil {
  336. return err
  337. }
  338. default:
  339. return errors.New("unknown ECDHE signature algorithm")
  340. }
  341. return nil
  342. }
  343. func (ka *ecdheKeyAgreement) generateClientKeyExchange(config *Config, clientHello *clientHelloMsg, cert *x509.Certificate) ([]byte, *clientKeyExchangeMsg, error) {
  344. if ka.curve == nil {
  345. return nil, nil, errors.New("missing ServerKeyExchange message")
  346. }
  347. priv, mx, my, err := elliptic.GenerateKey(ka.curve, config.rand())
  348. if err != nil {
  349. return nil, nil, err
  350. }
  351. x, _ := ka.curve.ScalarMult(ka.x, ka.y, priv)
  352. preMasterSecret := make([]byte, (ka.curve.Params().BitSize+7)>>3)
  353. xBytes := x.Bytes()
  354. copy(preMasterSecret[len(preMasterSecret)-len(xBytes):], xBytes)
  355. serialized := elliptic.Marshal(ka.curve, mx, my)
  356. ckx := new(clientKeyExchangeMsg)
  357. ckx.ciphertext = make([]byte, 1+len(serialized))
  358. ckx.ciphertext[0] = byte(len(serialized))
  359. copy(ckx.ciphertext[1:], serialized)
  360. return preMasterSecret, ckx, nil
  361. }