• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2 Copyright (C) 1996-1997 Id Software, Inc.
3 
4 This program is free software; you can redistribute it and/or
5 modify it under the terms of the GNU General Public License
6 as published by the Free Software Foundation; either version 2
7 of the License, or (at your option) any later version.
8 
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
12 
13 See the GNU General Public License for more details.
14 
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
18 
19 */
20 #include <go32.h>
21 #include "mpdosock.h"
22 
23 //#include "types.h"
24 typedef unsigned char BYTE;
25 typedef unsigned short WORD;
26 typedef unsigned long DWORD;
27 
28 //#include "lpc.h"
29 typedef struct {
30    short  version;            // version of LPC requested
31    short  sizeOfArgs;         // size of arguments
32    short  service;            // service # requested
33    char   Data[1];            // data
34 } LPCData;
35 
36 typedef struct {
37    short version;             // LPC version
38    short sizeOfReturn;        // return data size
39    short error;               // any error codes
40    short noRet;               // number of returns
41    char  Data[1];             // data
42 } LPCReturn;
43 
44 //#include "services.h"
45 #define  MAXSOCKETS  20
46 
47 // services
48 #define LPC_SOCKBIND        4
49 #define LPC_SOCKGETHOSTBYNAME   5
50 #define LPC_SOCKGETHOSTNAME     6
51 #define LPC_SOCKGETHOSTBYADDR   7
52 #define LPC_SOCKCLOSE           8
53 #define LPC_SOCKSOCKET          9
54 #define LPC_SOCKRECVFROM        10
55 #define LPC_SOCKSENDTO          11
56 #define LPC_SOCKIOCTL           12
57 #define LPC_SOCKGETSOCKNAME     13
58 #define LPC_SOCKFLUSH           14
59 #define LPC_SOCKSETOPT          15
60 #define LPC_SOCKGETLASTERROR    16
61 #define LPC_SOCKINETADDR        17
62 
63 // htons, ntohs, htonl, ntohl implemented locally
64 
65 // errors
66 #define LPC_UNRECOGNIZED_SERVICE  -1
67 #define LPC_NOERROR                0
68 
69 // structures for support
70 typedef struct {
71    SOCKET s;
72    int    namelen;
73    char   name[1];
74 } BindArgs;
75 
76 typedef struct {
77    SOCKET s;
78    long   cmd;
79    char   data[1];
80 } IoctlArgs;
81 
82 typedef struct {
83    int retVal;
84    int namelen;
85    char name[1];
86 } GetSockNameRet;
87 
88 typedef GetSockNameRet GetHostNameRet;
89 
90 typedef struct {
91    int   retVal;
92    int   h_addr_0;    // that's the only important value
93 } GetHostByNameRet;
94 
95 typedef struct {
96    int   len;
97    int   type;
98    char  addr[1];
99 } GetHostByAddrArgs;
100 
101 typedef struct {
102    int   retVal;
103    char  h_name[1];  // h_name is the only important value
104 } GetHostByAddrRet;
105 
106 typedef struct {
107    SOCKET s;
108    int flags;
109 } RecvFromArgs;
110 
111 typedef struct {
112    int  retVal;
113    int  errCode;
114    int  len;   // message len
115    struct sockaddr    sockaddr;
116    int  sockaddrlen;
117    char Data[1];
118 } RecvFromRet;
119 
120 typedef struct {
121    SOCKET s;
122    int    flags;
123    int    len;
124    struct sockaddr sockaddr;
125    int    sockaddrlen;
126    char   Data[1];
127 } SendToArgs;
128 
129 typedef struct {
130    int   retVal;
131    int   errCode;
132 } SendToRet;
133 
134 typedef struct {
135    int     bufflen;
136    SOCKET  s;
137    int     len;
138    int     sockaddrlen;
139    struct sockaddr    address;
140    char               data[1];
141 } SocketChannelData;
142 
143 typedef struct {
144    int af;
145    int type;
146    int protocol;
147 } SocketArgs;
148 
149 typedef struct {
150    SOCKET s;
151    int len;
152    int flags;
153    int addrlen;
154    struct sockaddr addr;
155    char data[1];
156 } WinSockData;
157 
158 typedef struct {
159    SOCKET s;
160    int level;
161    int optname;
162    int optlen;
163    char optval[1];
164 } SetSockOptArgs;
165 
166 typedef struct {
167    SOCKET   sock[MAXSOCKETS];
168 } SocketMap;
169 
170 //#include "rtq.h"
171 #define RTQ_NODE struct rtq_node
172 
173 RTQ_NODE
174    {
175       RTQ_NODE *self; // Ring zero address of this node
176       RTQ_NODE *left; // Ring zero address of preceding node
177       RTQ_NODE *right; // Ring zero address of succeding node
178       BYTE *      rtqDatum;  // Ring 3 Datum of Buffer (start of preface)
179       BYTE *      rtqInsert; // Ring 3 insertion position
180       WORD     rtqLen; // Length of buffer, excluding preface
181       WORD     rtqUpCtr;  // Up Counter of bytes used so far
182       WORD     rtqQCtr;   // number of nodes attached
183       WORD     padding;   // DWORD alignment
184    };
185 
186 #define RTQ_PARAM_MOVENODE struct rtq_param_movenode
187 RTQ_PARAM_MOVENODE
188    {
189       WORD     rtqFromDQ;
190       WORD     rtqToDQ;
191    };
192 
193 RTQ_NODE* rtq_fetch(RTQ_NODE*, RTQ_NODE*); // To, From
194 
195 //#include "mplib.h"
196 // give up time slice
197 void Yield(void);
198 void MGenWakeupDll(void);
199 
200 // post a message to win32 side
201 void PostWindowsMessage(void);
202 
203 // get # of items on qNo
204 int MGenGetQueueCtr(int qNo);
205 
206 // move first node from qFrom to qTo
207 RTQ_NODE *MGenMoveTo(int qFrom, int qTo);
208 
209 // get first node from q
210 RTQ_NODE *MGenGetNode(int q);
211 
212 // get master node, returning size of RTQ_NODE for size verification
213 RTQ_NODE *MGenGetMasterNode(unsigned *size);
214 
215 // move all nodes from qFrom to qTo
216 RTQ_NODE *MGenFlushNodes(int qFrom, int qTo);
217 
218 // count number of nodes in queues designated by bitmask
219 // lowerOrderBits == 0..31, upperOrderBits == 32-63
220 int MGenMCount(unsigned lowerOrderBits, unsigned upperOrderBits);
221 
222 // perform consistency check on chunnel address space
223 int MGenSanityCheck(void);
224 
225 #include <stdio.h>
226 #include <sys/farptr.h>
227 
228 extern short flat_selector;
229 
230 #define SOCKET_MAP_QUEUE  41
231 
232 #define IDLE_QUEUE    44
233 #define REC_QUEUE     45
234 #define SEND_QUEUE    46
235 
236 //  queue sizes
237 #define FREEQBASE      58
238 #define FREEQ64        58
239 #define FREEQ128       59
240 #define FREEQ256       60
241 #define FREEQ512       61
242 #define FREEQ1024      62
243 #define FREEQ2048      63
244 
245 #define NFREEQ         6
246 
247 #define QLIMIT         10
248 
249 #define PRIVATEQ       50
250 
251 #define FARPKL(x)  (_farnspeekl((unsigned long) x))
252 #define FARPKB(x)  (_farnspeekb((unsigned long) x))
253 #define FARPKS(x)  (_farnspeekw((unsigned long) x))
254 
255 #define FARPOKL(x, y) (_farnspokel((unsigned long) x, (unsigned long) y))
256 #define FARPOKB(x, y) (_farnspokeb((unsigned long) x, (unsigned char) y))
257 
258 int Qsizes[] = { 64, 128, 256, 512, 1024, 2048 };
259 
260 int SocketError = 0;
261 
262 SocketMap *SockMap;
263 
264 #define HOSTENT_ALIAS_LIMIT    5
265 #define HOSTENT_STRLEN_LIMIT   50
266 #define HOSTENT_ADDR_LIST_LIMIT   5
267 
268 struct hostent  HostEnt;
269 
270 char HostEnt_hname[HOSTENT_STRLEN_LIMIT];
271 char *HostEnt_h_aliases[HOSTENT_ALIAS_LIMIT];
272 char HostEnt_names[HOSTENT_ALIAS_LIMIT][HOSTENT_STRLEN_LIMIT];
273 struct in_addr* HostEnt_addr_list[HOSTENT_ADDR_LIST_LIMIT];
274 struct in_addr HostEnt_addrs[HOSTENT_ADDR_LIST_LIMIT];
275 
276 void
fmemcpyto(void * to,const void * from,int length)277 fmemcpyto(void *to, const void *from, int length)
278 {
279    movedata(_my_ds(), (unsigned)from, flat_selector, (unsigned)to, length);
280 }
281 
282 void
fmemcpyfrom(void * to,const void * from,int length)283 fmemcpyfrom(void *to, const void *from, int length)
284 {
285    movedata(flat_selector, (unsigned)from, _my_ds(), (unsigned)to, length);
286 }
287 
288 void
fstrcpyto(char * to,const char * from)289 fstrcpyto(char *to, const char *from)
290 {
291    while (*from) {
292       FARPOKB(to, *from);
293       to++; from++;
294    }
295    FARPOKB(to, 0);
296 }
297 
298 void
fstrncpyto(char * to,const char * from,int len)299 fstrncpyto(char *to, const char *from, int len)
300 {
301    while (*from && len) {
302       FARPOKB(to, *from);
303       to++; from++; len--;
304    }
305    FARPOKB(to, 0);
306 }
307 
308 void
fstrcpyfrom(char * to,const char * from)309 fstrcpyfrom(char *to, const char *from)
310 {
311    while (FARPKB(from)) {
312       *to = FARPKB(from);
313       from++; to++;
314    }
315    *to = 0;
316 }
317 
318 void
fstrncpyfrom(char * to,const char * from,int len)319 fstrncpyfrom(char *to, const char *from, int len)
320 {
321    while (FARPKB(from) && len) {
322       *to =  FARPKB(from);
323       from++; to++; len--;
324    }
325    *to = 0;
326 }
327 
328 void
GetSocketMap(void)329 GetSocketMap(void)
330 {
331    RTQ_NODE *n = MGenGetNode(SOCKET_MAP_QUEUE);
332 
333    SockMap = (SocketMap *) FARPKL(&n->rtqDatum);
334 }
335 
336 void *
GetFreeBufferToQueue(int q,int bufSize)337 GetFreeBufferToQueue(int q, int bufSize)
338 {
339    int i;
340 
341    for (i = 0; i < NFREEQ; i++) {
342       if (Qsizes[i] >= bufSize && MGenGetQueueCtr(i+FREEQBASE)) {
343          RTQ_NODE *n = MGenMoveTo(i+FREEQBASE, q);
344          if (!n)
345             continue;
346          FARPOKL(&n->rtqUpCtr, bufSize);
347          return (void *) FARPKL(&n->rtqDatum);
348       }
349    }
350 
351    return 0;
352 }
353 
354 void
FreeBufferFromQueue(int q)355 FreeBufferFromQueue(int q)
356 {
357    int i;
358    RTQ_NODE *n = MGenGetNode(q);
359 
360    for (i = 0; i < NFREEQ; i++) {
361       if (Qsizes[i] == FARPKS(&n->rtqLen)) {
362          MGenMoveTo(q, i+FREEQBASE);
363          return;
364       }
365    }
366 }
367 
368 void
SetLPCData(LPCData * lpc)369 SetLPCData(LPCData *lpc)
370 {
371 
372    FARPOKL(&(lpc->version), 1);
373    FARPOKL(&(lpc->sizeOfArgs), 0);
374    FARPOKL(&(lpc->service), 0);
375 }
376 
377 int
bind(SOCKET s,const struct sockaddr * name,int namelen)378 bind(SOCKET s, const struct sockaddr *name, int namelen)
379 {
380    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
381    LPCData  *p;
382    LPCReturn *r;
383    BindArgs  *bargs;
384    int       retVal;
385 
386    _farsetsel(flat_selector);
387    SocketError = 0;
388    p = (LPCData *) FARPKL(&n->rtqDatum);
389    SetLPCData(p);
390    FARPOKL(&p->service, LPC_SOCKBIND);
391    bargs = (BindArgs *) p->Data;
392    FARPOKL(&bargs->s, s);
393    FARPOKL(&bargs->namelen, namelen);
394    fmemcpyto(bargs->name, name, namelen);
395    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
396    PostWindowsMessage();
397 
398    while ((n = MGenGetNode(REC_QUEUE)) == 0)
399       Yield();
400 
401    r = (LPCReturn *) FARPKL(&n->rtqDatum);
402 
403    if (FARPKS(&r->error) != LPC_NOERROR) {
404       return -1;
405    }
406 
407    retVal = FARPKL(r->Data);
408 
409    // get ready for next call
410    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
411 
412    return retVal;
413 }
414 
415 int
closesocket(SOCKET s)416 closesocket(SOCKET s)
417 {
418    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
419    LPCData  *p;
420    LPCReturn *r;
421    int       retVal;
422 
423    _farsetsel(flat_selector);
424    SocketError = 0;
425    p = (LPCData *) FARPKL(&n->rtqDatum);
426    SetLPCData(p);
427    FARPOKL(&p->service, LPC_SOCKCLOSE);
428    FARPOKL(p->Data, s);
429 
430    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
431    PostWindowsMessage();
432 
433    while ((n = MGenGetNode(REC_QUEUE)) == 0)
434       Yield();
435 
436    r = (LPCReturn *) FARPKL(&n->rtqDatum);
437 
438    if (FARPKS(&r->error) != LPC_NOERROR) {
439       return -1;
440    }
441 
442    retVal = FARPKL(r->Data);
443 
444    // get ready for next call
445    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
446 
447    return retVal;
448 }
449 
450 void
ZapHostEnt()451 ZapHostEnt()
452 {
453    // do nothing
454 }
455 
456 void
ReconstructHostEnt(struct hostent * s,void * flattened)457 ReconstructHostEnt(struct hostent *s, void *flattened)
458 {
459    struct hostent   *old = (struct hostent *) flattened;
460    int i;
461    char **ptr;
462 
463 
464    s->h_name = HostEnt_hname;
465    fstrncpyfrom(s->h_name, (char *) FARPKL(&old->h_name), HOSTENT_STRLEN_LIMIT-1);
466    s->h_name[HOSTENT_STRLEN_LIMIT-1] = 0;
467 
468    s->h_aliases = HostEnt_h_aliases;
469    ptr = (char **) FARPKL(&old->h_aliases);
470    for (i = 0; i < (HOSTENT_ALIAS_LIMIT-1) && FARPKL(ptr); i++, ptr++) {
471       s->h_aliases[i] = HostEnt_names[i];
472       // fstrncpyfrom(s->h_aliases[i], (void *) FARPKL(ptr), HOSTENT_STRLEN_LIMIT-1);
473       s->h_aliases[i][HOSTENT_STRLEN_LIMIT-1] = 0;
474    }
475    s->h_aliases[i] = 0;
476 
477    s->h_addrtype = FARPKS(&old->h_addrtype);
478    s->h_length = FARPKS(&old->h_length);
479 
480    if (FARPKS(&old->h_length) != sizeof(struct in_addr)) {
481       printf("Error!\n");
482       exit(0);
483    }
484 
485    s->h_addr_list = (char **) HostEnt_addr_list;
486    ptr = (char **) FARPKL(&old->h_addr_list);
487    for (i = 0; i < (HOSTENT_ADDR_LIST_LIMIT - 1) && FARPKL(ptr); i++, ptr++) {
488       s->h_addr_list[i] = (char *) &(HostEnt_addrs[i]);
489       fmemcpyfrom(s->h_addr_list[i], (void *) FARPKL(ptr), s->h_length);
490    }
491    s->h_addr_list[i] = 0;
492 }
493 
494 
495 int
getsockname(SOCKET s,struct sockaddr * name,int * namelen)496 getsockname(SOCKET s, struct sockaddr *name, int *namelen)
497 {
498    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
499    LPCData  *p;
500    LPCReturn *r;
501    GetSockNameRet  *ret;
502    int       retVal;
503 
504    SocketError = 0;
505    _farsetsel(flat_selector);
506    p = (LPCData *) FARPKL(&n->rtqDatum);
507    SetLPCData(p);
508    FARPOKL(&p->service, LPC_SOCKGETSOCKNAME);
509    FARPOKL(p->Data, s);
510 
511    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
512    PostWindowsMessage();
513 
514    while ((n = MGenGetNode(REC_QUEUE)) == 0)
515       Yield();
516 
517 
518    r = (LPCReturn *) FARPKL(&n->rtqDatum);
519 
520    if (FARPKS(&r->error) != LPC_NOERROR) {
521       return -1;
522    }
523 
524    ret = (GetSockNameRet *) r->Data;
525    retVal = FARPKL(&ret->retVal);
526    fmemcpyfrom(name, ret->name, FARPKL(&ret->namelen));
527    *namelen = FARPKL(&ret->namelen);
528 
529    // get ready for next call
530    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
531 
532    return retVal;
533 }
534 
535 int
gethostname(char * name,int namelen)536 gethostname(char *name, int namelen)
537 {
538    RTQ_NODE *n;
539    LPCData  *p;
540    LPCReturn *r;
541    GetHostNameRet  *ret;
542    int       retVal;
543    char  *s;
544 
545    _farsetsel(flat_selector);
546    SocketError = 0;
547    n = (RTQ_NODE *) MGenGetNode(IDLE_QUEUE);
548    p = (LPCData *) FARPKL(&n->rtqDatum);
549    SetLPCData(p);
550    FARPOKL(&p->service,LPC_SOCKGETHOSTNAME);
551    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
552    PostWindowsMessage();
553 
554    while ((n = (RTQ_NODE *) (MGenGetNode(REC_QUEUE))) == 0)
555       Yield();
556 
557    r = (LPCReturn *) FARPKL(&n->rtqDatum);
558 
559    if (FARPKS(&r->error) != LPC_NOERROR) {
560       return -1;
561    }
562 
563    ret = (GetHostNameRet *) r->Data;
564 
565    retVal = FARPKL(&ret->retVal);
566 
567    s = ret->name;
568 
569    fstrncpyfrom(name, s, namelen);
570 
571 #if 0
572    len = strlen(ret->name);
573 
574    if (len > namelen)
575       memcpy(name, ret->name, ret->namelen);
576    else
577       strcpy(name, ret->name);
578 #endif
579 
580    // get ready for next call
581    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
582 
583    return retVal;
584 }
585 
586 struct hostent *
gethostbyname(const char * name)587 gethostbyname(const char *name)
588 {
589    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
590    LPCData  *p;
591    LPCReturn *r;
592    struct hostent *retVal;
593 
594    _farsetsel(flat_selector);
595    SocketError = 0;
596    p = (LPCData *) FARPKL(&n->rtqDatum);
597    SetLPCData(p);
598    FARPOKL(&p->service, LPC_SOCKGETHOSTBYNAME);
599    fstrcpyto(p->Data, name);
600 
601    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
602    PostWindowsMessage();
603 
604    while ((n = MGenGetNode(REC_QUEUE)) == 0)
605       Yield();
606 
607    r = (LPCReturn *) FARPKL(&n->rtqDatum);
608    retVal = (struct hostent *) r->Data;
609 
610    if (FARPKL(&retVal->h_name) == 0) {
611       retVal = 0;
612    } else {
613       ZapHostEnt();
614       ReconstructHostEnt(&HostEnt, (void *) retVal);
615       retVal = &HostEnt;
616    }
617 
618    // get ready for next call
619    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
620 
621    return retVal;
622 }
623 
624 struct hostent *
gethostbyaddr(const char * addr,int len,int type)625 gethostbyaddr(const char *addr, int len, int type)
626 {
627    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
628    LPCData  *p;
629    LPCReturn *r;
630    GetHostByAddrArgs *args;
631    struct hostent *retVal;
632 
633    SocketError = 0;
634    _farsetsel(flat_selector);
635    p = (LPCData *) FARPKL(&n->rtqDatum);
636    SetLPCData(p);
637    FARPOKL(&p->service, LPC_SOCKGETHOSTBYADDR);
638    args = (GetHostByAddrArgs *) p->Data;
639    FARPOKL(&args->len, len);
640    FARPOKL(&args->type, type);
641    fmemcpyto(args->addr, addr, len);
642 
643    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
644    PostWindowsMessage();
645 
646    while ((n = MGenGetNode(REC_QUEUE)) == 0)
647       Yield();
648    r = (LPCReturn *) FARPKL(&n->rtqDatum);
649    retVal = (struct hostent *) r->Data;
650 
651    if (FARPKL(&retVal->h_name) == 0) {
652       retVal = 0;
653    } else {
654       ZapHostEnt();
655 
656       ReconstructHostEnt(&HostEnt, (void *) retVal);
657       retVal = &HostEnt;
658    }
659 
660    // get ready for next call
661    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
662 
663    return retVal;
664 }
665 
666 
667 SOCKET
socket(int af,int type,int protocol)668 socket(int af, int type, int protocol)
669 {
670    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
671    LPCData  *p;
672    LPCReturn *r;
673    SocketArgs  *args;
674    int       retVal;
675 
676    _farsetsel(flat_selector);
677    SocketError = 0;
678    p = (LPCData *) FARPKL(&n->rtqDatum);
679    SetLPCData(p);
680    FARPOKL(&p->service, LPC_SOCKSOCKET);
681    args = (SocketArgs *) p->Data;
682    FARPOKL(&args->af, af);
683    FARPOKL(&args->type, type);
684    FARPOKL(&args->protocol, protocol);
685 
686    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
687    PostWindowsMessage();
688 
689    while ((n = MGenGetNode(REC_QUEUE)) == 0)
690       Yield();
691 
692    r = (LPCReturn *) FARPKL(&n->rtqDatum);
693 
694 
695    if (FARPKS(&r->error) != LPC_NOERROR) {
696       return -1;
697    }
698 
699    retVal = FARPKL(r->Data);
700 
701    // get ready for next call
702    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
703 
704    return retVal;
705 }
706 
707 void
sockets_flush(void)708 sockets_flush(void)
709 {
710    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
711    LPCData  *p;
712 
713    SocketError = 0;
714    p = (LPCData *) FARPKL(&n->rtqDatum);
715    SetLPCData(p);
716    FARPOKL(&p->service, LPC_SOCKFLUSH);
717 
718    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
719    PostWindowsMessage();
720 
721    while ((n = MGenGetNode(REC_QUEUE)) == 0)
722       Yield();
723 
724    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
725 }
726 
727 int
recvfrom(SOCKET s,char * buf,int len,int flags,struct sockaddr * from,int * fromlen)728 recvfrom(SOCKET s, char *buf, int len, int flags, struct sockaddr *from,
729          int *fromlen)
730 {
731    int i;
732    RTQ_NODE *n;
733    WinSockData  *data;
734    int  bytesRead;
735 
736    SocketError = 0;
737    _farsetsel(flat_selector);
738    if (!SockMap)
739       GetSocketMap();
740 
741    for (i = 0; i < MAXSOCKETS; i++) {
742       if (FARPKL(&(SockMap->sock[i])) == s)
743          break;
744    }
745 
746    if (i == MAXSOCKETS)
747       return SOCKET_ERROR;
748 
749    // pick up node
750    n = MGenGetNode(i);
751    if (n == 0) {
752       SocketError = WSAEWOULDBLOCK;
753       return -1;
754    }
755 
756    data = (WinSockData *) FARPKL(&n->rtqDatum);
757    bytesRead = FARPKL(&data->len);
758 
759    if (from) {
760       fmemcpyfrom(from, &data->addr, sizeof(struct sockaddr));
761    }
762 
763    if (fromlen) {
764       *fromlen = FARPKL(&data->addrlen);
765    }
766 
767    fmemcpyfrom(buf, data->data, len > bytesRead ? bytesRead : len);
768 
769    if ((flags & MSG_PEEK) == 0) {
770       FreeBufferFromQueue(i);
771    }
772 
773    return bytesRead;
774 }
775 
776 int
sendto(SOCKET s,const char * buf,int len,int flags,const struct sockaddr * to,int tolen)777 sendto(SOCKET s, const char *buf, int len, int flags, const struct sockaddr *to, int tolen)
778 {
779    int i;
780    int outQ;
781    WinSockData *data;
782 
783    SocketError = 0;
784    _farsetsel(flat_selector);
785    if (!SockMap)
786       GetSocketMap();
787 
788    for (i = 0; i < MAXSOCKETS; i++) {
789       if (FARPKL(&SockMap->sock[i]) == s) {
790          break;
791       }
792    }
793 
794    if (i == MAXSOCKETS) {
795       SocketError = WSAENOTSOCK;
796       return SOCKET_ERROR;
797    }
798 
799    outQ = i + MAXSOCKETS;
800 
801    if (MGenGetQueueCtr(outQ) >= QLIMIT) {
802       SocketError = WSAEWOULDBLOCK;
803       return SOCKET_ERROR;
804    }
805 
806    data = GetFreeBufferToQueue(PRIVATEQ, len + sizeof(WinSockData));
807 
808    if (!data) {
809       SocketError = WSAEWOULDBLOCK;
810       return SOCKET_ERROR;
811    }
812 
813    FARPOKL(&data->s, s);
814    FARPOKL(&data->len, len);
815    if (to) {
816       fmemcpyto(&data->addr, to, tolen);
817       FARPOKL(&data->addrlen, tolen);
818    } else {
819       FARPOKL(&data->addrlen, 0);
820    }
821 
822    FARPOKL(&data->flags, flags);
823 
824    fmemcpyto(data->data, buf, len);
825 
826    MGenMoveTo(PRIVATEQ, outQ);
827 
828    return len;
829 }
830 
831 int
ioctlsocket(SOCKET s,long cmd,unsigned long * argp)832 ioctlsocket(SOCKET s, long cmd, unsigned long *argp)
833 {
834    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
835    LPCData  *p;
836    LPCReturn *r;
837    IoctlArgs  *args;
838    int       retVal;
839 
840    SocketError = 0;
841    _farsetsel(flat_selector);
842    p = (LPCData *) FARPKL(&n->rtqDatum);
843    SetLPCData(p);
844    FARPOKL(&p->service, LPC_SOCKIOCTL);
845    args = (IoctlArgs *) p->Data;
846    FARPOKL(&args->s, s);
847    FARPOKL(&args->cmd, cmd);
848 
849    switch(cmd) {
850    case FIONBIO:
851       FARPOKL(args->data, *argp);
852       break;
853    default:
854       return SOCKET_ERROR;
855    }
856 
857    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
858    PostWindowsMessage();
859 
860    while ((n = MGenGetNode(REC_QUEUE)) == 0)
861       Yield();
862 
863    r = (LPCReturn *) FARPKL(&n->rtqDatum);
864 
865 
866    retVal = FARPKL(r->Data);
867 
868    // get ready for next call
869    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
870 
871    return retVal;
872 }
873 
874 int
setsockopt(SOCKET s,int level,int optname,const char * optval,int optlen)875 setsockopt(SOCKET s, int level, int optname, const char *optval, int optlen)
876 {
877    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
878    LPCData  *p;
879    LPCReturn *r;
880    SetSockOptArgs  *args;
881    int       retVal;
882 
883    SocketError = 0;
884    _farsetsel(flat_selector);
885    p = (LPCData *) FARPKL(&n->rtqDatum);
886    SetLPCData(p);
887    FARPOKL(&p->service, LPC_SOCKSETOPT);
888    args = (SetSockOptArgs *) p->Data;
889    FARPOKL(&args->s, s);
890    FARPOKL(&args->level, level);
891    FARPOKL(&args->optname, optname);
892    FARPOKL(&args->optlen, optlen);
893    fmemcpyto(args->optval, optval, optlen);
894 
895    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
896    PostWindowsMessage();
897 
898    while ((n = MGenGetNode(REC_QUEUE)) == 0)
899       Yield();
900 
901    r = (LPCReturn *) FARPKL(&n->rtqDatum);
902 
903    retVal = FARPKL(r->Data);
904 
905    // get ready for next call
906    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
907 
908    return retVal;
909 }
910 
911 int
WSAGetLastError(void)912 WSAGetLastError(void)
913 {
914    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
915    LPCData  *p;
916    LPCReturn *r;
917    int       retVal;
918 
919 
920    _farsetsel(flat_selector);
921    if (SocketError) {
922       int err = SocketError;
923 
924       SocketError = 0;
925       return err;
926    }
927 
928    p = (LPCData *) FARPKL(&n->rtqDatum);
929    SetLPCData(p);
930    FARPOKL(&p->service, LPC_SOCKGETLASTERROR);
931 
932    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
933    PostWindowsMessage();
934 
935    while ((n = MGenGetNode(REC_QUEUE)) == 0)
936       Yield();
937 
938    r = (LPCReturn *) FARPKL(&n->rtqDatum);
939 
940 
941    retVal = FARPKL(r->Data);
942 
943    // get ready for next call
944    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
945 
946    return retVal;
947 }
948 
inet_addr(const char * cp)949 unsigned long inet_addr(const char *cp)
950 {
951 	int ret;
952 	unsigned int ha1, ha2, ha3, ha4;
953 	unsigned long ipaddr;
954 
955 	ret = sscanf(cp, "%d.%d.%d.%d", &ha1, &ha2, &ha3, &ha4);
956 	if (ret != 4)
957 		return -1;
958 	ipaddr = (ha1 << 24) | (ha2 << 16) | (ha3 << 8) | ha4;
959 	return ipaddr;
960 #if 0
961    RTQ_NODE *n = MGenGetNode(IDLE_QUEUE);
962    LPCData  *p;
963    LPCReturn *r;
964    int       retVal;
965 
966    SocketError = 0;
967    _farsetsel(flat_selector);
968    p = (LPCData *) FARPKL(&n->rtqDatum);
969    SetLPCData(p);
970    FARPOKL(&p->service, LPC_SOCKINETADDR);
971 
972    fstrcpyto(p->Data, cp);
973 
974    MGenMoveTo(IDLE_QUEUE, SEND_QUEUE);
975    PostWindowsMessage();
976 
977    while ((n = MGenGetNode(REC_QUEUE)) == 0)
978       Yield();
979 
980    r = (LPCReturn *) FARPKL(&n->rtqDatum);
981 
982    if (FARPKS(&r->error) != LPC_NOERROR) {
983       return -1;
984    }
985 
986    retVal = FARPKL(r->Data);
987 
988    // get ready for next call
989    MGenMoveTo(REC_QUEUE, IDLE_QUEUE);
990 
991    return retVal;
992  #endif
993 }
994 
inet_ntoa(struct in_addr in)995 char *inet_ntoa (struct in_addr in)
996 {
997 	static char buf [32];
998 
999 	sprintf(buf, "%u.%u.%u.%u", in.S_un.S_un_b.s_b1, in.S_un.S_un_b.s_b2, in.S_un.S_un_b.s_b3, in.S_un.S_un_b.s_b4);
1000 	return buf;
1001 }
1002