Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: downloads/enet-1.1/win32.c @ 28

Last change on this file since 28 was 13, checked in by landauf, 17 years ago

added enet

File size: 7.3 KB
Line 
1/**
2 @file  win32.c
3 @brief ENet Win32 system specific functions
4*/
5#ifdef WIN32
6
7#include <time.h>
8#define ENET_BUILDING_LIB 1
9#include "enet/enet.h"
10
11static enet_uint32 timeBase = 0;
12
13int
14enet_initialize (void)
15{
16    WORD versionRequested = MAKEWORD (1, 1);
17    WSADATA wsaData;
18   
19    if (WSAStartup (versionRequested, & wsaData))
20       return -1;
21
22    if (LOBYTE (wsaData.wVersion) != 1||
23        HIBYTE (wsaData.wVersion) != 1)
24    {
25       WSACleanup ();
26       
27       return -1;
28    }
29
30    timeBeginPeriod (1);
31
32    return 0;
33}
34
35void
36enet_deinitialize (void)
37{
38    timeEndPeriod (1);
39
40    WSACleanup ();
41}
42
43enet_uint32
44enet_time_get (void)
45{
46    return (enet_uint32) timeGetTime () - timeBase;
47}
48
49void
50enet_time_set (enet_uint32 newTimeBase)
51{
52    timeBase = (enet_uint32) timeGetTime () - newTimeBase;
53}
54
55int
56enet_address_set_host (ENetAddress * address, const char * name)
57{
58    struct hostent * hostEntry;
59
60    hostEntry = gethostbyname (name);
61    if (hostEntry == NULL ||
62        hostEntry -> h_addrtype != AF_INET)
63    {
64        unsigned long host = inet_addr (name);
65        if (host == INADDR_NONE)
66            return -1;
67        address -> host = host;
68        return 0;
69    }
70
71    address -> host = * (enet_uint32 *) hostEntry -> h_addr_list [0];
72
73    return 0;
74}
75
76int
77enet_address_get_host_ip (const ENetAddress * address, char * name, size_t nameLength)
78{
79    char * addr = inet_ntoa (* (struct in_addr *) & address -> host);
80    if (addr == NULL)
81        return -1;
82    strncpy (name, addr, nameLength);
83    return 0;
84}
85
86int
87enet_address_get_host (const ENetAddress * address, char * name, size_t nameLength)
88{
89    struct in_addr in;
90    struct hostent * hostEntry;
91   
92    in.s_addr = address -> host;
93   
94    hostEntry = gethostbyaddr ((char *) & in, sizeof (struct in_addr), AF_INET);
95    if (hostEntry == NULL)
96      return enet_address_get_host_ip (address, name, nameLength);
97
98    strncpy (name, hostEntry -> h_name, nameLength);
99
100    return 0;
101}
102
103ENetSocket
104enet_socket_create (ENetSocketType type, const ENetAddress * address)
105{
106    ENetSocket newSocket = socket (PF_INET, type == ENET_SOCKET_TYPE_DATAGRAM ? SOCK_DGRAM : SOCK_STREAM, 0);
107    u_long nonBlocking = 1;
108    int receiveBufferSize = ENET_HOST_RECEIVE_BUFFER_SIZE,
109        sendBufferSize = ENET_HOST_SEND_BUFFER_SIZE,
110        allowBroadcasting = 1;
111    struct sockaddr_in sin;
112
113    if (newSocket == ENET_SOCKET_NULL)
114      return ENET_SOCKET_NULL;
115
116    if (type == ENET_SOCKET_TYPE_DATAGRAM)
117    {
118        ioctlsocket (newSocket, FIONBIO, & nonBlocking);
119
120        setsockopt (newSocket, SOL_SOCKET, SO_RCVBUF, (char *) & receiveBufferSize, sizeof (int));
121        setsockopt (newSocket, SOL_SOCKET, SO_SNDBUF, (char *) & sendBufferSize, sizeof (int));
122        setsockopt (newSocket, SOL_SOCKET, SO_BROADCAST, (char *) & allowBroadcasting, sizeof (int));
123    }
124
125    memset (& sin, 0, sizeof (struct sockaddr_in));
126
127    sin.sin_family = AF_INET;
128   
129    if (address != NULL)
130    {
131       sin.sin_port = ENET_HOST_TO_NET_16 (address -> port);
132       sin.sin_addr.s_addr = address -> host;
133    }
134    else
135    {
136       sin.sin_port = 0;
137       sin.sin_addr.s_addr = INADDR_ANY;
138    }
139
140    if (bind (newSocket,   
141              (struct sockaddr *) & sin,
142              sizeof (struct sockaddr_in)) == SOCKET_ERROR ||
143        (type == ENET_SOCKET_TYPE_STREAM &&
144          address != NULL &&
145          address -> port != ENET_PORT_ANY &&
146          listen (newSocket, SOMAXCONN) == SOCKET_ERROR))
147    {
148       closesocket (newSocket);
149
150       return ENET_SOCKET_NULL;
151    }
152
153    return newSocket;
154}
155
156int
157enet_socket_connect (ENetSocket socket, const ENetAddress * address)
158{
159    struct sockaddr_in sin;
160
161    memset (& sin, 0, sizeof (struct sockaddr_in));
162
163    sin.sin_family = AF_INET;
164    sin.sin_port = ENET_HOST_TO_NET_16 (address -> port);
165    sin.sin_addr.s_addr = address -> host;
166
167    return connect (socket, (struct sockaddr *) & sin, sizeof (struct sockaddr_in));
168}
169
170ENetSocket
171enet_socket_accept (ENetSocket socket, ENetAddress * address)
172{
173    SOCKET result;
174    struct sockaddr_in sin;
175    int sinLength = sizeof (struct sockaddr_in);
176
177    result = accept (socket, 
178                     address != NULL ? (struct sockaddr *) & sin : NULL, 
179                     address != NULL ? & sinLength : NULL);
180
181    if (result == INVALID_SOCKET)
182      return ENET_SOCKET_NULL;
183
184    if (address != NULL)
185    {
186        address -> host = (enet_uint32) sin.sin_addr.s_addr;
187        address -> port = ENET_NET_TO_HOST_16 (sin.sin_port);
188    }
189
190    return result;
191}
192
193void
194enet_socket_destroy (ENetSocket socket)
195{
196    closesocket (socket);
197}
198
199int
200enet_socket_send (ENetSocket socket,
201                  const ENetAddress * address,
202                  const ENetBuffer * buffers,
203                  size_t bufferCount)
204{
205    struct sockaddr_in sin;
206    DWORD sentLength;
207
208    if (address != NULL)
209    {
210        sin.sin_family = AF_INET;
211        sin.sin_port = ENET_HOST_TO_NET_16 (address -> port);
212        sin.sin_addr.s_addr = address -> host;
213    }
214
215    if (WSASendTo (socket, 
216                   (LPWSABUF) buffers,
217                   (DWORD) bufferCount,
218                   & sentLength,
219                   0,
220                   address != NULL ? (struct sockaddr *) & sin : 0,
221                   address != NULL ? sizeof (struct sockaddr_in) : 0,
222                   NULL,
223                   NULL) == SOCKET_ERROR)
224    {
225       if (WSAGetLastError () == WSAEWOULDBLOCK)
226         return 0;
227
228       return -1;
229    }
230
231    return (int) sentLength;
232}
233
234int
235enet_socket_receive (ENetSocket socket,
236                     ENetAddress * address,
237                     ENetBuffer * buffers,
238                     size_t bufferCount)
239{
240    INT sinLength = sizeof (struct sockaddr_in);
241    DWORD flags = 0,
242          recvLength;
243    struct sockaddr_in sin;
244
245    if (WSARecvFrom (socket,
246                     (LPWSABUF) buffers,
247                     (DWORD) bufferCount,
248                     & recvLength,
249                     & flags,
250                     address != NULL ? (struct sockaddr *) & sin : NULL,
251                     address != NULL ? & sinLength : NULL,
252                     NULL,
253                     NULL) == SOCKET_ERROR)
254    {
255       switch (WSAGetLastError ())
256       {
257       case WSAEWOULDBLOCK:
258       case WSAECONNRESET:
259          return 0;
260       }
261
262       return -1;
263    }
264
265    if (flags & MSG_PARTIAL)
266      return -1;
267
268    if (address != NULL)
269    {
270        address -> host = (enet_uint32) sin.sin_addr.s_addr;
271        address -> port = ENET_NET_TO_HOST_16 (sin.sin_port);
272    }
273
274    return (int) recvLength;
275}
276
277int
278enet_socket_wait (ENetSocket socket, enet_uint32 * condition, enet_uint32 timeout)
279{
280    fd_set readSet, writeSet;
281    struct timeval timeVal;
282    int selectCount;
283   
284    timeVal.tv_sec = timeout / 1000;
285    timeVal.tv_usec = (timeout % 1000) * 1000;
286   
287    FD_ZERO (& readSet);
288    FD_ZERO (& writeSet);
289
290    if (* condition & ENET_SOCKET_WAIT_SEND)
291      FD_SET (socket, & writeSet);
292
293    if (* condition & ENET_SOCKET_WAIT_RECEIVE)
294      FD_SET (socket, & readSet);
295
296    selectCount = select (socket + 1, & readSet, & writeSet, NULL, & timeVal);
297
298    if (selectCount < 0)
299      return -1;
300
301    * condition = ENET_SOCKET_WAIT_NONE;
302
303    if (selectCount == 0)
304      return 0;
305
306    if (FD_ISSET (socket, & writeSet))
307      * condition |= ENET_SOCKET_WAIT_SEND;
308   
309    if (FD_ISSET (socket, & readSet))
310      * condition |= ENET_SOCKET_WAIT_RECEIVE;
311
312    return 0;
313} 
314
315#endif
316
Note: See TracBrowser for help on using the repository browser.