OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2011 The WebRTC Project Authors. All rights reserved. | 2 * Copyright 2011 The WebRTC Project Authors. All rights reserved. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license | 4 * Use of this source code is governed by a BSD-style license |
5 * that can be found in the LICENSE file in the root of the source | 5 * that can be found in the LICENSE file in the root of the source |
6 * tree. An additional intellectual property rights grant can be found | 6 * tree. An additional intellectual property rights grant can be found |
7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
9 */ | 9 */ |
10 | 10 |
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
74 return certificate_; | 74 return certificate_; |
75 } | 75 } |
76 void SetupSrtp() { | 76 void SetupSrtp() { |
77 ASSERT(certificate_); | 77 ASSERT(certificate_); |
78 use_dtls_srtp_ = true; | 78 use_dtls_srtp_ = true; |
79 } | 79 } |
80 void SetupMaxProtocolVersion(rtc::SSLProtocolVersion version) { | 80 void SetupMaxProtocolVersion(rtc::SSLProtocolVersion version) { |
81 ASSERT(!transport_); | 81 ASSERT(!transport_); |
82 ssl_max_version_ = version; | 82 ssl_max_version_ = version; |
83 } | 83 } |
84 void SetupChannels(int count, cricket::IceRole role, int async_delay_ms = 0) { | 84 void SetupChannels(int count, cricket::IceRole role) { |
85 transport_.reset(new cricket::DtlsTransport<cricket::FakeTransport>( | 85 transport_.reset(new cricket::DtlsTransport<cricket::FakeTransport>( |
86 "dtls content name", nullptr, certificate_)); | 86 "dtls content name", nullptr, certificate_)); |
87 transport_->SetAsync(true); | 87 transport_->SetAsync(true); |
88 transport_->SetAsyncDelay(async_delay_ms); | |
89 transport_->SetIceRole(role); | 88 transport_->SetIceRole(role); |
90 transport_->SetIceTiebreaker( | 89 transport_->SetIceTiebreaker( |
91 (role == cricket::ICEROLE_CONTROLLING) ? 1 : 2); | 90 (role == cricket::ICEROLE_CONTROLLING) ? 1 : 2); |
92 | 91 |
93 for (int i = 0; i < count; ++i) { | 92 for (int i = 0; i < count; ++i) { |
94 cricket::DtlsTransportChannelWrapper* channel = | 93 cricket::DtlsTransportChannelWrapper* channel = |
95 static_cast<cricket::DtlsTransportChannelWrapper*>( | 94 static_cast<cricket::DtlsTransportChannelWrapper*>( |
96 transport_->CreateChannel(i)); | 95 transport_->CreateChannel(i)); |
97 ASSERT_TRUE(channel != NULL); | 96 ASSERT_TRUE(channel != NULL); |
98 channel->SetSslMaxProtocolVersion(ssl_max_version_); | 97 channel->SetSslMaxProtocolVersion(ssl_max_version_); |
(...skipping 14 matching lines...) Expand all Loading... |
113 cricket::Transport* transport() { return transport_.get(); } | 112 cricket::Transport* transport() { return transport_.get(); } |
114 | 113 |
115 cricket::FakeTransportChannel* GetFakeChannel(int component) { | 114 cricket::FakeTransportChannel* GetFakeChannel(int component) { |
116 cricket::TransportChannelImpl* ch = transport_->GetChannel(component); | 115 cricket::TransportChannelImpl* ch = transport_->GetChannel(component); |
117 cricket::DtlsTransportChannelWrapper* wrapper = | 116 cricket::DtlsTransportChannelWrapper* wrapper = |
118 static_cast<cricket::DtlsTransportChannelWrapper*>(ch); | 117 static_cast<cricket::DtlsTransportChannelWrapper*>(ch); |
119 return (wrapper) ? | 118 return (wrapper) ? |
120 static_cast<cricket::FakeTransportChannel*>(wrapper->channel()) : NULL; | 119 static_cast<cricket::FakeTransportChannel*>(wrapper->channel()) : NULL; |
121 } | 120 } |
122 | 121 |
123 cricket::DtlsTransportChannelWrapper* GetDtlsChannel(int component) { | |
124 cricket::TransportChannelImpl* ch = transport_->GetChannel(component); | |
125 return static_cast<cricket::DtlsTransportChannelWrapper*>(ch); | |
126 } | |
127 | |
128 // Offer DTLS if we have an identity; pass in a remote fingerprint only if | 122 // Offer DTLS if we have an identity; pass in a remote fingerprint only if |
129 // both sides support DTLS. | 123 // both sides support DTLS. |
130 void Negotiate(DtlsTestClient* peer, cricket::ContentAction action, | 124 void Negotiate(DtlsTestClient* peer, cricket::ContentAction action, |
131 ConnectionRole local_role, ConnectionRole remote_role, | 125 ConnectionRole local_role, ConnectionRole remote_role, |
132 int flags) { | 126 int flags) { |
133 Negotiate(certificate_, certificate_ ? peer->certificate_ : nullptr, action, | 127 Negotiate(certificate_, certificate_ ? peer->certificate_ : nullptr, action, |
134 local_role, remote_role, flags); | 128 local_role, remote_role, flags); |
135 } | 129 } |
136 | 130 |
137 void MaybeSetSrtpCryptoSuites() { | 131 void MaybeSetSrtpCryptoSuites() { |
(...skipping 13 matching lines...) Expand all Loading... |
151 cricket::ContentAction action, | 145 cricket::ContentAction action, |
152 ConnectionRole role, | 146 ConnectionRole role, |
153 int flags) { | 147 int flags) { |
154 // If |NF_EXPECT_FAILURE| is set, expect SRTD or SLTD to fail when | 148 // If |NF_EXPECT_FAILURE| is set, expect SRTD or SLTD to fail when |
155 // content action is CA_ANSWER. | 149 // content action is CA_ANSWER. |
156 bool expect_success = | 150 bool expect_success = |
157 !((action == cricket::CA_ANSWER) && (flags & NF_EXPECT_FAILURE)); | 151 !((action == cricket::CA_ANSWER) && (flags & NF_EXPECT_FAILURE)); |
158 EXPECT_EQ(expect_success, | 152 EXPECT_EQ(expect_success, |
159 transport_->SetLocalTransportDescription( | 153 transport_->SetLocalTransportDescription( |
160 MakeTransportDescription(cert, role), action, nullptr)); | 154 MakeTransportDescription(cert, role), action, nullptr)); |
| 155 set_local_cert_ = (cert != nullptr); |
161 } | 156 } |
162 | 157 |
163 void SetRemoteTransportDescription( | 158 void SetRemoteTransportDescription( |
164 const rtc::scoped_refptr<rtc::RTCCertificate>& cert, | 159 const rtc::scoped_refptr<rtc::RTCCertificate>& cert, |
165 cricket::ContentAction action, | 160 cricket::ContentAction action, |
166 ConnectionRole role, | 161 ConnectionRole role, |
167 int flags) { | 162 int flags) { |
168 // If |NF_EXPECT_FAILURE| is set, expect SRTD or SLTD to fail when | 163 // If |NF_EXPECT_FAILURE| is set, expect SRTD or SLTD to fail when |
169 // content action is CA_ANSWER. | 164 // content action is CA_ANSWER. |
170 bool expect_success = | 165 bool expect_success = |
171 !((action == cricket::CA_ANSWER) && (flags & NF_EXPECT_FAILURE)); | 166 !((action == cricket::CA_ANSWER) && (flags & NF_EXPECT_FAILURE)); |
172 EXPECT_EQ(expect_success, | 167 EXPECT_EQ(expect_success, |
173 transport_->SetRemoteTransportDescription( | 168 transport_->SetRemoteTransportDescription( |
174 MakeTransportDescription(cert, role), action, nullptr)); | 169 MakeTransportDescription(cert, role), action, nullptr)); |
| 170 set_remote_cert_ = (cert != nullptr); |
175 } | 171 } |
176 | 172 |
177 // Allow any DTLS configuration to be specified (including invalid ones). | 173 // Allow any DTLS configuration to be specified (including invalid ones). |
178 void Negotiate(const rtc::scoped_refptr<rtc::RTCCertificate>& local_cert, | 174 void Negotiate(const rtc::scoped_refptr<rtc::RTCCertificate>& local_cert, |
179 const rtc::scoped_refptr<rtc::RTCCertificate>& remote_cert, | 175 const rtc::scoped_refptr<rtc::RTCCertificate>& remote_cert, |
180 cricket::ContentAction action, | 176 cricket::ContentAction action, |
181 ConnectionRole local_role, | 177 ConnectionRole local_role, |
182 ConnectionRole remote_role, | 178 ConnectionRole remote_role, |
183 int flags) { | 179 int flags) { |
184 if (!(flags & NF_REOFFER)) { | 180 if (!(flags & NF_REOFFER)) { |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
226 return false; | 222 return false; |
227 } | 223 } |
228 } | 224 } |
229 return true; | 225 return true; |
230 } | 226 } |
231 | 227 |
232 int received_dtls_client_hellos() const { | 228 int received_dtls_client_hellos() const { |
233 return received_dtls_client_hellos_; | 229 return received_dtls_client_hellos_; |
234 } | 230 } |
235 | 231 |
236 int received_dtls_server_hellos() const { | 232 bool negotiated_dtls() const { return set_local_cert_ && set_remote_cert_; } |
237 return received_dtls_server_hellos_; | |
238 } | |
239 | |
240 bool negotiated_dtls() const { | |
241 return transport_->local_description() && | |
242 transport_->local_description()->identity_fingerprint && | |
243 transport_->remote_description() && | |
244 transport_->remote_description()->identity_fingerprint; | |
245 } | |
246 | 233 |
247 void CheckRole(rtc::SSLRole role) { | 234 void CheckRole(rtc::SSLRole role) { |
248 if (role == rtc::SSL_CLIENT) { | 235 if (role == rtc::SSL_CLIENT) { |
249 ASSERT_EQ(0, received_dtls_client_hellos_); | 236 ASSERT_EQ(0, received_dtls_client_hellos_); |
250 ASSERT_GT(received_dtls_server_hellos_, 0); | 237 ASSERT_GT(received_dtls_server_hellos_, 0); |
251 } else { | 238 } else { |
252 ASSERT_GT(received_dtls_client_hellos_, 0); | 239 ASSERT_GT(received_dtls_client_hellos_, 0); |
253 ASSERT_EQ(0, received_dtls_server_hellos_); | 240 ASSERT_EQ(0, received_dtls_server_hellos_); |
254 } | 241 } |
255 } | 242 } |
(...skipping 161 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
417 | 404 |
418 private: | 405 private: |
419 std::string name_; | 406 std::string name_; |
420 rtc::scoped_refptr<rtc::RTCCertificate> certificate_; | 407 rtc::scoped_refptr<rtc::RTCCertificate> certificate_; |
421 std::unique_ptr<cricket::FakeTransport> transport_; | 408 std::unique_ptr<cricket::FakeTransport> transport_; |
422 std::vector<cricket::DtlsTransportChannelWrapper*> channels_; | 409 std::vector<cricket::DtlsTransportChannelWrapper*> channels_; |
423 size_t packet_size_ = 0u; | 410 size_t packet_size_ = 0u; |
424 std::set<int> received_; | 411 std::set<int> received_; |
425 bool use_dtls_srtp_ = false; | 412 bool use_dtls_srtp_ = false; |
426 rtc::SSLProtocolVersion ssl_max_version_ = rtc::SSL_PROTOCOL_DTLS_12; | 413 rtc::SSLProtocolVersion ssl_max_version_ = rtc::SSL_PROTOCOL_DTLS_12; |
| 414 bool set_local_cert_ = false; |
| 415 bool set_remote_cert_ = false; |
427 int received_dtls_client_hellos_ = 0; | 416 int received_dtls_client_hellos_ = 0; |
428 int received_dtls_server_hellos_ = 0; | 417 int received_dtls_server_hellos_ = 0; |
429 rtc::SentPacket sent_packet_; | 418 rtc::SentPacket sent_packet_; |
430 }; | 419 }; |
431 | 420 |
432 // Base class for DtlsTransportChannelTest and DtlsEventOrderingTest, which | |
433 // inherit from different variants of testing::Test. | |
434 // | |
435 // Note that this test always uses a FakeClock, due to the |fake_clock_| member | 421 // Note that this test always uses a FakeClock, due to the |fake_clock_| member |
436 // variable. | 422 // variable. |
437 class DtlsTransportChannelTestBase { | 423 class DtlsTransportChannelTest : public testing::Test { |
438 public: | 424 public: |
439 DtlsTransportChannelTestBase() | 425 DtlsTransportChannelTest() |
440 : client1_("P1"), | 426 : client1_("P1"), |
441 client2_("P2"), | 427 client2_("P2"), |
442 channel_ct_(1), | 428 channel_ct_(1), |
443 use_dtls_(false), | 429 use_dtls_(false), |
444 use_dtls_srtp_(false), | 430 use_dtls_srtp_(false), |
445 ssl_expected_version_(rtc::SSL_PROTOCOL_DTLS_12) {} | 431 ssl_expected_version_(rtc::SSL_PROTOCOL_DTLS_12) {} |
446 | 432 |
447 void SetChannelCount(size_t channel_ct) { | 433 void SetChannelCount(size_t channel_ct) { |
448 channel_ct_ = static_cast<int>(channel_ct); | 434 channel_ct_ = static_cast<int>(channel_ct); |
449 } | 435 } |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
502 client2_.certificate(), cricket::CA_ANSWER, client2_role, 0); | 488 client2_.certificate(), cricket::CA_ANSWER, client2_role, 0); |
503 rv = client1_.Connect(&client2_, false); | 489 rv = client1_.Connect(&client2_, false); |
504 client1_.SetRemoteTransportDescription( | 490 client1_.SetRemoteTransportDescription( |
505 client2_.certificate(), cricket::CA_ANSWER, client2_role, 0); | 491 client2_.certificate(), cricket::CA_ANSWER, client2_role, 0); |
506 } | 492 } |
507 | 493 |
508 EXPECT_TRUE(rv); | 494 EXPECT_TRUE(rv); |
509 if (!rv) | 495 if (!rv) |
510 return false; | 496 return false; |
511 | 497 |
512 EXPECT_TRUE_SIMULATED_WAIT( | 498 EXPECT_TRUE_WAIT( |
513 client1_.all_channels_writable() && client2_.all_channels_writable(), | 499 client1_.all_channels_writable() && client2_.all_channels_writable(), |
514 kTimeout, fake_clock_); | 500 kTimeout); |
515 if (!client1_.all_channels_writable() || !client2_.all_channels_writable()) | 501 if (!client1_.all_channels_writable() || !client2_.all_channels_writable()) |
516 return false; | 502 return false; |
517 | 503 |
518 // Check that we used the right roles. | 504 // Check that we used the right roles. |
519 if (use_dtls_) { | 505 if (use_dtls_) { |
520 rtc::SSLRole client1_ssl_role = | 506 rtc::SSLRole client1_ssl_role = |
521 (client1_role == cricket::CONNECTIONROLE_ACTIVE || | 507 (client1_role == cricket::CONNECTIONROLE_ACTIVE || |
522 (client2_role == cricket::CONNECTIONROLE_PASSIVE && | 508 (client2_role == cricket::CONNECTIONROLE_PASSIVE && |
523 client1_role == cricket::CONNECTIONROLE_ACTPASS)) ? | 509 client1_role == cricket::CONNECTIONROLE_ACTPASS)) ? |
524 rtc::SSL_CLIENT : rtc::SSL_SERVER; | 510 rtc::SSL_CLIENT : rtc::SSL_SERVER; |
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
595 client2_role, client1_role, flags); | 581 client2_role, client1_role, flags); |
596 client1_.Negotiate(&client2_, cricket::CA_ANSWER, | 582 client1_.Negotiate(&client2_, cricket::CA_ANSWER, |
597 client1_role, client2_role, flags); | 583 client1_role, client2_role, flags); |
598 } | 584 } |
599 } | 585 } |
600 | 586 |
601 void TestTransfer(size_t channel, size_t size, size_t count, bool srtp) { | 587 void TestTransfer(size_t channel, size_t size, size_t count, bool srtp) { |
602 LOG(LS_INFO) << "Expect packets, size=" << size; | 588 LOG(LS_INFO) << "Expect packets, size=" << size; |
603 client2_.ExpectPackets(channel, size); | 589 client2_.ExpectPackets(channel, size); |
604 client1_.SendPackets(channel, size, count, srtp); | 590 client1_.SendPackets(channel, size, count, srtp); |
605 EXPECT_EQ_SIMULATED_WAIT(count, client2_.NumPacketsReceived(), kTimeout, | 591 EXPECT_EQ_WAIT(count, client2_.NumPacketsReceived(), kTimeout); |
606 fake_clock_); | |
607 } | 592 } |
608 | 593 |
609 protected: | 594 protected: |
610 rtc::ScopedFakeClock fake_clock_; | 595 rtc::ScopedFakeClock fake_clock_; |
611 DtlsTestClient client1_; | 596 DtlsTestClient client1_; |
612 DtlsTestClient client2_; | 597 DtlsTestClient client2_; |
613 int channel_ct_; | 598 int channel_ct_; |
614 bool use_dtls_; | 599 bool use_dtls_; |
615 bool use_dtls_srtp_; | 600 bool use_dtls_srtp_; |
616 rtc::SSLProtocolVersion ssl_expected_version_; | 601 rtc::SSLProtocolVersion ssl_expected_version_; |
617 }; | 602 }; |
618 | 603 |
619 class DtlsTransportChannelTest : public DtlsTransportChannelTestBase, | |
620 public ::testing::Test {}; | |
621 | |
622 // Test that transport negotiation of ICE, no DTLS works properly. | 604 // Test that transport negotiation of ICE, no DTLS works properly. |
623 TEST_F(DtlsTransportChannelTest, TestChannelSetupIce) { | 605 TEST_F(DtlsTransportChannelTest, TestChannelSetupIce) { |
624 Negotiate(); | 606 Negotiate(); |
625 cricket::FakeTransportChannel* channel1 = client1_.GetFakeChannel(0); | 607 cricket::FakeTransportChannel* channel1 = client1_.GetFakeChannel(0); |
626 cricket::FakeTransportChannel* channel2 = client2_.GetFakeChannel(0); | 608 cricket::FakeTransportChannel* channel2 = client2_.GetFakeChannel(0); |
627 ASSERT_TRUE(channel1 != NULL); | 609 ASSERT_TRUE(channel1 != NULL); |
628 ASSERT_TRUE(channel2 != NULL); | 610 ASSERT_TRUE(channel2 != NULL); |
629 EXPECT_EQ(cricket::ICEROLE_CONTROLLING, channel1->GetIceRole()); | 611 EXPECT_EQ(cricket::ICEROLE_CONTROLLING, channel1->GetIceRole()); |
630 EXPECT_EQ(1U, channel1->IceTiebreaker()); | 612 EXPECT_EQ(1U, channel1->IceTiebreaker()); |
631 EXPECT_EQ(kIceUfrag1, channel1->ice_ufrag()); | 613 EXPECT_EQ(kIceUfrag1, channel1->ice_ufrag()); |
(...skipping 263 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
895 MAYBE_SKIP_TEST(HaveDtlsSrtp); | 877 MAYBE_SKIP_TEST(HaveDtlsSrtp); |
896 SetChannelCount(2); | 878 SetChannelCount(2); |
897 PrepareDtls(true, true, rtc::KT_DEFAULT); | 879 PrepareDtls(true, true, rtc::KT_DEFAULT); |
898 PrepareDtlsSrtp(true, true); | 880 PrepareDtlsSrtp(true, true); |
899 Negotiate(); | 881 Negotiate(); |
900 | 882 |
901 Renegotiate(&client1_, cricket::CONNECTIONROLE_ACTPASS, | 883 Renegotiate(&client1_, cricket::CONNECTIONROLE_ACTPASS, |
902 cricket::CONNECTIONROLE_ACTIVE, NF_REOFFER); | 884 cricket::CONNECTIONROLE_ACTIVE, NF_REOFFER); |
903 bool rv = client1_.Connect(&client2_, false); | 885 bool rv = client1_.Connect(&client2_, false); |
904 EXPECT_TRUE(rv); | 886 EXPECT_TRUE(rv); |
905 EXPECT_TRUE_SIMULATED_WAIT( | 887 EXPECT_TRUE_WAIT( |
906 client1_.all_channels_writable() && client2_.all_channels_writable(), | 888 client1_.all_channels_writable() && client2_.all_channels_writable(), |
907 kTimeout, fake_clock_); | 889 kTimeout); |
908 | 890 |
909 TestTransfer(0, 1000, 100, true); | 891 TestTransfer(0, 1000, 100, true); |
910 TestTransfer(1, 1000, 100, true); | 892 TestTransfer(1, 1000, 100, true); |
911 } | 893 } |
912 | 894 |
913 // Test Certificates state after negotiation but before connection. | 895 // Test Certificates state after negotiation but before connection. |
914 TEST_F(DtlsTransportChannelTest, TestCertificatesBeforeConnect) { | 896 TEST_F(DtlsTransportChannelTest, TestCertificatesBeforeConnect) { |
915 MAYBE_SKIP_TEST(HaveDtls); | 897 MAYBE_SKIP_TEST(HaveDtls); |
916 PrepareDtls(true, true, rtc::KT_DEFAULT); | 898 PrepareDtls(true, true, rtc::KT_DEFAULT); |
917 Negotiate(); | 899 Negotiate(); |
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
952 ASSERT_TRUE(remote_cert1); | 934 ASSERT_TRUE(remote_cert1); |
953 ASSERT_EQ(remote_cert1->ToPEMString(), | 935 ASSERT_EQ(remote_cert1->ToPEMString(), |
954 certificate2->ssl_certificate().ToPEMString()); | 936 certificate2->ssl_certificate().ToPEMString()); |
955 std::unique_ptr<rtc::SSLCertificate> remote_cert2 = | 937 std::unique_ptr<rtc::SSLCertificate> remote_cert2 = |
956 client2_.transport()->GetRemoteSSLCertificate(); | 938 client2_.transport()->GetRemoteSSLCertificate(); |
957 ASSERT_TRUE(remote_cert2); | 939 ASSERT_TRUE(remote_cert2); |
958 ASSERT_EQ(remote_cert2->ToPEMString(), | 940 ASSERT_EQ(remote_cert2->ToPEMString(), |
959 certificate1->ssl_certificate().ToPEMString()); | 941 certificate1->ssl_certificate().ToPEMString()); |
960 } | 942 } |
961 | 943 |
| 944 // Test that DTLS completes promptly if a ClientHello is received before the |
| 945 // transport channel is writable (allowing a ServerHello to be sent). |
| 946 TEST_F(DtlsTransportChannelTest, TestReceiveClientHelloBeforeWritable) { |
| 947 MAYBE_SKIP_TEST(HaveDtls); |
| 948 PrepareDtls(true, true, rtc::KT_DEFAULT); |
| 949 // Exchange transport descriptions. |
| 950 Negotiate(cricket::CONNECTIONROLE_ACTPASS, cricket::CONNECTIONROLE_ACTIVE); |
| 951 |
| 952 // Make client2_ writable, but not client1_. |
| 953 EXPECT_TRUE(client2_.Connect(&client1_, true)); |
| 954 EXPECT_TRUE_WAIT(client2_.all_raw_channels_writable(), kTimeout); |
| 955 |
| 956 // Expect a DTLS ClientHello to be sent even while client1_ isn't writable. |
| 957 EXPECT_EQ_WAIT(1, client1_.received_dtls_client_hellos(), kTimeout); |
| 958 EXPECT_FALSE(client1_.all_raw_channels_writable()); |
| 959 |
| 960 // Now make client1_ writable and expect the handshake to complete |
| 961 // without client2_ needing to retransmit the ClientHello. |
| 962 EXPECT_TRUE(client1_.Connect(&client2_, true)); |
| 963 EXPECT_TRUE_WAIT( |
| 964 client1_.all_channels_writable() && client2_.all_channels_writable(), |
| 965 kTimeout); |
| 966 EXPECT_EQ(1, client1_.received_dtls_client_hellos()); |
| 967 } |
| 968 |
| 969 // Test that DTLS completes promptly if a ClientHello is received before the |
| 970 // transport channel has a remote fingerprint (allowing a ServerHello to be |
| 971 // sent). |
| 972 TEST_F(DtlsTransportChannelTest, |
| 973 TestReceiveClientHelloBeforeRemoteFingerprint) { |
| 974 MAYBE_SKIP_TEST(HaveDtls); |
| 975 PrepareDtls(true, true, rtc::KT_DEFAULT); |
| 976 client1_.SetupChannels(channel_ct_, cricket::ICEROLE_CONTROLLING); |
| 977 client2_.SetupChannels(channel_ct_, cricket::ICEROLE_CONTROLLED); |
| 978 |
| 979 // Make client2_ writable and give it local/remote certs, but don't yet give |
| 980 // client1_ a remote fingerprint. |
| 981 client1_.transport()->SetLocalTransportDescription( |
| 982 MakeTransportDescription(client1_.certificate(), |
| 983 cricket::CONNECTIONROLE_ACTPASS), |
| 984 cricket::CA_OFFER, nullptr); |
| 985 client2_.Negotiate(&client1_, cricket::CA_ANSWER, |
| 986 cricket::CONNECTIONROLE_ACTIVE, |
| 987 cricket::CONNECTIONROLE_ACTPASS, 0); |
| 988 EXPECT_TRUE(client2_.Connect(&client1_, true)); |
| 989 EXPECT_TRUE_WAIT(client2_.all_raw_channels_writable(), kTimeout); |
| 990 |
| 991 // Expect a DTLS ClientHello to be sent even while client1_ doesn't have a |
| 992 // remote fingerprint. |
| 993 EXPECT_EQ_WAIT(1, client1_.received_dtls_client_hellos(), kTimeout); |
| 994 EXPECT_FALSE(client1_.all_raw_channels_writable()); |
| 995 |
| 996 // Now make give client1_ its remote fingerprint and make it writable, and |
| 997 // expect the handshake to complete without client2_ needing to retransmit |
| 998 // the ClientHello. |
| 999 client1_.transport()->SetRemoteTransportDescription( |
| 1000 MakeTransportDescription(client2_.certificate(), |
| 1001 cricket::CONNECTIONROLE_ACTIVE), |
| 1002 cricket::CA_ANSWER, nullptr); |
| 1003 EXPECT_TRUE(client1_.Connect(&client2_, true)); |
| 1004 EXPECT_TRUE_WAIT( |
| 1005 client1_.all_channels_writable() && client2_.all_channels_writable(), |
| 1006 kTimeout); |
| 1007 EXPECT_EQ(1, client1_.received_dtls_client_hellos()); |
| 1008 } |
| 1009 |
962 // Test that packets are retransmitted according to the expected schedule. | 1010 // Test that packets are retransmitted according to the expected schedule. |
963 // Each time a timeout occurs, the retransmission timer should be doubled up to | 1011 // Each time a timeout occurs, the retransmission timer should be doubled up to |
964 // 60 seconds. The timer defaults to 1 second, but for WebRTC we should be | 1012 // 60 seconds. The timer defaults to 1 second, but for WebRTC we should be |
965 // initializing it to 50ms. | 1013 // initializing it to 50ms. |
966 TEST_F(DtlsTransportChannelTest, TestRetransmissionSchedule) { | 1014 TEST_F(DtlsTransportChannelTest, TestRetransmissionSchedule) { |
967 MAYBE_SKIP_TEST(HaveDtls); | 1015 MAYBE_SKIP_TEST(HaveDtls); |
968 // We can only change the retransmission schedule with a recently-added | 1016 // We can only change the retransmission schedule with a recently-added |
969 // BoringSSL API. Skip the test if not built with BoringSSL. | 1017 // BoringSSL API. Skip the test if not built with BoringSSL. |
970 MAYBE_SKIP_TEST(IsBoringSsl); | 1018 MAYBE_SKIP_TEST(IsBoringSsl); |
971 | 1019 |
972 PrepareDtls(true, true, rtc::KT_DEFAULT); | 1020 PrepareDtls(true, true, rtc::KT_DEFAULT); |
973 // Exchange transport descriptions. | 1021 // Exchange transport descriptions. |
974 Negotiate(cricket::CONNECTIONROLE_ACTPASS, cricket::CONNECTIONROLE_ACTIVE); | 1022 Negotiate(cricket::CONNECTIONROLE_ACTPASS, cricket::CONNECTIONROLE_ACTIVE); |
975 | 1023 |
976 // Make client2_ writable, but not client1_. | 1024 // Make client2_ writable, but not client1_. |
977 // This means client1_ will send DTLS client hellos but get no response. | 1025 // This means client1_ will send DTLS client hellos but get no response. |
978 EXPECT_TRUE(client2_.Connect(&client1_, true)); | 1026 EXPECT_TRUE(client2_.Connect(&client1_, true)); |
979 EXPECT_TRUE_SIMULATED_WAIT(client2_.all_raw_channels_writable(), kTimeout, | 1027 EXPECT_TRUE_WAIT(client2_.all_raw_channels_writable(), kTimeout); |
980 fake_clock_); | |
981 | 1028 |
982 // Wait for the first client hello to be sent. | 1029 // Wait for the first client hello to be sent. |
983 EXPECT_EQ_WAIT(1, client1_.received_dtls_client_hellos(), kTimeout); | 1030 EXPECT_EQ_WAIT(1, client1_.received_dtls_client_hellos(), kTimeout); |
984 EXPECT_FALSE(client1_.all_raw_channels_writable()); | 1031 EXPECT_FALSE(client1_.all_raw_channels_writable()); |
985 | 1032 |
986 static int timeout_schedule_ms[] = {50, 100, 200, 400, 800, 1600, | 1033 static int timeout_schedule_ms[] = {50, 100, 200, 400, 800, 1600, |
987 3200, 6400, 12800, 25600, 51200, 60000}; | 1034 3200, 6400, 12800, 25600, 51200, 60000}; |
988 | 1035 |
989 int expected_hellos = 1; | 1036 int expected_hellos = 1; |
990 for (size_t i = 0; | 1037 for (size_t i = 0; |
(...skipping 14 matching lines...) Expand all Loading... |
1005 // Test that a DTLS connection can be made even if the underlying transport | 1052 // Test that a DTLS connection can be made even if the underlying transport |
1006 // is connected before DTLS fingerprints/roles have been negotiated. | 1053 // is connected before DTLS fingerprints/roles have been negotiated. |
1007 TEST_F(DtlsTransportChannelTest, TestConnectBeforeNegotiate) { | 1054 TEST_F(DtlsTransportChannelTest, TestConnectBeforeNegotiate) { |
1008 MAYBE_SKIP_TEST(HaveDtls); | 1055 MAYBE_SKIP_TEST(HaveDtls); |
1009 PrepareDtls(true, true, rtc::KT_DEFAULT); | 1056 PrepareDtls(true, true, rtc::KT_DEFAULT); |
1010 ASSERT_TRUE(Connect(cricket::CONNECTIONROLE_ACTPASS, | 1057 ASSERT_TRUE(Connect(cricket::CONNECTIONROLE_ACTPASS, |
1011 cricket::CONNECTIONROLE_ACTIVE, | 1058 cricket::CONNECTIONROLE_ACTIVE, |
1012 CONNECT_BEFORE_NEGOTIATE)); | 1059 CONNECT_BEFORE_NEGOTIATE)); |
1013 TestTransfer(0, 1000, 100, false); | 1060 TestTransfer(0, 1000, 100, false); |
1014 } | 1061 } |
1015 | |
1016 // The following events can occur in many different orders: | |
1017 // 1. Caller receives remote fingerprint. | |
1018 // 2. Caller is writable. | |
1019 // 3. Caller receives ClientHello. | |
1020 // 4. DTLS handshake finishes. | |
1021 // | |
1022 // The tests below cover all causally consistent permutations of these events; | |
1023 // the caller must be writable and receive a ClientHello before the handshake | |
1024 // finishes, but otherwise any ordering is possible. | |
1025 // | |
1026 // For each permutation, the test verifies that a connection is established and | |
1027 // fingerprint verified without any DTLS packet needing to be retransmitted. | |
1028 // | |
1029 // Each permutation is also tested with a valid and invalid fingerprint, | |
1030 // ensuring that the handshake fails with an invalid fingerprint. | |
1031 enum DtlsTransportEvent { | |
1032 CALLER_RECEIVES_FINGERPRINT, | |
1033 CALLER_WRITABLE, | |
1034 CALLER_RECEIVES_CLIENTHELLO, | |
1035 HANDSHAKE_FINISHES | |
1036 }; | |
1037 | |
1038 class DtlsEventOrderingTest | |
1039 : public DtlsTransportChannelTestBase, | |
1040 public ::testing::TestWithParam< | |
1041 ::testing::tuple<std::vector<DtlsTransportEvent>, bool>> { | |
1042 protected: | |
1043 // If |valid_fingerprint| is false, the caller will receive a fingerprint | |
1044 // that doesn't match the callee's certificate, so the handshake should fail. | |
1045 void TestEventOrdering(const std::vector<DtlsTransportEvent>& events, | |
1046 bool valid_fingerprint) { | |
1047 // Pre-setup: Set local certificate on both caller and callee, and | |
1048 // remote fingerprint on callee, but neither is writable and the caller | |
1049 // doesn't have the callee's fingerprint. | |
1050 PrepareDtls(true, true, rtc::KT_DEFAULT); | |
1051 // Simulate packets being sent and arriving asynchronously. | |
1052 // Otherwise the entire DTLS handshake would occur in one clock tick, and | |
1053 // we couldn't inject method calls in the middle of it. | |
1054 int simulated_delay_ms = 10; | |
1055 client1_.SetupChannels(channel_ct_, cricket::ICEROLE_CONTROLLING, | |
1056 simulated_delay_ms); | |
1057 client2_.SetupChannels(channel_ct_, cricket::ICEROLE_CONTROLLED, | |
1058 simulated_delay_ms); | |
1059 client1_.SetLocalTransportDescription(client1_.certificate(), | |
1060 cricket::CA_OFFER, | |
1061 cricket::CONNECTIONROLE_ACTPASS, 0); | |
1062 client2_.Negotiate(&client1_, cricket::CA_ANSWER, | |
1063 cricket::CONNECTIONROLE_ACTIVE, | |
1064 cricket::CONNECTIONROLE_ACTPASS, 0); | |
1065 | |
1066 for (DtlsTransportEvent e : events) { | |
1067 switch (e) { | |
1068 case CALLER_RECEIVES_FINGERPRINT: | |
1069 if (valid_fingerprint) { | |
1070 client1_.SetRemoteTransportDescription( | |
1071 client2_.certificate(), cricket::CA_ANSWER, | |
1072 cricket::CONNECTIONROLE_ACTIVE, 0); | |
1073 } else { | |
1074 // Create a fingerprint with a correct algorithm but an invalid | |
1075 // digest. | |
1076 cricket::TransportDescription remote_desc = | |
1077 MakeTransportDescription(client2_.certificate(), | |
1078 cricket::CONNECTIONROLE_ACTIVE); | |
1079 ++(remote_desc.identity_fingerprint->digest[0]); | |
1080 // Even if certificate verification fails inside this method, | |
1081 // it should return true as long as the fingerprint was formatted | |
1082 // correctly. | |
1083 EXPECT_TRUE(client1_.transport()->SetRemoteTransportDescription( | |
1084 remote_desc, cricket::CA_ANSWER, nullptr)); | |
1085 } | |
1086 break; | |
1087 case CALLER_WRITABLE: | |
1088 EXPECT_TRUE(client1_.Connect(&client2_, true)); | |
1089 EXPECT_TRUE_SIMULATED_WAIT(client1_.all_raw_channels_writable(), | |
1090 kTimeout, fake_clock_); | |
1091 break; | |
1092 case CALLER_RECEIVES_CLIENTHELLO: | |
1093 // Sanity check that a ClientHello hasn't already been received. | |
1094 EXPECT_EQ(0, client1_.received_dtls_client_hellos()); | |
1095 // Making client2_ writable will cause it to send the ClientHello. | |
1096 EXPECT_TRUE(client2_.Connect(&client1_, true)); | |
1097 EXPECT_TRUE_SIMULATED_WAIT(client2_.all_raw_channels_writable(), | |
1098 kTimeout, fake_clock_); | |
1099 EXPECT_EQ_SIMULATED_WAIT(1, client1_.received_dtls_client_hellos(), | |
1100 kTimeout, fake_clock_); | |
1101 break; | |
1102 case HANDSHAKE_FINISHES: | |
1103 // Sanity check that the handshake hasn't already finished. | |
1104 EXPECT_FALSE(client1_.GetDtlsChannel(0)->IsDtlsConnected() || | |
1105 client1_.GetDtlsChannel(0)->dtls_state() == | |
1106 cricket::DTLS_TRANSPORT_FAILED); | |
1107 EXPECT_TRUE_SIMULATED_WAIT( | |
1108 client1_.GetDtlsChannel(0)->IsDtlsConnected() || | |
1109 client1_.GetDtlsChannel(0)->dtls_state() == | |
1110 cricket::DTLS_TRANSPORT_FAILED, | |
1111 kTimeout, fake_clock_); | |
1112 break; | |
1113 } | |
1114 } | |
1115 | |
1116 cricket::DtlsTransportState expected_final_state = | |
1117 valid_fingerprint ? cricket::DTLS_TRANSPORT_CONNECTED | |
1118 : cricket::DTLS_TRANSPORT_FAILED; | |
1119 EXPECT_EQ_SIMULATED_WAIT(expected_final_state, | |
1120 client1_.GetDtlsChannel(0)->dtls_state(), kTimeout, | |
1121 fake_clock_); | |
1122 EXPECT_EQ_SIMULATED_WAIT(expected_final_state, | |
1123 client2_.GetDtlsChannel(0)->dtls_state(), kTimeout, | |
1124 fake_clock_); | |
1125 | |
1126 // Channel should be writable iff there was a valid fingerprint. | |
1127 EXPECT_EQ(valid_fingerprint, client1_.GetDtlsChannel(0)->writable()); | |
1128 EXPECT_EQ(valid_fingerprint, client2_.GetDtlsChannel(0)->writable()); | |
1129 | |
1130 // Check that no hello needed to be retransmitted. | |
1131 EXPECT_EQ(1, client1_.received_dtls_client_hellos()); | |
1132 EXPECT_EQ(1, client2_.received_dtls_server_hellos()); | |
1133 | |
1134 if (valid_fingerprint) { | |
1135 TestTransfer(0, 1000, 100, false); | |
1136 } | |
1137 } | |
1138 }; | |
1139 | |
1140 TEST_P(DtlsEventOrderingTest, TestEventOrdering) { | |
1141 MAYBE_SKIP_TEST(HaveDtls); | |
1142 TestEventOrdering(::testing::get<0>(GetParam()), | |
1143 ::testing::get<1>(GetParam())); | |
1144 } | |
1145 | |
1146 INSTANTIATE_TEST_CASE_P( | |
1147 TestEventOrdering, | |
1148 DtlsEventOrderingTest, | |
1149 ::testing::Combine( | |
1150 ::testing::Values( | |
1151 std::vector<DtlsTransportEvent>{ | |
1152 CALLER_RECEIVES_FINGERPRINT, CALLER_WRITABLE, | |
1153 CALLER_RECEIVES_CLIENTHELLO, HANDSHAKE_FINISHES}, | |
1154 std::vector<DtlsTransportEvent>{ | |
1155 CALLER_WRITABLE, CALLER_RECEIVES_FINGERPRINT, | |
1156 CALLER_RECEIVES_CLIENTHELLO, HANDSHAKE_FINISHES}, | |
1157 std::vector<DtlsTransportEvent>{ | |
1158 CALLER_WRITABLE, CALLER_RECEIVES_CLIENTHELLO, | |
1159 CALLER_RECEIVES_FINGERPRINT, HANDSHAKE_FINISHES}, | |
1160 std::vector<DtlsTransportEvent>{ | |
1161 CALLER_WRITABLE, CALLER_RECEIVES_CLIENTHELLO, | |
1162 HANDSHAKE_FINISHES, CALLER_RECEIVES_FINGERPRINT}, | |
1163 std::vector<DtlsTransportEvent>{ | |
1164 CALLER_RECEIVES_FINGERPRINT, CALLER_RECEIVES_CLIENTHELLO, | |
1165 CALLER_WRITABLE, HANDSHAKE_FINISHES}, | |
1166 std::vector<DtlsTransportEvent>{ | |
1167 CALLER_RECEIVES_CLIENTHELLO, CALLER_RECEIVES_FINGERPRINT, | |
1168 CALLER_WRITABLE, HANDSHAKE_FINISHES}, | |
1169 std::vector<DtlsTransportEvent>{ | |
1170 CALLER_RECEIVES_CLIENTHELLO, CALLER_WRITABLE, | |
1171 CALLER_RECEIVES_FINGERPRINT, HANDSHAKE_FINISHES}, | |
1172 std::vector<DtlsTransportEvent>{CALLER_RECEIVES_CLIENTHELLO, | |
1173 CALLER_WRITABLE, HANDSHAKE_FINISHES, | |
1174 CALLER_RECEIVES_FINGERPRINT}), | |
1175 ::testing::Bool())); | |
OLD | NEW |