This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
[inseparable changes from patch from perl5.003_23 to perl5.003_24]
[perl5.git] / win32 / win32sck.c
CommitLineData
0a753a76
PP
1// NTSock.C
2
3// (c) 1995 Microsoft Corporation. All rights reserved.
4// Developed by hip communications inc., http://info.hip.com/info/
5// Portions (c) 1993 Intergraph Corporation. All rights reserved.
6
7// You may distribute under the terms of either the GNU General Public
8// License or the Artistic License, as specified in the README file.
9
10#include <windows.h>
11#define WIN32_LEAN_AND_MEAN
12#include "EXTERN.h"
13#include "perl.h"
14#include <sys/socket.h>
15#include <fcntl.h>
16#include <sys/stat.h>
17#include <assert.h>
18
19#define CROAK croak
20
21#ifdef USE_SOCKETS_AS_HANDLES
22// thanks to Beverly Brown (beverly@datacube.com)
23
24# if defined(_WIN32) && !defined(WIN95_OSFHANDLE_FIXED) && defined(_M_IX86)
25//# define OPEN_SOCKET(x) _patch_open_osfhandle(x, _O_RDWR | _O_BINARY)
26# define OPEN_SOCKET(x) _open_osfhandle(x,_O_RDWR|_O_BINARY)
27# else
28# define OPEN_SOCKET(x) _open_osfhandle(x,_O_RDWR|_O_BINARY)
29# endif
30# define TO_SOCKET(x) _get_osfhandle(x)
31
32#else
33
34# define OPEN_SOCKET(x) (x)
35# define TO_SOCKET(x) (x)
36
37#endif // USE_SOCKETS_AS_HANDLES
38
39//
40// This is a clone of fdopen so that we can handle the version of sockets that NT gets to use.
41//
42// The problem is that sockets are not real file handles and
43// cannot be fdopen'ed. This causes problems in the do_socket
44// routine in doio.c, since it tries to create two file pointers
45// for the socket just created. We'll fake out an fdopen and see
46// if we can prevent perl from trying to do stdio on sockets.
47//
48
49#if defined(_WIN32) && !defined(WIN95_OSFHANDLE_FIXED) && defined(_M_IX86)
50
51# ifdef __cplusplus
52#define EXT_C_FUNC extern "C"
53# else
54#define EXT_C_FUNC extern
55# endif
56
57EXT_C_FUNC int __cdecl _alloc_osfhnd(void);
58EXT_C_FUNC int __cdecl _set_osfhnd(int fh, long value);
59EXT_C_FUNC void __cdecl _lock_fhandle(int);
60EXT_C_FUNC void __cdecl _unlock_fhandle(int);
61EXT_C_FUNC void __cdecl _unlock(int);
62EXT_C_FUNC struct servent* win32_savecopyservent(struct servent*d, struct servent*s, const char *proto);
63
64#if (_MSC_VER >= 1000)
65 typedef struct
66 {
67 long osfhnd; /* underlying OS file HANDLE */
68 char osfile; /* attributes of file (e.g., open in text mode?) */
69 char pipech; /* one char buffer for handles opened on pipes */
70#if defined (_MT) && !defined (DLL_FOR_WIN32S)
71 int lockinitflag;
72 CRITICAL_SECTION lock;
73#endif /* defined (_MT) && !defined (DLL_FOR_WIN32S) */
74 } ioinfo;
75
76 EXT_C_FUNC ioinfo * __pioinfo[];
77
78 #define IOINFO_L2E 5
79 #define IOINFO_ARRAY_ELTS (1 << IOINFO_L2E)
80 #define _pioinfo(i) (__pioinfo[i >> IOINFO_L2E] + (i & (IOINFO_ARRAY_ELTS - 1)))
81 #define _osfile(i) (_pioinfo(i)->osfile)
82#else
83 extern "C" extern char _osfile[];
84#endif // (_MSC_VER >= 1000)
85
86#define FOPEN 0x01 // file handle open
87#define FAPPEND 0x20 // file handle opened O_APPEND
88#define FDEV 0x40 // file handle refers to device
89#define FTEXT 0x80 // file handle is in text mode
90
91#define _STREAM_LOCKS 26 // Table of stream locks
92#define _LAST_STREAM_LOCK (_STREAM_LOCKS+_NSTREAM_-1) // Last stream lock
93#define _FH_LOCKS (_LAST_STREAM_LOCK+1) // Table of fh locks
94
95/***
96*int _patch_open_osfhandle(long osfhandle, int flags) - open C Runtime file handle
97*
98*Purpose:
99* This function allocates a free C Runtime file handle and associates
100* it with the Win32 HANDLE specified by the first parameter. This is a
101* temperary fix for WIN95's brain damage GetFileType() error on socket
102* we just bypass that call for socket
103*
104*Entry:
105* long osfhandle - Win32 HANDLE to associate with C Runtime file handle.
106* int flags - flags to associate with C Runtime file handle.
107*
108*Exit:
109* returns index of entry in fh, if successful
110* return -1, if no free entry is found
111*
112*Exceptions:
113*
114*******************************************************************************/
115
116int __cdecl _patch_open_osfhandle(long osfhandle, int flags)
117{
118 int fh;
119 char fileflags; // _osfile flags
120
121 // copy relevant flags from second parameter
122 fileflags = FDEV;
123
124 if(flags & _O_APPEND)
125 fileflags |= FAPPEND;
126
127 if(flags & _O_TEXT)
128 fileflags |= FTEXT;
129
130 // attempt to allocate a C Runtime file handle
131 if((fh = _alloc_osfhnd()) == -1)
132 {
133 errno = EMFILE; // too many open files
134 _doserrno = 0L; // not an OS error
135 return -1; // return error to caller
136 }
137
138 // the file is open. now, set the info in _osfhnd array
139 _set_osfhnd(fh, osfhandle);
140
141 fileflags |= FOPEN; // mark as open
142
143#if (_MSC_VER >= 1000)
144 _osfile(fh) = fileflags; // set osfile entry
145 _unlock_fhandle(fh);
146#else
147 _osfile[fh] = fileflags; // set osfile entry
148 _unlock(fh+_FH_LOCKS); // unlock handle
149#endif
150
151
152 return fh; // return handle
153}
154#endif // _M_IX86
155
156#define SOCKETAPI PASCAL
157
158typedef SOCKET (SOCKETAPI *LPSOCKACCEPT)(SOCKET, struct sockaddr *, int *);
159typedef int (SOCKETAPI *LPSOCKBIND)(SOCKET, const struct sockaddr *, int);
160typedef int (SOCKETAPI *LPSOCKCLOSESOCKET)(SOCKET);
161typedef int (SOCKETAPI *LPSOCKCONNECT)(SOCKET, const struct sockaddr *, int);
162typedef int (SOCKETAPI *LPSOCKIOCTLSOCKET)(SOCKET, long, u_long *);
163typedef int (SOCKETAPI *LPSOCKGETPEERNAME)(SOCKET, struct sockaddr *, int *);
164typedef int (SOCKETAPI *LPSOCKGETSOCKNAME)(SOCKET, struct sockaddr *, int *);
165typedef int (SOCKETAPI *LPSOCKGETSOCKOPT)(SOCKET, int, int, char *, int *);
166typedef u_long (SOCKETAPI *LPSOCKHTONL)(u_long);
167typedef u_short (SOCKETAPI *LPSOCKHTONS)(u_short);
168typedef int (SOCKETAPI *LPSOCKLISTEN)(SOCKET, int);
169typedef u_long (SOCKETAPI *LPSOCKNTOHL)(u_long);
170typedef u_short (SOCKETAPI *LPSOCKNTOHS)(u_short);
171typedef int (SOCKETAPI *LPSOCKRECV)(SOCKET, char *, int, int);
172typedef int (SOCKETAPI *LPSOCKRECVFROM)(SOCKET, char *, int, int, struct sockaddr *, int *);
173typedef int (SOCKETAPI *LPSOCKSELECT)(int, fd_set *, fd_set *, fd_set *, const struct timeval *);
174typedef int (SOCKETAPI *LPSOCKSEND)(SOCKET, const char *, int, int);
175typedef int (SOCKETAPI *LPSOCKSENDTO)(SOCKET, const char *, int, int, const struct sockaddr *, int);
176typedef int (SOCKETAPI *LPSOCKSETSOCKOPT)(SOCKET, int, int, const char *, int);
177typedef int (SOCKETAPI *LPSOCKSHUTDOWN)(SOCKET, int);
178typedef SOCKET (SOCKETAPI *LPSOCKSOCKET)(int, int, int);
179typedef char FAR *(SOCKETAPI *LPSOCKINETNTOA)(struct in_addr in);
180typedef unsigned long (SOCKETAPI *LPSOCKINETADDR)(const char FAR * cp);
181
182
183/* Database function prototypes */
184typedef struct hostent *(SOCKETAPI *LPSOCKGETHOSTBYADDR)(const char *, int, int);
185typedef struct hostent *(SOCKETAPI *LPSOCKGETHOSTBYNAME)(const char *);
186typedef int (SOCKETAPI *LPSOCKGETHOSTNAME)(char *, int);
187typedef struct servent *(SOCKETAPI *LPSOCKGETSERVBYPORT)(int, const char *);
188typedef struct servent *(SOCKETAPI *LPSOCKGETSERVBYNAME)(const char *, const char *);
189typedef struct protoent *(SOCKETAPI *LPSOCKGETPROTOBYNUMBER)(int);
190typedef struct protoent *(SOCKETAPI *LPSOCKGETPROTOBYNAME)(const char *);
191
192/* Microsoft Windows Extension function prototypes */
193typedef int (SOCKETAPI *LPSOCKWSASTARTUP)(unsigned short, LPWSADATA);
194typedef int (SOCKETAPI *LPSOCKWSACLEANUP)(void);
195typedef int (SOCKETAPI *LPSOCKWSAGETLASTERROR)(void);
196typedef int (SOCKETAPI *LPWSAFDIsSet)(SOCKET, fd_set *);
197
198static HINSTANCE hWinSockDll = 0;
199// extern CRITICAL_SECTION csSock;
200
201static LPSOCKACCEPT paccept = 0;
202static LPSOCKBIND pbind = 0;
203static LPSOCKCLOSESOCKET pclosesocket = 0;
204static LPSOCKCONNECT pconnect = 0;
205static LPSOCKIOCTLSOCKET pioctlsocket = 0;
206static LPSOCKGETPEERNAME pgetpeername = 0;
207static LPSOCKGETSOCKNAME pgetsockname = 0;
208static LPSOCKGETSOCKOPT pgetsockopt = 0;
209static LPSOCKHTONL phtonl = 0;
210static LPSOCKHTONS phtons = 0;
211static LPSOCKLISTEN plisten = 0;
212static LPSOCKNTOHL pntohl = 0;
213static LPSOCKNTOHS pntohs = 0;
214static LPSOCKRECV precv = 0;
215static LPSOCKRECVFROM precvfrom = 0;
216static LPSOCKSELECT pselect = 0;
217static LPSOCKSEND psend = 0;
218static LPSOCKSENDTO psendto = 0;
219static LPSOCKSETSOCKOPT psetsockopt = 0;
220static LPSOCKSHUTDOWN pshutdown = 0;
221static LPSOCKSOCKET psocket = 0;
222static LPSOCKGETHOSTBYADDR pgethostbyaddr = 0;
223static LPSOCKGETHOSTBYNAME pgethostbyname = 0;
224static LPSOCKGETHOSTNAME pgethostname = 0;
225static LPSOCKGETSERVBYPORT pgetservbyport = 0;
226static LPSOCKGETSERVBYNAME pgetservbyname = 0;
227static LPSOCKGETPROTOBYNUMBER pgetprotobynumber = 0;
228static LPSOCKGETPROTOBYNAME pgetprotobyname = 0;
229static LPSOCKWSASTARTUP pWSAStartup = 0;
230static LPSOCKWSACLEANUP pWSACleanup = 0;
231static LPSOCKWSAGETLASTERROR pWSAGetLastError = 0;
232static LPWSAFDIsSet pWSAFDIsSet = 0;
233static LPSOCKINETNTOA pinet_ntoa = 0;
234static LPSOCKINETADDR pinet_addr = 0;
235
236__declspec(thread) struct servent myservent;
237
238
239void *GetAddress(HINSTANCE hInstance, char *lpFunctionName)
240{
241 char buffer[512];
242 FARPROC proc = GetProcAddress(hInstance, lpFunctionName);
243 if(proc == 0)
244 {
245 sprintf(buffer, "Unable to get address of %s in WSock32.dll", lpFunctionName);
246 CROAK(buffer);
247 }
248 return proc;
249}
250
251void LoadWinSock(void)
252{
253// EnterCriticalSection(&csSock);
254 if(hWinSockDll == NULL)
255 {
256 HINSTANCE hLib = LoadLibrary("WSock32.DLL");
257 if(hLib == NULL)
258 CROAK("Could not load WSock32.dll\n");
259
260 paccept = (LPSOCKACCEPT)GetAddress(hLib, "accept");
261 pbind = (LPSOCKBIND)GetAddress(hLib, "bind");
262 pclosesocket = (LPSOCKCLOSESOCKET)GetAddress(hLib, "closesocket");
263 pconnect = (LPSOCKCONNECT)GetAddress(hLib, "connect");
264 pioctlsocket = (LPSOCKIOCTLSOCKET)GetAddress(hLib, "ioctlsocket");
265 pgetpeername = (LPSOCKGETPEERNAME)GetAddress(hLib, "getpeername");
266 pgetsockname = (LPSOCKGETSOCKNAME)GetAddress(hLib, "getsockname");
267 pgetsockopt = (LPSOCKGETSOCKOPT)GetAddress(hLib, "getsockopt");
268 phtonl = (LPSOCKHTONL)GetAddress(hLib, "htonl");
269 phtons = (LPSOCKHTONS)GetAddress(hLib, "htons");
270 plisten = (LPSOCKLISTEN)GetAddress(hLib, "listen");
271 pntohl = (LPSOCKNTOHL)GetAddress(hLib, "ntohl");
272 pntohs = (LPSOCKNTOHS)GetAddress(hLib, "ntohs");
273 precv = (LPSOCKRECV)GetAddress(hLib, "recv");
274 precvfrom = (LPSOCKRECVFROM)GetAddress(hLib, "recvfrom");
275 pselect = (LPSOCKSELECT)GetAddress(hLib, "select");
276 psend = (LPSOCKSEND)GetAddress(hLib, "send");
277 psendto = (LPSOCKSENDTO)GetAddress(hLib, "sendto");
278 psetsockopt = (LPSOCKSETSOCKOPT)GetAddress(hLib, "setsockopt");
279 pshutdown = (LPSOCKSHUTDOWN)GetAddress(hLib, "shutdown");
280 psocket = (LPSOCKSOCKET)GetAddress(hLib, "socket");
281 pgethostbyaddr = (LPSOCKGETHOSTBYADDR)GetAddress(hLib, "gethostbyaddr");
282 pgethostbyname = (LPSOCKGETHOSTBYNAME)GetAddress(hLib, "gethostbyname");
283 pgethostname = (LPSOCKGETHOSTNAME)GetAddress(hLib, "gethostname");
284 pgetservbyport = (LPSOCKGETSERVBYPORT)GetAddress(hLib, "getservbyport");
285 pgetservbyname = (LPSOCKGETSERVBYNAME)GetAddress(hLib, "getservbyname");
286 pgetprotobynumber = (LPSOCKGETPROTOBYNUMBER)GetAddress(hLib, "getprotobynumber");
287 pgetprotobyname = (LPSOCKGETPROTOBYNAME)GetAddress(hLib, "getprotobyname");
288 pWSAStartup = (LPSOCKWSASTARTUP)GetAddress(hLib, "WSAStartup");
289 pWSACleanup = (LPSOCKWSACLEANUP)GetAddress(hLib, "WSACleanup");
290 pWSAGetLastError = (LPSOCKWSAGETLASTERROR)GetAddress(hLib, "WSAGetLastError");
291 pWSAFDIsSet = (LPWSAFDIsSet)GetAddress(hLib, "__WSAFDIsSet");
292 pinet_addr = (LPSOCKINETADDR)GetAddress(hLib,"inet_addr");
293 pinet_ntoa = (LPSOCKINETNTOA)GetAddress(hLib,"inet_ntoa");
294
295 hWinSockDll = hLib;
296 }
297// LeaveCriticalSection(&csSock);
298}
299
300void EndSockets(void)
301{
302 if(hWinSockDll != NULL)
303 {
304 pWSACleanup();
305 FreeLibrary(hWinSockDll);
306 }
307 hWinSockDll = NULL;
308}
309
310void StartSockets(void)
311{
312 unsigned short version;
313 WSADATA retdata;
314 int ret;
315 int iSockOpt = SO_SYNCHRONOUS_NONALERT;
316
317 LoadWinSock();
318 //
319 // initalize the winsock interface and insure that it is
320 // cleaned up at exit.
321 //
322 version = 0x101;
323 if(ret = pWSAStartup(version, &retdata))
324 CROAK("Unable to locate winsock library!\n");
325 if(retdata.wVersion != version)
326 CROAK("Could not find version 1.1 of winsock dll\n");
327
328 // atexit((void (*)(void)) EndSockets);
329
330#ifdef USE_SOCKETS_AS_HANDLES
331 //
332 // Enable the use of sockets as filehandles
333 //
334 psetsockopt(INVALID_SOCKET, SOL_SOCKET, SO_OPENTYPE, (char *)&iSockOpt, sizeof(iSockOpt));
335#endif // USE_SOCKETS_AS_HANDLES
336}
337
338
339#ifndef USE_SOCKETS_AS_HANDLES
340FILE *myfdopen(int fd, char *mode)
341{
342 FILE *fp;
343 char sockbuf[256];
344 int optlen = sizeof(sockbuf);
345 int retval;
346
347
348 if(hWinSockDll == 0)
349 LoadWinSock();
350
351 retval = pgetsockopt((SOCKET)fd, SOL_SOCKET, SO_TYPE, sockbuf, &optlen);
352 if(retval == SOCKET_ERROR && pWSAGetLastError() == WSAENOTSOCK)
353 {
354 return(_fdopen(fd, mode));
355 }
356
357 //
358 // If we get here, then fd is actually a socket.
359 //
360 Newz(1601, fp, 1, FILE);
361 if(fp == NULL)
362 {
363 errno = ENOMEM;
364 return NULL;
365 }
366
367 fp->_file = fd;
368 if(*mode == 'r')
369 fp->_flag = _IOREAD;
370 else
371 fp->_flag = _IOWRT;
372
373 return fp;
374}
375#endif // USE_SOCKETS_AS_HANDLES
376
377
378u_long win32_htonl(u_long hostlong)
379{
380 if(hWinSockDll == 0)
381 LoadWinSock();
382
383 return phtonl(hostlong);
384}
385
386u_short win32_htons(u_short hostshort)
387{
388 if(hWinSockDll == 0)
389 LoadWinSock();
390
391 return phtons(hostshort);
392}
393
394u_long win32_ntohl(u_long netlong)
395{
396 if(hWinSockDll == 0)
397 LoadWinSock();
398
399 return pntohl(netlong);
400}
401
402u_short win32_ntohs(u_short netshort)
403{
404 if(hWinSockDll == 0)
405 LoadWinSock();
406
407 return pntohs(netshort);
408}
409
410
411#define SOCKET_TEST(x, y) if(hWinSockDll == 0) StartSockets();\
412 if((x) == (y)) errno = pWSAGetLastError()
413
414#define SOCKET_TEST_ERROR(x) SOCKET_TEST(x, SOCKET_ERROR)
415
416SOCKET win32_accept(SOCKET s, struct sockaddr *addr, int *addrlen)
417{
418 SOCKET r;
419
420 SOCKET_TEST((r = paccept(TO_SOCKET(s), addr, addrlen)), INVALID_SOCKET);
421 return OPEN_SOCKET(r);
422}
423
424int win32_bind(SOCKET s, const struct sockaddr *addr, int addrlen)
425{
426 int r;
427
428 SOCKET_TEST_ERROR(r = pbind(TO_SOCKET(s), addr, addrlen));
429 return r;
430}
431
432int win32_connect(SOCKET s, const struct sockaddr *addr, int addrlen)
433{
434 int r;
435
436 SOCKET_TEST_ERROR(r = pconnect(TO_SOCKET(s), addr, addrlen));
437 return r;
438}
439
440
441int win32_getpeername(SOCKET s, struct sockaddr *addr, int *addrlen)
442{
443 int r;
444
445 SOCKET_TEST_ERROR(r = pgetpeername(TO_SOCKET(s), addr, addrlen));
446 return r;
447}
448
449int win32_getsockname(SOCKET s, struct sockaddr *addr, int *addrlen)
450{
451 int r;
452
453 SOCKET_TEST_ERROR(r = pgetsockname(TO_SOCKET(s), addr, addrlen));
454 return r;
455}
456
457int win32_getsockopt(SOCKET s, int level, int optname, char *optval, int *optlen)
458{
459 int r;
460
461 SOCKET_TEST_ERROR(r = pgetsockopt(TO_SOCKET(s), level, optname, optval, optlen));
462 return r;
463}
464
465int win32_ioctlsocket(SOCKET s, long cmd, u_long *argp)
466{
467 int r;
468
469 SOCKET_TEST_ERROR(r = pioctlsocket(TO_SOCKET(s), cmd, argp));
470 return r;
471}
472
473int win32_listen(SOCKET s, int backlog)
474{
475 int r;
476
477 SOCKET_TEST_ERROR(r = plisten(TO_SOCKET(s), backlog));
478 return r;
479}
480
481int win32_recv(SOCKET s, char *buf, int len, int flags)
482{
483 int r;
484
485 SOCKET_TEST_ERROR(r = precv(TO_SOCKET(s), buf, len, flags));
486 return r;
487}
488
489int win32_recvfrom(SOCKET s, char *buf, int len, int flags, struct sockaddr *from, int *fromlen)
490{
491 int r;
492
493 SOCKET_TEST_ERROR(r = precvfrom(TO_SOCKET(s), buf, len, flags, from, fromlen));
494 return r;
495}
496
497// select contributed by Vincent R. Slyngstad (vrs@ibeam.intel.com)
498int win32_select(int nfds, int* rd, int* wr, int* ex, const struct timeval* timeout)
499{
500 long r;
501 int dummy = 0;
502 int i, fd, bit, offset;
503 FD_SET nrd, nwr, nex,*prd,*pwr,*pex;
504
505 if (!rd) rd = &dummy, prd = NULL;
506 else prd = &nrd;
507 if (!wr) wr = &dummy, pwr = NULL;
508 else pwr = &nwr;
509 if (!ex) ex = &dummy, pex = NULL;
510 else pex = &nex;
511
512 FD_ZERO(&nrd);
513 FD_ZERO(&nwr);
514 FD_ZERO(&nex);
515 for (i = 0; i < nfds; i++)
516 {
517 fd = TO_SOCKET(i);
518 bit = 1L<<(i % (sizeof(int)*8));
519 offset = i / (sizeof(int)*8);
520 if (rd[offset] & bit)
521 FD_SET(fd, &nrd);
522 if (wr[offset] & bit)
523 FD_SET(fd, &nwr);
524 if (ex[offset] & bit)
525 FD_SET(fd, &nex);
526 }
527
528 SOCKET_TEST_ERROR(r = pselect(nfds, prd, pwr, pex, timeout));
529
530 for (i = 0; i < nfds; i++)
531 {
532 fd = TO_SOCKET(i);
533 bit = 1L<<(i % (sizeof(int)*8));
534 offset = i / (sizeof(int)*8);
535 if (rd[offset] & bit)
536 {
537 if (!pWSAFDIsSet(fd, &nrd))
538 rd[offset] &= ~bit;
539 }
540 if (wr[offset] & bit)
541 {
542 if (!pWSAFDIsSet(fd, &nwr))
543 wr[offset] &= ~bit;
544 }
545 if (ex[offset] & bit)
546 {
547 if (!pWSAFDIsSet(fd, &nex))
548 ex[offset] &= ~bit;
549 }
550 }
551 return r;
552}
553
554int win32_send(SOCKET s, const char *buf, int len, int flags)
555{
556 int r;
557
558 SOCKET_TEST_ERROR(r = psend(TO_SOCKET(s), buf, len, flags));
559 return r;
560}
561
562int win32_sendto(SOCKET s, const char *buf, int len, int flags, const struct sockaddr *to, int tolen)
563{
564 int r;
565
566 SOCKET_TEST_ERROR(r = psendto(TO_SOCKET(s), buf, len, flags, to, tolen));
567 return r;
568}
569
570int win32_setsockopt(SOCKET s, int level, int optname, const char *optval, int optlen)
571{
572 int r;
573
574 SOCKET_TEST_ERROR(r = psetsockopt(TO_SOCKET(s), level, optname, optval, optlen));
575 return r;
576}
577
578int win32_shutdown(SOCKET s, int how)
579{
580 int r;
581
582 SOCKET_TEST_ERROR(r = pshutdown(TO_SOCKET(s), how));
583 return r;
584}
585
586SOCKET win32_socket(int af, int type, int protocol)
587{
588 SOCKET s;
589
590#ifndef USE_SOCKETS_AS_HANDLES
591 SOCKET_TEST(s = psocket(af, type, protocol), INVALID_SOCKET);
592#else
593 if(hWinSockDll == 0)
594 StartSockets();
595
596 if((s = psocket(af, type, protocol)) == INVALID_SOCKET)
597 errno = pWSAGetLastError();
598 else
599 s = OPEN_SOCKET(s);
600#endif // USE_SOCKETS_AS_HANDLES
601
602 return s;
603}
604
605struct hostent *win32_gethostbyaddr(const char *addr, int len, int type)
606{
607 struct hostent *r;
608
609 SOCKET_TEST(r = pgethostbyaddr(addr, len, type), NULL);
610 return r;
611}
612
613struct hostent *win32_gethostbyname(const char *name)
614{
615 struct hostent *r;
616
617 SOCKET_TEST(r = pgethostbyname(name), NULL);
618 return r;
619}
620
621int win32_gethostname(char *name, int len)
622{
623 int r;
624
625 SOCKET_TEST_ERROR(r = pgethostname(name, len));
626 return r;
627}
628
629struct protoent *win32_getprotobyname(const char *name)
630{
631 struct protoent *r;
632
633 SOCKET_TEST(r = pgetprotobyname(name), NULL);
634 return r;
635}
636
637struct protoent *win32_getprotobynumber(int num)
638{
639 struct protoent *r;
640
641 SOCKET_TEST(r = pgetprotobynumber(num), NULL);
642 return r;
643}
644
645struct servent *win32_getservbyname(const char *name, const char *proto)
646{
647 struct servent *r;
648
649 SOCKET_TEST(r = pgetservbyname(name, proto), NULL);
650 if (r) {
651 r = win32_savecopyservent(&myservent, r, proto);
652 }
653 return r;
654}
655
656struct servent *win32_getservbyport(int port, const char *proto)
657{
658 struct servent *r;
659
660 SOCKET_TEST(r = pgetservbyport(port, proto), NULL);
661 if (r) {
662 r = win32_savecopyservent(&myservent, r, proto);
663 }
664 return r;
665}
666
667char FAR *win32_inet_ntoa(struct in_addr in)
668{
669 if(hWinSockDll == 0) LoadWinSock();
670
671 return pinet_ntoa(in);
672}
673
674unsigned long win32_inet_addr(const char FAR *cp)
675{
676 if(hWinSockDll == 0) LoadWinSock();
677
678 return pinet_addr(cp);
679
680}
681//
682// Networking stubs
683//
684#undef CROAK
685#define CROAK croak
686
687void win32_endhostent()
688{
689 CROAK("endhostent not implemented!\n");
690}
691
692void win32_endnetent()
693{
694 CROAK("endnetent not implemented!\n");
695}
696
697void win32_endprotoent()
698{
699 CROAK("endprotoent not implemented!\n");
700}
701
702void win32_endservent()
703{
704 CROAK("endservent not implemented!\n");
705}
706
707
708struct netent *win32_getnetent(void)
709{
710 CROAK("getnetent not implemented!\n");
711 return (struct netent *) NULL;
712}
713
714struct netent *win32_getnetbyname(char *name)
715{
716 CROAK("getnetbyname not implemented!\n");
717 return (struct netent *)NULL;
718}
719
720struct netent *win32_getnetbyaddr(long net, int type)
721{
722 CROAK("getnetbyaddr not implemented!\n");
723 return (struct netent *)NULL;
724}
725
726struct protoent *win32_getprotoent(void)
727{
728 CROAK("getprotoent not implemented!\n");
729 return (struct protoent *) NULL;
730}
731
732struct servent *win32_getservent(void)
733{
734 CROAK("getservent not implemented!\n");
735 return (struct servent *) NULL;
736}
737
738void win32_sethostent(int stayopen)
739{
740 CROAK("sethostent not implemented!\n");
741}
742
743
744void win32_setnetent(int stayopen)
745{
746 CROAK("setnetent not implemented!\n");
747}
748
749
750void win32_setprotoent(int stayopen)
751{
752 CROAK("setprotoent not implemented!\n");
753}
754
755
756void win32_setservent(int stayopen)
757{
758 CROAK("setservent not implemented!\n");
759}
760
761