1f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 2f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "pipe/p_compiler.h" 3f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "util/u_network.h" 4f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "util/u_debug.h" 5f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 6f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_SUBSYSTEM_WINDOWS_USER) 7f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org# include <winsock2.h> 8f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org# include <windows.h> 9f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#elif defined(PIPE_OS_LINUX) || defined(PIPE_OS_HAIKU) || \ 10f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org defined(PIPE_OS_APPLE) || defined(PIPE_OS_CYGWIN) || defined(PIPE_OS_SOLARIS) 11f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org# include <sys/socket.h> 12f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org# include <netinet/in.h> 13f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org# include <unistd.h> 14f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org# include <fcntl.h> 15f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org# include <netdb.h> 16f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#else 17f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org# warning "No socket implementation" 18f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 19f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 20f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgboolean 21f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgu_socket_init() 22f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{ 23f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_SUBSYSTEM_WINDOWS_USER) 24f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org WORD wVersionRequested; 25f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org WSADATA wsaData; 26f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org int err; 27f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 28f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org /* Use the MAKEWORD(lowbyte, highbyte) macro declared in Windef.h */ 29f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org wVersionRequested = MAKEWORD(1, 1); 30f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 31f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org err = WSAStartup(wVersionRequested, &wsaData); 32f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org if (err != 0) { 33f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org debug_printf("WSAStartup failed with error: %d\n", err); 34f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return FALSE; 35f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org } 36f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return TRUE; 37f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#elif defined(PIPE_HAVE_SOCKETS) 38f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return TRUE; 39f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#else 40f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return FALSE; 41f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 42f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org} 43f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 44f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgvoid 45f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgu_socket_stop() 46f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{ 47f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_SUBSYSTEM_WINDOWS_USER) 48f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org WSACleanup(); 49f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 50f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org} 51f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 52f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgvoid 53f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgu_socket_close(int s) 54f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{ 55f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org if (s < 0) 56f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return; 57f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 58f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_OS_LINUX) || defined(PIPE_OS_HAIKU) \ 59f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org || defined(PIPE_OS_APPLE) || defined(PIPE_OS_SOLARIS) 60f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org shutdown(s, SHUT_RDWR); 61f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org close(s); 62f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#elif defined(PIPE_SUBSYSTEM_WINDOWS_USER) 63f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org shutdown(s, SD_BOTH); 64f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org closesocket(s); 65f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#else 66f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org assert(0); 67f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 68f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org} 69f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 70f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgint u_socket_accept(int s) 71f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{ 72f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_HAVE_SOCKETS) 73f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return accept(s, NULL, NULL); 74f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#else 75f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 76f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 77f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org} 78f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 79f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgint 80f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgu_socket_send(int s, void *data, size_t size) 81f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{ 82f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_HAVE_SOCKETS) 83f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return send(s, data, size, 0); 84f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#else 85f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 86f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 87f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org} 88f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 89f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgint 90f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgu_socket_peek(int s, void *data, size_t size) 91f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{ 92f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_HAVE_SOCKETS) 93f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return recv(s, data, size, MSG_PEEK); 94f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#else 95f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 96f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 97f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org} 98f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 99f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgint 100f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgu_socket_recv(int s, void *data, size_t size) 101f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{ 102f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_HAVE_SOCKETS) 103f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return recv(s, data, size, 0); 104f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#else 105f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 106f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 107f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org} 108f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 109f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgint 110f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgu_socket_connect(const char *hostname, uint16_t port) 111f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{ 112f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_HAVE_SOCKETS) 113f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org int s; 114f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org struct sockaddr_in sa; 115f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org struct hostent *host = NULL; 116f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 117f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org memset(&sa, 0, sizeof(struct sockaddr_in)); 118f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org host = gethostbyname(hostname); 119f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org if (!host) 120f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 121f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 122f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org memcpy((char *)&sa.sin_addr,host->h_addr_list[0],host->h_length); 123f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org sa.sin_family= host->h_addrtype; 124f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org sa.sin_port = htons(port); 125f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 126f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org s = socket(host->h_addrtype, SOCK_STREAM, IPPROTO_TCP); 127f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org if (s < 0) 128f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 129f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 130f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org if (connect(s, (struct sockaddr *)&sa, sizeof(sa))) { 131f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org u_socket_close(s); 132f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 133f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org } 134f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 135f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return s; 136f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#else 137f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org assert(0); 138f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 139f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 140f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org} 141f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 142f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgint 143f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgu_socket_listen_on_port(uint16_t portnum) 144f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{ 145f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_HAVE_SOCKETS) 146f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org int s; 147f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org struct sockaddr_in sa; 148f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org memset(&sa, 0, sizeof(struct sockaddr_in)); 149f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 150f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org sa.sin_family = AF_INET; 151f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org sa.sin_port = htons(portnum); 152f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 153f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org s = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); 154f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org if (s < 0) 155f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 156f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 157f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org if (bind(s, (struct sockaddr *)&sa, sizeof(struct sockaddr_in)) == -1) { 158f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org u_socket_close(s); 159f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 160f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org } 161f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 162f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org listen(s, 0); 163f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 164f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return s; 165f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#else 166f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org assert(0); 167f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return -1; 168f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 169f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org} 170f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 171f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgvoid 172f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgu_socket_block(int s, boolean block) 173f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{ 174f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if defined(PIPE_OS_LINUX) || defined(PIPE_OS_HAIKU) \ 175f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org || defined(PIPE_OS_APPLE) || defined(PIPE_OS_SOLARIS) 176f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org int old = fcntl(s, F_GETFL, 0); 177f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org if (old == -1) 178f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org return; 179f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org 180f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org /* TODO obey block */ 181f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org if (block) 182f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org fcntl(s, F_SETFL, old & ~O_NONBLOCK); 183f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org else 184f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org fcntl(s, F_SETFL, old | O_NONBLOCK); 185f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#elif defined(PIPE_SUBSYSTEM_WINDOWS_USER) 186f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org u_long iMode = block ? 0 : 1; 187f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org ioctlsocket(s, FIONBIO, &iMode); 188f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#else 189f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org assert(0); 190f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif 191f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org} 192