1 /* 2 * libjingle 3 * Copyright 2004 Google Inc. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright notice, 9 * this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright notice, 11 * this list of conditions and the following disclaimer in the documentation 12 * and/or other materials provided with the distribution. 13 * 3. The name of the author may not be used to endorse or promote products 14 * derived from this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED 17 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 18 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO 19 * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 20 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 21 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 22 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 23 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 24 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 25 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 */ 27 28 #include <string> 29 30 #include "talk/p2p/base/relayserver.h" 31 #include "webrtc/base/gunit.h" 32 #include "webrtc/base/helpers.h" 33 #include "webrtc/base/logging.h" 34 #include "webrtc/base/physicalsocketserver.h" 35 #include "webrtc/base/socketaddress.h" 36 #include "webrtc/base/ssladapter.h" 37 #include "webrtc/base/testclient.h" 38 #include "webrtc/base/thread.h" 39 40 using rtc::SocketAddress; 41 using namespace cricket; 42 43 static const uint32 LIFETIME = 4; // seconds 44 static const SocketAddress server_int_addr("127.0.0.1", 5000); 45 static const SocketAddress server_ext_addr("127.0.0.1", 5001); 46 static const SocketAddress client1_addr("127.0.0.1", 6000 + (rand() % 1000)); 47 static const SocketAddress client2_addr("127.0.0.1", 7000 + (rand() % 1000)); 48 static const char* bad = "this is a completely nonsensical message whose only " 49 "purpose is to make the parser go 'ack'. it doesn't " 50 "look anything like a normal stun message"; 51 static const char* msg1 = "spamspamspamspamspamspamspambakedbeansspam"; 52 static const char* msg2 = "Lobster Thermidor a Crevette with a mornay sauce..."; 53 54 class RelayServerTest : public testing::Test { 55 public: 56 static void SetUpTestCase() { 57 rtc::InitializeSSL(); 58 } 59 60 static void TearDownTestCase() { 61 rtc::CleanupSSL(); 62 } 63 64 RelayServerTest() 65 : main_(rtc::Thread::Current()), ss_(main_->socketserver()), 66 username_(rtc::CreateRandomString(12)), 67 password_(rtc::CreateRandomString(12)) { 68 } 69 protected: 70 virtual void SetUp() { 71 server_.reset(new RelayServer(main_)); 72 73 server_->AddInternalSocket( 74 rtc::AsyncUDPSocket::Create(ss_, server_int_addr)); 75 server_->AddExternalSocket( 76 rtc::AsyncUDPSocket::Create(ss_, server_ext_addr)); 77 78 client1_.reset(new rtc::TestClient( 79 rtc::AsyncUDPSocket::Create(ss_, client1_addr))); 80 client2_.reset(new rtc::TestClient( 81 rtc::AsyncUDPSocket::Create(ss_, client2_addr))); 82 } 83 84 void Allocate() { 85 rtc::scoped_ptr<StunMessage> req( 86 CreateStunMessage(STUN_ALLOCATE_REQUEST)); 87 AddUsernameAttr(req.get(), username_); 88 AddLifetimeAttr(req.get(), LIFETIME); 89 Send1(req.get()); 90 delete Receive1(); 91 } 92 void Bind() { 93 rtc::scoped_ptr<StunMessage> req( 94 CreateStunMessage(STUN_BINDING_REQUEST)); 95 AddUsernameAttr(req.get(), username_); 96 Send2(req.get()); 97 delete Receive1(); 98 } 99 100 void Send1(const StunMessage* msg) { 101 rtc::ByteBuffer buf; 102 msg->Write(&buf); 103 SendRaw1(buf.Data(), static_cast<int>(buf.Length())); 104 } 105 void Send2(const StunMessage* msg) { 106 rtc::ByteBuffer buf; 107 msg->Write(&buf); 108 SendRaw2(buf.Data(), static_cast<int>(buf.Length())); 109 } 110 void SendRaw1(const char* data, int len) { 111 return Send(client1_.get(), data, len, server_int_addr); 112 } 113 void SendRaw2(const char* data, int len) { 114 return Send(client2_.get(), data, len, server_ext_addr); 115 } 116 void Send(rtc::TestClient* client, const char* data, 117 int len, const SocketAddress& addr) { 118 client->SendTo(data, len, addr); 119 } 120 121 StunMessage* Receive1() { 122 return Receive(client1_.get()); 123 } 124 StunMessage* Receive2() { 125 return Receive(client2_.get()); 126 } 127 std::string ReceiveRaw1() { 128 return ReceiveRaw(client1_.get()); 129 } 130 std::string ReceiveRaw2() { 131 return ReceiveRaw(client2_.get()); 132 } 133 StunMessage* Receive(rtc::TestClient* client) { 134 StunMessage* msg = NULL; 135 rtc::TestClient::Packet* packet = client->NextPacket(); 136 if (packet) { 137 rtc::ByteBuffer buf(packet->buf, packet->size); 138 msg = new RelayMessage(); 139 msg->Read(&buf); 140 delete packet; 141 } 142 return msg; 143 } 144 std::string ReceiveRaw(rtc::TestClient* client) { 145 std::string raw; 146 rtc::TestClient::Packet* packet = client->NextPacket(); 147 if (packet) { 148 raw = std::string(packet->buf, packet->size); 149 delete packet; 150 } 151 return raw; 152 } 153 154 static StunMessage* CreateStunMessage(int type) { 155 StunMessage* msg = new RelayMessage(); 156 msg->SetType(type); 157 msg->SetTransactionID( 158 rtc::CreateRandomString(kStunTransactionIdLength)); 159 return msg; 160 } 161 static void AddMagicCookieAttr(StunMessage* msg) { 162 StunByteStringAttribute* attr = 163 StunAttribute::CreateByteString(STUN_ATTR_MAGIC_COOKIE); 164 attr->CopyBytes(TURN_MAGIC_COOKIE_VALUE, sizeof(TURN_MAGIC_COOKIE_VALUE)); 165 msg->AddAttribute(attr); 166 } 167 static void AddUsernameAttr(StunMessage* msg, const std::string& val) { 168 StunByteStringAttribute* attr = 169 StunAttribute::CreateByteString(STUN_ATTR_USERNAME); 170 attr->CopyBytes(val.c_str(), val.size()); 171 msg->AddAttribute(attr); 172 } 173 static void AddLifetimeAttr(StunMessage* msg, int val) { 174 StunUInt32Attribute* attr = 175 StunAttribute::CreateUInt32(STUN_ATTR_LIFETIME); 176 attr->SetValue(val); 177 msg->AddAttribute(attr); 178 } 179 static void AddDestinationAttr(StunMessage* msg, const SocketAddress& addr) { 180 StunAddressAttribute* attr = 181 StunAttribute::CreateAddress(STUN_ATTR_DESTINATION_ADDRESS); 182 attr->SetIP(addr.ipaddr()); 183 attr->SetPort(addr.port()); 184 msg->AddAttribute(attr); 185 } 186 187 rtc::Thread* main_; 188 rtc::SocketServer* ss_; 189 rtc::scoped_ptr<RelayServer> server_; 190 rtc::scoped_ptr<rtc::TestClient> client1_; 191 rtc::scoped_ptr<rtc::TestClient> client2_; 192 std::string username_; 193 std::string password_; 194 }; 195 196 // Send a complete nonsense message and verify that it is eaten. 197 TEST_F(RelayServerTest, TestBadRequest) { 198 rtc::scoped_ptr<StunMessage> res; 199 200 SendRaw1(bad, static_cast<int>(strlen(bad))); 201 res.reset(Receive1()); 202 203 ASSERT_TRUE(!res); 204 } 205 206 // Send an allocate request without a username and verify it is rejected. 207 TEST_F(RelayServerTest, TestAllocateNoUsername) { 208 rtc::scoped_ptr<StunMessage> req( 209 CreateStunMessage(STUN_ALLOCATE_REQUEST)), res; 210 211 Send1(req.get()); 212 res.reset(Receive1()); 213 214 ASSERT_TRUE(res); 215 EXPECT_EQ(STUN_ALLOCATE_ERROR_RESPONSE, res->type()); 216 EXPECT_EQ(req->transaction_id(), res->transaction_id()); 217 218 const StunErrorCodeAttribute* err = res->GetErrorCode(); 219 ASSERT_TRUE(err != NULL); 220 EXPECT_EQ(4, err->eclass()); 221 EXPECT_EQ(32, err->number()); 222 EXPECT_EQ("Missing Username", err->reason()); 223 } 224 225 // Send a binding request and verify that it is rejected. 226 TEST_F(RelayServerTest, TestBindingRequest) { 227 rtc::scoped_ptr<StunMessage> req( 228 CreateStunMessage(STUN_BINDING_REQUEST)), res; 229 AddUsernameAttr(req.get(), username_); 230 231 Send1(req.get()); 232 res.reset(Receive1()); 233 234 ASSERT_TRUE(res); 235 EXPECT_EQ(STUN_BINDING_ERROR_RESPONSE, res->type()); 236 EXPECT_EQ(req->transaction_id(), res->transaction_id()); 237 238 const StunErrorCodeAttribute* err = res->GetErrorCode(); 239 ASSERT_TRUE(err != NULL); 240 EXPECT_EQ(6, err->eclass()); 241 EXPECT_EQ(0, err->number()); 242 EXPECT_EQ("Operation Not Supported", err->reason()); 243 } 244 245 // Send an allocate request and verify that it is accepted. 246 TEST_F(RelayServerTest, TestAllocate) { 247 rtc::scoped_ptr<StunMessage> req( 248 CreateStunMessage(STUN_ALLOCATE_REQUEST)), res; 249 AddUsernameAttr(req.get(), username_); 250 AddLifetimeAttr(req.get(), LIFETIME); 251 252 Send1(req.get()); 253 res.reset(Receive1()); 254 255 ASSERT_TRUE(res); 256 EXPECT_EQ(STUN_ALLOCATE_RESPONSE, res->type()); 257 EXPECT_EQ(req->transaction_id(), res->transaction_id()); 258 259 const StunAddressAttribute* mapped_addr = 260 res->GetAddress(STUN_ATTR_MAPPED_ADDRESS); 261 ASSERT_TRUE(mapped_addr != NULL); 262 EXPECT_EQ(1, mapped_addr->family()); 263 EXPECT_EQ(server_ext_addr.port(), mapped_addr->port()); 264 EXPECT_EQ(server_ext_addr.ipaddr(), mapped_addr->ipaddr()); 265 266 const StunUInt32Attribute* res_lifetime_attr = 267 res->GetUInt32(STUN_ATTR_LIFETIME); 268 ASSERT_TRUE(res_lifetime_attr != NULL); 269 EXPECT_EQ(LIFETIME, res_lifetime_attr->value()); 270 } 271 272 // Send a second allocate request and verify that it is also accepted, though 273 // the lifetime should be ignored. 274 TEST_F(RelayServerTest, TestReallocate) { 275 Allocate(); 276 277 rtc::scoped_ptr<StunMessage> req( 278 CreateStunMessage(STUN_ALLOCATE_REQUEST)), res; 279 AddMagicCookieAttr(req.get()); 280 AddUsernameAttr(req.get(), username_); 281 282 Send1(req.get()); 283 res.reset(Receive1()); 284 285 ASSERT_TRUE(res); 286 EXPECT_EQ(STUN_ALLOCATE_RESPONSE, res->type()); 287 EXPECT_EQ(req->transaction_id(), res->transaction_id()); 288 289 const StunAddressAttribute* mapped_addr = 290 res->GetAddress(STUN_ATTR_MAPPED_ADDRESS); 291 ASSERT_TRUE(mapped_addr != NULL); 292 EXPECT_EQ(1, mapped_addr->family()); 293 EXPECT_EQ(server_ext_addr.port(), mapped_addr->port()); 294 EXPECT_EQ(server_ext_addr.ipaddr(), mapped_addr->ipaddr()); 295 296 const StunUInt32Attribute* lifetime_attr = 297 res->GetUInt32(STUN_ATTR_LIFETIME); 298 ASSERT_TRUE(lifetime_attr != NULL); 299 EXPECT_EQ(LIFETIME, lifetime_attr->value()); 300 } 301 302 // Send a request from another client and see that it arrives at the first 303 // client in the binding. 304 TEST_F(RelayServerTest, TestRemoteBind) { 305 Allocate(); 306 307 rtc::scoped_ptr<StunMessage> req( 308 CreateStunMessage(STUN_BINDING_REQUEST)), res; 309 AddUsernameAttr(req.get(), username_); 310 311 Send2(req.get()); 312 res.reset(Receive1()); 313 314 ASSERT_TRUE(res); 315 EXPECT_EQ(STUN_DATA_INDICATION, res->type()); 316 317 const StunByteStringAttribute* recv_data = 318 res->GetByteString(STUN_ATTR_DATA); 319 ASSERT_TRUE(recv_data != NULL); 320 321 rtc::ByteBuffer buf(recv_data->bytes(), recv_data->length()); 322 rtc::scoped_ptr<StunMessage> res2(new StunMessage()); 323 EXPECT_TRUE(res2->Read(&buf)); 324 EXPECT_EQ(STUN_BINDING_REQUEST, res2->type()); 325 EXPECT_EQ(req->transaction_id(), res2->transaction_id()); 326 327 const StunAddressAttribute* src_addr = 328 res->GetAddress(STUN_ATTR_SOURCE_ADDRESS2); 329 ASSERT_TRUE(src_addr != NULL); 330 EXPECT_EQ(1, src_addr->family()); 331 EXPECT_EQ(client2_addr.ipaddr(), src_addr->ipaddr()); 332 EXPECT_EQ(client2_addr.port(), src_addr->port()); 333 334 EXPECT_TRUE(Receive2() == NULL); 335 } 336 337 // Send a complete nonsense message to the established connection and verify 338 // that it is dropped by the server. 339 TEST_F(RelayServerTest, TestRemoteBadRequest) { 340 Allocate(); 341 Bind(); 342 343 SendRaw1(bad, static_cast<int>(strlen(bad))); 344 EXPECT_TRUE(Receive1() == NULL); 345 EXPECT_TRUE(Receive2() == NULL); 346 } 347 348 // Send a send request without a username and verify it is rejected. 349 TEST_F(RelayServerTest, TestSendRequestMissingUsername) { 350 Allocate(); 351 Bind(); 352 353 rtc::scoped_ptr<StunMessage> req( 354 CreateStunMessage(STUN_SEND_REQUEST)), res; 355 AddMagicCookieAttr(req.get()); 356 357 Send1(req.get()); 358 res.reset(Receive1()); 359 360 ASSERT_TRUE(res); 361 EXPECT_EQ(STUN_SEND_ERROR_RESPONSE, res->type()); 362 EXPECT_EQ(req->transaction_id(), res->transaction_id()); 363 364 const StunErrorCodeAttribute* err = res->GetErrorCode(); 365 ASSERT_TRUE(err != NULL); 366 EXPECT_EQ(4, err->eclass()); 367 EXPECT_EQ(32, err->number()); 368 EXPECT_EQ("Missing Username", err->reason()); 369 } 370 371 // Send a send request with the wrong username and verify it is rejected. 372 TEST_F(RelayServerTest, TestSendRequestBadUsername) { 373 Allocate(); 374 Bind(); 375 376 rtc::scoped_ptr<StunMessage> req( 377 CreateStunMessage(STUN_SEND_REQUEST)), res; 378 AddMagicCookieAttr(req.get()); 379 AddUsernameAttr(req.get(), "foobarbizbaz"); 380 381 Send1(req.get()); 382 res.reset(Receive1()); 383 384 ASSERT_TRUE(res); 385 EXPECT_EQ(STUN_SEND_ERROR_RESPONSE, res->type()); 386 EXPECT_EQ(req->transaction_id(), res->transaction_id()); 387 388 const StunErrorCodeAttribute* err = res->GetErrorCode(); 389 ASSERT_TRUE(err != NULL); 390 EXPECT_EQ(4, err->eclass()); 391 EXPECT_EQ(30, err->number()); 392 EXPECT_EQ("Stale Credentials", err->reason()); 393 } 394 395 // Send a send request without a destination address and verify that it is 396 // rejected. 397 TEST_F(RelayServerTest, TestSendRequestNoDestinationAddress) { 398 Allocate(); 399 Bind(); 400 401 rtc::scoped_ptr<StunMessage> req( 402 CreateStunMessage(STUN_SEND_REQUEST)), res; 403 AddMagicCookieAttr(req.get()); 404 AddUsernameAttr(req.get(), username_); 405 406 Send1(req.get()); 407 res.reset(Receive1()); 408 409 ASSERT_TRUE(res); 410 EXPECT_EQ(STUN_SEND_ERROR_RESPONSE, res->type()); 411 EXPECT_EQ(req->transaction_id(), res->transaction_id()); 412 413 const StunErrorCodeAttribute* err = res->GetErrorCode(); 414 ASSERT_TRUE(err != NULL); 415 EXPECT_EQ(4, err->eclass()); 416 EXPECT_EQ(0, err->number()); 417 EXPECT_EQ("Bad Request", err->reason()); 418 } 419 420 // Send a send request without data and verify that it is rejected. 421 TEST_F(RelayServerTest, TestSendRequestNoData) { 422 Allocate(); 423 Bind(); 424 425 rtc::scoped_ptr<StunMessage> req( 426 CreateStunMessage(STUN_SEND_REQUEST)), res; 427 AddMagicCookieAttr(req.get()); 428 AddUsernameAttr(req.get(), username_); 429 AddDestinationAttr(req.get(), client2_addr); 430 431 Send1(req.get()); 432 res.reset(Receive1()); 433 434 ASSERT_TRUE(res); 435 EXPECT_EQ(STUN_SEND_ERROR_RESPONSE, res->type()); 436 EXPECT_EQ(req->transaction_id(), res->transaction_id()); 437 438 const StunErrorCodeAttribute* err = res->GetErrorCode(); 439 ASSERT_TRUE(err != NULL); 440 EXPECT_EQ(4, err->eclass()); 441 EXPECT_EQ(00, err->number()); 442 EXPECT_EQ("Bad Request", err->reason()); 443 } 444 445 // Send a binding request after an allocate and verify that it is rejected. 446 TEST_F(RelayServerTest, TestSendRequestWrongType) { 447 Allocate(); 448 Bind(); 449 450 rtc::scoped_ptr<StunMessage> req( 451 CreateStunMessage(STUN_BINDING_REQUEST)), res; 452 AddMagicCookieAttr(req.get()); 453 AddUsernameAttr(req.get(), username_); 454 455 Send1(req.get()); 456 res.reset(Receive1()); 457 458 ASSERT_TRUE(res); 459 EXPECT_EQ(STUN_BINDING_ERROR_RESPONSE, res->type()); 460 EXPECT_EQ(req->transaction_id(), res->transaction_id()); 461 462 const StunErrorCodeAttribute* err = res->GetErrorCode(); 463 ASSERT_TRUE(err != NULL); 464 EXPECT_EQ(6, err->eclass()); 465 EXPECT_EQ(0, err->number()); 466 EXPECT_EQ("Operation Not Supported", err->reason()); 467 } 468 469 // Verify that we can send traffic back and forth between the clients after a 470 // successful allocate and bind. 471 TEST_F(RelayServerTest, TestSendRaw) { 472 Allocate(); 473 Bind(); 474 475 for (int i = 0; i < 10; i++) { 476 rtc::scoped_ptr<StunMessage> req( 477 CreateStunMessage(STUN_SEND_REQUEST)), res; 478 AddMagicCookieAttr(req.get()); 479 AddUsernameAttr(req.get(), username_); 480 AddDestinationAttr(req.get(), client2_addr); 481 482 StunByteStringAttribute* send_data = 483 StunAttribute::CreateByteString(STUN_ATTR_DATA); 484 send_data->CopyBytes(msg1); 485 req->AddAttribute(send_data); 486 487 Send1(req.get()); 488 EXPECT_EQ(msg1, ReceiveRaw2()); 489 SendRaw2(msg2, static_cast<int>(strlen(msg2))); 490 res.reset(Receive1()); 491 492 ASSERT_TRUE(res); 493 EXPECT_EQ(STUN_DATA_INDICATION, res->type()); 494 495 const StunAddressAttribute* src_addr = 496 res->GetAddress(STUN_ATTR_SOURCE_ADDRESS2); 497 ASSERT_TRUE(src_addr != NULL); 498 EXPECT_EQ(1, src_addr->family()); 499 EXPECT_EQ(client2_addr.ipaddr(), src_addr->ipaddr()); 500 EXPECT_EQ(client2_addr.port(), src_addr->port()); 501 502 const StunByteStringAttribute* recv_data = 503 res->GetByteString(STUN_ATTR_DATA); 504 ASSERT_TRUE(recv_data != NULL); 505 EXPECT_EQ(strlen(msg2), recv_data->length()); 506 EXPECT_EQ(0, memcmp(msg2, recv_data->bytes(), recv_data->length())); 507 } 508 } 509 510 // Verify that a binding expires properly, and rejects send requests. 511 TEST_F(RelayServerTest, TestExpiration) { 512 Allocate(); 513 Bind(); 514 515 // Wait twice the lifetime to make sure the server has expired the binding. 516 rtc::Thread::Current()->ProcessMessages((LIFETIME * 2) * 1000); 517 518 rtc::scoped_ptr<StunMessage> req( 519 CreateStunMessage(STUN_SEND_REQUEST)), res; 520 AddMagicCookieAttr(req.get()); 521 AddUsernameAttr(req.get(), username_); 522 AddDestinationAttr(req.get(), client2_addr); 523 524 StunByteStringAttribute* data_attr = 525 StunAttribute::CreateByteString(STUN_ATTR_DATA); 526 data_attr->CopyBytes(msg1); 527 req->AddAttribute(data_attr); 528 529 Send1(req.get()); 530 res.reset(Receive1()); 531 532 ASSERT_TRUE(res.get() != NULL); 533 EXPECT_EQ(STUN_SEND_ERROR_RESPONSE, res->type()); 534 535 const StunErrorCodeAttribute* err = res->GetErrorCode(); 536 ASSERT_TRUE(err != NULL); 537 EXPECT_EQ(6, err->eclass()); 538 EXPECT_EQ(0, err->number()); 539 EXPECT_EQ("Operation Not Supported", err->reason()); 540 541 // Also verify that traffic from the external client is ignored. 542 SendRaw2(msg2, static_cast<int>(strlen(msg2))); 543 EXPECT_TRUE(ReceiveRaw1().empty()); 544 } 545