diff options
author | wolfbeast <mcwerewolf@gmail.com> | 2018-08-14 07:52:35 +0200 |
---|---|---|
committer | wolfbeast <mcwerewolf@gmail.com> | 2018-08-14 16:42:52 +0200 |
commit | ab1060037931158d3a8bf4c8f9f6cb4dbfe916e9 (patch) | |
tree | 5e4677e52b9a349602f04135a44b3000c8baa97b /security/nss/gtests/ssl_gtest/ssl_drop_unittest.cc | |
parent | f44e99950fc25d16a3cdaffe26dadf7b58a9d38c (diff) | |
download | UXP-ab1060037931158d3a8bf4c8f9f6cb4dbfe916e9.tar UXP-ab1060037931158d3a8bf4c8f9f6cb4dbfe916e9.tar.gz UXP-ab1060037931158d3a8bf4c8f9f6cb4dbfe916e9.tar.lz UXP-ab1060037931158d3a8bf4c8f9f6cb4dbfe916e9.tar.xz UXP-ab1060037931158d3a8bf4c8f9f6cb4dbfe916e9.zip |
Update NSS to 3.38
- Added HACL*Poly1305 32-bit (INRIA/Microsoft)
- Updated to final TLS 1.3 draft version (28)
- Removed TLS 1.3 prerelease draft limit check
- Removed NPN code
- Enabled dev/urandom-only RNG on Linux with NSS_SEED_ONLY_DEV_URANDOM for non-standard environments
- Fixed several bugs with TLS 1.3 negotiation
- Updated internal certificate store
- Added support for the TLS Record Size Limit Extension.
- Fixed CVE-2018-0495
- Various security fixes in the ASN.1 code.
Diffstat (limited to 'security/nss/gtests/ssl_gtest/ssl_drop_unittest.cc')
-rw-r--r-- | security/nss/gtests/ssl_gtest/ssl_drop_unittest.cc | 126 |
1 files changed, 97 insertions, 29 deletions
diff --git a/security/nss/gtests/ssl_gtest/ssl_drop_unittest.cc b/security/nss/gtests/ssl_gtest/ssl_drop_unittest.cc index ee8906deb..e5b52ff06 100644 --- a/security/nss/gtests/ssl_gtest/ssl_drop_unittest.cc +++ b/security/nss/gtests/ssl_gtest/ssl_drop_unittest.cc @@ -66,7 +66,8 @@ TEST_P(TlsConnectDatagramPre13, DropServerSecondFlightThrice) { Connect(); } -class TlsDropDatagram13 : public TlsConnectDatagram13 { +class TlsDropDatagram13 : public TlsConnectDatagram13, + public ::testing::WithParamInterface<bool> { public: TlsDropDatagram13() : client_filters_(), @@ -77,6 +78,9 @@ class TlsDropDatagram13 : public TlsConnectDatagram13 { void SetUp() override { TlsConnectDatagram13::SetUp(); ConfigureSessionCache(RESUME_NONE, RESUME_NONE); + int short_header = GetParam() ? PR_TRUE : PR_FALSE; + client_->SetOption(SSL_ENABLE_DTLS_SHORT_HEADER, short_header); + server_->SetOption(SSL_ENABLE_DTLS_SHORT_HEADER, short_header); SetFilters(); } @@ -138,10 +142,13 @@ class TlsDropDatagram13 : public TlsConnectDatagram13 { void CheckAcks(const DropAckChain& chain, size_t index, std::vector<uint64_t> acks) { const DataBuffer& buf = chain.ack_->record(index).buffer; - size_t offset = 0; + size_t offset = 2; + uint64_t len; - EXPECT_EQ(acks.size() * 8, buf.len()); - if ((acks.size() * 8) != buf.len()) { + EXPECT_EQ(2 + acks.size() * 8, buf.len()); + ASSERT_TRUE(buf.Read(0, 2, &len)); + ASSERT_EQ(static_cast<size_t>(len + 2), buf.len()); + if ((2 + acks.size() * 8) != buf.len()) { while (offset < buf.len()) { uint64_t ack; ASSERT_TRUE(buf.Read(offset, 8, &ack)); @@ -186,7 +193,7 @@ class TlsDropDatagram13 : public TlsConnectDatagram13 { // to the client upon receiving the client Finished. // Dropping complete first and second flights does not produce // ACKs -TEST_F(TlsDropDatagram13, DropClientFirstFlightOnce) { +TEST_P(TlsDropDatagram13, DropClientFirstFlightOnce) { client_filters_.drop_->Reset({0}); StartConnect(); client_->Handshake(); @@ -195,7 +202,7 @@ TEST_F(TlsDropDatagram13, DropClientFirstFlightOnce) { CheckAcks(server_filters_, 0, {0x0002000000000000ULL}); } -TEST_F(TlsDropDatagram13, DropServerFirstFlightOnce) { +TEST_P(TlsDropDatagram13, DropServerFirstFlightOnce) { server_filters_.drop_->Reset(0xff); StartConnect(); client_->Handshake(); @@ -209,7 +216,7 @@ TEST_F(TlsDropDatagram13, DropServerFirstFlightOnce) { // Dropping the server's first record also does not produce // an ACK because the next record is ignored. // TODO(ekr@rtfm.com): We should generate an empty ACK. -TEST_F(TlsDropDatagram13, DropServerFirstRecordOnce) { +TEST_P(TlsDropDatagram13, DropServerFirstRecordOnce) { server_filters_.drop_->Reset({0}); StartConnect(); client_->Handshake(); @@ -221,7 +228,7 @@ TEST_F(TlsDropDatagram13, DropServerFirstRecordOnce) { // Dropping the second packet of the server's flight should // produce an ACK. -TEST_F(TlsDropDatagram13, DropServerSecondRecordOnce) { +TEST_P(TlsDropDatagram13, DropServerSecondRecordOnce) { server_filters_.drop_->Reset({1}); StartConnect(); client_->Handshake(); @@ -235,7 +242,7 @@ TEST_F(TlsDropDatagram13, DropServerSecondRecordOnce) { // Drop the server ACK and verify that the client retransmits // the ClientHello. -TEST_F(TlsDropDatagram13, DropServerAckOnce) { +TEST_P(TlsDropDatagram13, DropServerAckOnce) { StartConnect(); client_->Handshake(); server_->Handshake(); @@ -263,7 +270,7 @@ TEST_F(TlsDropDatagram13, DropServerAckOnce) { } // Drop the client certificate verify. -TEST_F(TlsDropDatagram13, DropClientCertVerify) { +TEST_P(TlsDropDatagram13, DropClientCertVerify) { StartConnect(); client_->SetupClientAuth(); server_->RequestClientAuth(true); @@ -284,7 +291,7 @@ TEST_F(TlsDropDatagram13, DropClientCertVerify) { } // Shrink the MTU down so that certs get split and drop the first piece. -TEST_F(TlsDropDatagram13, DropFirstHalfOfServerCertificate) { +TEST_P(TlsDropDatagram13, DropFirstHalfOfServerCertificate) { server_filters_.drop_->Reset({2}); StartConnect(); ShrinkPostServerHelloMtu(); @@ -311,7 +318,7 @@ TEST_F(TlsDropDatagram13, DropFirstHalfOfServerCertificate) { } // Shrink the MTU down so that certs get split and drop the second piece. -TEST_F(TlsDropDatagram13, DropSecondHalfOfServerCertificate) { +TEST_P(TlsDropDatagram13, DropSecondHalfOfServerCertificate) { server_filters_.drop_->Reset({3}); StartConnect(); ShrinkPostServerHelloMtu(); @@ -524,11 +531,11 @@ class TlsFragmentationAndRecoveryTest : public TlsDropDatagram13 { size_t cert_len_; }; -TEST_F(TlsFragmentationAndRecoveryTest, DropFirstHalf) { RunTest(0); } +TEST_P(TlsFragmentationAndRecoveryTest, DropFirstHalf) { RunTest(0); } -TEST_F(TlsFragmentationAndRecoveryTest, DropSecondHalf) { RunTest(1); } +TEST_P(TlsFragmentationAndRecoveryTest, DropSecondHalf) { RunTest(1); } -TEST_F(TlsDropDatagram13, NoDropsDuringZeroRtt) { +TEST_P(TlsDropDatagram13, NoDropsDuringZeroRtt) { SetupForZeroRtt(); SetFilters(); std::cerr << "Starting second handshake" << std::endl; @@ -546,7 +553,7 @@ TEST_F(TlsDropDatagram13, NoDropsDuringZeroRtt) { 0x0002000000000000ULL}); // Finished } -TEST_F(TlsDropDatagram13, DropEEDuringZeroRtt) { +TEST_P(TlsDropDatagram13, DropEEDuringZeroRtt) { SetupForZeroRtt(); SetFilters(); std::cerr << "Starting second handshake" << std::endl; @@ -591,7 +598,7 @@ class TlsReorderDatagram13 : public TlsDropDatagram13 { // Reorder the server records so that EE comes at the end // of the flight and will still produce an ACK. -TEST_F(TlsDropDatagram13, ReorderServerEE) { +TEST_P(TlsDropDatagram13, ReorderServerEE) { server_filters_.drop_->Reset({1}); StartConnect(); client_->Handshake(); @@ -647,7 +654,7 @@ class TlsSendCipherSpecCapturer { std::vector<std::shared_ptr<TlsCipherSpec>> send_cipher_specs_; }; -TEST_F(TlsDropDatagram13, SendOutOfOrderAppWithHandshakeKey) { +TEST_P(TlsDropDatagram13, SendOutOfOrderAppWithHandshakeKey) { StartConnect(); TlsSendCipherSpecCapturer capturer(client_); client_->Handshake(); @@ -662,9 +669,9 @@ TEST_F(TlsDropDatagram13, SendOutOfOrderAppWithHandshakeKey) { auto spec = capturer.spec(0); ASSERT_NE(nullptr, spec.get()); ASSERT_EQ(2, spec->epoch()); - ASSERT_TRUE(client_->SendEncryptedRecord( - spec, SSL_LIBRARY_VERSION_DTLS_1_2_WIRE, 0x0002000000000002, - kTlsApplicationDataType, DataBuffer(buf, sizeof(buf)))); + ASSERT_TRUE(client_->SendEncryptedRecord(spec, 0x0002000000000002, + kTlsApplicationDataType, + DataBuffer(buf, sizeof(buf)))); // Now have the server consume the bogus message. server_->ExpectSendAlert(illegal_parameter, kTlsAlertFatal); @@ -673,7 +680,7 @@ TEST_F(TlsDropDatagram13, SendOutOfOrderAppWithHandshakeKey) { EXPECT_EQ(SSL_ERROR_RX_UNKNOWN_RECORD_TYPE, PORT_GetError()); } -TEST_F(TlsDropDatagram13, SendOutOfOrderHsNonsenseWithHandshakeKey) { +TEST_P(TlsDropDatagram13, SendOutOfOrderHsNonsenseWithHandshakeKey) { StartConnect(); TlsSendCipherSpecCapturer capturer(client_); client_->Handshake(); @@ -688,9 +695,9 @@ TEST_F(TlsDropDatagram13, SendOutOfOrderHsNonsenseWithHandshakeKey) { auto spec = capturer.spec(0); ASSERT_NE(nullptr, spec.get()); ASSERT_EQ(2, spec->epoch()); - ASSERT_TRUE(client_->SendEncryptedRecord( - spec, SSL_LIBRARY_VERSION_DTLS_1_2_WIRE, 0x0002000000000002, - kTlsHandshakeType, DataBuffer(buf, sizeof(buf)))); + ASSERT_TRUE(client_->SendEncryptedRecord(spec, 0x0002000000000002, + kTlsHandshakeType, + DataBuffer(buf, sizeof(buf)))); server_->Handshake(); EXPECT_EQ(2UL, server_filters_.ack_->count()); // The server acknowledges client Finished twice. @@ -700,7 +707,7 @@ TEST_F(TlsDropDatagram13, SendOutOfOrderHsNonsenseWithHandshakeKey) { // Shrink the MTU down so that certs get split and then swap the first and // second pieces of the server certificate. -TEST_F(TlsReorderDatagram13, ReorderServerCertificate) { +TEST_P(TlsReorderDatagram13, ReorderServerCertificate) { StartConnect(); ShrinkPostServerHelloMtu(); client_->Handshake(); @@ -722,7 +729,7 @@ TEST_F(TlsReorderDatagram13, ReorderServerCertificate) { CheckAcks(server_filters_, 0, {0x0002000000000000ULL}); } -TEST_F(TlsReorderDatagram13, DataAfterEOEDDuringZeroRtt) { +TEST_P(TlsReorderDatagram13, DataAfterEOEDDuringZeroRtt) { SetupForZeroRtt(); SetFilters(); std::cerr << "Starting second handshake" << std::endl; @@ -761,7 +768,7 @@ TEST_F(TlsReorderDatagram13, DataAfterEOEDDuringZeroRtt) { EXPECT_EQ(PR_WOULD_BLOCK_ERROR, PORT_GetError()); } -TEST_F(TlsReorderDatagram13, DataAfterFinDuringZeroRtt) { +TEST_P(TlsReorderDatagram13, DataAfterFinDuringZeroRtt) { SetupForZeroRtt(); SetFilters(); std::cerr << "Starting second handshake" << std::endl; @@ -812,12 +819,17 @@ static void GetCipherAndLimit(uint16_t version, uint16_t* cipher, *cipher = TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256; *limit = (1ULL << 48) - 1; } else { + // This test probably isn't especially useful for TLS 1.3, which has a much + // shorter sequence number encoding. That space can probably be searched in + // a reasonable amount of time. *cipher = TLS_CHACHA20_POLY1305_SHA256; - *limit = (1ULL << 48) - 1; + // Assume that we are starting with an expected sequence number of 0. + *limit = (1ULL << 29) - 1; } } // This simulates a huge number of drops on one side. +// See Bug 12965514 where a large gap was handled very inefficiently. TEST_P(TlsConnectDatagram, MissLotsOfPackets) { uint16_t cipher; uint64_t limit; @@ -834,6 +846,17 @@ TEST_P(TlsConnectDatagram, MissLotsOfPackets) { SendReceive(); } +// Send a sequence number of 0xfffffffd and it should be interpreted as that +// (and not -3 or UINT64_MAX - 2). +TEST_F(TlsConnectDatagram13, UnderflowSequenceNumber) { + Connect(); + // This is only valid if short headers are disabled. + client_->SetOption(SSL_ENABLE_DTLS_SHORT_HEADER, PR_FALSE); + EXPECT_EQ(SECSuccess, + SSLInt_AdvanceWriteSeqNum(client_->ssl_fd(), (1ULL << 30) - 3)); + SendReceive(); +} + class TlsConnectDatagram12Plus : public TlsConnectDatagram { public: TlsConnectDatagram12Plus() : TlsConnectDatagram() {} @@ -861,9 +884,54 @@ TEST_P(TlsConnectDatagram12Plus, MissAWindowAndOne) { SendReceive(); } +// This filter replaces the first record it sees with junk application data. +class TlsReplaceFirstRecordWithJunk : public TlsRecordFilter { + public: + TlsReplaceFirstRecordWithJunk(const std::shared_ptr<TlsAgent>& a) + : TlsRecordFilter(a), replaced_(false) {} + + protected: + PacketFilter::Action FilterRecord(const TlsRecordHeader& header, + const DataBuffer& record, size_t* offset, + DataBuffer* output) override { + if (replaced_) { + return KEEP; + } + replaced_ = true; + TlsRecordHeader out_header(header.variant(), header.version(), + kTlsApplicationDataType, + header.sequence_number()); + + static const uint8_t junk[] = {1, 2, 3, 4}; + *offset = out_header.Write(output, *offset, DataBuffer(junk, sizeof(junk))); + return CHANGE; + } + + private: + bool replaced_; +}; + +// DTLS needs to discard application_data that it receives prior to handshake +// completion, not generate an error. +TEST_P(TlsConnectDatagram, ReplaceFirstServerRecordWithApplicationData) { + MakeTlsFilter<TlsReplaceFirstRecordWithJunk>(server_); + Connect(); +} + +TEST_P(TlsConnectDatagram, ReplaceFirstClientRecordWithApplicationData) { + MakeTlsFilter<TlsReplaceFirstRecordWithJunk>(client_); + Connect(); +} + INSTANTIATE_TEST_CASE_P(Datagram12Plus, TlsConnectDatagram12Plus, TlsConnectTestBase::kTlsV12Plus); INSTANTIATE_TEST_CASE_P(DatagramPre13, TlsConnectDatagramPre13, TlsConnectTestBase::kTlsV11V12); +INSTANTIATE_TEST_CASE_P(DatagramDrop13, TlsDropDatagram13, + ::testing::Values(true, false)); +INSTANTIATE_TEST_CASE_P(DatagramReorder13, TlsReorderDatagram13, + ::testing::Values(true, false)); +INSTANTIATE_TEST_CASE_P(DatagramFragment13, TlsFragmentationAndRecoveryTest, + ::testing::Values(true, false)); } // namespace nss_test |