| OLD | NEW | 
|---|
| 1 /* | 1 /* | 
| 2  *  Copyright 2004 The WebRTC Project Authors. All rights reserved. | 2  *  Copyright 2004 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 | 
| 11 #include "webrtc/p2p/base/stunrequest.h" | 11 #include "webrtc/p2p/base/stunrequest.h" | 
| 12 #include "webrtc/base/fakeclock.h" | 12 #include "webrtc/base/fakeclock.h" | 
| 13 #include "webrtc/base/gunit.h" | 13 #include "webrtc/base/gunit.h" | 
| 14 #include "webrtc/base/helpers.h" | 14 #include "webrtc/base/helpers.h" | 
| 15 #include "webrtc/base/logging.h" | 15 #include "webrtc/base/logging.h" | 
| 16 #include "webrtc/base/ssladapter.h" | 16 #include "webrtc/base/ssladapter.h" | 
| 17 #include "webrtc/base/timeutils.h" | 17 #include "webrtc/base/timeutils.h" | 
| 18 | 18 | 
| 19 using namespace cricket; | 19 using namespace cricket; | 
| 20 | 20 | 
| 21 class StunRequestTest : public testing::Test, | 21 class StunRequestTest : public testing::Test, | 
| 22                         public sigslot::has_slots<> { | 22                         public sigslot::has_slots<> { | 
| 23  public: | 23  public: | 
| 24   StunRequestTest() | 24   StunRequestTest() | 
| 25       : manager_(rtc::Thread::Current()), | 25       : manager_(rtc::Thread::Current()), | 
| 26         request_count_(0), response_(NULL), | 26         request_count_(0), | 
| 27         success_(false), failure_(false), timeout_(false) { | 27         response_(nullptr), | 
|  | 28         success_(false), | 
|  | 29         failure_(false), | 
|  | 30         timeout_(false) { | 
| 28     manager_.SignalSendPacket.connect(this, &StunRequestTest::OnSendPacket); | 31     manager_.SignalSendPacket.connect(this, &StunRequestTest::OnSendPacket); | 
| 29   } | 32   } | 
| 30 | 33 | 
| 31   void OnSendPacket(const void* data, size_t size, StunRequest* req) { | 34   void OnSendPacket(const void* data, size_t size, StunRequest* req) { | 
| 32     request_count_++; | 35     request_count_++; | 
| 33   } | 36   } | 
| 34 | 37 | 
| 35   void OnResponse(StunMessage* res) { | 38   void OnResponse(StunMessage* res) { | 
| 36     response_ = res; | 39     response_ = res; | 
| 37     success_ = true; | 40     success_ = true; | 
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 87 | 90 | 
| 88   virtual void Prepare(StunMessage* request) { | 91   virtual void Prepare(StunMessage* request) { | 
| 89     request->SetType(STUN_BINDING_REQUEST); | 92     request->SetType(STUN_BINDING_REQUEST); | 
| 90   } | 93   } | 
| 91 | 94 | 
| 92   StunRequestTest* test_; | 95   StunRequestTest* test_; | 
| 93 }; | 96 }; | 
| 94 | 97 | 
| 95 // Test handling of a normal binding response. | 98 // Test handling of a normal binding response. | 
| 96 TEST_F(StunRequestTest, TestSuccess) { | 99 TEST_F(StunRequestTest, TestSuccess) { | 
| 97   StunMessage* req = CreateStunMessage(STUN_BINDING_REQUEST, NULL); | 100   StunMessage* req = CreateStunMessage(STUN_BINDING_REQUEST, nullptr); | 
| 98 | 101 | 
| 99   manager_.Send(new StunRequestThunker(req, this)); | 102   manager_.Send(new StunRequestThunker(req, this)); | 
| 100   StunMessage* res = CreateStunMessage(STUN_BINDING_RESPONSE, req); | 103   StunMessage* res = CreateStunMessage(STUN_BINDING_RESPONSE, req); | 
| 101   EXPECT_TRUE(manager_.CheckResponse(res)); | 104   EXPECT_TRUE(manager_.CheckResponse(res)); | 
| 102 | 105 | 
| 103   EXPECT_TRUE(response_ == res); | 106   EXPECT_TRUE(response_ == res); | 
| 104   EXPECT_TRUE(success_); | 107   EXPECT_TRUE(success_); | 
| 105   EXPECT_FALSE(failure_); | 108   EXPECT_FALSE(failure_); | 
| 106   EXPECT_FALSE(timeout_); | 109   EXPECT_FALSE(timeout_); | 
| 107   delete res; | 110   delete res; | 
| 108 } | 111 } | 
| 109 | 112 | 
| 110 // Test handling of an error binding response. | 113 // Test handling of an error binding response. | 
| 111 TEST_F(StunRequestTest, TestError) { | 114 TEST_F(StunRequestTest, TestError) { | 
| 112   StunMessage* req = CreateStunMessage(STUN_BINDING_REQUEST, NULL); | 115   StunMessage* req = CreateStunMessage(STUN_BINDING_REQUEST, nullptr); | 
| 113 | 116 | 
| 114   manager_.Send(new StunRequestThunker(req, this)); | 117   manager_.Send(new StunRequestThunker(req, this)); | 
| 115   StunMessage* res = CreateStunMessage(STUN_BINDING_ERROR_RESPONSE, req); | 118   StunMessage* res = CreateStunMessage(STUN_BINDING_ERROR_RESPONSE, req); | 
| 116   EXPECT_TRUE(manager_.CheckResponse(res)); | 119   EXPECT_TRUE(manager_.CheckResponse(res)); | 
| 117 | 120 | 
| 118   EXPECT_TRUE(response_ == res); | 121   EXPECT_TRUE(response_ == res); | 
| 119   EXPECT_FALSE(success_); | 122   EXPECT_FALSE(success_); | 
| 120   EXPECT_TRUE(failure_); | 123   EXPECT_TRUE(failure_); | 
| 121   EXPECT_FALSE(timeout_); | 124   EXPECT_FALSE(timeout_); | 
| 122   delete res; | 125   delete res; | 
| 123 } | 126 } | 
| 124 | 127 | 
| 125 // Test handling of a binding response with the wrong transaction id. | 128 // Test handling of a binding response with the wrong transaction id. | 
| 126 TEST_F(StunRequestTest, TestUnexpected) { | 129 TEST_F(StunRequestTest, TestUnexpected) { | 
| 127   StunMessage* req = CreateStunMessage(STUN_BINDING_REQUEST, NULL); | 130   StunMessage* req = CreateStunMessage(STUN_BINDING_REQUEST, nullptr); | 
| 128 | 131 | 
| 129   manager_.Send(new StunRequestThunker(req, this)); | 132   manager_.Send(new StunRequestThunker(req, this)); | 
| 130   StunMessage* res = CreateStunMessage(STUN_BINDING_RESPONSE, NULL); | 133   StunMessage* res = CreateStunMessage(STUN_BINDING_RESPONSE, nullptr); | 
| 131   EXPECT_FALSE(manager_.CheckResponse(res)); | 134   EXPECT_FALSE(manager_.CheckResponse(res)); | 
| 132 | 135 | 
| 133   EXPECT_TRUE(response_ == NULL); | 136   EXPECT_TRUE(response_ == nullptr); | 
| 134   EXPECT_FALSE(success_); | 137   EXPECT_FALSE(success_); | 
| 135   EXPECT_FALSE(failure_); | 138   EXPECT_FALSE(failure_); | 
| 136   EXPECT_FALSE(timeout_); | 139   EXPECT_FALSE(timeout_); | 
| 137   delete res; | 140   delete res; | 
| 138 } | 141 } | 
| 139 | 142 | 
| 140 // Test that requests are sent at the right times. | 143 // Test that requests are sent at the right times. | 
| 141 TEST_F(StunRequestTest, TestBackoff) { | 144 TEST_F(StunRequestTest, TestBackoff) { | 
| 142   rtc::ScopedFakeClock fake_clock; | 145   rtc::ScopedFakeClock fake_clock; | 
| 143   StunMessage* req = CreateStunMessage(STUN_BINDING_REQUEST, NULL); | 146   StunMessage* req = CreateStunMessage(STUN_BINDING_REQUEST, nullptr); | 
| 144 | 147 | 
| 145   int64_t start = rtc::TimeMillis(); | 148   int64_t start = rtc::TimeMillis(); | 
| 146   manager_.Send(new StunRequestThunker(req, this)); | 149   manager_.Send(new StunRequestThunker(req, this)); | 
| 147   StunMessage* res = CreateStunMessage(STUN_BINDING_RESPONSE, req); | 150   StunMessage* res = CreateStunMessage(STUN_BINDING_RESPONSE, req); | 
| 148   for (int i = 0; i < 9; ++i) { | 151   for (int i = 0; i < 9; ++i) { | 
| 149     EXPECT_TRUE_SIMULATED_WAIT(request_count_ != i, STUN_TOTAL_TIMEOUT, | 152     EXPECT_TRUE_SIMULATED_WAIT(request_count_ != i, STUN_TOTAL_TIMEOUT, | 
| 150                                fake_clock); | 153                                fake_clock); | 
| 151     int64_t elapsed = rtc::TimeMillis() - start; | 154     int64_t elapsed = rtc::TimeMillis() - start; | 
| 152     LOG(LS_INFO) << "STUN request #" << (i + 1) | 155     LOG(LS_INFO) << "STUN request #" << (i + 1) | 
| 153                  << " sent at " << elapsed << " ms"; | 156                  << " sent at " << elapsed << " ms"; | 
| 154     EXPECT_EQ(TotalDelay(i), elapsed); | 157     EXPECT_EQ(TotalDelay(i), elapsed); | 
| 155   } | 158   } | 
| 156   EXPECT_TRUE(manager_.CheckResponse(res)); | 159   EXPECT_TRUE(manager_.CheckResponse(res)); | 
| 157 | 160 | 
| 158   EXPECT_TRUE(response_ == res); | 161   EXPECT_TRUE(response_ == res); | 
| 159   EXPECT_TRUE(success_); | 162   EXPECT_TRUE(success_); | 
| 160   EXPECT_FALSE(failure_); | 163   EXPECT_FALSE(failure_); | 
| 161   EXPECT_FALSE(timeout_); | 164   EXPECT_FALSE(timeout_); | 
| 162   delete res; | 165   delete res; | 
| 163 } | 166 } | 
| 164 | 167 | 
| 165 // Test that we timeout properly if no response is received. | 168 // Test that we timeout properly if no response is received. | 
| 166 TEST_F(StunRequestTest, TestTimeout) { | 169 TEST_F(StunRequestTest, TestTimeout) { | 
| 167   rtc::ScopedFakeClock fake_clock; | 170   rtc::ScopedFakeClock fake_clock; | 
| 168   StunMessage* req = CreateStunMessage(STUN_BINDING_REQUEST, NULL); | 171   StunMessage* req = CreateStunMessage(STUN_BINDING_REQUEST, nullptr); | 
| 169   StunMessage* res = CreateStunMessage(STUN_BINDING_RESPONSE, req); | 172   StunMessage* res = CreateStunMessage(STUN_BINDING_RESPONSE, req); | 
| 170 | 173 | 
| 171   manager_.Send(new StunRequestThunker(req, this)); | 174   manager_.Send(new StunRequestThunker(req, this)); | 
| 172   SIMULATED_WAIT(false, cricket::STUN_TOTAL_TIMEOUT, fake_clock); | 175   SIMULATED_WAIT(false, cricket::STUN_TOTAL_TIMEOUT, fake_clock); | 
| 173 | 176 | 
| 174   EXPECT_FALSE(manager_.CheckResponse(res)); | 177   EXPECT_FALSE(manager_.CheckResponse(res)); | 
| 175   EXPECT_TRUE(response_ == NULL); | 178   EXPECT_TRUE(response_ == nullptr); | 
| 176   EXPECT_FALSE(success_); | 179   EXPECT_FALSE(success_); | 
| 177   EXPECT_FALSE(failure_); | 180   EXPECT_FALSE(failure_); | 
| 178   EXPECT_TRUE(timeout_); | 181   EXPECT_TRUE(timeout_); | 
| 179   delete res; | 182   delete res; | 
| 180 } | 183 } | 
| 181 | 184 | 
| 182 // Regression test for specific crash where we receive a response with the | 185 // Regression test for specific crash where we receive a response with the | 
| 183 // same id as a request that doesn't have an underlying StunMessage yet. | 186 // same id as a request that doesn't have an underlying StunMessage yet. | 
| 184 TEST_F(StunRequestTest, TestNoEmptyRequest) { | 187 TEST_F(StunRequestTest, TestNoEmptyRequest) { | 
| 185   StunRequestThunker* request = new StunRequestThunker(this); | 188   StunRequestThunker* request = new StunRequestThunker(this); | 
| 186 | 189 | 
| 187   manager_.SendDelayed(request, 100); | 190   manager_.SendDelayed(request, 100); | 
| 188 | 191 | 
| 189   StunMessage dummy_req; | 192   StunMessage dummy_req; | 
| 190   dummy_req.SetTransactionID(request->id()); | 193   dummy_req.SetTransactionID(request->id()); | 
| 191   StunMessage* res = CreateStunMessage(STUN_BINDING_RESPONSE, &dummy_req); | 194   StunMessage* res = CreateStunMessage(STUN_BINDING_RESPONSE, &dummy_req); | 
| 192 | 195 | 
| 193   EXPECT_TRUE(manager_.CheckResponse(res)); | 196   EXPECT_TRUE(manager_.CheckResponse(res)); | 
| 194 | 197 | 
| 195   EXPECT_TRUE(response_ == res); | 198   EXPECT_TRUE(response_ == res); | 
| 196   EXPECT_TRUE(success_); | 199   EXPECT_TRUE(success_); | 
| 197   EXPECT_FALSE(failure_); | 200   EXPECT_FALSE(failure_); | 
| 198   EXPECT_FALSE(timeout_); | 201   EXPECT_FALSE(timeout_); | 
| 199   delete res; | 202   delete res; | 
| 200 } | 203 } | 
| OLD | NEW | 
|---|