Nelze vybrat více než 25 témat Téma musí začínat písmenem nebo číslem, může obsahovat pomlčky („-“) a může být dlouhé až 35 znaků.
 
 
 
 
 
 

2734 řádky
70 KiB

  1. package main
  2. import (
  3. "bytes"
  4. "crypto/ecdsa"
  5. "crypto/elliptic"
  6. "crypto/x509"
  7. "encoding/base64"
  8. "encoding/pem"
  9. "flag"
  10. "fmt"
  11. "io"
  12. "io/ioutil"
  13. "net"
  14. "os"
  15. "os/exec"
  16. "path"
  17. "runtime"
  18. "strconv"
  19. "strings"
  20. "sync"
  21. "syscall"
  22. "time"
  23. )
  24. var (
  25. useValgrind = flag.Bool("valgrind", false, "If true, run code under valgrind")
  26. useGDB = flag.Bool("gdb", false, "If true, run BoringSSL code under gdb")
  27. flagDebug *bool = flag.Bool("debug", false, "Hexdump the contents of the connection")
  28. mallocTest *int64 = flag.Int64("malloc-test", -1, "If non-negative, run each test with each malloc in turn failing from the given number onwards.")
  29. mallocTestDebug *bool = flag.Bool("malloc-test-debug", false, "If true, ask bssl_shim to abort rather than fail a malloc. This can be used with a specific value for --malloc-test to identity the malloc failing that is causing problems.")
  30. )
  31. const (
  32. rsaCertificateFile = "cert.pem"
  33. ecdsaCertificateFile = "ecdsa_cert.pem"
  34. )
  35. const (
  36. rsaKeyFile = "key.pem"
  37. ecdsaKeyFile = "ecdsa_key.pem"
  38. channelIDKeyFile = "channel_id_key.pem"
  39. )
  40. var rsaCertificate, ecdsaCertificate Certificate
  41. var channelIDKey *ecdsa.PrivateKey
  42. var channelIDBytes []byte
  43. var testOCSPResponse = []byte{1, 2, 3, 4}
  44. var testSCTList = []byte{5, 6, 7, 8}
  45. func initCertificates() {
  46. var err error
  47. rsaCertificate, err = LoadX509KeyPair(rsaCertificateFile, rsaKeyFile)
  48. if err != nil {
  49. panic(err)
  50. }
  51. rsaCertificate.OCSPStaple = testOCSPResponse
  52. rsaCertificate.SignedCertificateTimestampList = testSCTList
  53. ecdsaCertificate, err = LoadX509KeyPair(ecdsaCertificateFile, ecdsaKeyFile)
  54. if err != nil {
  55. panic(err)
  56. }
  57. ecdsaCertificate.OCSPStaple = testOCSPResponse
  58. ecdsaCertificate.SignedCertificateTimestampList = testSCTList
  59. channelIDPEMBlock, err := ioutil.ReadFile(channelIDKeyFile)
  60. if err != nil {
  61. panic(err)
  62. }
  63. channelIDDERBlock, _ := pem.Decode(channelIDPEMBlock)
  64. if channelIDDERBlock.Type != "EC PRIVATE KEY" {
  65. panic("bad key type")
  66. }
  67. channelIDKey, err = x509.ParseECPrivateKey(channelIDDERBlock.Bytes)
  68. if err != nil {
  69. panic(err)
  70. }
  71. if channelIDKey.Curve != elliptic.P256() {
  72. panic("bad curve")
  73. }
  74. channelIDBytes = make([]byte, 64)
  75. writeIntPadded(channelIDBytes[:32], channelIDKey.X)
  76. writeIntPadded(channelIDBytes[32:], channelIDKey.Y)
  77. }
  78. var certificateOnce sync.Once
  79. func getRSACertificate() Certificate {
  80. certificateOnce.Do(initCertificates)
  81. return rsaCertificate
  82. }
  83. func getECDSACertificate() Certificate {
  84. certificateOnce.Do(initCertificates)
  85. return ecdsaCertificate
  86. }
  87. type testType int
  88. const (
  89. clientTest testType = iota
  90. serverTest
  91. )
  92. type protocol int
  93. const (
  94. tls protocol = iota
  95. dtls
  96. )
  97. const (
  98. alpn = 1
  99. npn = 2
  100. )
  101. type testCase struct {
  102. testType testType
  103. protocol protocol
  104. name string
  105. config Config
  106. shouldFail bool
  107. expectedError string
  108. // expectedLocalError, if not empty, contains a substring that must be
  109. // found in the local error.
  110. expectedLocalError string
  111. // expectedVersion, if non-zero, specifies the TLS version that must be
  112. // negotiated.
  113. expectedVersion uint16
  114. // expectedResumeVersion, if non-zero, specifies the TLS version that
  115. // must be negotiated on resumption. If zero, expectedVersion is used.
  116. expectedResumeVersion uint16
  117. // expectChannelID controls whether the connection should have
  118. // negotiated a Channel ID with channelIDKey.
  119. expectChannelID bool
  120. // expectedNextProto controls whether the connection should
  121. // negotiate a next protocol via NPN or ALPN.
  122. expectedNextProto string
  123. // expectedNextProtoType, if non-zero, is the expected next
  124. // protocol negotiation mechanism.
  125. expectedNextProtoType int
  126. // expectedSRTPProtectionProfile is the DTLS-SRTP profile that
  127. // should be negotiated. If zero, none should be negotiated.
  128. expectedSRTPProtectionProfile uint16
  129. // messageLen is the length, in bytes, of the test message that will be
  130. // sent.
  131. messageLen int
  132. // certFile is the path to the certificate to use for the server.
  133. certFile string
  134. // keyFile is the path to the private key to use for the server.
  135. keyFile string
  136. // resumeSession controls whether a second connection should be tested
  137. // which attempts to resume the first session.
  138. resumeSession bool
  139. // resumeConfig, if not nil, points to a Config to be used on
  140. // resumption. Unless newSessionsOnResume is set,
  141. // SessionTicketKey, ServerSessionCache, and
  142. // ClientSessionCache are copied from the initial connection's
  143. // config. If nil, the initial connection's config is used.
  144. resumeConfig *Config
  145. // newSessionsOnResume, if true, will cause resumeConfig to
  146. // use a different session resumption context.
  147. newSessionsOnResume bool
  148. // sendPrefix sends a prefix on the socket before actually performing a
  149. // handshake.
  150. sendPrefix string
  151. // shimWritesFirst controls whether the shim sends an initial "hello"
  152. // message before doing a roundtrip with the runner.
  153. shimWritesFirst bool
  154. // renegotiate indicates the the connection should be renegotiated
  155. // during the exchange.
  156. renegotiate bool
  157. // renegotiateCiphers is a list of ciphersuite ids that will be
  158. // switched in just before renegotiation.
  159. renegotiateCiphers []uint16
  160. // replayWrites, if true, configures the underlying transport
  161. // to replay every write it makes in DTLS tests.
  162. replayWrites bool
  163. // damageFirstWrite, if true, configures the underlying transport to
  164. // damage the final byte of the first application data write.
  165. damageFirstWrite bool
  166. // flags, if not empty, contains a list of command-line flags that will
  167. // be passed to the shim program.
  168. flags []string
  169. }
  170. var testCases = []testCase{
  171. {
  172. name: "BadRSASignature",
  173. config: Config{
  174. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  175. Bugs: ProtocolBugs{
  176. InvalidSKXSignature: true,
  177. },
  178. },
  179. shouldFail: true,
  180. expectedError: ":BAD_SIGNATURE:",
  181. },
  182. {
  183. name: "BadECDSASignature",
  184. config: Config{
  185. CipherSuites: []uint16{TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256},
  186. Bugs: ProtocolBugs{
  187. InvalidSKXSignature: true,
  188. },
  189. Certificates: []Certificate{getECDSACertificate()},
  190. },
  191. shouldFail: true,
  192. expectedError: ":BAD_SIGNATURE:",
  193. },
  194. {
  195. name: "BadECDSACurve",
  196. config: Config{
  197. CipherSuites: []uint16{TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256},
  198. Bugs: ProtocolBugs{
  199. InvalidSKXCurve: true,
  200. },
  201. Certificates: []Certificate{getECDSACertificate()},
  202. },
  203. shouldFail: true,
  204. expectedError: ":WRONG_CURVE:",
  205. },
  206. {
  207. testType: serverTest,
  208. name: "BadRSAVersion",
  209. config: Config{
  210. CipherSuites: []uint16{TLS_RSA_WITH_RC4_128_SHA},
  211. Bugs: ProtocolBugs{
  212. RsaClientKeyExchangeVersion: VersionTLS11,
  213. },
  214. },
  215. shouldFail: true,
  216. expectedError: ":DECRYPTION_FAILED_OR_BAD_RECORD_MAC:",
  217. },
  218. {
  219. name: "NoFallbackSCSV",
  220. config: Config{
  221. Bugs: ProtocolBugs{
  222. FailIfNotFallbackSCSV: true,
  223. },
  224. },
  225. shouldFail: true,
  226. expectedLocalError: "no fallback SCSV found",
  227. },
  228. {
  229. name: "SendFallbackSCSV",
  230. config: Config{
  231. Bugs: ProtocolBugs{
  232. FailIfNotFallbackSCSV: true,
  233. },
  234. },
  235. flags: []string{"-fallback-scsv"},
  236. },
  237. {
  238. name: "ClientCertificateTypes",
  239. config: Config{
  240. ClientAuth: RequestClientCert,
  241. ClientCertificateTypes: []byte{
  242. CertTypeDSSSign,
  243. CertTypeRSASign,
  244. CertTypeECDSASign,
  245. },
  246. },
  247. flags: []string{
  248. "-expect-certificate-types",
  249. base64.StdEncoding.EncodeToString([]byte{
  250. CertTypeDSSSign,
  251. CertTypeRSASign,
  252. CertTypeECDSASign,
  253. }),
  254. },
  255. },
  256. {
  257. name: "NoClientCertificate",
  258. config: Config{
  259. ClientAuth: RequireAnyClientCert,
  260. },
  261. shouldFail: true,
  262. expectedLocalError: "client didn't provide a certificate",
  263. },
  264. {
  265. name: "UnauthenticatedECDH",
  266. config: Config{
  267. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  268. Bugs: ProtocolBugs{
  269. UnauthenticatedECDH: true,
  270. },
  271. },
  272. shouldFail: true,
  273. expectedError: ":UNEXPECTED_MESSAGE:",
  274. },
  275. {
  276. name: "SkipServerKeyExchange",
  277. config: Config{
  278. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  279. Bugs: ProtocolBugs{
  280. SkipServerKeyExchange: true,
  281. },
  282. },
  283. shouldFail: true,
  284. expectedError: ":UNEXPECTED_MESSAGE:",
  285. },
  286. {
  287. name: "SkipChangeCipherSpec-Client",
  288. config: Config{
  289. Bugs: ProtocolBugs{
  290. SkipChangeCipherSpec: true,
  291. },
  292. },
  293. shouldFail: true,
  294. expectedError: ":HANDSHAKE_RECORD_BEFORE_CCS:",
  295. },
  296. {
  297. testType: serverTest,
  298. name: "SkipChangeCipherSpec-Server",
  299. config: Config{
  300. Bugs: ProtocolBugs{
  301. SkipChangeCipherSpec: true,
  302. },
  303. },
  304. shouldFail: true,
  305. expectedError: ":HANDSHAKE_RECORD_BEFORE_CCS:",
  306. },
  307. {
  308. testType: serverTest,
  309. name: "SkipChangeCipherSpec-Server-NPN",
  310. config: Config{
  311. NextProtos: []string{"bar"},
  312. Bugs: ProtocolBugs{
  313. SkipChangeCipherSpec: true,
  314. },
  315. },
  316. flags: []string{
  317. "-advertise-npn", "\x03foo\x03bar\x03baz",
  318. },
  319. shouldFail: true,
  320. expectedError: ":HANDSHAKE_RECORD_BEFORE_CCS:",
  321. },
  322. {
  323. name: "FragmentAcrossChangeCipherSpec-Client",
  324. config: Config{
  325. Bugs: ProtocolBugs{
  326. FragmentAcrossChangeCipherSpec: true,
  327. },
  328. },
  329. shouldFail: true,
  330. expectedError: ":HANDSHAKE_RECORD_BEFORE_CCS:",
  331. },
  332. {
  333. testType: serverTest,
  334. name: "FragmentAcrossChangeCipherSpec-Server",
  335. config: Config{
  336. Bugs: ProtocolBugs{
  337. FragmentAcrossChangeCipherSpec: true,
  338. },
  339. },
  340. shouldFail: true,
  341. expectedError: ":HANDSHAKE_RECORD_BEFORE_CCS:",
  342. },
  343. {
  344. testType: serverTest,
  345. name: "FragmentAcrossChangeCipherSpec-Server-NPN",
  346. config: Config{
  347. NextProtos: []string{"bar"},
  348. Bugs: ProtocolBugs{
  349. FragmentAcrossChangeCipherSpec: true,
  350. },
  351. },
  352. flags: []string{
  353. "-advertise-npn", "\x03foo\x03bar\x03baz",
  354. },
  355. shouldFail: true,
  356. expectedError: ":HANDSHAKE_RECORD_BEFORE_CCS:",
  357. },
  358. {
  359. testType: serverTest,
  360. name: "FragmentAlert",
  361. config: Config{
  362. Bugs: ProtocolBugs{
  363. FragmentAlert: true,
  364. SendSpuriousAlert: true,
  365. },
  366. },
  367. shouldFail: true,
  368. expectedError: ":BAD_ALERT:",
  369. },
  370. {
  371. testType: serverTest,
  372. name: "EarlyChangeCipherSpec-server-1",
  373. config: Config{
  374. Bugs: ProtocolBugs{
  375. EarlyChangeCipherSpec: 1,
  376. },
  377. },
  378. shouldFail: true,
  379. expectedError: ":CCS_RECEIVED_EARLY:",
  380. },
  381. {
  382. testType: serverTest,
  383. name: "EarlyChangeCipherSpec-server-2",
  384. config: Config{
  385. Bugs: ProtocolBugs{
  386. EarlyChangeCipherSpec: 2,
  387. },
  388. },
  389. shouldFail: true,
  390. expectedError: ":CCS_RECEIVED_EARLY:",
  391. },
  392. {
  393. name: "SkipNewSessionTicket",
  394. config: Config{
  395. Bugs: ProtocolBugs{
  396. SkipNewSessionTicket: true,
  397. },
  398. },
  399. shouldFail: true,
  400. expectedError: ":CCS_RECEIVED_EARLY:",
  401. },
  402. {
  403. testType: serverTest,
  404. name: "FallbackSCSV",
  405. config: Config{
  406. MaxVersion: VersionTLS11,
  407. Bugs: ProtocolBugs{
  408. SendFallbackSCSV: true,
  409. },
  410. },
  411. shouldFail: true,
  412. expectedError: ":INAPPROPRIATE_FALLBACK:",
  413. },
  414. {
  415. testType: serverTest,
  416. name: "FallbackSCSV-VersionMatch",
  417. config: Config{
  418. Bugs: ProtocolBugs{
  419. SendFallbackSCSV: true,
  420. },
  421. },
  422. },
  423. {
  424. testType: serverTest,
  425. name: "FragmentedClientVersion",
  426. config: Config{
  427. Bugs: ProtocolBugs{
  428. MaxHandshakeRecordLength: 1,
  429. FragmentClientVersion: true,
  430. },
  431. },
  432. expectedVersion: VersionTLS12,
  433. },
  434. {
  435. testType: serverTest,
  436. name: "MinorVersionTolerance",
  437. config: Config{
  438. Bugs: ProtocolBugs{
  439. SendClientVersion: 0x03ff,
  440. },
  441. },
  442. expectedVersion: VersionTLS12,
  443. },
  444. {
  445. testType: serverTest,
  446. name: "MajorVersionTolerance",
  447. config: Config{
  448. Bugs: ProtocolBugs{
  449. SendClientVersion: 0x0400,
  450. },
  451. },
  452. expectedVersion: VersionTLS12,
  453. },
  454. {
  455. testType: serverTest,
  456. name: "VersionTooLow",
  457. config: Config{
  458. Bugs: ProtocolBugs{
  459. SendClientVersion: 0x0200,
  460. },
  461. },
  462. shouldFail: true,
  463. expectedError: ":UNSUPPORTED_PROTOCOL:",
  464. },
  465. {
  466. testType: serverTest,
  467. name: "HttpGET",
  468. sendPrefix: "GET / HTTP/1.0\n",
  469. shouldFail: true,
  470. expectedError: ":HTTP_REQUEST:",
  471. },
  472. {
  473. testType: serverTest,
  474. name: "HttpPOST",
  475. sendPrefix: "POST / HTTP/1.0\n",
  476. shouldFail: true,
  477. expectedError: ":HTTP_REQUEST:",
  478. },
  479. {
  480. testType: serverTest,
  481. name: "HttpHEAD",
  482. sendPrefix: "HEAD / HTTP/1.0\n",
  483. shouldFail: true,
  484. expectedError: ":HTTP_REQUEST:",
  485. },
  486. {
  487. testType: serverTest,
  488. name: "HttpPUT",
  489. sendPrefix: "PUT / HTTP/1.0\n",
  490. shouldFail: true,
  491. expectedError: ":HTTP_REQUEST:",
  492. },
  493. {
  494. testType: serverTest,
  495. name: "HttpCONNECT",
  496. sendPrefix: "CONNECT www.google.com:443 HTTP/1.0\n",
  497. shouldFail: true,
  498. expectedError: ":HTTPS_PROXY_REQUEST:",
  499. },
  500. {
  501. testType: serverTest,
  502. name: "Garbage",
  503. sendPrefix: "blah",
  504. shouldFail: true,
  505. expectedError: ":UNKNOWN_PROTOCOL:",
  506. },
  507. {
  508. name: "SkipCipherVersionCheck",
  509. config: Config{
  510. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_GCM_SHA256},
  511. MaxVersion: VersionTLS11,
  512. Bugs: ProtocolBugs{
  513. SkipCipherVersionCheck: true,
  514. },
  515. },
  516. shouldFail: true,
  517. expectedError: ":WRONG_CIPHER_RETURNED:",
  518. },
  519. {
  520. name: "RSAServerKeyExchange",
  521. config: Config{
  522. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_CBC_SHA},
  523. Bugs: ProtocolBugs{
  524. RSAServerKeyExchange: true,
  525. },
  526. },
  527. shouldFail: true,
  528. expectedError: ":UNEXPECTED_MESSAGE:",
  529. },
  530. {
  531. name: "DisableEverything",
  532. flags: []string{"-no-tls12", "-no-tls11", "-no-tls1", "-no-ssl3"},
  533. shouldFail: true,
  534. expectedError: ":WRONG_SSL_VERSION:",
  535. },
  536. {
  537. protocol: dtls,
  538. name: "DisableEverything-DTLS",
  539. flags: []string{"-no-tls12", "-no-tls1"},
  540. shouldFail: true,
  541. expectedError: ":WRONG_SSL_VERSION:",
  542. },
  543. {
  544. name: "NoSharedCipher",
  545. config: Config{
  546. CipherSuites: []uint16{},
  547. },
  548. shouldFail: true,
  549. expectedError: ":HANDSHAKE_FAILURE_ON_CLIENT_HELLO:",
  550. },
  551. {
  552. protocol: dtls,
  553. testType: serverTest,
  554. name: "MTU",
  555. config: Config{
  556. Bugs: ProtocolBugs{
  557. MaxPacketLength: 256,
  558. },
  559. },
  560. flags: []string{"-mtu", "256"},
  561. },
  562. {
  563. protocol: dtls,
  564. testType: serverTest,
  565. name: "MTUExceeded",
  566. config: Config{
  567. Bugs: ProtocolBugs{
  568. MaxPacketLength: 255,
  569. },
  570. },
  571. flags: []string{"-mtu", "256"},
  572. shouldFail: true,
  573. expectedLocalError: "dtls: exceeded maximum packet length",
  574. },
  575. {
  576. name: "CertMismatchRSA",
  577. config: Config{
  578. CipherSuites: []uint16{TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256},
  579. Certificates: []Certificate{getECDSACertificate()},
  580. Bugs: ProtocolBugs{
  581. SendCipherSuite: TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,
  582. },
  583. },
  584. shouldFail: true,
  585. expectedError: ":WRONG_CERTIFICATE_TYPE:",
  586. },
  587. {
  588. name: "CertMismatchECDSA",
  589. config: Config{
  590. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  591. Certificates: []Certificate{getRSACertificate()},
  592. Bugs: ProtocolBugs{
  593. SendCipherSuite: TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,
  594. },
  595. },
  596. shouldFail: true,
  597. expectedError: ":WRONG_CERTIFICATE_TYPE:",
  598. },
  599. {
  600. name: "TLSFatalBadPackets",
  601. damageFirstWrite: true,
  602. shouldFail: true,
  603. expectedError: ":DECRYPTION_FAILED_OR_BAD_RECORD_MAC:",
  604. },
  605. {
  606. protocol: dtls,
  607. name: "DTLSIgnoreBadPackets",
  608. damageFirstWrite: true,
  609. },
  610. {
  611. protocol: dtls,
  612. name: "DTLSIgnoreBadPackets-Async",
  613. damageFirstWrite: true,
  614. flags: []string{"-async"},
  615. },
  616. {
  617. name: "AppDataAfterChangeCipherSpec",
  618. config: Config{
  619. Bugs: ProtocolBugs{
  620. AppDataAfterChangeCipherSpec: []byte("TEST MESSAGE"),
  621. },
  622. },
  623. shouldFail: true,
  624. expectedError: ":DATA_BETWEEN_CCS_AND_FINISHED:",
  625. },
  626. {
  627. protocol: dtls,
  628. name: "AppDataAfterChangeCipherSpec-DTLS",
  629. config: Config{
  630. Bugs: ProtocolBugs{
  631. AppDataAfterChangeCipherSpec: []byte("TEST MESSAGE"),
  632. },
  633. },
  634. },
  635. }
  636. func doExchange(test *testCase, config *Config, conn net.Conn, messageLen int, isResume bool) error {
  637. var connDebug *recordingConn
  638. var connDamage *damageAdaptor
  639. if *flagDebug {
  640. connDebug = &recordingConn{Conn: conn}
  641. conn = connDebug
  642. defer func() {
  643. connDebug.WriteTo(os.Stdout)
  644. }()
  645. }
  646. if test.protocol == dtls {
  647. config.Bugs.PacketAdaptor = newPacketAdaptor(conn)
  648. conn = config.Bugs.PacketAdaptor
  649. if test.replayWrites {
  650. conn = newReplayAdaptor(conn)
  651. }
  652. }
  653. if test.damageFirstWrite {
  654. connDamage = newDamageAdaptor(conn)
  655. conn = connDamage
  656. }
  657. if test.sendPrefix != "" {
  658. if _, err := conn.Write([]byte(test.sendPrefix)); err != nil {
  659. return err
  660. }
  661. }
  662. var tlsConn *Conn
  663. if test.testType == clientTest {
  664. if test.protocol == dtls {
  665. tlsConn = DTLSServer(conn, config)
  666. } else {
  667. tlsConn = Server(conn, config)
  668. }
  669. } else {
  670. config.InsecureSkipVerify = true
  671. if test.protocol == dtls {
  672. tlsConn = DTLSClient(conn, config)
  673. } else {
  674. tlsConn = Client(conn, config)
  675. }
  676. }
  677. if err := tlsConn.Handshake(); err != nil {
  678. return err
  679. }
  680. // TODO(davidben): move all per-connection expectations into a dedicated
  681. // expectations struct that can be specified separately for the two
  682. // legs.
  683. expectedVersion := test.expectedVersion
  684. if isResume && test.expectedResumeVersion != 0 {
  685. expectedVersion = test.expectedResumeVersion
  686. }
  687. if vers := tlsConn.ConnectionState().Version; expectedVersion != 0 && vers != expectedVersion {
  688. return fmt.Errorf("got version %x, expected %x", vers, expectedVersion)
  689. }
  690. if test.expectChannelID {
  691. channelID := tlsConn.ConnectionState().ChannelID
  692. if channelID == nil {
  693. return fmt.Errorf("no channel ID negotiated")
  694. }
  695. if channelID.Curve != channelIDKey.Curve ||
  696. channelIDKey.X.Cmp(channelIDKey.X) != 0 ||
  697. channelIDKey.Y.Cmp(channelIDKey.Y) != 0 {
  698. return fmt.Errorf("incorrect channel ID")
  699. }
  700. }
  701. if expected := test.expectedNextProto; expected != "" {
  702. if actual := tlsConn.ConnectionState().NegotiatedProtocol; actual != expected {
  703. return fmt.Errorf("next proto mismatch: got %s, wanted %s", actual, expected)
  704. }
  705. }
  706. if test.expectedNextProtoType != 0 {
  707. if (test.expectedNextProtoType == alpn) != tlsConn.ConnectionState().NegotiatedProtocolFromALPN {
  708. return fmt.Errorf("next proto type mismatch")
  709. }
  710. }
  711. if p := tlsConn.ConnectionState().SRTPProtectionProfile; p != test.expectedSRTPProtectionProfile {
  712. return fmt.Errorf("SRTP profile mismatch: got %d, wanted %d", p, test.expectedSRTPProtectionProfile)
  713. }
  714. if test.shimWritesFirst {
  715. var buf [5]byte
  716. _, err := io.ReadFull(tlsConn, buf[:])
  717. if err != nil {
  718. return err
  719. }
  720. if string(buf[:]) != "hello" {
  721. return fmt.Errorf("bad initial message")
  722. }
  723. }
  724. if test.renegotiate {
  725. if test.renegotiateCiphers != nil {
  726. config.CipherSuites = test.renegotiateCiphers
  727. }
  728. if err := tlsConn.Renegotiate(); err != nil {
  729. return err
  730. }
  731. } else if test.renegotiateCiphers != nil {
  732. panic("renegotiateCiphers without renegotiate")
  733. }
  734. if test.damageFirstWrite {
  735. connDamage.setDamage(true)
  736. tlsConn.Write([]byte("DAMAGED WRITE"))
  737. connDamage.setDamage(false)
  738. }
  739. if messageLen < 0 {
  740. if test.protocol == dtls {
  741. return fmt.Errorf("messageLen < 0 not supported for DTLS tests")
  742. }
  743. // Read until EOF.
  744. _, err := io.Copy(ioutil.Discard, tlsConn)
  745. return err
  746. }
  747. var testMessage []byte
  748. if config.Bugs.AppDataAfterChangeCipherSpec != nil {
  749. // We've already sent a message. Expect the shim to echo it
  750. // back.
  751. testMessage = config.Bugs.AppDataAfterChangeCipherSpec
  752. } else {
  753. if messageLen == 0 {
  754. messageLen = 32
  755. }
  756. testMessage = make([]byte, messageLen)
  757. for i := range testMessage {
  758. testMessage[i] = 0x42
  759. }
  760. tlsConn.Write(testMessage)
  761. }
  762. buf := make([]byte, len(testMessage))
  763. if test.protocol == dtls {
  764. bufTmp := make([]byte, len(buf)+1)
  765. n, err := tlsConn.Read(bufTmp)
  766. if err != nil {
  767. return err
  768. }
  769. if n != len(buf) {
  770. return fmt.Errorf("bad reply; length mismatch (%d vs %d)", n, len(buf))
  771. }
  772. copy(buf, bufTmp)
  773. } else {
  774. _, err := io.ReadFull(tlsConn, buf)
  775. if err != nil {
  776. return err
  777. }
  778. }
  779. for i, v := range buf {
  780. if v != testMessage[i]^0xff {
  781. return fmt.Errorf("bad reply contents at byte %d", i)
  782. }
  783. }
  784. return nil
  785. }
  786. func valgrindOf(dbAttach bool, path string, args ...string) *exec.Cmd {
  787. valgrindArgs := []string{"--error-exitcode=99", "--track-origins=yes", "--leak-check=full"}
  788. if dbAttach {
  789. valgrindArgs = append(valgrindArgs, "--db-attach=yes", "--db-command=xterm -e gdb -nw %f %p")
  790. }
  791. valgrindArgs = append(valgrindArgs, path)
  792. valgrindArgs = append(valgrindArgs, args...)
  793. return exec.Command("valgrind", valgrindArgs...)
  794. }
  795. func gdbOf(path string, args ...string) *exec.Cmd {
  796. xtermArgs := []string{"-e", "gdb", "--args"}
  797. xtermArgs = append(xtermArgs, path)
  798. xtermArgs = append(xtermArgs, args...)
  799. return exec.Command("xterm", xtermArgs...)
  800. }
  801. func openSocketPair() (shimEnd *os.File, conn net.Conn) {
  802. socks, err := syscall.Socketpair(syscall.AF_UNIX, syscall.SOCK_STREAM, 0)
  803. if err != nil {
  804. panic(err)
  805. }
  806. syscall.CloseOnExec(socks[0])
  807. syscall.CloseOnExec(socks[1])
  808. shimEnd = os.NewFile(uintptr(socks[0]), "shim end")
  809. connFile := os.NewFile(uintptr(socks[1]), "our end")
  810. conn, err = net.FileConn(connFile)
  811. if err != nil {
  812. panic(err)
  813. }
  814. connFile.Close()
  815. if err != nil {
  816. panic(err)
  817. }
  818. return shimEnd, conn
  819. }
  820. type moreMallocsError struct{}
  821. func (moreMallocsError) Error() string {
  822. return "child process did not exhaust all allocation calls"
  823. }
  824. var errMoreMallocs = moreMallocsError{}
  825. func runTest(test *testCase, buildDir string, mallocNumToFail int64) error {
  826. if !test.shouldFail && (len(test.expectedError) > 0 || len(test.expectedLocalError) > 0) {
  827. panic("Error expected without shouldFail in " + test.name)
  828. }
  829. shimEnd, conn := openSocketPair()
  830. shimEndResume, connResume := openSocketPair()
  831. shim_path := path.Join(buildDir, "ssl/test/bssl_shim")
  832. var flags []string
  833. if test.testType == serverTest {
  834. flags = append(flags, "-server")
  835. flags = append(flags, "-key-file")
  836. if test.keyFile == "" {
  837. flags = append(flags, rsaKeyFile)
  838. } else {
  839. flags = append(flags, test.keyFile)
  840. }
  841. flags = append(flags, "-cert-file")
  842. if test.certFile == "" {
  843. flags = append(flags, rsaCertificateFile)
  844. } else {
  845. flags = append(flags, test.certFile)
  846. }
  847. }
  848. if test.protocol == dtls {
  849. flags = append(flags, "-dtls")
  850. }
  851. if test.resumeSession {
  852. flags = append(flags, "-resume")
  853. }
  854. if test.shimWritesFirst {
  855. flags = append(flags, "-shim-writes-first")
  856. }
  857. flags = append(flags, test.flags...)
  858. var shim *exec.Cmd
  859. if *useValgrind {
  860. shim = valgrindOf(false, shim_path, flags...)
  861. } else if *useGDB {
  862. shim = gdbOf(shim_path, flags...)
  863. } else {
  864. shim = exec.Command(shim_path, flags...)
  865. }
  866. shim.ExtraFiles = []*os.File{shimEnd, shimEndResume}
  867. shim.Stdin = os.Stdin
  868. var stdoutBuf, stderrBuf bytes.Buffer
  869. shim.Stdout = &stdoutBuf
  870. shim.Stderr = &stderrBuf
  871. if mallocNumToFail >= 0 {
  872. shim.Env = []string{"MALLOC_NUMBER_TO_FAIL=" + strconv.FormatInt(mallocNumToFail, 10)}
  873. if *mallocTestDebug {
  874. shim.Env = append(shim.Env, "MALLOC_ABORT_ON_FAIL=1")
  875. }
  876. shim.Env = append(shim.Env, "_MALLOC_CHECK=1")
  877. }
  878. if err := shim.Start(); err != nil {
  879. panic(err)
  880. }
  881. shimEnd.Close()
  882. shimEndResume.Close()
  883. config := test.config
  884. config.ClientSessionCache = NewLRUClientSessionCache(1)
  885. config.ServerSessionCache = NewLRUServerSessionCache(1)
  886. if test.testType == clientTest {
  887. if len(config.Certificates) == 0 {
  888. config.Certificates = []Certificate{getRSACertificate()}
  889. }
  890. }
  891. err := doExchange(test, &config, conn, test.messageLen,
  892. false /* not a resumption */)
  893. conn.Close()
  894. if err == nil && test.resumeSession {
  895. var resumeConfig Config
  896. if test.resumeConfig != nil {
  897. resumeConfig = *test.resumeConfig
  898. if len(resumeConfig.Certificates) == 0 {
  899. resumeConfig.Certificates = []Certificate{getRSACertificate()}
  900. }
  901. if !test.newSessionsOnResume {
  902. resumeConfig.SessionTicketKey = config.SessionTicketKey
  903. resumeConfig.ClientSessionCache = config.ClientSessionCache
  904. resumeConfig.ServerSessionCache = config.ServerSessionCache
  905. }
  906. } else {
  907. resumeConfig = config
  908. }
  909. err = doExchange(test, &resumeConfig, connResume, test.messageLen,
  910. true /* resumption */)
  911. }
  912. connResume.Close()
  913. childErr := shim.Wait()
  914. if exitError, ok := childErr.(*exec.ExitError); ok {
  915. if exitError.Sys().(syscall.WaitStatus).ExitStatus() == 88 {
  916. return errMoreMallocs
  917. }
  918. }
  919. stdout := string(stdoutBuf.Bytes())
  920. stderr := string(stderrBuf.Bytes())
  921. failed := err != nil || childErr != nil
  922. correctFailure := len(test.expectedError) == 0 || strings.Contains(stdout, test.expectedError)
  923. localError := "none"
  924. if err != nil {
  925. localError = err.Error()
  926. }
  927. if len(test.expectedLocalError) != 0 {
  928. correctFailure = correctFailure && strings.Contains(localError, test.expectedLocalError)
  929. }
  930. if failed != test.shouldFail || failed && !correctFailure {
  931. childError := "none"
  932. if childErr != nil {
  933. childError = childErr.Error()
  934. }
  935. var msg string
  936. switch {
  937. case failed && !test.shouldFail:
  938. msg = "unexpected failure"
  939. case !failed && test.shouldFail:
  940. msg = "unexpected success"
  941. case failed && !correctFailure:
  942. msg = "bad error (wanted '" + test.expectedError + "' / '" + test.expectedLocalError + "')"
  943. default:
  944. panic("internal error")
  945. }
  946. return fmt.Errorf("%s: local error '%s', child error '%s', stdout:\n%s\nstderr:\n%s", msg, localError, childError, string(stdoutBuf.Bytes()), stderr)
  947. }
  948. if !*useValgrind && len(stderr) > 0 {
  949. println(stderr)
  950. }
  951. return nil
  952. }
  953. var tlsVersions = []struct {
  954. name string
  955. version uint16
  956. flag string
  957. hasDTLS bool
  958. }{
  959. {"SSL3", VersionSSL30, "-no-ssl3", false},
  960. {"TLS1", VersionTLS10, "-no-tls1", true},
  961. {"TLS11", VersionTLS11, "-no-tls11", false},
  962. {"TLS12", VersionTLS12, "-no-tls12", true},
  963. }
  964. var testCipherSuites = []struct {
  965. name string
  966. id uint16
  967. }{
  968. {"3DES-SHA", TLS_RSA_WITH_3DES_EDE_CBC_SHA},
  969. {"AES128-GCM", TLS_RSA_WITH_AES_128_GCM_SHA256},
  970. {"AES128-SHA", TLS_RSA_WITH_AES_128_CBC_SHA},
  971. {"AES128-SHA256", TLS_RSA_WITH_AES_128_CBC_SHA256},
  972. {"AES256-GCM", TLS_RSA_WITH_AES_256_GCM_SHA384},
  973. {"AES256-SHA", TLS_RSA_WITH_AES_256_CBC_SHA},
  974. {"AES256-SHA256", TLS_RSA_WITH_AES_256_CBC_SHA256},
  975. {"DHE-RSA-AES128-GCM", TLS_DHE_RSA_WITH_AES_128_GCM_SHA256},
  976. {"DHE-RSA-AES128-SHA", TLS_DHE_RSA_WITH_AES_128_CBC_SHA},
  977. {"DHE-RSA-AES128-SHA256", TLS_DHE_RSA_WITH_AES_128_CBC_SHA256},
  978. {"DHE-RSA-AES256-GCM", TLS_DHE_RSA_WITH_AES_256_GCM_SHA384},
  979. {"DHE-RSA-AES256-SHA", TLS_DHE_RSA_WITH_AES_256_CBC_SHA},
  980. {"DHE-RSA-AES256-SHA256", TLS_DHE_RSA_WITH_AES_256_CBC_SHA256},
  981. {"ECDHE-ECDSA-AES128-GCM", TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256},
  982. {"ECDHE-ECDSA-AES128-SHA", TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA},
  983. {"ECDHE-ECDSA-AES128-SHA256", TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256},
  984. {"ECDHE-ECDSA-AES256-GCM", TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384},
  985. {"ECDHE-ECDSA-AES256-SHA", TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA},
  986. {"ECDHE-ECDSA-AES256-SHA384", TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384},
  987. {"ECDHE-ECDSA-RC4-SHA", TLS_ECDHE_ECDSA_WITH_RC4_128_SHA},
  988. {"ECDHE-PSK-WITH-AES-128-GCM-SHA256", TLS_ECDHE_PSK_WITH_AES_128_GCM_SHA256},
  989. {"ECDHE-RSA-AES128-GCM", TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  990. {"ECDHE-RSA-AES128-SHA", TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA},
  991. {"ECDHE-RSA-AES128-SHA256", TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256},
  992. {"ECDHE-RSA-AES256-GCM", TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384},
  993. {"ECDHE-RSA-AES256-SHA", TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA},
  994. {"ECDHE-RSA-AES256-SHA384", TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384},
  995. {"ECDHE-RSA-RC4-SHA", TLS_ECDHE_RSA_WITH_RC4_128_SHA},
  996. {"PSK-AES128-CBC-SHA", TLS_PSK_WITH_AES_128_CBC_SHA},
  997. {"PSK-AES256-CBC-SHA", TLS_PSK_WITH_AES_256_CBC_SHA},
  998. {"PSK-RC4-SHA", TLS_PSK_WITH_RC4_128_SHA},
  999. {"RC4-MD5", TLS_RSA_WITH_RC4_128_MD5},
  1000. {"RC4-SHA", TLS_RSA_WITH_RC4_128_SHA},
  1001. }
  1002. func hasComponent(suiteName, component string) bool {
  1003. return strings.Contains("-"+suiteName+"-", "-"+component+"-")
  1004. }
  1005. func isTLS12Only(suiteName string) bool {
  1006. return hasComponent(suiteName, "GCM") ||
  1007. hasComponent(suiteName, "SHA256") ||
  1008. hasComponent(suiteName, "SHA384")
  1009. }
  1010. func isDTLSCipher(suiteName string) bool {
  1011. return !hasComponent(suiteName, "RC4")
  1012. }
  1013. func addCipherSuiteTests() {
  1014. for _, suite := range testCipherSuites {
  1015. const psk = "12345"
  1016. const pskIdentity = "luggage combo"
  1017. var cert Certificate
  1018. var certFile string
  1019. var keyFile string
  1020. if hasComponent(suite.name, "ECDSA") {
  1021. cert = getECDSACertificate()
  1022. certFile = ecdsaCertificateFile
  1023. keyFile = ecdsaKeyFile
  1024. } else {
  1025. cert = getRSACertificate()
  1026. certFile = rsaCertificateFile
  1027. keyFile = rsaKeyFile
  1028. }
  1029. var flags []string
  1030. if hasComponent(suite.name, "PSK") {
  1031. flags = append(flags,
  1032. "-psk", psk,
  1033. "-psk-identity", pskIdentity)
  1034. }
  1035. for _, ver := range tlsVersions {
  1036. if ver.version < VersionTLS12 && isTLS12Only(suite.name) {
  1037. continue
  1038. }
  1039. testCases = append(testCases, testCase{
  1040. testType: clientTest,
  1041. name: ver.name + "-" + suite.name + "-client",
  1042. config: Config{
  1043. MinVersion: ver.version,
  1044. MaxVersion: ver.version,
  1045. CipherSuites: []uint16{suite.id},
  1046. Certificates: []Certificate{cert},
  1047. PreSharedKey: []byte(psk),
  1048. PreSharedKeyIdentity: pskIdentity,
  1049. },
  1050. flags: flags,
  1051. resumeSession: true,
  1052. })
  1053. testCases = append(testCases, testCase{
  1054. testType: serverTest,
  1055. name: ver.name + "-" + suite.name + "-server",
  1056. config: Config{
  1057. MinVersion: ver.version,
  1058. MaxVersion: ver.version,
  1059. CipherSuites: []uint16{suite.id},
  1060. Certificates: []Certificate{cert},
  1061. PreSharedKey: []byte(psk),
  1062. PreSharedKeyIdentity: pskIdentity,
  1063. },
  1064. certFile: certFile,
  1065. keyFile: keyFile,
  1066. flags: flags,
  1067. resumeSession: true,
  1068. })
  1069. if ver.hasDTLS && isDTLSCipher(suite.name) {
  1070. testCases = append(testCases, testCase{
  1071. testType: clientTest,
  1072. protocol: dtls,
  1073. name: "D" + ver.name + "-" + suite.name + "-client",
  1074. config: Config{
  1075. MinVersion: ver.version,
  1076. MaxVersion: ver.version,
  1077. CipherSuites: []uint16{suite.id},
  1078. Certificates: []Certificate{cert},
  1079. PreSharedKey: []byte(psk),
  1080. PreSharedKeyIdentity: pskIdentity,
  1081. },
  1082. flags: flags,
  1083. resumeSession: true,
  1084. })
  1085. testCases = append(testCases, testCase{
  1086. testType: serverTest,
  1087. protocol: dtls,
  1088. name: "D" + ver.name + "-" + suite.name + "-server",
  1089. config: Config{
  1090. MinVersion: ver.version,
  1091. MaxVersion: ver.version,
  1092. CipherSuites: []uint16{suite.id},
  1093. Certificates: []Certificate{cert},
  1094. PreSharedKey: []byte(psk),
  1095. PreSharedKeyIdentity: pskIdentity,
  1096. },
  1097. certFile: certFile,
  1098. keyFile: keyFile,
  1099. flags: flags,
  1100. resumeSession: true,
  1101. })
  1102. }
  1103. }
  1104. }
  1105. }
  1106. func addBadECDSASignatureTests() {
  1107. for badR := BadValue(1); badR < NumBadValues; badR++ {
  1108. for badS := BadValue(1); badS < NumBadValues; badS++ {
  1109. testCases = append(testCases, testCase{
  1110. name: fmt.Sprintf("BadECDSA-%d-%d", badR, badS),
  1111. config: Config{
  1112. CipherSuites: []uint16{TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256},
  1113. Certificates: []Certificate{getECDSACertificate()},
  1114. Bugs: ProtocolBugs{
  1115. BadECDSAR: badR,
  1116. BadECDSAS: badS,
  1117. },
  1118. },
  1119. shouldFail: true,
  1120. expectedError: "SIGNATURE",
  1121. })
  1122. }
  1123. }
  1124. }
  1125. func addCBCPaddingTests() {
  1126. testCases = append(testCases, testCase{
  1127. name: "MaxCBCPadding",
  1128. config: Config{
  1129. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA},
  1130. Bugs: ProtocolBugs{
  1131. MaxPadding: true,
  1132. },
  1133. },
  1134. messageLen: 12, // 20 bytes of SHA-1 + 12 == 0 % block size
  1135. })
  1136. testCases = append(testCases, testCase{
  1137. name: "BadCBCPadding",
  1138. config: Config{
  1139. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA},
  1140. Bugs: ProtocolBugs{
  1141. PaddingFirstByteBad: true,
  1142. },
  1143. },
  1144. shouldFail: true,
  1145. expectedError: "DECRYPTION_FAILED_OR_BAD_RECORD_MAC",
  1146. })
  1147. // OpenSSL previously had an issue where the first byte of padding in
  1148. // 255 bytes of padding wasn't checked.
  1149. testCases = append(testCases, testCase{
  1150. name: "BadCBCPadding255",
  1151. config: Config{
  1152. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA},
  1153. Bugs: ProtocolBugs{
  1154. MaxPadding: true,
  1155. PaddingFirstByteBadIf255: true,
  1156. },
  1157. },
  1158. messageLen: 12, // 20 bytes of SHA-1 + 12 == 0 % block size
  1159. shouldFail: true,
  1160. expectedError: "DECRYPTION_FAILED_OR_BAD_RECORD_MAC",
  1161. })
  1162. }
  1163. func addCBCSplittingTests() {
  1164. testCases = append(testCases, testCase{
  1165. name: "CBCRecordSplitting",
  1166. config: Config{
  1167. MaxVersion: VersionTLS10,
  1168. MinVersion: VersionTLS10,
  1169. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA},
  1170. },
  1171. messageLen: -1, // read until EOF
  1172. flags: []string{
  1173. "-async",
  1174. "-write-different-record-sizes",
  1175. "-cbc-record-splitting",
  1176. },
  1177. })
  1178. testCases = append(testCases, testCase{
  1179. name: "CBCRecordSplittingPartialWrite",
  1180. config: Config{
  1181. MaxVersion: VersionTLS10,
  1182. MinVersion: VersionTLS10,
  1183. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA},
  1184. },
  1185. messageLen: -1, // read until EOF
  1186. flags: []string{
  1187. "-async",
  1188. "-write-different-record-sizes",
  1189. "-cbc-record-splitting",
  1190. "-partial-write",
  1191. },
  1192. })
  1193. }
  1194. func addClientAuthTests() {
  1195. // Add a dummy cert pool to stress certificate authority parsing.
  1196. // TODO(davidben): Add tests that those values parse out correctly.
  1197. certPool := x509.NewCertPool()
  1198. cert, err := x509.ParseCertificate(rsaCertificate.Certificate[0])
  1199. if err != nil {
  1200. panic(err)
  1201. }
  1202. certPool.AddCert(cert)
  1203. for _, ver := range tlsVersions {
  1204. testCases = append(testCases, testCase{
  1205. testType: clientTest,
  1206. name: ver.name + "-Client-ClientAuth-RSA",
  1207. config: Config{
  1208. MinVersion: ver.version,
  1209. MaxVersion: ver.version,
  1210. ClientAuth: RequireAnyClientCert,
  1211. ClientCAs: certPool,
  1212. },
  1213. flags: []string{
  1214. "-cert-file", rsaCertificateFile,
  1215. "-key-file", rsaKeyFile,
  1216. },
  1217. })
  1218. testCases = append(testCases, testCase{
  1219. testType: serverTest,
  1220. name: ver.name + "-Server-ClientAuth-RSA",
  1221. config: Config{
  1222. MinVersion: ver.version,
  1223. MaxVersion: ver.version,
  1224. Certificates: []Certificate{rsaCertificate},
  1225. },
  1226. flags: []string{"-require-any-client-certificate"},
  1227. })
  1228. if ver.version != VersionSSL30 {
  1229. testCases = append(testCases, testCase{
  1230. testType: serverTest,
  1231. name: ver.name + "-Server-ClientAuth-ECDSA",
  1232. config: Config{
  1233. MinVersion: ver.version,
  1234. MaxVersion: ver.version,
  1235. Certificates: []Certificate{ecdsaCertificate},
  1236. },
  1237. flags: []string{"-require-any-client-certificate"},
  1238. })
  1239. testCases = append(testCases, testCase{
  1240. testType: clientTest,
  1241. name: ver.name + "-Client-ClientAuth-ECDSA",
  1242. config: Config{
  1243. MinVersion: ver.version,
  1244. MaxVersion: ver.version,
  1245. ClientAuth: RequireAnyClientCert,
  1246. ClientCAs: certPool,
  1247. },
  1248. flags: []string{
  1249. "-cert-file", ecdsaCertificateFile,
  1250. "-key-file", ecdsaKeyFile,
  1251. },
  1252. })
  1253. }
  1254. }
  1255. }
  1256. func addExtendedMasterSecretTests() {
  1257. const expectEMSFlag = "-expect-extended-master-secret"
  1258. for _, with := range []bool{false, true} {
  1259. prefix := "No"
  1260. var flags []string
  1261. if with {
  1262. prefix = ""
  1263. flags = []string{expectEMSFlag}
  1264. }
  1265. for _, isClient := range []bool{false, true} {
  1266. suffix := "-Server"
  1267. testType := serverTest
  1268. if isClient {
  1269. suffix = "-Client"
  1270. testType = clientTest
  1271. }
  1272. for _, ver := range tlsVersions {
  1273. test := testCase{
  1274. testType: testType,
  1275. name: prefix + "ExtendedMasterSecret-" + ver.name + suffix,
  1276. config: Config{
  1277. MinVersion: ver.version,
  1278. MaxVersion: ver.version,
  1279. Bugs: ProtocolBugs{
  1280. NoExtendedMasterSecret: !with,
  1281. RequireExtendedMasterSecret: with,
  1282. },
  1283. },
  1284. flags: flags,
  1285. shouldFail: ver.version == VersionSSL30 && with,
  1286. }
  1287. if test.shouldFail {
  1288. test.expectedLocalError = "extended master secret required but not supported by peer"
  1289. }
  1290. testCases = append(testCases, test)
  1291. }
  1292. }
  1293. }
  1294. // When a session is resumed, it should still be aware that its master
  1295. // secret was generated via EMS and thus it's safe to use tls-unique.
  1296. testCases = append(testCases, testCase{
  1297. name: "ExtendedMasterSecret-Resume",
  1298. config: Config{
  1299. Bugs: ProtocolBugs{
  1300. RequireExtendedMasterSecret: true,
  1301. },
  1302. },
  1303. flags: []string{expectEMSFlag},
  1304. resumeSession: true,
  1305. })
  1306. }
  1307. // Adds tests that try to cover the range of the handshake state machine, under
  1308. // various conditions. Some of these are redundant with other tests, but they
  1309. // only cover the synchronous case.
  1310. func addStateMachineCoverageTests(async, splitHandshake bool, protocol protocol) {
  1311. var suffix string
  1312. var flags []string
  1313. var maxHandshakeRecordLength int
  1314. if protocol == dtls {
  1315. suffix = "-DTLS"
  1316. }
  1317. if async {
  1318. suffix += "-Async"
  1319. flags = append(flags, "-async")
  1320. } else {
  1321. suffix += "-Sync"
  1322. }
  1323. if splitHandshake {
  1324. suffix += "-SplitHandshakeRecords"
  1325. maxHandshakeRecordLength = 1
  1326. }
  1327. // Basic handshake, with resumption. Client and server,
  1328. // session ID and session ticket.
  1329. testCases = append(testCases, testCase{
  1330. protocol: protocol,
  1331. name: "Basic-Client" + suffix,
  1332. config: Config{
  1333. Bugs: ProtocolBugs{
  1334. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1335. },
  1336. },
  1337. flags: flags,
  1338. resumeSession: true,
  1339. })
  1340. testCases = append(testCases, testCase{
  1341. protocol: protocol,
  1342. name: "Basic-Client-RenewTicket" + suffix,
  1343. config: Config{
  1344. Bugs: ProtocolBugs{
  1345. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1346. RenewTicketOnResume: true,
  1347. },
  1348. },
  1349. flags: flags,
  1350. resumeSession: true,
  1351. })
  1352. testCases = append(testCases, testCase{
  1353. protocol: protocol,
  1354. name: "Basic-Client-NoTicket" + suffix,
  1355. config: Config{
  1356. SessionTicketsDisabled: true,
  1357. Bugs: ProtocolBugs{
  1358. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1359. },
  1360. },
  1361. flags: flags,
  1362. resumeSession: true,
  1363. })
  1364. testCases = append(testCases, testCase{
  1365. protocol: protocol,
  1366. testType: serverTest,
  1367. name: "Basic-Server" + suffix,
  1368. config: Config{
  1369. Bugs: ProtocolBugs{
  1370. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1371. },
  1372. },
  1373. flags: flags,
  1374. resumeSession: true,
  1375. })
  1376. testCases = append(testCases, testCase{
  1377. protocol: protocol,
  1378. testType: serverTest,
  1379. name: "Basic-Server-NoTickets" + suffix,
  1380. config: Config{
  1381. SessionTicketsDisabled: true,
  1382. Bugs: ProtocolBugs{
  1383. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1384. },
  1385. },
  1386. flags: flags,
  1387. resumeSession: true,
  1388. })
  1389. // TLS client auth.
  1390. testCases = append(testCases, testCase{
  1391. protocol: protocol,
  1392. testType: clientTest,
  1393. name: "ClientAuth-Client" + suffix,
  1394. config: Config{
  1395. ClientAuth: RequireAnyClientCert,
  1396. Bugs: ProtocolBugs{
  1397. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1398. },
  1399. },
  1400. flags: append(flags,
  1401. "-cert-file", rsaCertificateFile,
  1402. "-key-file", rsaKeyFile),
  1403. })
  1404. testCases = append(testCases, testCase{
  1405. protocol: protocol,
  1406. testType: serverTest,
  1407. name: "ClientAuth-Server" + suffix,
  1408. config: Config{
  1409. Certificates: []Certificate{rsaCertificate},
  1410. },
  1411. flags: append(flags, "-require-any-client-certificate"),
  1412. })
  1413. // No session ticket support; server doesn't send NewSessionTicket.
  1414. testCases = append(testCases, testCase{
  1415. protocol: protocol,
  1416. name: "SessionTicketsDisabled-Client" + suffix,
  1417. config: Config{
  1418. SessionTicketsDisabled: true,
  1419. Bugs: ProtocolBugs{
  1420. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1421. },
  1422. },
  1423. flags: flags,
  1424. })
  1425. testCases = append(testCases, testCase{
  1426. protocol: protocol,
  1427. testType: serverTest,
  1428. name: "SessionTicketsDisabled-Server" + suffix,
  1429. config: Config{
  1430. SessionTicketsDisabled: true,
  1431. Bugs: ProtocolBugs{
  1432. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1433. },
  1434. },
  1435. flags: flags,
  1436. })
  1437. // Skip ServerKeyExchange in PSK key exchange if there's no
  1438. // identity hint.
  1439. testCases = append(testCases, testCase{
  1440. protocol: protocol,
  1441. name: "EmptyPSKHint-Client" + suffix,
  1442. config: Config{
  1443. CipherSuites: []uint16{TLS_PSK_WITH_AES_128_CBC_SHA},
  1444. PreSharedKey: []byte("secret"),
  1445. Bugs: ProtocolBugs{
  1446. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1447. },
  1448. },
  1449. flags: append(flags, "-psk", "secret"),
  1450. })
  1451. testCases = append(testCases, testCase{
  1452. protocol: protocol,
  1453. testType: serverTest,
  1454. name: "EmptyPSKHint-Server" + suffix,
  1455. config: Config{
  1456. CipherSuites: []uint16{TLS_PSK_WITH_AES_128_CBC_SHA},
  1457. PreSharedKey: []byte("secret"),
  1458. Bugs: ProtocolBugs{
  1459. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1460. },
  1461. },
  1462. flags: append(flags, "-psk", "secret"),
  1463. })
  1464. if protocol == tls {
  1465. // NPN on client and server; results in post-handshake message.
  1466. testCases = append(testCases, testCase{
  1467. protocol: protocol,
  1468. name: "NPN-Client" + suffix,
  1469. config: Config{
  1470. NextProtos: []string{"foo"},
  1471. Bugs: ProtocolBugs{
  1472. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1473. },
  1474. },
  1475. flags: append(flags, "-select-next-proto", "foo"),
  1476. expectedNextProto: "foo",
  1477. expectedNextProtoType: npn,
  1478. })
  1479. testCases = append(testCases, testCase{
  1480. protocol: protocol,
  1481. testType: serverTest,
  1482. name: "NPN-Server" + suffix,
  1483. config: Config{
  1484. NextProtos: []string{"bar"},
  1485. Bugs: ProtocolBugs{
  1486. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1487. },
  1488. },
  1489. flags: append(flags,
  1490. "-advertise-npn", "\x03foo\x03bar\x03baz",
  1491. "-expect-next-proto", "bar"),
  1492. expectedNextProto: "bar",
  1493. expectedNextProtoType: npn,
  1494. })
  1495. // Client does False Start and negotiates NPN.
  1496. testCases = append(testCases, testCase{
  1497. protocol: protocol,
  1498. name: "FalseStart" + suffix,
  1499. config: Config{
  1500. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  1501. NextProtos: []string{"foo"},
  1502. Bugs: ProtocolBugs{
  1503. ExpectFalseStart: true,
  1504. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1505. },
  1506. },
  1507. flags: append(flags,
  1508. "-false-start",
  1509. "-select-next-proto", "foo"),
  1510. shimWritesFirst: true,
  1511. resumeSession: true,
  1512. })
  1513. // Client does False Start and negotiates ALPN.
  1514. testCases = append(testCases, testCase{
  1515. protocol: protocol,
  1516. name: "FalseStart-ALPN" + suffix,
  1517. config: Config{
  1518. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  1519. NextProtos: []string{"foo"},
  1520. Bugs: ProtocolBugs{
  1521. ExpectFalseStart: true,
  1522. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1523. },
  1524. },
  1525. flags: append(flags,
  1526. "-false-start",
  1527. "-advertise-alpn", "\x03foo"),
  1528. shimWritesFirst: true,
  1529. resumeSession: true,
  1530. })
  1531. // False Start without session tickets.
  1532. testCases = append(testCases, testCase{
  1533. name: "FalseStart-SessionTicketsDisabled",
  1534. config: Config{
  1535. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  1536. NextProtos: []string{"foo"},
  1537. SessionTicketsDisabled: true,
  1538. Bugs: ProtocolBugs{
  1539. ExpectFalseStart: true,
  1540. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1541. },
  1542. },
  1543. flags: append(flags,
  1544. "-false-start",
  1545. "-select-next-proto", "foo",
  1546. ),
  1547. shimWritesFirst: true,
  1548. })
  1549. // Server parses a V2ClientHello.
  1550. testCases = append(testCases, testCase{
  1551. protocol: protocol,
  1552. testType: serverTest,
  1553. name: "SendV2ClientHello" + suffix,
  1554. config: Config{
  1555. // Choose a cipher suite that does not involve
  1556. // elliptic curves, so no extensions are
  1557. // involved.
  1558. CipherSuites: []uint16{TLS_RSA_WITH_RC4_128_SHA},
  1559. Bugs: ProtocolBugs{
  1560. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1561. SendV2ClientHello: true,
  1562. },
  1563. },
  1564. flags: flags,
  1565. })
  1566. // Client sends a Channel ID.
  1567. testCases = append(testCases, testCase{
  1568. protocol: protocol,
  1569. name: "ChannelID-Client" + suffix,
  1570. config: Config{
  1571. RequestChannelID: true,
  1572. Bugs: ProtocolBugs{
  1573. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1574. },
  1575. },
  1576. flags: append(flags,
  1577. "-send-channel-id", channelIDKeyFile,
  1578. ),
  1579. resumeSession: true,
  1580. expectChannelID: true,
  1581. })
  1582. // Server accepts a Channel ID.
  1583. testCases = append(testCases, testCase{
  1584. protocol: protocol,
  1585. testType: serverTest,
  1586. name: "ChannelID-Server" + suffix,
  1587. config: Config{
  1588. ChannelID: channelIDKey,
  1589. Bugs: ProtocolBugs{
  1590. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1591. },
  1592. },
  1593. flags: append(flags,
  1594. "-expect-channel-id",
  1595. base64.StdEncoding.EncodeToString(channelIDBytes),
  1596. ),
  1597. resumeSession: true,
  1598. expectChannelID: true,
  1599. })
  1600. } else {
  1601. testCases = append(testCases, testCase{
  1602. protocol: protocol,
  1603. name: "SkipHelloVerifyRequest" + suffix,
  1604. config: Config{
  1605. Bugs: ProtocolBugs{
  1606. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1607. SkipHelloVerifyRequest: true,
  1608. },
  1609. },
  1610. flags: flags,
  1611. })
  1612. testCases = append(testCases, testCase{
  1613. testType: serverTest,
  1614. protocol: protocol,
  1615. name: "CookieExchange" + suffix,
  1616. config: Config{
  1617. Bugs: ProtocolBugs{
  1618. MaxHandshakeRecordLength: maxHandshakeRecordLength,
  1619. },
  1620. },
  1621. flags: append(flags, "-cookie-exchange"),
  1622. })
  1623. }
  1624. }
  1625. func addVersionNegotiationTests() {
  1626. for i, shimVers := range tlsVersions {
  1627. // Assemble flags to disable all newer versions on the shim.
  1628. var flags []string
  1629. for _, vers := range tlsVersions[i+1:] {
  1630. flags = append(flags, vers.flag)
  1631. }
  1632. for _, runnerVers := range tlsVersions {
  1633. protocols := []protocol{tls}
  1634. if runnerVers.hasDTLS && shimVers.hasDTLS {
  1635. protocols = append(protocols, dtls)
  1636. }
  1637. for _, protocol := range protocols {
  1638. expectedVersion := shimVers.version
  1639. if runnerVers.version < shimVers.version {
  1640. expectedVersion = runnerVers.version
  1641. }
  1642. suffix := shimVers.name + "-" + runnerVers.name
  1643. if protocol == dtls {
  1644. suffix += "-DTLS"
  1645. }
  1646. shimVersFlag := strconv.Itoa(int(versionToWire(shimVers.version, protocol == dtls)))
  1647. clientVers := shimVers.version
  1648. if clientVers > VersionTLS10 {
  1649. clientVers = VersionTLS10
  1650. }
  1651. testCases = append(testCases, testCase{
  1652. protocol: protocol,
  1653. testType: clientTest,
  1654. name: "VersionNegotiation-Client-" + suffix,
  1655. config: Config{
  1656. MaxVersion: runnerVers.version,
  1657. Bugs: ProtocolBugs{
  1658. ExpectInitialRecordVersion: clientVers,
  1659. },
  1660. },
  1661. flags: flags,
  1662. expectedVersion: expectedVersion,
  1663. })
  1664. testCases = append(testCases, testCase{
  1665. protocol: protocol,
  1666. testType: clientTest,
  1667. name: "VersionNegotiation-Client2-" + suffix,
  1668. config: Config{
  1669. MaxVersion: runnerVers.version,
  1670. Bugs: ProtocolBugs{
  1671. ExpectInitialRecordVersion: clientVers,
  1672. },
  1673. },
  1674. flags: []string{"-max-version", shimVersFlag},
  1675. expectedVersion: expectedVersion,
  1676. })
  1677. testCases = append(testCases, testCase{
  1678. protocol: protocol,
  1679. testType: serverTest,
  1680. name: "VersionNegotiation-Server-" + suffix,
  1681. config: Config{
  1682. MaxVersion: runnerVers.version,
  1683. Bugs: ProtocolBugs{
  1684. ExpectInitialRecordVersion: expectedVersion,
  1685. },
  1686. },
  1687. flags: flags,
  1688. expectedVersion: expectedVersion,
  1689. })
  1690. testCases = append(testCases, testCase{
  1691. protocol: protocol,
  1692. testType: serverTest,
  1693. name: "VersionNegotiation-Server2-" + suffix,
  1694. config: Config{
  1695. MaxVersion: runnerVers.version,
  1696. Bugs: ProtocolBugs{
  1697. ExpectInitialRecordVersion: expectedVersion,
  1698. },
  1699. },
  1700. flags: []string{"-max-version", shimVersFlag},
  1701. expectedVersion: expectedVersion,
  1702. })
  1703. }
  1704. }
  1705. }
  1706. }
  1707. func addMinimumVersionTests() {
  1708. for i, shimVers := range tlsVersions {
  1709. // Assemble flags to disable all older versions on the shim.
  1710. var flags []string
  1711. for _, vers := range tlsVersions[:i] {
  1712. flags = append(flags, vers.flag)
  1713. }
  1714. for _, runnerVers := range tlsVersions {
  1715. protocols := []protocol{tls}
  1716. if runnerVers.hasDTLS && shimVers.hasDTLS {
  1717. protocols = append(protocols, dtls)
  1718. }
  1719. for _, protocol := range protocols {
  1720. suffix := shimVers.name + "-" + runnerVers.name
  1721. if protocol == dtls {
  1722. suffix += "-DTLS"
  1723. }
  1724. shimVersFlag := strconv.Itoa(int(versionToWire(shimVers.version, protocol == dtls)))
  1725. var expectedVersion uint16
  1726. var shouldFail bool
  1727. var expectedError string
  1728. var expectedLocalError string
  1729. if runnerVers.version >= shimVers.version {
  1730. expectedVersion = runnerVers.version
  1731. } else {
  1732. shouldFail = true
  1733. expectedError = ":UNSUPPORTED_PROTOCOL:"
  1734. if runnerVers.version > VersionSSL30 {
  1735. expectedLocalError = "remote error: protocol version not supported"
  1736. } else {
  1737. expectedLocalError = "remote error: handshake failure"
  1738. }
  1739. }
  1740. testCases = append(testCases, testCase{
  1741. protocol: protocol,
  1742. testType: clientTest,
  1743. name: "MinimumVersion-Client-" + suffix,
  1744. config: Config{
  1745. MaxVersion: runnerVers.version,
  1746. },
  1747. flags: flags,
  1748. expectedVersion: expectedVersion,
  1749. shouldFail: shouldFail,
  1750. expectedError: expectedError,
  1751. expectedLocalError: expectedLocalError,
  1752. })
  1753. testCases = append(testCases, testCase{
  1754. protocol: protocol,
  1755. testType: clientTest,
  1756. name: "MinimumVersion-Client2-" + suffix,
  1757. config: Config{
  1758. MaxVersion: runnerVers.version,
  1759. },
  1760. flags: []string{"-min-version", shimVersFlag},
  1761. expectedVersion: expectedVersion,
  1762. shouldFail: shouldFail,
  1763. expectedError: expectedError,
  1764. expectedLocalError: expectedLocalError,
  1765. })
  1766. testCases = append(testCases, testCase{
  1767. protocol: protocol,
  1768. testType: serverTest,
  1769. name: "MinimumVersion-Server-" + suffix,
  1770. config: Config{
  1771. MaxVersion: runnerVers.version,
  1772. },
  1773. flags: flags,
  1774. expectedVersion: expectedVersion,
  1775. shouldFail: shouldFail,
  1776. expectedError: expectedError,
  1777. expectedLocalError: expectedLocalError,
  1778. })
  1779. testCases = append(testCases, testCase{
  1780. protocol: protocol,
  1781. testType: serverTest,
  1782. name: "MinimumVersion-Server2-" + suffix,
  1783. config: Config{
  1784. MaxVersion: runnerVers.version,
  1785. },
  1786. flags: []string{"-min-version", shimVersFlag},
  1787. expectedVersion: expectedVersion,
  1788. shouldFail: shouldFail,
  1789. expectedError: expectedError,
  1790. expectedLocalError: expectedLocalError,
  1791. })
  1792. }
  1793. }
  1794. }
  1795. }
  1796. func addD5BugTests() {
  1797. testCases = append(testCases, testCase{
  1798. testType: serverTest,
  1799. name: "D5Bug-NoQuirk-Reject",
  1800. config: Config{
  1801. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_GCM_SHA256},
  1802. Bugs: ProtocolBugs{
  1803. SSL3RSAKeyExchange: true,
  1804. },
  1805. },
  1806. shouldFail: true,
  1807. expectedError: ":TLS_RSA_ENCRYPTED_VALUE_LENGTH_IS_WRONG:",
  1808. })
  1809. testCases = append(testCases, testCase{
  1810. testType: serverTest,
  1811. name: "D5Bug-Quirk-Normal",
  1812. config: Config{
  1813. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_GCM_SHA256},
  1814. },
  1815. flags: []string{"-tls-d5-bug"},
  1816. })
  1817. testCases = append(testCases, testCase{
  1818. testType: serverTest,
  1819. name: "D5Bug-Quirk-Bug",
  1820. config: Config{
  1821. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_GCM_SHA256},
  1822. Bugs: ProtocolBugs{
  1823. SSL3RSAKeyExchange: true,
  1824. },
  1825. },
  1826. flags: []string{"-tls-d5-bug"},
  1827. })
  1828. }
  1829. func addExtensionTests() {
  1830. testCases = append(testCases, testCase{
  1831. testType: clientTest,
  1832. name: "DuplicateExtensionClient",
  1833. config: Config{
  1834. Bugs: ProtocolBugs{
  1835. DuplicateExtension: true,
  1836. },
  1837. },
  1838. shouldFail: true,
  1839. expectedLocalError: "remote error: error decoding message",
  1840. })
  1841. testCases = append(testCases, testCase{
  1842. testType: serverTest,
  1843. name: "DuplicateExtensionServer",
  1844. config: Config{
  1845. Bugs: ProtocolBugs{
  1846. DuplicateExtension: true,
  1847. },
  1848. },
  1849. shouldFail: true,
  1850. expectedLocalError: "remote error: error decoding message",
  1851. })
  1852. testCases = append(testCases, testCase{
  1853. testType: clientTest,
  1854. name: "ServerNameExtensionClient",
  1855. config: Config{
  1856. Bugs: ProtocolBugs{
  1857. ExpectServerName: "example.com",
  1858. },
  1859. },
  1860. flags: []string{"-host-name", "example.com"},
  1861. })
  1862. testCases = append(testCases, testCase{
  1863. testType: clientTest,
  1864. name: "ServerNameExtensionClient",
  1865. config: Config{
  1866. Bugs: ProtocolBugs{
  1867. ExpectServerName: "mismatch.com",
  1868. },
  1869. },
  1870. flags: []string{"-host-name", "example.com"},
  1871. shouldFail: true,
  1872. expectedLocalError: "tls: unexpected server name",
  1873. })
  1874. testCases = append(testCases, testCase{
  1875. testType: clientTest,
  1876. name: "ServerNameExtensionClient",
  1877. config: Config{
  1878. Bugs: ProtocolBugs{
  1879. ExpectServerName: "missing.com",
  1880. },
  1881. },
  1882. shouldFail: true,
  1883. expectedLocalError: "tls: unexpected server name",
  1884. })
  1885. testCases = append(testCases, testCase{
  1886. testType: serverTest,
  1887. name: "ServerNameExtensionServer",
  1888. config: Config{
  1889. ServerName: "example.com",
  1890. },
  1891. flags: []string{"-expect-server-name", "example.com"},
  1892. resumeSession: true,
  1893. })
  1894. testCases = append(testCases, testCase{
  1895. testType: clientTest,
  1896. name: "ALPNClient",
  1897. config: Config{
  1898. NextProtos: []string{"foo"},
  1899. },
  1900. flags: []string{
  1901. "-advertise-alpn", "\x03foo\x03bar\x03baz",
  1902. "-expect-alpn", "foo",
  1903. },
  1904. expectedNextProto: "foo",
  1905. expectedNextProtoType: alpn,
  1906. resumeSession: true,
  1907. })
  1908. testCases = append(testCases, testCase{
  1909. testType: serverTest,
  1910. name: "ALPNServer",
  1911. config: Config{
  1912. NextProtos: []string{"foo", "bar", "baz"},
  1913. },
  1914. flags: []string{
  1915. "-expect-advertised-alpn", "\x03foo\x03bar\x03baz",
  1916. "-select-alpn", "foo",
  1917. },
  1918. expectedNextProto: "foo",
  1919. expectedNextProtoType: alpn,
  1920. resumeSession: true,
  1921. })
  1922. // Test that the server prefers ALPN over NPN.
  1923. testCases = append(testCases, testCase{
  1924. testType: serverTest,
  1925. name: "ALPNServer-Preferred",
  1926. config: Config{
  1927. NextProtos: []string{"foo", "bar", "baz"},
  1928. },
  1929. flags: []string{
  1930. "-expect-advertised-alpn", "\x03foo\x03bar\x03baz",
  1931. "-select-alpn", "foo",
  1932. "-advertise-npn", "\x03foo\x03bar\x03baz",
  1933. },
  1934. expectedNextProto: "foo",
  1935. expectedNextProtoType: alpn,
  1936. resumeSession: true,
  1937. })
  1938. testCases = append(testCases, testCase{
  1939. testType: serverTest,
  1940. name: "ALPNServer-Preferred-Swapped",
  1941. config: Config{
  1942. NextProtos: []string{"foo", "bar", "baz"},
  1943. Bugs: ProtocolBugs{
  1944. SwapNPNAndALPN: true,
  1945. },
  1946. },
  1947. flags: []string{
  1948. "-expect-advertised-alpn", "\x03foo\x03bar\x03baz",
  1949. "-select-alpn", "foo",
  1950. "-advertise-npn", "\x03foo\x03bar\x03baz",
  1951. },
  1952. expectedNextProto: "foo",
  1953. expectedNextProtoType: alpn,
  1954. resumeSession: true,
  1955. })
  1956. // Resume with a corrupt ticket.
  1957. testCases = append(testCases, testCase{
  1958. testType: serverTest,
  1959. name: "CorruptTicket",
  1960. config: Config{
  1961. Bugs: ProtocolBugs{
  1962. CorruptTicket: true,
  1963. },
  1964. },
  1965. resumeSession: true,
  1966. flags: []string{"-expect-session-miss"},
  1967. })
  1968. // Resume with an oversized session id.
  1969. testCases = append(testCases, testCase{
  1970. testType: serverTest,
  1971. name: "OversizedSessionId",
  1972. config: Config{
  1973. Bugs: ProtocolBugs{
  1974. OversizedSessionId: true,
  1975. },
  1976. },
  1977. resumeSession: true,
  1978. shouldFail: true,
  1979. expectedError: ":DECODE_ERROR:",
  1980. })
  1981. // Basic DTLS-SRTP tests. Include fake profiles to ensure they
  1982. // are ignored.
  1983. testCases = append(testCases, testCase{
  1984. protocol: dtls,
  1985. name: "SRTP-Client",
  1986. config: Config{
  1987. SRTPProtectionProfiles: []uint16{40, SRTP_AES128_CM_HMAC_SHA1_80, 42},
  1988. },
  1989. flags: []string{
  1990. "-srtp-profiles",
  1991. "SRTP_AES128_CM_SHA1_80:SRTP_AES128_CM_SHA1_32",
  1992. },
  1993. expectedSRTPProtectionProfile: SRTP_AES128_CM_HMAC_SHA1_80,
  1994. })
  1995. testCases = append(testCases, testCase{
  1996. protocol: dtls,
  1997. testType: serverTest,
  1998. name: "SRTP-Server",
  1999. config: Config{
  2000. SRTPProtectionProfiles: []uint16{40, SRTP_AES128_CM_HMAC_SHA1_80, 42},
  2001. },
  2002. flags: []string{
  2003. "-srtp-profiles",
  2004. "SRTP_AES128_CM_SHA1_80:SRTP_AES128_CM_SHA1_32",
  2005. },
  2006. expectedSRTPProtectionProfile: SRTP_AES128_CM_HMAC_SHA1_80,
  2007. })
  2008. // Test that the MKI is ignored.
  2009. testCases = append(testCases, testCase{
  2010. protocol: dtls,
  2011. testType: serverTest,
  2012. name: "SRTP-Server-IgnoreMKI",
  2013. config: Config{
  2014. SRTPProtectionProfiles: []uint16{SRTP_AES128_CM_HMAC_SHA1_80},
  2015. Bugs: ProtocolBugs{
  2016. SRTPMasterKeyIdentifer: "bogus",
  2017. },
  2018. },
  2019. flags: []string{
  2020. "-srtp-profiles",
  2021. "SRTP_AES128_CM_SHA1_80:SRTP_AES128_CM_SHA1_32",
  2022. },
  2023. expectedSRTPProtectionProfile: SRTP_AES128_CM_HMAC_SHA1_80,
  2024. })
  2025. // Test that SRTP isn't negotiated on the server if there were
  2026. // no matching profiles.
  2027. testCases = append(testCases, testCase{
  2028. protocol: dtls,
  2029. testType: serverTest,
  2030. name: "SRTP-Server-NoMatch",
  2031. config: Config{
  2032. SRTPProtectionProfiles: []uint16{100, 101, 102},
  2033. },
  2034. flags: []string{
  2035. "-srtp-profiles",
  2036. "SRTP_AES128_CM_SHA1_80:SRTP_AES128_CM_SHA1_32",
  2037. },
  2038. expectedSRTPProtectionProfile: 0,
  2039. })
  2040. // Test that the server returning an invalid SRTP profile is
  2041. // flagged as an error by the client.
  2042. testCases = append(testCases, testCase{
  2043. protocol: dtls,
  2044. name: "SRTP-Client-NoMatch",
  2045. config: Config{
  2046. Bugs: ProtocolBugs{
  2047. SendSRTPProtectionProfile: SRTP_AES128_CM_HMAC_SHA1_32,
  2048. },
  2049. },
  2050. flags: []string{
  2051. "-srtp-profiles",
  2052. "SRTP_AES128_CM_SHA1_80",
  2053. },
  2054. shouldFail: true,
  2055. expectedError: ":BAD_SRTP_PROTECTION_PROFILE_LIST:",
  2056. })
  2057. // Test OCSP stapling and SCT list.
  2058. testCases = append(testCases, testCase{
  2059. name: "OCSPStapling",
  2060. flags: []string{
  2061. "-enable-ocsp-stapling",
  2062. "-expect-ocsp-response",
  2063. base64.StdEncoding.EncodeToString(testOCSPResponse),
  2064. },
  2065. })
  2066. testCases = append(testCases, testCase{
  2067. name: "SignedCertificateTimestampList",
  2068. flags: []string{
  2069. "-enable-signed-cert-timestamps",
  2070. "-expect-signed-cert-timestamps",
  2071. base64.StdEncoding.EncodeToString(testSCTList),
  2072. },
  2073. })
  2074. }
  2075. func addResumptionVersionTests() {
  2076. for _, sessionVers := range tlsVersions {
  2077. for _, resumeVers := range tlsVersions {
  2078. protocols := []protocol{tls}
  2079. if sessionVers.hasDTLS && resumeVers.hasDTLS {
  2080. protocols = append(protocols, dtls)
  2081. }
  2082. for _, protocol := range protocols {
  2083. suffix := "-" + sessionVers.name + "-" + resumeVers.name
  2084. if protocol == dtls {
  2085. suffix += "-DTLS"
  2086. }
  2087. testCases = append(testCases, testCase{
  2088. protocol: protocol,
  2089. name: "Resume-Client" + suffix,
  2090. resumeSession: true,
  2091. config: Config{
  2092. MaxVersion: sessionVers.version,
  2093. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_CBC_SHA},
  2094. Bugs: ProtocolBugs{
  2095. AllowSessionVersionMismatch: true,
  2096. },
  2097. },
  2098. expectedVersion: sessionVers.version,
  2099. resumeConfig: &Config{
  2100. MaxVersion: resumeVers.version,
  2101. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_CBC_SHA},
  2102. Bugs: ProtocolBugs{
  2103. AllowSessionVersionMismatch: true,
  2104. },
  2105. },
  2106. expectedResumeVersion: resumeVers.version,
  2107. })
  2108. testCases = append(testCases, testCase{
  2109. protocol: protocol,
  2110. name: "Resume-Client-NoResume" + suffix,
  2111. flags: []string{"-expect-session-miss"},
  2112. resumeSession: true,
  2113. config: Config{
  2114. MaxVersion: sessionVers.version,
  2115. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_CBC_SHA},
  2116. },
  2117. expectedVersion: sessionVers.version,
  2118. resumeConfig: &Config{
  2119. MaxVersion: resumeVers.version,
  2120. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_CBC_SHA},
  2121. },
  2122. newSessionsOnResume: true,
  2123. expectedResumeVersion: resumeVers.version,
  2124. })
  2125. var flags []string
  2126. if sessionVers.version != resumeVers.version {
  2127. flags = append(flags, "-expect-session-miss")
  2128. }
  2129. testCases = append(testCases, testCase{
  2130. protocol: protocol,
  2131. testType: serverTest,
  2132. name: "Resume-Server" + suffix,
  2133. flags: flags,
  2134. resumeSession: true,
  2135. config: Config{
  2136. MaxVersion: sessionVers.version,
  2137. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_CBC_SHA},
  2138. },
  2139. expectedVersion: sessionVers.version,
  2140. resumeConfig: &Config{
  2141. MaxVersion: resumeVers.version,
  2142. CipherSuites: []uint16{TLS_RSA_WITH_AES_128_CBC_SHA},
  2143. },
  2144. expectedResumeVersion: resumeVers.version,
  2145. })
  2146. }
  2147. }
  2148. }
  2149. }
  2150. func addRenegotiationTests() {
  2151. testCases = append(testCases, testCase{
  2152. testType: serverTest,
  2153. name: "Renegotiate-Server",
  2154. flags: []string{"-renegotiate"},
  2155. shimWritesFirst: true,
  2156. })
  2157. testCases = append(testCases, testCase{
  2158. testType: serverTest,
  2159. name: "Renegotiate-Server-EmptyExt",
  2160. config: Config{
  2161. Bugs: ProtocolBugs{
  2162. EmptyRenegotiationInfo: true,
  2163. },
  2164. },
  2165. flags: []string{"-renegotiate"},
  2166. shimWritesFirst: true,
  2167. shouldFail: true,
  2168. expectedError: ":RENEGOTIATION_MISMATCH:",
  2169. })
  2170. testCases = append(testCases, testCase{
  2171. testType: serverTest,
  2172. name: "Renegotiate-Server-BadExt",
  2173. config: Config{
  2174. Bugs: ProtocolBugs{
  2175. BadRenegotiationInfo: true,
  2176. },
  2177. },
  2178. flags: []string{"-renegotiate"},
  2179. shimWritesFirst: true,
  2180. shouldFail: true,
  2181. expectedError: ":RENEGOTIATION_MISMATCH:",
  2182. })
  2183. testCases = append(testCases, testCase{
  2184. testType: serverTest,
  2185. name: "Renegotiate-Server-ClientInitiated",
  2186. renegotiate: true,
  2187. })
  2188. testCases = append(testCases, testCase{
  2189. testType: serverTest,
  2190. name: "Renegotiate-Server-ClientInitiated-NoExt",
  2191. renegotiate: true,
  2192. config: Config{
  2193. Bugs: ProtocolBugs{
  2194. NoRenegotiationInfo: true,
  2195. },
  2196. },
  2197. shouldFail: true,
  2198. expectedError: ":UNSAFE_LEGACY_RENEGOTIATION_DISABLED:",
  2199. })
  2200. testCases = append(testCases, testCase{
  2201. testType: serverTest,
  2202. name: "Renegotiate-Server-ClientInitiated-NoExt-Allowed",
  2203. renegotiate: true,
  2204. config: Config{
  2205. Bugs: ProtocolBugs{
  2206. NoRenegotiationInfo: true,
  2207. },
  2208. },
  2209. flags: []string{"-allow-unsafe-legacy-renegotiation"},
  2210. })
  2211. // TODO(agl): test the renegotiation info SCSV.
  2212. testCases = append(testCases, testCase{
  2213. name: "Renegotiate-Client",
  2214. renegotiate: true,
  2215. })
  2216. testCases = append(testCases, testCase{
  2217. name: "Renegotiate-Client-EmptyExt",
  2218. renegotiate: true,
  2219. config: Config{
  2220. Bugs: ProtocolBugs{
  2221. EmptyRenegotiationInfo: true,
  2222. },
  2223. },
  2224. shouldFail: true,
  2225. expectedError: ":RENEGOTIATION_MISMATCH:",
  2226. })
  2227. testCases = append(testCases, testCase{
  2228. name: "Renegotiate-Client-BadExt",
  2229. renegotiate: true,
  2230. config: Config{
  2231. Bugs: ProtocolBugs{
  2232. BadRenegotiationInfo: true,
  2233. },
  2234. },
  2235. shouldFail: true,
  2236. expectedError: ":RENEGOTIATION_MISMATCH:",
  2237. })
  2238. testCases = append(testCases, testCase{
  2239. name: "Renegotiate-Client-SwitchCiphers",
  2240. renegotiate: true,
  2241. config: Config{
  2242. CipherSuites: []uint16{TLS_RSA_WITH_RC4_128_SHA},
  2243. },
  2244. renegotiateCiphers: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  2245. })
  2246. testCases = append(testCases, testCase{
  2247. name: "Renegotiate-Client-SwitchCiphers2",
  2248. renegotiate: true,
  2249. config: Config{
  2250. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  2251. },
  2252. renegotiateCiphers: []uint16{TLS_RSA_WITH_RC4_128_SHA},
  2253. })
  2254. testCases = append(testCases, testCase{
  2255. name: "Renegotiate-SameClientVersion",
  2256. renegotiate: true,
  2257. config: Config{
  2258. MaxVersion: VersionTLS10,
  2259. Bugs: ProtocolBugs{
  2260. RequireSameRenegoClientVersion: true,
  2261. },
  2262. },
  2263. })
  2264. }
  2265. func addDTLSReplayTests() {
  2266. // Test that sequence number replays are detected.
  2267. testCases = append(testCases, testCase{
  2268. protocol: dtls,
  2269. name: "DTLS-Replay",
  2270. replayWrites: true,
  2271. })
  2272. // Test the outgoing sequence number skipping by values larger
  2273. // than the retransmit window.
  2274. testCases = append(testCases, testCase{
  2275. protocol: dtls,
  2276. name: "DTLS-Replay-LargeGaps",
  2277. config: Config{
  2278. Bugs: ProtocolBugs{
  2279. SequenceNumberIncrement: 127,
  2280. },
  2281. },
  2282. replayWrites: true,
  2283. })
  2284. }
  2285. func addFastRadioPaddingTests() {
  2286. testCases = append(testCases, testCase{
  2287. protocol: tls,
  2288. name: "FastRadio-Padding",
  2289. config: Config{
  2290. Bugs: ProtocolBugs{
  2291. RequireFastradioPadding: true,
  2292. },
  2293. },
  2294. flags: []string{"-fastradio-padding"},
  2295. })
  2296. testCases = append(testCases, testCase{
  2297. protocol: dtls,
  2298. name: "FastRadio-Padding",
  2299. config: Config{
  2300. Bugs: ProtocolBugs{
  2301. RequireFastradioPadding: true,
  2302. },
  2303. },
  2304. flags: []string{"-fastradio-padding"},
  2305. })
  2306. }
  2307. var testHashes = []struct {
  2308. name string
  2309. id uint8
  2310. }{
  2311. {"SHA1", hashSHA1},
  2312. {"SHA224", hashSHA224},
  2313. {"SHA256", hashSHA256},
  2314. {"SHA384", hashSHA384},
  2315. {"SHA512", hashSHA512},
  2316. }
  2317. func addSigningHashTests() {
  2318. // Make sure each hash works. Include some fake hashes in the list and
  2319. // ensure they're ignored.
  2320. for _, hash := range testHashes {
  2321. testCases = append(testCases, testCase{
  2322. name: "SigningHash-ClientAuth-" + hash.name,
  2323. config: Config{
  2324. ClientAuth: RequireAnyClientCert,
  2325. SignatureAndHashes: []signatureAndHash{
  2326. {signatureRSA, 42},
  2327. {signatureRSA, hash.id},
  2328. {signatureRSA, 255},
  2329. },
  2330. },
  2331. flags: []string{
  2332. "-cert-file", rsaCertificateFile,
  2333. "-key-file", rsaKeyFile,
  2334. },
  2335. })
  2336. testCases = append(testCases, testCase{
  2337. testType: serverTest,
  2338. name: "SigningHash-ServerKeyExchange-Sign-" + hash.name,
  2339. config: Config{
  2340. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  2341. SignatureAndHashes: []signatureAndHash{
  2342. {signatureRSA, 42},
  2343. {signatureRSA, hash.id},
  2344. {signatureRSA, 255},
  2345. },
  2346. },
  2347. })
  2348. }
  2349. // Test that hash resolution takes the signature type into account.
  2350. testCases = append(testCases, testCase{
  2351. name: "SigningHash-ClientAuth-SignatureType",
  2352. config: Config{
  2353. ClientAuth: RequireAnyClientCert,
  2354. SignatureAndHashes: []signatureAndHash{
  2355. {signatureECDSA, hashSHA512},
  2356. {signatureRSA, hashSHA384},
  2357. {signatureECDSA, hashSHA1},
  2358. },
  2359. },
  2360. flags: []string{
  2361. "-cert-file", rsaCertificateFile,
  2362. "-key-file", rsaKeyFile,
  2363. },
  2364. })
  2365. testCases = append(testCases, testCase{
  2366. testType: serverTest,
  2367. name: "SigningHash-ServerKeyExchange-SignatureType",
  2368. config: Config{
  2369. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  2370. SignatureAndHashes: []signatureAndHash{
  2371. {signatureECDSA, hashSHA512},
  2372. {signatureRSA, hashSHA384},
  2373. {signatureECDSA, hashSHA1},
  2374. },
  2375. },
  2376. })
  2377. // Test that, if the list is missing, the peer falls back to SHA-1.
  2378. testCases = append(testCases, testCase{
  2379. name: "SigningHash-ClientAuth-Fallback",
  2380. config: Config{
  2381. ClientAuth: RequireAnyClientCert,
  2382. SignatureAndHashes: []signatureAndHash{
  2383. {signatureRSA, hashSHA1},
  2384. },
  2385. Bugs: ProtocolBugs{
  2386. NoSignatureAndHashes: true,
  2387. },
  2388. },
  2389. flags: []string{
  2390. "-cert-file", rsaCertificateFile,
  2391. "-key-file", rsaKeyFile,
  2392. },
  2393. })
  2394. testCases = append(testCases, testCase{
  2395. testType: serverTest,
  2396. name: "SigningHash-ServerKeyExchange-Fallback",
  2397. config: Config{
  2398. CipherSuites: []uint16{TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
  2399. SignatureAndHashes: []signatureAndHash{
  2400. {signatureRSA, hashSHA1},
  2401. },
  2402. Bugs: ProtocolBugs{
  2403. NoSignatureAndHashes: true,
  2404. },
  2405. },
  2406. })
  2407. }
  2408. // timeouts is the retransmit schedule for BoringSSL. It doubles and
  2409. // caps at 60 seconds. On the 13th timeout, it gives up.
  2410. var timeouts = []time.Duration{
  2411. 1 * time.Second,
  2412. 2 * time.Second,
  2413. 4 * time.Second,
  2414. 8 * time.Second,
  2415. 16 * time.Second,
  2416. 32 * time.Second,
  2417. 60 * time.Second,
  2418. 60 * time.Second,
  2419. 60 * time.Second,
  2420. 60 * time.Second,
  2421. 60 * time.Second,
  2422. 60 * time.Second,
  2423. 60 * time.Second,
  2424. }
  2425. func addDTLSRetransmitTests() {
  2426. // Test that this is indeed the timeout schedule. Stress all
  2427. // four patterns of handshake.
  2428. for i := 1; i < len(timeouts); i++ {
  2429. number := strconv.Itoa(i)
  2430. testCases = append(testCases, testCase{
  2431. protocol: dtls,
  2432. name: "DTLS-Retransmit-Client-" + number,
  2433. config: Config{
  2434. Bugs: ProtocolBugs{
  2435. TimeoutSchedule: timeouts[:i],
  2436. },
  2437. },
  2438. resumeSession: true,
  2439. flags: []string{"-async"},
  2440. })
  2441. testCases = append(testCases, testCase{
  2442. protocol: dtls,
  2443. testType: serverTest,
  2444. name: "DTLS-Retransmit-Server-" + number,
  2445. config: Config{
  2446. Bugs: ProtocolBugs{
  2447. TimeoutSchedule: timeouts[:i],
  2448. },
  2449. },
  2450. resumeSession: true,
  2451. flags: []string{"-async"},
  2452. })
  2453. }
  2454. // Test that exceeding the timeout schedule hits a read
  2455. // timeout.
  2456. testCases = append(testCases, testCase{
  2457. protocol: dtls,
  2458. name: "DTLS-Retransmit-Timeout",
  2459. config: Config{
  2460. Bugs: ProtocolBugs{
  2461. TimeoutSchedule: timeouts,
  2462. },
  2463. },
  2464. resumeSession: true,
  2465. flags: []string{"-async"},
  2466. shouldFail: true,
  2467. expectedError: ":READ_TIMEOUT_EXPIRED:",
  2468. })
  2469. // Test that timeout handling has a fudge factor, due to API
  2470. // problems.
  2471. testCases = append(testCases, testCase{
  2472. protocol: dtls,
  2473. name: "DTLS-Retransmit-Fudge",
  2474. config: Config{
  2475. Bugs: ProtocolBugs{
  2476. TimeoutSchedule: []time.Duration{
  2477. timeouts[0] - 10*time.Millisecond,
  2478. },
  2479. },
  2480. },
  2481. resumeSession: true,
  2482. flags: []string{"-async"},
  2483. })
  2484. }
  2485. func worker(statusChan chan statusMsg, c chan *testCase, buildDir string, wg *sync.WaitGroup) {
  2486. defer wg.Done()
  2487. for test := range c {
  2488. var err error
  2489. if *mallocTest < 0 {
  2490. statusChan <- statusMsg{test: test, started: true}
  2491. err = runTest(test, buildDir, -1)
  2492. } else {
  2493. for mallocNumToFail := int64(*mallocTest); ; mallocNumToFail++ {
  2494. statusChan <- statusMsg{test: test, started: true}
  2495. if err = runTest(test, buildDir, mallocNumToFail); err != errMoreMallocs {
  2496. if err != nil {
  2497. fmt.Printf("\n\nmalloc test failed at %d: %s\n", mallocNumToFail, err)
  2498. }
  2499. break
  2500. }
  2501. }
  2502. }
  2503. statusChan <- statusMsg{test: test, err: err}
  2504. }
  2505. }
  2506. type statusMsg struct {
  2507. test *testCase
  2508. started bool
  2509. err error
  2510. }
  2511. func statusPrinter(doneChan chan struct{}, statusChan chan statusMsg, total int) {
  2512. var started, done, failed, lineLen int
  2513. defer close(doneChan)
  2514. for msg := range statusChan {
  2515. if msg.started {
  2516. started++
  2517. } else {
  2518. done++
  2519. }
  2520. fmt.Printf("\x1b[%dD\x1b[K", lineLen)
  2521. if msg.err != nil {
  2522. fmt.Printf("FAILED (%s)\n%s\n", msg.test.name, msg.err)
  2523. failed++
  2524. }
  2525. line := fmt.Sprintf("%d/%d/%d/%d", failed, done, started, total)
  2526. lineLen = len(line)
  2527. os.Stdout.WriteString(line)
  2528. }
  2529. }
  2530. func main() {
  2531. var flagTest *string = flag.String("test", "", "The name of a test to run, or empty to run all tests")
  2532. var flagNumWorkers *int = flag.Int("num-workers", runtime.NumCPU(), "The number of workers to run in parallel.")
  2533. var flagBuildDir *string = flag.String("build-dir", "../../../build", "The build directory to run the shim from.")
  2534. flag.Parse()
  2535. addCipherSuiteTests()
  2536. addBadECDSASignatureTests()
  2537. addCBCPaddingTests()
  2538. addCBCSplittingTests()
  2539. addClientAuthTests()
  2540. addVersionNegotiationTests()
  2541. addMinimumVersionTests()
  2542. addD5BugTests()
  2543. addExtensionTests()
  2544. addResumptionVersionTests()
  2545. addExtendedMasterSecretTests()
  2546. addRenegotiationTests()
  2547. addDTLSReplayTests()
  2548. addSigningHashTests()
  2549. addFastRadioPaddingTests()
  2550. addDTLSRetransmitTests()
  2551. for _, async := range []bool{false, true} {
  2552. for _, splitHandshake := range []bool{false, true} {
  2553. for _, protocol := range []protocol{tls, dtls} {
  2554. addStateMachineCoverageTests(async, splitHandshake, protocol)
  2555. }
  2556. }
  2557. }
  2558. var wg sync.WaitGroup
  2559. numWorkers := *flagNumWorkers
  2560. statusChan := make(chan statusMsg, numWorkers)
  2561. testChan := make(chan *testCase, numWorkers)
  2562. doneChan := make(chan struct{})
  2563. go statusPrinter(doneChan, statusChan, len(testCases))
  2564. for i := 0; i < numWorkers; i++ {
  2565. wg.Add(1)
  2566. go worker(statusChan, testChan, *flagBuildDir, &wg)
  2567. }
  2568. for i := range testCases {
  2569. if len(*flagTest) == 0 || *flagTest == testCases[i].name {
  2570. testChan <- &testCases[i]
  2571. }
  2572. }
  2573. close(testChan)
  2574. wg.Wait()
  2575. close(statusChan)
  2576. <-doneChan
  2577. fmt.Printf("\n")
  2578. }