1 //===-- SocketTest.cpp ------------------------------------------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #if defined(_MSC_VER) && (_HAS_EXCEPTIONS == 0) 11 // Workaround for MSVC standard library bug, which fails to include <thread> when 12 // exceptions are disabled. 13 #include <eh.h> 14 #endif 15 16 #include <thread> 17 18 #include "gtest/gtest.h" 19 20 #include "lldb/Host/Socket.h" 21 22 using namespace lldb_private; 23 24 class SocketTest : public testing::Test 25 { 26 public: 27 void 28 SetUp() override 29 { 30 #if defined(_MSC_VER) 31 WSADATA data; 32 ::WSAStartup(MAKEWORD(2, 2), &data); 33 #endif 34 } 35 36 void 37 TearDown() override 38 { 39 #if defined(_MSC_VER) 40 ::WSACleanup(); 41 #endif 42 } 43 44 protected: 45 static void 46 AcceptThread(Socket *listen_socket, const char *listen_remote_address, bool child_processes_inherit, 47 Socket **accept_socket, Error *error) 48 { 49 *error = listen_socket->BlockingAccept(listen_remote_address, child_processes_inherit, *accept_socket); 50 } 51 52 void 53 CreateConnectedSockets(std::unique_ptr<Socket> *a_up, std::unique_ptr<Socket> *b_up) 54 { 55 Predicate<uint16_t> port_predicate; 56 // Used when binding to port zero to wait for the thread 57 // that creates the socket, binds and listens to resolve 58 // the port number. 59 60 port_predicate.SetValue(0, eBroadcastNever); 61 62 bool child_processes_inherit = false; 63 Socket *socket = nullptr; 64 const char *listen_remote_address = "localhost:0"; 65 Error error = Socket::TcpListen(listen_remote_address, child_processes_inherit, socket, &port_predicate); 66 std::unique_ptr<Socket> listen_socket_up(socket); 67 socket = nullptr; 68 EXPECT_FALSE(error.Fail()); 69 EXPECT_NE(nullptr, listen_socket_up.get()); 70 EXPECT_TRUE(listen_socket_up->IsValid()); 71 72 Error accept_error; 73 Socket *accept_socket; 74 std::thread accept_thread(AcceptThread, listen_socket_up.get(), listen_remote_address, child_processes_inherit, 75 &accept_socket, &accept_error); 76 77 char connect_remote_address[64]; 78 snprintf(connect_remote_address, sizeof(connect_remote_address), "localhost:%u", port_predicate.GetValue()); 79 error = Socket::TcpConnect(connect_remote_address, child_processes_inherit, socket); 80 a_up->reset(socket); 81 socket = nullptr; 82 EXPECT_TRUE(error.Success()); 83 EXPECT_NE(nullptr, a_up->get()); 84 EXPECT_TRUE((*a_up)->IsValid()); 85 86 accept_thread.join(); 87 b_up->reset(accept_socket); 88 EXPECT_TRUE(accept_error.Success()); 89 EXPECT_NE(nullptr, b_up->get()); 90 EXPECT_TRUE((*b_up)->IsValid()); 91 92 listen_socket_up.reset(); 93 } 94 }; 95 96 TEST_F (SocketTest, DecodeHostAndPort) 97 { 98 std::string host_str; 99 std::string port_str; 100 int32_t port; 101 Error error; 102 EXPECT_TRUE (Socket::DecodeHostAndPort ("localhost:1138", host_str, port_str, port, &error)); 103 EXPECT_STREQ ("localhost", host_str.c_str ()); 104 EXPECT_STREQ ("1138", port_str.c_str ()); 105 EXPECT_EQ (1138, port); 106 EXPECT_TRUE (error.Success ()); 107 108 EXPECT_FALSE (Socket::DecodeHostAndPort ("google.com:65536", host_str, port_str, port, &error)); 109 EXPECT_TRUE (error.Fail ()); 110 EXPECT_STREQ ("invalid host:port specification: 'google.com:65536'", error.AsCString ()); 111 112 EXPECT_FALSE (Socket::DecodeHostAndPort ("google.com:-1138", host_str, port_str, port, &error)); 113 EXPECT_TRUE (error.Fail ()); 114 EXPECT_STREQ ("invalid host:port specification: 'google.com:-1138'", error.AsCString ()); 115 116 EXPECT_TRUE (Socket::DecodeHostAndPort ("12345", host_str, port_str, port, &error)); 117 EXPECT_STREQ ("", host_str.c_str ()); 118 EXPECT_STREQ ("12345", port_str.c_str ()); 119 EXPECT_EQ (12345, port); 120 EXPECT_TRUE (error.Success ()); 121 122 EXPECT_TRUE (Socket::DecodeHostAndPort ("*:0", host_str, port_str, port, &error)); 123 EXPECT_STREQ ("*", host_str.c_str ()); 124 EXPECT_STREQ ("0", port_str.c_str ()); 125 EXPECT_EQ (0, port); 126 EXPECT_TRUE (error.Success ()); 127 128 } 129 130 TEST_F (SocketTest, Listen0ConnectAccept) 131 { 132 std::unique_ptr<Socket> socket_a_up; 133 std::unique_ptr<Socket> socket_b_up; 134 CreateConnectedSockets (&socket_a_up, &socket_b_up); 135 } 136 137 TEST_F (SocketTest, GetAddress) 138 { 139 std::unique_ptr<Socket> socket_a_up; 140 std::unique_ptr<Socket> socket_b_up; 141 CreateConnectedSockets (&socket_a_up, &socket_b_up); 142 143 EXPECT_EQ (socket_a_up->GetLocalPortNumber (), socket_b_up->GetRemotePortNumber ()); 144 EXPECT_EQ (socket_b_up->GetLocalPortNumber (), socket_a_up->GetRemotePortNumber ()); 145 EXPECT_NE (socket_a_up->GetLocalPortNumber (), socket_b_up->GetLocalPortNumber ()); 146 EXPECT_STREQ ("127.0.0.1", socket_a_up->GetRemoteIPAddress ().c_str ()); 147 EXPECT_STREQ ("127.0.0.1", socket_b_up->GetRemoteIPAddress ().c_str ()); 148 } 149