Ignore:
Timestamp:
Mar 24, 2000, 8:28:12 PM (25 years ago)
Author:
sandervl
Message:

replaced with new wsock32

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/wsock32/wsock32.cpp

    r3199 r3229  
    1 /* $Id: wsock32.cpp,v 1.23 2000-03-22 20:07:28 sandervl Exp $ */
     1/* $Id: wsock32.cpp,v 1.24 2000-03-24 19:28:09 sandervl Exp $ */
    22
    33/*
     
    88 *
    99 * Copyright (C) 1999 Patrick Haller <phaller@gmx.net>
     10 * Copyright (C) 2000 Sander van Leeuwen (sandervl@xs4all.nl)
     11 *
     12 * Some parts based on Wine code: (dlls\winsock\socket.c)
     13 * (C) 1993,1994,1996,1997 John Brezak, Erik Bos, Alex Korobka.
    1014 *
    1115 */
     
    1721 *            -> open issue: WSASetLastError / WSAGetLastError
    1822 *               call SetLastError / GetLastError according to docs
     23 *
     24 * 2000/22/03 Complete rewrite -> got rid of pmwsock
    1925 *
    2026 * identical structures:
     
    3844 *****************************************************************************/
    3945
    40 #include <pmwsock.h>
    41 #include <odin.h>
     46#define INCL_BASE
     47#include <os2wrap.h>    //Odin32 OS/2 api wrappers
     48
     49#include <string.h>
    4250#include <odinwrap.h>
    4351#include <os2sel.h>
    44 #include <misc.h>
    45 #include <wprocess.h>
    46 #include <heapstring.h>
    47 #include <win32wnd.h>
    4852#include <stdlib.h>
    4953#include <win32api.h>
     54#include <win32wnd.h>
     55#include <wprocess.h>
     56#include <misc.h>
    5057
    5158#include "wsock32.h"
    52 #include "relaywin.h"
     59#include "wsastruct.h"
     60#include "asyncthread.h"
     61
    5362#define DBG_LOCALLOG    DBG_wsock32
    5463#include "dbglocal.h"
     
    6271 *****************************************************************************/
    6372
    64 #define ERROR_SUCCESS 0
    65 
    66 
    67 static WSOCKTHREADDATA wstdFallthru; // for emergency only
    68 
    69 static HWND hwndRelay = NULL; // handle to our relay window
    70 
    71 BOOL fWSAInitialized = FALSE;
    72 
    73 /*****************************************************************************
    74  * Prototypes                                                                *
    75  *****************************************************************************/
    76 
    77 /*****************************************************************************
    78  * Name      :
    79  * Purpose   :
    80  * Parameters:
    81  * Variables :
    82  * Result    :
    83  * Remark    : free memory when thread dies
    84  * Status    : UNTESTED STUB
    85  *
    86  * Author    : Patrick Haller [Tue, 1998/06/16 23:00]
    87  *****************************************************************************/
    88 
    89 PWSOCKTHREADDATA iQueryWsockThreadData(void)
    90 {
    91   struct _THDB*     pThreadDB = (struct _THDB*)GetThreadTHDB();
    92   PWSOCKTHREADDATA pwstd;
    93 
    94   // check for existing pointer
    95   if (pThreadDB != NULL)
    96   {
    97     if (pThreadDB->pWsockData == NULL)
    98     {
    99       // allocate on demand + initialize
    100       pwstd = (PWSOCKTHREADDATA)HEAP_malloc (sizeof(WSOCKTHREADDATA));
    101       pThreadDB->pWsockData = (LPVOID)pwstd;
     73static LPWSINFO lpFirstIData = NULL;
     74
     75//******************************************************************************
     76//******************************************************************************
     77LPWSINFO WINSOCK_GetIData(HANDLE tid)
     78{
     79    LPWSINFO iData;
     80    BOOL     fCurrentThread = FALSE;
     81
     82    if(tid == CURRENT_THREAD) {
     83        tid = GetCurrentThread();
     84        fCurrentThread = TRUE;
    10285    }
    103     else
    104       // use already allocated memory
    105       pwstd = (PWSOCKTHREADDATA)pThreadDB->pWsockData;
    106   }
    107 
    108   if (pwstd == NULL)
    109     pwstd = &wstdFallthru; // no memory and not allocated already
    110 
    111   return pwstd;
    112 }
    113 
    114 
    115 #if 0
    116 /*****************************************************************************
    117  * Name      :
    118  * Purpose   :
    119  * Parameters:
    120  * Variables :
    121  * Result    :
    122  * Remark    :
    123  * Status    : UNTESTED STUB
    124  *
    125  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    126  *****************************************************************************/
    127 
    128 #define CASEERR2(a) case SOC##a: case a: return WSA##a;
    129 #define CASEERR1(a) case SOC##a: return WSA##a;
    130 
    131 int iTranslateSockErrToWSock(int iError)
    132 {
    133   switch(iError)
    134   {
    135     CASEERR2(EINTR)
    136     CASEERR2(EBADF)
    137     CASEERR2(EACCES)
    138     CASEERR2(EINVAL)
    139     CASEERR2(EMFILE)
    140 
    141     CASEERR1(EWOULDBLOCK)
    142     CASEERR1(EINPROGRESS)
    143     CASEERR1(EALREADY)
    144     CASEERR1(ENOTSOCK)
    145 //  CASEERR1(EDESTADRREQ)
    146     CASEERR1(EMSGSIZE)
    147     CASEERR1(EPROTOTYPE)
    148     CASEERR1(ENOPROTOOPT)
    149     CASEERR1(EPROTONOSUPPORT)
    150     CASEERR1(ESOCKTNOSUPPORT)
    151     CASEERR1(EOPNOTSUPP)
    152     CASEERR1(EPFNOSUPPORT)
    153     CASEERR1(EAFNOSUPPORT)
    154     CASEERR1(EADDRINUSE)
    155     CASEERR1(EADDRNOTAVAIL)
    156     CASEERR1(ENETDOWN)
    157     CASEERR1(ENETUNREACH)
    158     CASEERR1(ENETRESET)
    159     CASEERR1(ECONNABORTED)
    160     CASEERR1(ECONNRESET)
    161     CASEERR1(ENOBUFS)
    162     CASEERR1(EISCONN)
    163     CASEERR1(ENOTCONN)
    164     CASEERR1(ESHUTDOWN)
    165     CASEERR1(ETOOMANYREFS)
    166     CASEERR1(ETIMEDOUT)
    167     CASEERR1(ECONNREFUSED)
    168     CASEERR1(ELOOP)
    169     CASEERR1(ENAMETOOLONG)
    170     CASEERR1(EHOSTDOWN)
    171     CASEERR1(EHOSTUNREACH)
    172 
    173     CASEERR1(ENOTEMPTY)
    174 //    CASEERR(EPROCLIM)
    175 //    CASEERR(EUSERS)
    176 //    CASEERR(EDQUOT)
    177 //    CASEERR(ESTALE)
    178 //    CASEERR(EREMOTE)
    179 //    CASEERR(EDISCON)
    180 
    181 
    182     default:
    183       dprintf(("WSOCK32: Unknown error condition: %d\n",
    184                iError));
    185       return iError;
    186   }
    187 }
    188 
    189 #endif
    190 
    191 
    192 
    193 
    194 
    195 
    196 
    197 /*****************************************************************************
    198  * Name      :
    199  * Purpose   :
    200  * Parameters:
    201  * Variables :
    202  * Result    :
    203  * Remark    :
    204  * Status    : UNTESTED STUB
    205  *
    206  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    207  *****************************************************************************/
    208 
    209 
    210 ODINPROCEDURE1(OS2WSASetLastError,
    211                int,iError)
     86tryagain:
     87    for (iData = lpFirstIData; iData; iData = iData->lpNextIData) {
     88        if (iData->dwThisThread == tid)
     89            break;
     90    }
     91    if(iData == NULL && fCurrentThread) {
     92        WINSOCK_CreateIData();
     93        fCurrentThread = FALSE; //just to prevent infinite loops
     94        goto tryagain;
     95    }
     96    if(iData == NULL) {
     97        dprintf(("WINSOCK_GetIData: couldn't find struct for thread %x", tid));
     98        DebugInt3();// should never happen!!!!!!!
     99    }
     100    return iData;
     101}
     102//******************************************************************************
     103//******************************************************************************
     104BOOL WINSOCK_CreateIData(void)
     105{
     106    LPWSINFO iData;
     107   
     108    iData = (LPWSINFO)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(WSINFO));
     109    if (!iData)
     110        return FALSE;
     111    iData->dwThisThread = GetCurrentThread();
     112    iData->lpNextIData = lpFirstIData;
     113    lpFirstIData = iData;
     114    return TRUE;
     115}
     116//******************************************************************************
     117//******************************************************************************
     118void WINSOCK_DeleteIData(void)
     119{
     120    LPWSINFO ppid, iData;
     121
     122    if (iData) {
     123        ppid = lpFirstIData;
     124        while(ppid)
     125        {
     126                iData = ppid;
     127                ppid  = ppid->lpNextIData;
     128
     129                if( iData->flags & WSI_BLOCKINGCALL )
     130                        dprintf(("\tinside blocking call!\n"));
     131
     132                /* delete scratch buffers */
     133
     134                if(iData->he)   free(iData->he);
     135                if(iData->se)   free(iData->se);
     136                if(iData->pe)   free(iData->pe);
     137
     138        ////    if( iData->buffer ) SEGPTR_FREE(iData->buffer);
     139        ////    if( iData->dbuffer ) SEGPTR_FREE(iData->dbuffer);
     140
     141                HeapFree(GetProcessHeap(), 0, iData);
     142        }
     143    }
     144}
     145//******************************************************************************
     146//******************************************************************************
     147void WIN32API WSASetLastError(int iError)
    212148{
    213149  // according to the docs, WSASetLastError() is just a call-through
    214150  // to SetLastError()
    215   WSASetLastError(iError);
     151  if(iError) {
     152        dprintf(("WSASetLastError %x", iError));
     153  }
    216154  SetLastError(iError);
    217155}
    218 
    219 
    220 /*****************************************************************************
    221  * Name      :
    222  * Purpose   :
    223  * Parameters:
    224  * Variables :
    225  * Result    :
    226  * Remark    :
    227  * Status    : UNTESTED STUB
    228  *
    229  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    230  *****************************************************************************/
    231 
    232 ODINFUNCTION0(int,OS2WSAGetLastError)
    233 {
    234   // according to the docs, WSASetLastError() is just a call-through
    235   // to SetLastError(). However, what can be implemented here?
    236   return WSAGetLastError();
    237 }
    238 
    239 
    240 /*****************************************************************************
    241  * Name      :
    242  * Purpose   :
    243  * Parameters:
    244  * Variables :
    245  * Result    :
    246  * Remark    :
    247  * Status    : UNTESTED STUB
    248  *
    249  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    250  *****************************************************************************/
    251 
    252 ODINFUNCTION2(int,OS2__WSAFDIsSet,SOCKET, s,
    253                                   fd_set*,fds)
    254 {
    255   return (__WSAFDIsSet(s,fds));
    256 }
    257 
    258 
    259 /*****************************************************************************
    260  * Name      :
    261  * Purpose   :
    262  * Parameters:
    263  * Variables :
    264  * Result    :
    265  * Remark    :
    266  * Status    : UNTESTED STUB
    267  *
    268  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    269  *****************************************************************************/
    270 
     156//******************************************************************************
     157//******************************************************************************
     158int WIN32API WSAGetLastError()
     159{
     160  return GetLastError();
     161}
     162//******************************************************************************
     163//******************************************************************************
     164ODINFUNCTION2(int,OS2shutdown,
     165              SOCKET,s,
     166              int,how)
     167{
     168 int ret;
     169
     170   if(!fWSAInitialized) {
     171        WSASetLastError(WSANOTINITIALISED);
     172        return SOCKET_ERROR;
     173   }
     174   else
     175   if(WSAIsBlocking()) {
     176        WSASetLastError(WSAEINPROGRESS);
     177        return SOCKET_ERROR;
     178   }
     179   ret = shutdown(s, how);
     180   
     181   if(ret == SOCKET_ERROR) {
     182        WSASetLastError(wsaErrno());
     183   }
     184   else WSASetLastError(NO_ERROR);
     185   return ret;
     186}
     187//******************************************************************************
     188//******************************************************************************
     189ODINFUNCTION3(SOCKET,OS2socket,
     190              int,af,
     191              int,type,
     192              int,protocol)
     193{
     194 SOCKET s;
     195
     196   if(!fWSAInitialized) {
     197        WSASetLastError(WSANOTINITIALISED);
     198        return SOCKET_ERROR;
     199   }
     200   else
     201   if(WSAIsBlocking()) {
     202        WSASetLastError(WSAEINPROGRESS);
     203        return SOCKET_ERROR;
     204   }
     205   s = socket(af, type, protocol);
     206   
     207   if(s == SOCKET_ERROR && sock_errno() == SOCEPFNOSUPPORT) {
     208        //map SOCEPFNOSUPPORT to SOCEPFNOSUPPORT
     209        WSASetLastError(SOCEPFNOSUPPORT);
     210   }
     211   else
     212   if(s == SOCKET_ERROR) {
     213        WSASetLastError(wsaErrno());
     214   }
     215   else WSASetLastError(NO_ERROR);
     216   return s;
     217}
     218//******************************************************************************
     219//******************************************************************************
     220ODINFUNCTION1(int,OS2closesocket,SOCKET, s)
     221{
     222 int ret;
     223
     224   if(!fWSAInitialized) {
     225        WSASetLastError(WSANOTINITIALISED);
     226        return SOCKET_ERROR;
     227   }
     228   else
     229   if(WSAIsBlocking()) {
     230        WSASetLastError(WSAEINPROGRESS);
     231        return SOCKET_ERROR;
     232   }
     233   ret = soclose(s);
     234   //Close WSAAsyncSelect thread if one was created for this socket
     235   FindAndSetAsyncEvent(s, 0, 0, 0);
     236 
     237   if(ret == SOCKET_ERROR) {
     238        WSASetLastError(wsaErrno());
     239   }
     240   else WSASetLastError(NO_ERROR);
     241   return ret;
     242}
     243//******************************************************************************
     244//******************************************************************************
     245ODINFUNCTION3(int,OS2connect,
     246              SOCKET, s,
     247              const struct sockaddr *,name,
     248              int, namelen)
     249{
     250 int ret;
     251
     252   if(!fWSAInitialized) {
     253        WSASetLastError(WSANOTINITIALISED);
     254        return SOCKET_ERROR;
     255   }
     256   else
     257   if(WSAIsBlocking()) {
     258        WSASetLastError(WSAEINPROGRESS);
     259        return SOCKET_ERROR;
     260   }
     261   ret = connect(s, (sockaddr *)name, namelen);
     262   // map BSD error codes
     263   if(ret == SOCKET_ERROR) {
     264        if(sock_errno() == SOCEINPROGRESS) {
     265                WSASetLastError(WSAEWOULDBLOCK);
     266        }
     267        else
     268        if (sock_errno() == SOCEOPNOTSUPP) {
     269                WSASetLastError(WSAEINVAL);
     270        }
     271        else    WSASetLastError(wsaErrno());
     272   }
     273   else WSASetLastError(NO_ERROR);
     274   return ret;
     275}
     276//******************************************************************************
     277//******************************************************************************
     278ODINFUNCTION3(int,OS2ioctlsocket,
     279              SOCKET,s,
     280              long, cmd,
     281              u_long *,argp)
     282{
     283 int ret;
     284
     285   if(!fWSAInitialized) {
     286        WSASetLastError(WSANOTINITIALISED);
     287        return SOCKET_ERROR;
     288   }
     289   else
     290   if(WSAIsBlocking()) {
     291        WSASetLastError(WSAEINPROGRESS);
     292        return SOCKET_ERROR;
     293   }
     294   // clear high word (not used in OS/2's tcpip stack)
     295   cmd = LOUSHORT(cmd);
     296
     297   if(cmd != FIONBIO && cmd != FIONREAD && cmd != SIOCATMARK) {
     298        WSASetLastError(WSAEINVAL);
     299        return SOCKET_ERROR;
     300   }
     301
     302   WSASetLastError(NO_ERROR);
     303
     304   //check if app want to set a socket, which has an outstanding async select,
     305   //to blocking mode
     306   if (cmd == FIONBIO) {
     307        HWND  hwnd;
     308        int   msg;
     309        ULONG lEvent;
     310
     311        if(QueryAsyncEvent(s, &hwnd, &msg, &lEvent) == TRUE) {
     312                if(*argp != 0) {
     313                        //nothing to do; already non-blocking
     314                        return NO_ERROR;
     315                }
     316                else {
     317                        dprintf(("Trying to set socket to blocking mode while async select active -> return error!"));
     318                        WSASetLastError(WSAEINVAL);
     319                        return SOCKET_ERROR;
     320                }
     321        }
     322   }
     323   ret = ioctl(s, cmd, (char *)argp, sizeof(int));
     324
     325   // Map EOPNOTSUPP to EINVAL
     326   if(ret == SOCKET_ERROR && sock_errno() == SOCEOPNOTSUPP)
     327        WSASetLastError(WSAEINVAL);
     328   else
     329   if(ret == SOCKET_ERROR) {
     330        WSASetLastError(wsaErrno());
     331   }
     332   else WSASetLastError(NO_ERROR);
     333   return ret;
     334}
     335//******************************************************************************
     336//******************************************************************************
     337ODINFUNCTION3(int,OS2getpeername,
     338              SOCKET, s,
     339              struct sockaddr *,name,
     340              int *, namelen)
     341{
     342 int ret;
     343
     344   if(!fWSAInitialized) {
     345        WSASetLastError(WSANOTINITIALISED);
     346        return SOCKET_ERROR;
     347   }
     348   else
     349   if(WSAIsBlocking()) {
     350        WSASetLastError(WSAEINPROGRESS);
     351        return SOCKET_ERROR;
     352   }
     353   else
     354   if (namelen == NULL || *namelen < (int)sizeof(struct sockaddr_in)) {
     355        WSASetLastError(WSAEFAULT);
     356        return SOCKET_ERROR;
     357   }
     358   ret = getsockname(s, name, namelen);
     359   if(ret == SOCKET_ERROR) {
     360        WSASetLastError(wsaErrno());
     361   }
     362   else WSASetLastError(NO_ERROR);
     363   return ret;
     364}
     365//******************************************************************************
     366//******************************************************************************
     367ODINFUNCTION3(int,OS2getsockname,
     368              SOCKET,s,
     369              struct sockaddr *,name,
     370              int *, namelen)
     371{
     372 int ret;
     373
     374   if(!fWSAInitialized) {
     375        WSASetLastError(WSANOTINITIALISED);
     376        return SOCKET_ERROR;
     377   }
     378   else
     379   if(WSAIsBlocking()) {
     380        WSASetLastError(WSAEINPROGRESS);
     381        return SOCKET_ERROR;
     382   }
     383   else
     384   if (namelen == NULL || *namelen < (int)sizeof(struct sockaddr_in)) {
     385        WSASetLastError(WSAEFAULT);
     386        return SOCKET_ERROR;
     387   }
     388   ret = getsockname(s, name, namelen);
     389   if(ret == SOCKET_ERROR) {
     390        WSASetLastError(wsaErrno());
     391   }
     392   else WSASetLastError(NO_ERROR);
     393   return ret;
     394}
     395//******************************************************************************
     396//******************************************************************************
     397ODINFUNCTION1(u_long,OS2htonl,
     398              u_long,hostlong)
     399{
     400  return(htonl(hostlong));
     401}
     402//******************************************************************************
     403//******************************************************************************
     404ODINFUNCTION1(u_short,OS2htons,
     405              u_short,hostshort)
     406{
     407  return(htons(hostshort));
     408}
     409//******************************************************************************
     410//******************************************************************************
     411ODINFUNCTION1(u_long,OS2ntohl,
     412              u_long,netlong)
     413{
     414  return(ntohl(netlong));
     415}
     416//******************************************************************************
     417//******************************************************************************
     418ODINFUNCTION1(u_short,OS2ntohs,
     419              u_short,netshort)
     420{
     421  return(ntohs(netshort));
     422}
     423//******************************************************************************
     424//******************************************************************************
     425ODINFUNCTION1(unsigned long,OS2inet_addr,
     426              const char *, cp)
     427{
     428  dprintf(("WSOCK32: OS2inet_addr(%s)\n",
     429           cp));
     430
     431  return (inet_addr((char *)cp));
     432}
     433//******************************************************************************
     434//******************************************************************************
     435ODINFUNCTION1(char *,OS2inet_ntoa,
     436              struct in_addr, in)
     437{
     438  return(inet_ntoa(in));
     439}
     440//******************************************************************************
     441//******************************************************************************
    271442ODINFUNCTION3(SOCKET,OS2accept, SOCKET,           s,
    272443                                struct sockaddr *,addr,
    273444                                int *,            addrlen)
    274445{
    275   return(accept(s,addr,addrlen));
    276 }
    277 
    278 
    279 /*****************************************************************************
    280  * Name      :
    281  * Purpose   :
    282  * Parameters:
    283  * Variables :
    284  * Result    :
    285  * Remark    :
    286  * Status    : UNTESTED STUB
    287  *
    288  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    289  *****************************************************************************/
    290 
     446 int   ret, msg;
     447 HWND  hwnd;
     448 ULONG lEvent;
     449
     450   if(!fWSAInitialized) {
     451        WSASetLastError(WSANOTINITIALISED);
     452        return SOCKET_ERROR;
     453   }
     454   else
     455   if(WSAIsBlocking()) {
     456        WSASetLastError(WSAEINPROGRESS);
     457        return SOCKET_ERROR;
     458   }
     459   else
     460   if ((addr != NULL) && (addrlen != NULL)) {
     461        if (*addrlen < (int)sizeof(struct sockaddr_in)) {
     462                WSASetLastError(WSAEFAULT);
     463                return SOCKET_ERROR;
     464        }
     465   }
     466   ret = accept(s, addr, addrlen);
     467
     468   if(ret != SOCKET_ERROR) {
     469        //Enable FD_ACCEPT event flag if WSAAsyncSelect was called for this socket
     470        EnableAsyncEvent(s, FD_ACCEPT);
     471
     472        //if this socket has an active async. select pending, then call WSAAsyncSelect
     473        //with the same parameters for the new socket (see docs)
     474        if(QueryAsyncEvent(s, &hwnd, &msg, &lEvent) == TRUE) {
     475                if(WSAAsyncSelect(ret, hwnd, msg, lEvent) == SOCKET_ERROR) {
     476                        ret = SOCKET_ERROR;
     477                }
     478        }
     479   }
     480   if(ret == SOCKET_ERROR) {
     481        WSASetLastError(wsaErrno());
     482   }
     483   else WSASetLastError(NO_ERROR);
     484   return ret;
     485}
     486//******************************************************************************
     487//******************************************************************************
    291488ODINFUNCTION3(int,OS2bind,
    292489              SOCKET ,s,
     
    294491              int, namelen)
    295492{
    296   return(bind(s,addr,namelen));
    297 }
    298 
    299 
    300 /*****************************************************************************
    301  * Name      :
    302  * Purpose   :
    303  * Parameters:
    304  * Variables :
    305  * Result    :
    306  * Remark    :
    307  * Status    : UNTESTED STUB
    308  *
    309  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    310  *****************************************************************************/
    311 
    312 ODINFUNCTION1(int,OS2closesocket,SOCKET, s)
    313 {
    314   return(closesocket(s));
    315 }
    316 
    317 
    318 /*****************************************************************************
    319  * Name      :
    320  * Purpose   :
    321  * Parameters:
    322  * Variables :
    323  * Result    :
    324  * Remark    :
    325  * Status    : UNTESTED STUB
    326  *
    327  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    328  *****************************************************************************/
    329 
    330 ODINFUNCTION3(int,OS2connect,
    331               SOCKET, s,
    332               const struct sockaddr *,name,
    333               int, namelen)
    334 {
    335   return(connect(s,name,namelen));
    336 }
    337 
    338 
    339 /*****************************************************************************
    340  * Name      :
    341  * Purpose   :
    342  * Parameters:
    343  * Variables :
    344  * Result    :
    345  * Remark    :
    346  * Status    : UNTESTED STUB
    347  *
    348  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    349  *****************************************************************************/
    350 
    351 ODINFUNCTION3(int,OS2ioctlsocket,
    352               SOCKET,s,
    353               long, cmd,
    354               u_long *,argp)
    355 {
    356   return(ioctlsocket(s,cmd,argp));
    357 }
    358 
    359 
    360 /*****************************************************************************
    361  * Name      :
    362  * Purpose   :
    363  * Parameters:
    364  * Variables :
    365  * Result    :
    366  * Remark    :
    367  * Status    : UNTESTED STUB
    368  *
    369  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    370  *****************************************************************************/
    371 
    372 ODINFUNCTION3(int,OS2getpeername,
    373               SOCKET, s,
    374               struct sockaddr *,name,
    375               int *, namelen)
    376 {
    377   return(getpeername(s,name,namelen));
    378 }
    379 
    380 
    381 /*****************************************************************************
    382  * Name      :
    383  * Purpose   :
    384  * Parameters:
    385  * Variables :
    386  * Result    :
    387  * Remark    :
    388  * Status    : UNTESTED STUB
    389  *
    390  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    391  *****************************************************************************/
    392 
    393 ODINFUNCTION3(int,OS2getsockname,
    394               SOCKET,s,
    395               struct sockaddr *,name,
    396               int *, namelen)
    397 {
    398   return(getsockname(s,name,namelen));
    399 }
    400 
    401 
    402 /*****************************************************************************
    403  * Name      :
    404  * Purpose   :
    405  * Parameters:
    406  * Variables :
    407  * Result    :
    408  * Remark    :
    409  * Status    : UNTESTED STUB
    410  *
    411  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    412  *****************************************************************************/
    413 
    414 ODINFUNCTION5(int,OS2getsockopt,
    415               SOCKET, s,
    416               int, level,
    417               int, optname,
    418               char *, optval,
    419               int *,optlen)
    420 {
    421   return(getsockopt(s,
    422                     level,
    423                     optname,
    424                     optval,
    425                     optlen));
    426 }
    427 
    428 
    429 /*****************************************************************************
    430  * Name      :
    431  * Purpose   :
    432  * Parameters:
    433  * Variables :
    434  * Result    :
    435  * Remark    :
    436  * Status    : UNTESTED STUB
    437  *
    438  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    439  *****************************************************************************/
    440 
    441 ODINFUNCTION1(u_long,OS2htonl,
    442               u_long,hostlong)
    443 {
    444   return(htonl(hostlong));
    445 }
    446 
    447 
    448 /*****************************************************************************
    449  * Name      :
    450  * Purpose   :
    451  * Parameters:
    452  * Variables :
    453  * Result    :
    454  * Remark    :
    455  * Status    : UNTESTED STUB
    456  *
    457  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    458  *****************************************************************************/
    459 
    460 ODINFUNCTION1(u_short,OS2htons,
    461               u_short,hostshort)
    462 {
    463   return(htons(hostshort));
    464 }
    465 
    466 
    467 /*****************************************************************************
    468  * Name      :
    469  * Purpose   :
    470  * Parameters:
    471  * Variables :
    472  * Result    :
    473  * Remark    :
    474  * Status    : UNTESTED STUB
    475  *
    476  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    477  *****************************************************************************/
    478 
    479 ODINFUNCTION1(unsigned long,OS2inet_addr,
    480               const char *, cp)
    481 {
    482   dprintf(("WSOCK32: OS2inet_addr(%s)\n",
    483            cp));
    484 
    485   return (inet_addr(cp));
    486 }
    487 
    488 
    489 /*****************************************************************************
    490  * Name      :
    491  * Purpose   :
    492  * Parameters:
    493  * Variables :
    494  * Result    :
    495  * Remark    :
    496  * Status    : UNTESTED STUB
    497  *
    498  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    499  *****************************************************************************/
    500 
    501 ODINFUNCTION1(char *,OS2inet_ntoa,
    502               struct in_addr, in)
    503 {
    504   return(inet_ntoa(in));
    505 }
    506 
    507 
    508 /*****************************************************************************
    509  * Name      :
    510  * Purpose   :
    511  * Parameters:
    512  * Variables :
    513  * Result    :
    514  * Remark    :
    515  * Status    : UNTESTED STUB
    516  *
    517  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    518  *****************************************************************************/
    519 
     493 int ret;
     494
     495   if(!fWSAInitialized) {
     496        WSASetLastError(WSANOTINITIALISED);
     497        return SOCKET_ERROR;
     498   }
     499   else
     500   if(WSAIsBlocking()) {
     501        WSASetLastError(WSAEINPROGRESS);
     502        return SOCKET_ERROR;
     503   }
     504   else
     505   if(namelen < (int)sizeof(struct sockaddr_in)) {
     506        WSASetLastError(WSAEFAULT);
     507        return SOCKET_ERROR;
     508   }
     509   ret = bind(s, (struct sockaddr *)addr, namelen);
     510
     511   if(ret == SOCKET_ERROR) {
     512        WSASetLastError(wsaErrno());
     513   }
     514   else WSASetLastError(NO_ERROR);
     515   return ret;
     516}
     517//******************************************************************************
     518//******************************************************************************
    520519ODINFUNCTION2(int,OS2listen,
    521520              SOCKET, s,
    522521              int, backlog)
    523522{
    524   return(listen(s,backlog));
    525 }
    526 
    527 
    528 /*****************************************************************************
    529  * Name      :
    530  * Purpose   :
    531  * Parameters:
    532  * Variables :
    533  * Result    :
    534  * Remark    :
    535  * Status    : UNTESTED STUB
    536  *
    537  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    538  *****************************************************************************/
    539 
    540 ODINFUNCTION1(u_long,OS2ntohl,
    541               u_long,netlong)
    542 {
    543   return(ntohl(netlong));
    544 }
    545 
    546 
    547 /*****************************************************************************
    548  * Name      :
    549  * Purpose   :
    550  * Parameters:
    551  * Variables :
    552  * Result    :
    553  * Remark    :
    554  * Status    : UNTESTED STUB
    555  *
    556  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    557  *****************************************************************************/
    558 
    559 ODINFUNCTION1(u_short,OS2ntohs,
    560               u_short,netshort)
    561 {
    562   return(ntohs(netshort));
    563 }
    564 
    565 
    566 /*****************************************************************************
    567  * Name      :
    568  * Purpose   :
    569  * Parameters:
    570  * Variables :
    571  * Result    :
    572  * Remark    :
    573  * Status    : UNTESTED STUB
    574  *
    575  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    576  *****************************************************************************/
    577 
     523   int ret, tmp, namelen;
     524   struct sockaddr_in name;
     525
     526   if(!fWSAInitialized) {
     527        WSASetLastError(WSANOTINITIALISED);
     528        return SOCKET_ERROR;
     529   }
     530   else
     531   if(WSAIsBlocking()) {
     532        WSASetLastError(WSAEINPROGRESS);
     533        return SOCKET_ERROR;
     534   }
     535   namelen = sizeof(name);
     536   ret = getsockname(s, (struct sockaddr *)&name, &namelen);
     537   if (ret == 0) {
     538        if (name.sin_port == 0 && name.sin_addr.s_addr == 0) {
     539                // Socket is not bound
     540                WSASetLastError(WSAEINVAL);
     541                return SOCKET_ERROR;
     542        }
     543        ret = ioctl(s, FIOBSTATUS, (char *)&tmp, sizeof(tmp)) &
     544                   (SS_ISCONNECTING | SS_ISCONNECTED | SS_ISDISCONNECTING);
     545        if(ret) {
     546                // Socket is already connected
     547                WSASetLastError(WSAEISCONN);
     548                return SOCKET_ERROR;
     549        }
     550        ret = listen(s, backlog);
     551        //todo: reset FD_ACCEPT bit? (wine seems to do this, but it's not documented)
     552   }
     553   if(ret == SOCKET_ERROR) {
     554        WSASetLastError(wsaErrno());
     555   }
     556   else WSASetLastError(NO_ERROR);
     557   return ret;
     558}
     559//******************************************************************************
     560//******************************************************************************
    578561ODINFUNCTION4(int,OS2recv,
    579562              SOCKET,s,
     
    582565              int,flags)
    583566{
    584   return(recv(s,
    585               buf,
    586               len,
    587               flags));
    588 }
    589 
    590 
    591 /*****************************************************************************
    592  * Name      :
    593  * Purpose   :
    594  * Parameters:
    595  * Variables :
    596  * Result    :
    597  * Remark    :
    598  * Status    : UNTESTED STUB
    599  *
    600  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    601  *****************************************************************************/
    602 
     567   int ret;
     568
     569   if(!fWSAInitialized) {
     570        WSASetLastError(WSANOTINITIALISED);
     571        return SOCKET_ERROR;
     572   }
     573   else
     574   if(WSAIsBlocking()) {
     575        WSASetLastError(WSAEINPROGRESS);
     576        return SOCKET_ERROR;
     577   }
     578   ret = recv(s, buf, len, flags);
     579
     580   if(ret == SOCKET_ERROR) {
     581        WSASetLastError(wsaErrno());
     582   }
     583   else WSASetLastError(NO_ERROR);
     584
     585   //Reset FD_READ event flagfor  WSAAsyncSelect thread if one was created for this socket
     586   EnableAsyncEvent(s, FD_READ);
     587   return ret;
     588}
     589//******************************************************************************
     590//******************************************************************************
    603591ODINFUNCTION6(int,OS2recvfrom,
    604592              SOCKET,s,
     
    609597              int *,fromlen)
    610598{
    611 
    612   return(recvfrom(s,
    613                 buf,
    614                 len,
    615                 flags,
    616                 from,
    617                 fromlen));
    618 }
    619 
    620 
    621 /*****************************************************************************
    622  * Name      :
    623  * Purpose   :
    624  * Parameters:
    625  * Variables :
    626  * Result    :
    627  * Remark    :
    628  * Status    : UNTESTED STUB
    629  *
    630  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    631  *****************************************************************************/
    632 
    633 ODINFUNCTION5(int,OS2select,
    634               int,nfds,
    635               fd_set *,readfds,
    636               fd_set *,writefds,
    637               fd_set *,exceptfds,
    638               const struct timeval *,timeout)
    639 {
    640   return(select(nfds,
    641                 readfds,
    642                 writefds,
    643                 exceptfds,
    644                 timeout));
    645 }
    646 
    647 
    648 /*****************************************************************************
    649  * Name      :
    650  * Purpose   :
    651  * Parameters:
    652  * Variables :
    653  * Result    :
    654  * Remark    :
    655  * Status    : UNTESTED STUB
    656  *
    657  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    658  *****************************************************************************/
    659 
     599   int ret;
     600
     601   if(!fWSAInitialized) {
     602        WSASetLastError(WSANOTINITIALISED);
     603        return SOCKET_ERROR;
     604   }
     605   else
     606   if(WSAIsBlocking()) {
     607        WSASetLastError(WSAEINPROGRESS);
     608        return SOCKET_ERROR;
     609   }
     610   else
     611   if(fromlen == NULL || *fromlen < (int)sizeof(struct sockaddr_in)) {
     612        WSASetLastError(WSAEFAULT);
     613        return SOCKET_ERROR;
     614   }
     615   ret = recvfrom(s, buf, len, flags, from, fromlen);
     616
     617   if(ret == SOCKET_ERROR) {
     618        WSASetLastError(wsaErrno());
     619   }
     620   else WSASetLastError(NO_ERROR);
     621
     622   //Reset FD_READ event flagfor  WSAAsyncSelect thread if one was created for this socket
     623   EnableAsyncEvent(s, FD_READ);
     624   return ret;
     625}
     626//******************************************************************************
     627//******************************************************************************
    660628ODINFUNCTION4(int,OS2send,
    661629              SOCKET,s,
     
    664632              int,flags)
    665633{
    666   return(send(s,
    667               buf,
    668               len,
    669               flags));
    670 }
    671 
    672 
    673 /*****************************************************************************
    674  * Name      :
    675  * Purpose   :
    676  * Parameters:
    677  * Variables :
    678  * Result    :
    679  * Remark    :
    680  * Status    : UNTESTED STUB
    681  *
    682  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    683  *****************************************************************************/
    684 
     634   int ret;
     635
     636   if(!fWSAInitialized) {
     637        WSASetLastError(WSANOTINITIALISED);
     638        return SOCKET_ERROR;
     639   }
     640   else
     641   if(WSAIsBlocking()) {
     642        WSASetLastError(WSAEINPROGRESS);
     643        return SOCKET_ERROR;
     644   }
     645   ret = send(s, (char *)buf, len, flags);
     646
     647   if(ret == SOCKET_ERROR) {
     648        WSASetLastError(wsaErrno());
     649   }
     650   else WSASetLastError(NO_ERROR);
     651
     652   //Reset FD_WRITE event flagfor  WSAAsyncSelect thread if one was created for this socket
     653   EnableAsyncEvent(s, FD_WRITE);
     654   return ret;
     655}
     656//******************************************************************************
     657//******************************************************************************
    685658ODINFUNCTION6(int,OS2sendto,
    686659              SOCKET,s,
     
    691664              int,tolen)
    692665{
    693   return(sendto(s,
    694               buf,
    695               len,
    696               flags,
    697               to,
    698               tolen));
    699 }
    700 
    701 
    702 /*****************************************************************************
    703  * Name      :
    704  * Purpose   :
    705  * Parameters:
    706  * Variables :
    707  * Result    :
    708  * Remark    :
    709  * Status    : UNTESTED STUB
    710  *
    711  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    712  *****************************************************************************/
    713 
     666   int ret;
     667
     668   if(!fWSAInitialized) {
     669        WSASetLastError(WSANOTINITIALISED);
     670        return SOCKET_ERROR;
     671   }
     672   else
     673   if(WSAIsBlocking()) {
     674        WSASetLastError(WSAEINPROGRESS);
     675        return SOCKET_ERROR;
     676   }
     677   else
     678   if(tolen < (int)sizeof(struct sockaddr_in)) {
     679        WSASetLastError(WSAEFAULT);
     680        return SOCKET_ERROR;
     681   }
     682   ret = sendto(s, (char *)buf, len, flags, (struct sockaddr *)to, tolen);
     683
     684   if(ret == SOCKET_ERROR) {
     685        WSASetLastError(wsaErrno());
     686   }
     687   else WSASetLastError(NO_ERROR);
     688
     689   //Reset FD_WRITE event flagfor  WSAAsyncSelect thread if one was created for this socket
     690   EnableAsyncEvent(s, FD_WRITE);
     691   return ret;
     692}
     693//******************************************************************************
     694//******************************************************************************
     695ODINFUNCTION5(int,OS2select,
     696              int,nfds,
     697              ws_fd_set *,readfds,
     698              ws_fd_set *,writefds,
     699              ws_fd_set *,exceptfds,
     700              const struct timeval *,timeout)
     701{
     702 int ret, i, j;
     703 int *sockets, *socktmp;
     704 int nrread, nrwrite, nrexcept;
     705 ULONG ttimeout;
     706
     707   WSASetLastError(NO_ERROR);
     708
     709   if(!fWSAInitialized) {
     710        WSASetLastError(WSANOTINITIALISED);
     711        return SOCKET_ERROR;
     712   }
     713   else
     714   if(WSAIsBlocking()) {
     715        WSASetLastError(WSAEINPROGRESS);
     716        return SOCKET_ERROR;
     717   }
     718   else {
     719        nrread = nrwrite = nrexcept = 0;
     720        if(readfds) {
     721                nrread += readfds->fd_count;
     722        }
     723        if(writefds) {
     724                nrwrite += writefds->fd_count;
     725        }
     726        if(exceptfds) {
     727                nrexcept += exceptfds->fd_count;
     728        }
     729        if(nrread + nrwrite + nrexcept  == 0) {
     730                WSASetLastError(WSAEINVAL);
     731                return SOCKET_ERROR;
     732        }
     733        if(timeout != NULL && (timeout->tv_sec < 0 || timeout->tv_usec < 0)) {
     734                WSASetLastError(WSAEINVAL);
     735                return SOCKET_ERROR;
     736        }
     737        if(timeout == NULL) {
     738                ttimeout = -1L; // no timeout
     739        }
     740        else    ttimeout = timeout->tv_sec * 1000 + timeout->tv_usec / 1000;
     741       
     742        sockets = (int *)malloc(sizeof(int) * (nrread+nrwrite+nrexcept));
     743        if(readfds) {
     744                memcpy(&sockets[0], readfds->fd_array, nrread * sizeof(SOCKET));
     745        }
     746        if(writefds) {
     747                memcpy(&sockets[nrread], writefds->fd_array, nrwrite * sizeof(SOCKET));
     748        }
     749        if(exceptfds) {
     750                memcpy(&sockets[nrread+nrwrite], exceptfds->fd_array, nrexcept * sizeof(SOCKET));
     751        }
     752
     753        ret = select(sockets, nrread, nrwrite, nrexcept, ttimeout);
     754
     755        if(ret == SOCKET_ERROR)
     756        {
     757                if(readfds != NULL)
     758                        readfds->fd_count = 0;
     759
     760                if(writefds != NULL)
     761                        writefds->fd_count = 0;
     762
     763                if(exceptfds != NULL)
     764                        exceptfds->fd_count = 0;
     765
     766                WSASetLastError(wsaErrno());
     767                free(sockets);
     768                return SOCKET_ERROR;
     769        }
     770
     771        if(ret != 0) {
     772                socktmp = sockets;
     773                if(readfds != NULL) {
     774                        for(i=0;i<nrread;i++) {
     775                                if(socktmp[i] != -1) {
     776                                        readfds->fd_array[j] = socktmp[i];
     777                                }
     778                        }
     779                        readfds->fd_count = i;
     780                        socktmp += nrread;
     781                }
     782
     783                if(writefds != NULL) {
     784                        for(i=0;i<nrwrite;i++) {
     785                                if(socktmp[i] != -1) {
     786                                        writefds->fd_array[j] = socktmp[i];
     787                                }
     788                        }
     789                        writefds->fd_count = i;
     790                        socktmp += nrwrite;
     791                }
     792                if(exceptfds != NULL) {
     793                        for(i=0;i<nrexcept;i++) {
     794                                if(socktmp[i] != -1) {
     795                                        exceptfds->fd_array[j] = socktmp[i];
     796                                }
     797                        }
     798                        exceptfds->fd_count = i;
     799                }
     800         }
     801        else {
     802            if(readfds != NULL)
     803               readfds->fd_count = 0;
     804
     805            if(writefds != NULL)
     806               writefds->fd_count = 0;
     807
     808            if(exceptfds != NULL)
     809               exceptfds->fd_count = 0;
     810        }
     811        free(sockets);
     812   }
     813   return ret;
     814}
     815//******************************************************************************
     816//******************************************************************************
    714817ODINFUNCTION5(int,OS2setsockopt,
    715818              SOCKET,s,
     
    719822              int,optlen)
    720823{
    721   struct Wlinger *yy;
    722   struct linger xx;
    723   int    rc;
    724 
    725   if(level   == SOL_SOCKET &&
    726      optname == SO_LINGER)
    727   {
    728     yy = (struct Wlinger *)optval;
    729     xx.l_onoff = (int)yy->l_onoff;
    730     xx.l_linger = (int)yy->l_linger;
    731 
    732     rc = setsockopt(s,level,optname,(char *)&xx, sizeof(xx));
    733   }
    734   else
    735   if(level == SOL_SOCKET && (optname == SO_SNDBUF || optname == SO_RCVBUF)) {
    736         ULONG size;
    737 
    738         size = *(ULONG *)optval;
     824  struct ws_linger *yy;
     825  struct linger     xx;
     826  int               ret;
     827  ULONG             size;
     828
     829   if(!fWSAInitialized) {
     830        WSASetLastError(WSANOTINITIALISED);
     831        return SOCKET_ERROR;
     832   }
     833   else
     834   if(WSAIsBlocking()) {
     835        WSASetLastError(WSAEINPROGRESS);
     836        return SOCKET_ERROR;
     837   }
     838   if (level == SOL_SOCKET) {
     839        switch(optname) {
     840        case SO_DONTLINGER:
     841        case SO_LINGER:
     842                if(optlen < (int)sizeof(ws_linger)) {
     843                        WSASetLastError(WSAEFAULT);
     844                        return SOCKET_ERROR;
     845                }
     846                yy = (struct ws_linger *)optval;
     847                xx.l_onoff  = (optname == SO_DONTLINGER) ? !yy->l_onoff : yy->l_onoff;
     848                xx.l_linger = yy->l_linger;
     849
     850                ret = setsockopt(s,level,optname,(char *)&xx, sizeof(xx));
     851                break;
     852        case SO_SNDBUF:
     853        case SO_RCVBUF:
     854                if(optlen < (int)sizeof(int)) {
     855                        WSASetLastError(WSAEFAULT);
     856                        return SOCKET_ERROR;
     857                }
     858
     859                size = *(ULONG *)optval;
    739860tryagain:
    740         rc = setsockopt(s,level,optname, (char *)&size, sizeof(ULONG));
    741         if(rc == SOCKET_ERROR && size > 65535) {
    742                 //SvL: Limit send & receive buffer length to 64k
    743                 //     (only happens with 16 bits tcpip stack?)
    744                 size = 65000;
    745                 goto tryagain;
    746         }
    747 
    748   }
    749   else {
    750     rc = setsockopt(s,level,optname,(char *)optval,optlen);
    751   }
    752 
    753   if (rc == SOCKET_ERROR)
    754     //OS2WSASetLastError(iTranslateSockErrToWSock(sock_errno()));
    755     OS2WSASetLastError(WSAEINVAL);
    756   else
    757     OS2WSASetLastError(ERROR_SUCCESS);
    758 
    759   return rc;
    760 }
    761 
    762 
    763 /*****************************************************************************
    764  * Name      :
    765  * Purpose   :
    766  * Parameters:
    767  * Variables :
    768  * Result    :
    769  * Remark    :
    770  * Status    : UNTESTED STUB
    771  *
    772  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    773  *****************************************************************************/
    774 
    775 ODINFUNCTION2(int,OS2shutdown,
    776               SOCKET,s,
    777               int,how)
    778 {
    779   return(shutdown(s,
    780                   how));
    781 }
    782 
    783 
    784 /*****************************************************************************
    785  * Name      :
    786  * Purpose   :
    787  * Parameters:
    788  * Variables :
    789  * Result    :
    790  * Remark    :
    791  * Status    : UNTESTED STUB
    792  *
    793  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    794  *****************************************************************************/
    795 
    796 ODINFUNCTION3(SOCKET,OS2socket,
    797               int,af,
    798               int,type,
    799               int,protocol)
    800 {
    801   return(socket(af,
    802                 type,
    803                 protocol));
    804 }
    805 
    806 
     861                ret = setsockopt(s,level,optname, (char *)&size, sizeof(ULONG));
     862                if(ret == SOCKET_ERROR && size > 65535) {
     863                        dprintf(("setsockopt: change size from %d to 65000", size));
     864                        //SvL: Limit send & receive buffer length to 64k
     865                        //     (only happens with 16 bits tcpip stack?)
     866                        size = 65000;
     867                        goto tryagain;
     868                }
     869                break;
     870
     871        case SO_BROADCAST:
     872        case SO_DEBUG:
     873        case SO_KEEPALIVE:
     874        case SO_DONTROUTE:
     875        case SO_OOBINLINE:
     876        case SO_REUSEADDR:
     877                if(optlen < (int)sizeof(int)) {
     878                        WSASetLastError(WSAEFAULT);
     879                        return SOCKET_ERROR;
     880                }
     881                ret = setsockopt(s, level, optname, (char *)optval, optlen);
     882                break;
     883        default:
     884                dprintf(("setsockopt: unknown option %x", optname));
     885                WSASetLastError(WSAENOPROTOOPT);
     886                return SOCKET_ERROR;
     887        }
     888   }
     889   else
     890   if(level == IPPROTO_TCP) {
     891        if(optname == TCP_NODELAY) {
     892                if(optlen < (int)sizeof(int)) {
     893                        WSASetLastError(WSAEFAULT);
     894                        return SOCKET_ERROR;
     895                }
     896                ret = setsockopt(s, level, optname, (char *)optval, optlen);
     897        }
     898        else {
     899                dprintf(("setsockopt: unknown option %x", optname));
     900                WSASetLastError(WSAENOPROTOOPT);
     901                return SOCKET_ERROR;
     902        }
     903   }
     904   else {
     905        WSASetLastError(WSAEINVAL);
     906        return SOCKET_ERROR;
     907   }
     908
     909   if(ret == SOCKET_ERROR) {
     910        WSASetLastError(wsaErrno());
     911   }
     912   else WSASetLastError(NO_ERROR);
     913   return ret;
     914}
     915//******************************************************************************
     916//******************************************************************************
     917ODINFUNCTION5(int,OS2getsockopt,
     918              SOCKET, s,
     919              int, level,
     920              int, optname,
     921              char *, optval,
     922              int *,optlen)
     923{
     924  struct ws_linger *yy;
     925  struct linger     xx;
     926  int               ret;
     927  int               size, options;
     928
     929   if(!fWSAInitialized) {
     930        WSASetLastError(WSANOTINITIALISED);
     931        return SOCKET_ERROR;
     932   }
     933   else
     934   if(WSAIsBlocking()) {
     935        WSASetLastError(WSAEINPROGRESS);
     936        return SOCKET_ERROR;
     937   }
     938   if (level == SOL_SOCKET) {
     939        switch(optname) {
     940        case SO_DONTLINGER:
     941        case SO_LINGER:
     942                if(optlen == NULL || *optlen < sizeof(ws_linger)) {
     943                        WSASetLastError(WSAEFAULT);
     944                        return SOCKET_ERROR;
     945                }
     946                size = sizeof(xx);
     947                ret = getsockopt(s,level,optname,(char *)&xx, &size);
     948                yy = (struct ws_linger *)optval;
     949                yy->l_onoff  = (optname == SO_DONTLINGER) ? !xx.l_onoff : xx.l_onoff;
     950                yy->l_linger = xx.l_linger;
     951                *optlen = size;
     952                break;
     953
     954        case SO_SNDBUF:
     955        case SO_RCVBUF:
     956        case SO_BROADCAST:
     957        case SO_DEBUG:
     958        case SO_KEEPALIVE:
     959        case SO_DONTROUTE:
     960        case SO_OOBINLINE:
     961        case SO_REUSEADDR:
     962        case SO_TYPE:
     963                if(optlen == NULL || *optlen < sizeof(int)) {
     964                        WSASetLastError(WSAEFAULT);
     965                        return SOCKET_ERROR;
     966                }
     967                ret = getsockopt(s, level, optname, (char *)optval, optlen);
     968                break;
     969        case SO_ACCEPTCONN:
     970                if(optlen == NULL || *optlen < sizeof(int)) {
     971                        WSASetLastError(WSAEFAULT);
     972                        return SOCKET_ERROR;
     973                }
     974                size = sizeof(options);
     975                ret = getsockopt(s, SOL_SOCKET, SO_OPTIONS, (char *)&options, &size);
     976                if(ret != SOCKET_ERROR) {
     977                        *(BOOL *)optval = (options & SO_ACCEPTCONN) == SO_ACCEPTCONN;
     978                        *optlen = sizeof(BOOL);
     979                }
     980                break;
     981        default:
     982                dprintf(("getsockopt: unknown option %x", optname));
     983                WSASetLastError(WSAENOPROTOOPT);
     984                return SOCKET_ERROR;
     985        }
     986   }
     987   else
     988   if(level == IPPROTO_TCP) {
     989        if(optname == TCP_NODELAY) {
     990                if(optlen == NULL || *optlen < sizeof(int)) {
     991                        WSASetLastError(WSAEFAULT);
     992                        return SOCKET_ERROR;
     993                }
     994                ret = getsockopt(s, level, optname, (char *)optval, optlen);
     995        }
     996        else {
     997                dprintf(("getsockopt: unknown option %x", optname));
     998                WSASetLastError(WSAENOPROTOOPT);
     999                return SOCKET_ERROR;
     1000        }
     1001   }
     1002   else {
     1003        WSASetLastError(WSAEINVAL);
     1004        return SOCKET_ERROR;
     1005   }
     1006
     1007   if(ret == SOCKET_ERROR) {
     1008        WSASetLastError(wsaErrno());
     1009   }
     1010   else WSASetLastError(NO_ERROR);
     1011   return ret;
     1012}
     1013//******************************************************************************
     1014//******************************************************************************
    8071015/* Database function prototypes */
    808 
    809 /*****************************************************************************
    810  * Name      :
    811  * Purpose   :
    812  * Parameters:
    813  * Variables :
    814  * Result    :
    815  * Remark    :
    816  * Status    : UNTESTED STUB
    817  *
    818  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    819  *****************************************************************************/
    820 
    821 ODINFUNCTION3(struct Whostent *,OS2gethostbyaddr,
     1016//******************************************************************************
     1017//******************************************************************************
     1018ODINFUNCTION2(int,OS2gethostname,
     1019              char *,name,
     1020              int,namelen)
     1021{
     1022 int ret;
     1023
     1024   ret = gethostname(name, namelen);
     1025   if(ret == NULL) {
     1026        WSASetLastError(NO_ERROR);
     1027        return 0;
     1028   }
     1029   WSASetLastError((errno == EINVAL) ? WSAEFAULT : wsaErrno());
     1030   return SOCKET_ERROR;
     1031}
     1032//******************************************************************************
     1033//******************************************************************************
     1034ODINFUNCTION3(ws_hostent *,OS2gethostbyaddr,
    8221035              const char *,addr,
    8231036              int,len,
    8241037              int,type)
    8251038{
    826   WHOSTENT         *yy;
    827   struct hostent   *xx;
    828   PWSOCKTHREADDATA pwstd;
    829 
    830   xx = gethostbyaddr((char *)addr,len,type);
    831   //PH: we assume PMWSOCK sets WSASetLastError correctly!
    832 
    833   if(xx == NULL)
    834      return (WHOSTENT *)NULL;
    835 
    836   // access current thread wsock data block
    837   pwstd = iQueryWsockThreadData();
    838 
    839   pwstd->whsnt.h_name      = xx->h_name;
    840   pwstd->whsnt.h_aliases   = xx->h_aliases;
    841   pwstd->whsnt.h_addrtype  = (short)xx->h_addrtype;
    842   pwstd->whsnt.h_length    = (short)xx->h_length;
    843   pwstd->whsnt.h_addr_list = xx->h_addr_list;
    844 
    845   return &pwstd->whsnt;
    846 }
    847 
    848 
    849 /*****************************************************************************
    850  * Name      :
    851  * Purpose   :
    852  * Parameters:
    853  * Variables :
    854  * Result    :
    855  * Remark    :
    856  * Status    : UNTESTED STUB
    857  *
    858  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    859  *****************************************************************************/
    860 
    861 ODINFUNCTION1(struct Whostent *,OS2gethostbyname,
     1039    LPWSINFO pwsi = WINSOCK_GetIData();
     1040
     1041    if( pwsi )
     1042    {
     1043        struct hostent* host;
     1044        if( (host = gethostbyaddr((char *)addr, len, type)) != NULL ) {
     1045                if( WS_dup_he(pwsi, host) ) {
     1046                        WSASetLastError(NO_ERROR);
     1047                        return pwsi->he;
     1048                }
     1049                else    WSASetLastError(WSAENOBUFS);
     1050        }
     1051        else    WSASetLastError((h_errno < 0) ? wsaErrno() : wsaHerrno());
     1052    }
     1053    else WSASetLastError(WSANOTINITIALISED);
     1054    return NULL;
     1055}
     1056//******************************************************************************
     1057//******************************************************************************
     1058ODINFUNCTION1(ws_hostent *,OS2gethostbyname,
    8621059              const char *,name)
    8631060{
    864   WHOSTENT         *yy;
    865   struct hostent   *xx;
    866   PWSOCKTHREADDATA pwstd;
    867 
    868 
    869   xx = gethostbyname((char *)name);
    870   //PH: we assume PMWSOCK sets WSASetLastError correctly!
    871 
    872   if(xx == NULL)
    873     return (WHOSTENT *)NULL;
    874 
    875   // access current thread wsock data block
    876   pwstd = iQueryWsockThreadData();
    877 
    878   pwstd->whsnt.h_name      = xx->h_name;
    879   pwstd->whsnt.h_aliases   = xx->h_aliases;
    880   pwstd->whsnt.h_addrtype  = (short)xx->h_addrtype;
    881   pwstd->whsnt.h_length    = (short)xx->h_length;
    882   pwstd->whsnt.h_addr_list = xx->h_addr_list;
    883 
    884   return &pwstd->whsnt;
    885 }
    886 
    887 
    888 /*****************************************************************************
    889  * Name      :
    890  * Purpose   :
    891  * Parameters:
    892  * Variables :
    893  * Result    :
    894  * Remark    :
    895  * Status    : UNTESTED STUB
    896  *
    897  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    898  *****************************************************************************/
    899 
    900 ODINFUNCTION2(int,OS2gethostname,
    901               char *,name,
    902               int,namelen)
    903 {
    904    //PH: we assume PMWSOCK sets WSASetLastError correctly!
    905    return(gethostname(name,
    906                      namelen));
    907 }
    908 
    909 
    910 /*****************************************************************************
    911  * Name      :
    912  * Purpose   :
    913  * Parameters:
    914  * Variables :
    915  * Result    :
    916  * Remark    :
    917  * Status    : UNTESTED STUB
    918  *
    919  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    920  *****************************************************************************/
    921 
    922 ODINFUNCTION2(struct Wservent *,OS2getservbyport,
     1061    LPWSINFO pwsi = WINSOCK_GetIData();
     1062
     1063    if( pwsi )
     1064    {
     1065        struct hostent*     host;
     1066        if( (host = gethostbyname((char *)name)) != NULL ) {
     1067                if( WS_dup_he(pwsi, host) ) {
     1068                        WSASetLastError(NO_ERROR);
     1069                        return pwsi->he;
     1070                }
     1071                else    WSASetLastError(WSAENOBUFS);
     1072        }
     1073        else    WSASetLastError((h_errno < 0) ? wsaErrno() : wsaHerrno());
     1074    }
     1075    else WSASetLastError(WSANOTINITIALISED);
     1076    return NULL;
     1077}
     1078//******************************************************************************
     1079//******************************************************************************
     1080ODINFUNCTION2(struct ws_servent *,OS2getservbyport,
    9231081              int,              port,
    9241082              const char *,     proto)
    9251083{
    926   struct servent   *xx;
    927   PWSOCKTHREADDATA pwstd;
    928 
    929   //PH: we assume PMWSOCK sets WSASetLastError correctly!
    930   xx = getservbyport(port,(char *)proto);
    931 
    932   if(xx == NULL)
    933     return (WSERVENT *)NULL;
    934 
    935   // access current thread wsock data block
    936   pwstd = iQueryWsockThreadData();
    937 
    938   pwstd->wsvnt.s_name    = xx->s_name;
    939   pwstd->wsvnt.s_aliases = xx->s_aliases;
    940   pwstd->wsvnt.s_port    = (short)xx->s_port;
    941   pwstd->wsvnt.s_proto   = xx->s_proto;
    942 
    943   return &pwstd->wsvnt;
    944 }
    945 
    946 
    947 /*****************************************************************************
    948  * Name      :
    949  * Purpose   :
    950  * Parameters:
    951  * Variables :
    952  * Result    :
    953  * Remark    :
    954  * Status    : UNTESTED STUB
    955  *
    956  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    957  *****************************************************************************/
    958 
    959 ODINFUNCTION2(struct Wservent *,OS2getservbyname,
     1084    LPWSINFO pwsi = WINSOCK_GetIData();
     1085
     1086    if( pwsi )
     1087    {
     1088        struct servent* serv;
     1089        if( (serv = getservbyport(port, pwsi->buffer)) != NULL ) {
     1090                if( WS_dup_se(pwsi, serv) ) {
     1091                        WSASetLastError(NO_ERROR);
     1092                        return pwsi->se;
     1093                }
     1094                else    WSASetLastError(WSAENOBUFS);
     1095        }
     1096        else    WSASetLastError(WSANO_DATA);
     1097    }
     1098    else WSASetLastError(WSANOTINITIALISED);
     1099    return NULL;
     1100}
     1101//******************************************************************************
     1102//******************************************************************************
     1103ODINFUNCTION2(struct ws_servent *,OS2getservbyname,
    9601104              const char *,     name,
    9611105              const char *,     proto)
    9621106{
    963   WSERVENT         *yy;
    964   struct servent   *xx;
    965   PWSOCKTHREADDATA pwstd;
    966 
    967 
    968   //PH: we assume PMWSOCK sets WSASetLastError correctly!
    969   xx = getservbyname((char *)name,(char *)proto);
    970 
    971   if(xx == NULL)
    972     return (WSERVENT *)NULL;
    973 
    974   // access current thread wsock data block
    975   pwstd = iQueryWsockThreadData();
    976 
    977   pwstd->wsvnt.s_name    = xx->s_name;
    978   pwstd->wsvnt.s_aliases = xx->s_aliases;
    979   pwstd->wsvnt.s_port    = (short)xx->s_port;
    980   pwstd->wsvnt.s_proto   = xx->s_proto;
    981 
    982   return &pwstd->wsvnt;
    983 }
    984 
    985 
    986 /*****************************************************************************
    987  * Name      :
    988  * Purpose   :
    989  * Parameters:
    990  * Variables :
    991  * Result    :
    992  * Remark    :
    993  * Status    : UNTESTED STUB
    994  *
    995  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    996  *****************************************************************************/
    997 
    998 ODINFUNCTION1(struct Wprotoent *,OS2getprotobynumber,
    999               int,proto)
    1000 {
    1001   struct protoent  *xx;
    1002   PWSOCKTHREADDATA pwstd;
    1003 
    1004   //PH: we assume PMWSOCK sets WSASetLastError correctly!
    1005   xx = getprotobynumber(proto);
    1006 
    1007   if(xx == NULL)
    1008     return (WPROTOENT *)NULL;
    1009 
    1010   // access current thread wsock data block
    1011   pwstd = iQueryWsockThreadData();
    1012 
    1013   pwstd->wptnt.p_name    = xx->p_name;
    1014   pwstd->wptnt.p_aliases = xx->p_aliases;
    1015   pwstd->wptnt.p_proto   = (short)xx->p_proto;
    1016 
    1017   return &pwstd->wptnt;
    1018 }
    1019 
    1020 
    1021 /*****************************************************************************
    1022  * Name      :
    1023  * Purpose   :
    1024  * Parameters:
    1025  * Variables :
    1026  * Result    :
    1027  * Remark    :
    1028  * Status    : UNTESTED STUB
    1029  *
    1030  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1031  *****************************************************************************/
    1032 
    1033 ODINFUNCTION1(struct Wprotoent *,OS2getprotobyname,
     1107    LPWSINFO pwsi = WINSOCK_GetIData();
     1108
     1109    if( pwsi )
     1110    {
     1111        struct servent*     serv;
     1112        if( (serv = getservbyname(pwsi->buffer, pwsi->buffer)) != NULL ) {
     1113                if( WS_dup_se(pwsi, serv) ) {
     1114                        WSASetLastError(NO_ERROR);
     1115                        return pwsi->se;
     1116                }
     1117                else    WSASetLastError(WSAENOBUFS);
     1118        }
     1119        else    WSASetLastError(WSANO_DATA);
     1120    }
     1121    else WSASetLastError(WSANOTINITIALISED);
     1122    return NULL;
     1123}
     1124//******************************************************************************
     1125//******************************************************************************
     1126ODINFUNCTION1(struct ws_protoent *,OS2getprotobynumber,
     1127              int,number)
     1128{
     1129    LPWSINFO pwsi = WINSOCK_GetIData();
     1130
     1131    if( pwsi )
     1132    {
     1133        struct protoent* proto;
     1134        if( (proto = getprotobynumber(number)) != NULL ) {
     1135                if( WS_dup_pe(pwsi, proto) ) {
     1136                        WSASetLastError(NO_ERROR);
     1137                        return pwsi->pe;
     1138                }
     1139                else    WSASetLastError(WSAENOBUFS);
     1140        }
     1141        else    WSASetLastError(WSANO_DATA);
     1142    }
     1143    else WSASetLastError(WSANOTINITIALISED);
     1144    return NULL;
     1145}
     1146//******************************************************************************
     1147//******************************************************************************
     1148ODINFUNCTION1(struct ws_protoent *,OS2getprotobyname,
    10341149              const char *,name)
    10351150{
    1036   struct protoent  *xx;
    1037   PWSOCKTHREADDATA pwstd;
    1038 
    1039   //PH: we assume PMWSOCK sets WSASetLastError correctly!
    1040   xx = getprotobyname((char *)name);
    1041 
    1042   if(xx == NULL)
    1043     return (WPROTOENT *)NULL;
    1044 
    1045   // access current thread wsock data block
    1046   pwstd = iQueryWsockThreadData();
    1047 
    1048   pwstd->wptnt.p_name    = xx->p_name;
    1049   pwstd->wptnt.p_aliases = xx->p_aliases;
    1050   pwstd->wptnt.p_proto   = (short)xx->p_proto;
    1051 
    1052   return &pwstd->wptnt;
    1053 }
    1054 
    1055 
    1056 
    1057 /* Microsoft Windows Extension function prototypes */
    1058 
    1059 /*****************************************************************************
    1060  * Name      :
    1061  * Purpose   :
    1062  * Parameters:
    1063  * Variables :
    1064  * Result    :
    1065  * Remark    :
    1066  * Status    : UNTESTED STUB
    1067  *
    1068  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1069  *****************************************************************************/
    1070 
    1071 ODINFUNCTION2(int,OS2WSAStartup,
    1072               USHORT,wVersionRequired,
    1073               LPWSADATA,lpWSAData)
    1074 {
    1075   fWSAInitialized = TRUE;
    1076   return(WSAStartup(wVersionRequired,
    1077                     lpWSAData));
    1078 }
    1079 
    1080 
    1081 /*****************************************************************************
    1082  * Name      :
    1083  * Purpose   :
    1084  * Parameters:
    1085  * Variables :
    1086  * Result    :
    1087  * Remark    :
    1088  * Status    : UNTESTED STUB
    1089  *
    1090  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1091  *****************************************************************************/
    1092 
    1093 ODINFUNCTION0(int,OS2WSACleanup)
    1094 {
    1095   fWSAInitialized = FALSE;
    1096   return(WSACleanup());
    1097 }
    1098 
    1099 
    1100 /*****************************************************************************
    1101  * Name      :
    1102  * Purpose   :
    1103  * Parameters:
    1104  * Variables :
    1105  * Result    :
    1106  * Remark    :
    1107  * Status    : UNTESTED STUB
    1108  *
    1109  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1110  *****************************************************************************/
    1111 
    1112 ODINFUNCTION0(BOOL,OS2WSAIsBlocking)
    1113 {
    1114   return WSAIsBlocking();
    1115 }
    1116 
    1117 
    1118 /*****************************************************************************
    1119  * Name      :
    1120  * Purpose   :
    1121  * Parameters:
    1122  * Variables :
    1123  * Result    :
    1124  * Remark    :
    1125  * Status    : UNTESTED STUB
    1126  *
    1127  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1128  *****************************************************************************/
    1129 
    1130 ODINFUNCTION0(int,OS2WSAUnhookBlockingHook)
    1131 {
    1132   return WSAUnhookBlockingHook();
    1133 }
    1134 
    1135 
    1136 /*****************************************************************************
    1137  * Name      :
    1138  * Purpose   :
    1139  * Parameters:
    1140  * Variables :
    1141  * Result    :
    1142  * Remark    :
    1143  * Status    : UNTESTED STUB
    1144  *
    1145  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1146  *****************************************************************************/
    1147 
    1148 ODINFUNCTION1(PFN,OS2WSASetBlockingHook,
    1149               PFN,lpBlockFunc)
    1150 {
    1151   return(WSASetBlockingHook(lpBlockFunc));
    1152 }
    1153 
    1154 
    1155 /*****************************************************************************
    1156  * Name      :
    1157  * Purpose   :
    1158  * Parameters:
    1159  * Variables :
    1160  * Result    :
    1161  * Remark    :
    1162  * Status    : UNTESTED STUB
    1163  *
    1164  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1165  *****************************************************************************/
    1166 
    1167 ODINFUNCTION0(int,OS2WSACancelBlockingCall)
    1168 {
    1169   return(WSACancelBlockingCall());
    1170 }
    1171 
    1172 
    1173 /*****************************************************************************
    1174  * Name      :
    1175  * Purpose   :
    1176  * Parameters:
    1177  * Variables :
    1178  * Result    :
    1179  * Remark    :
    1180  * Status    : UNTESTED STUB
    1181  *
    1182  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1183  *****************************************************************************/
    1184 
    1185 ODINFUNCTION6(LHANDLE,OS2WSAAsyncGetServByName,
    1186               HWND,hWnd,
    1187               u_int,wMsg,
    1188               const char *,name,
    1189               const char *,proto,
    1190               char *,buf,
    1191               int,buflen)
    1192 {
    1193   int   rc;
    1194   HWND  hwndOS2 = Win32ToOS2Handle(hWnd);
    1195   ULONG ulNewID;
    1196 
    1197   if (hwndRelay == NULL) // already initialized ?
    1198     hwndRelay = RelayInitialize(hwndOS2);
    1199 
    1200   // add entry to list, we need to store both our temp buffer and the apps buffer
    1201   ulNewID = RelayAlloc(hWnd,
    1202                        wMsg,
    1203                        ASYNCREQUEST_GETSERVBYNAME,
    1204                        FALSE,
    1205                        buf);
    1206 
    1207   // call pmwsock function, will fill our temp buffer
    1208   rc = WSAAsyncGetServByName(hwndRelay,
    1209                               ulNewID,
    1210                               name,
    1211                               proto,
    1212                               buf,
    1213                               buflen);
    1214 
    1215   // if an error occurs, free the allocated relay entry
    1216   if (rc == SOCKET_ERROR)
    1217     RelayFree(ulNewID);
    1218 
    1219   return (rc);
    1220 }
    1221 
    1222 
    1223 /*****************************************************************************
    1224  * Name      :
    1225  * Purpose   :
    1226  * Parameters:
    1227  * Variables :
    1228  * Result    :
    1229  * Remark    :
    1230  * Status    : UNTESTED STUB
    1231  *
    1232  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1233  *****************************************************************************/
    1234 
    1235 ODINFUNCTION6(LHANDLE,OS2WSAAsyncGetServByPort,
    1236               HWND,hWnd,
    1237               u_int,wMsg,
    1238               int,port,
    1239               const char *,proto,
    1240               char *,buf,
    1241               int,buflen)
    1242 {
    1243   int   rc;
    1244   HWND  hwndOS2 = Win32ToOS2Handle(hWnd);
    1245   ULONG ulNewID;
    1246 
    1247   if (hwndRelay == NULL) // already initialized ?
    1248     hwndRelay = RelayInitialize(hwndOS2);
    1249 
    1250   // add entry to list, we need to store both our temp buffer and the apps buffer
    1251   ulNewID = RelayAlloc(hWnd,
    1252                        wMsg,
    1253                        ASYNCREQUEST_GETSERVBYPORT,
    1254                        FALSE,
    1255                        buf);
    1256 
    1257   // call pmwsock function, will fill our temp buffer
    1258   rc = WSAAsyncGetServByPort(hwndRelay,
    1259                              ulNewID,
    1260                              port,
    1261                              proto,
    1262                              buf,
    1263                              buflen);
    1264 
    1265   // if an error occurs, free the allocated relay entry
    1266   if (rc == SOCKET_ERROR)
    1267     RelayFree(ulNewID);
    1268 
    1269   return rc;
    1270 }
    1271 
    1272 
    1273 /*****************************************************************************
    1274  * Name      :
    1275  * Purpose   :
    1276  * Parameters:
    1277  * Variables :
    1278  * Result    :
    1279  * Remark    :
    1280  * Status    : UNTESTED STUB
    1281  *
    1282  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1283  *****************************************************************************/
    1284 
    1285 ODINFUNCTION5(LHANDLE,OS2WSAAsyncGetProtoByName,
    1286               HWND,hWnd,
    1287               u_int,wMsg,
    1288               const char *,name,
    1289               char *,buf,
    1290               int,buflen)
    1291 {
    1292   int   rc;
    1293   HWND  hwndOS2 = Win32ToOS2Handle(hWnd);
    1294   ULONG ulNewID;
    1295 
    1296   if (hwndRelay == NULL) // already initialized ?
    1297     hwndRelay = RelayInitialize(hwndOS2);
    1298 
    1299   // add entry to list, we need to store both our temp buffer and the apps buffer
    1300   ulNewID = RelayAlloc(hWnd,
    1301                        wMsg,
    1302                        ASYNCREQUEST_GETPROTOBYNAME,
    1303                        FALSE,
    1304                        buf);
    1305 
    1306   // call pmwsock function, will fill our temp buffer
    1307   rc = WSAAsyncGetProtoByName(hwndRelay,
    1308                               ulNewID,
    1309                               name,
    1310                               buf,
    1311                               buflen);
    1312 
    1313   // if an error occurs, free the allocated relay entry
    1314   if (rc == SOCKET_ERROR)
    1315     RelayFree(ulNewID);
    1316 
    1317   return (rc);
    1318 }
    1319 
    1320 
    1321 /*****************************************************************************
    1322  * Name      :
    1323  * Purpose   :
    1324  * Parameters:
    1325  * Variables :
    1326  * Result    :
    1327  * Remark    :
    1328  * Status    : UNTESTED STUB
    1329  *
    1330  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1331  *****************************************************************************/
    1332 
    1333 ODINFUNCTION5(LHANDLE,OS2WSAAsyncGetProtoByNumber,
    1334               HWND,hWnd,
    1335               u_int,wMsg,
    1336               int,number,
    1337               char *,buf,
    1338               int,buflen)
    1339 {
    1340   int   rc;
    1341   HWND  hwndOS2 = Win32ToOS2Handle(hWnd);
    1342   ULONG ulNewID;
    1343 
    1344   if (hwndRelay == NULL) // already initialized ?
    1345     hwndRelay = RelayInitialize(hwndOS2);
    1346 
    1347   // add entry to list, we need to store both our temp buffer and the apps buffer
    1348   ulNewID = RelayAlloc(hWnd,
    1349                        wMsg,
    1350                        ASYNCREQUEST_GETPROTOBYNUMBER,
    1351                        FALSE,
    1352                        buf);
    1353 
    1354   // call pmwsock function, will fill our temp buffer
    1355   rc = WSAAsyncGetProtoByNumber(hwndRelay,
    1356                                 ulNewID,
    1357                                 number,
    1358                                 buf,
    1359                                 buflen);
    1360 
    1361   // if an error occurs, free the allocated relay entry
    1362   if (rc == SOCKET_ERROR)
    1363     RelayFree(ulNewID);
    1364 
    1365   return rc;
    1366 }
    1367 
    1368 
    1369 /*****************************************************************************
    1370  * Name      :
    1371  * Purpose   :
    1372  * Parameters:
    1373  * Variables :
    1374  * Result    :
    1375  * Remark    :
    1376  * Status    : UNTESTED STUB
    1377  *
    1378  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1379  *****************************************************************************/
    1380 
    1381 ODINFUNCTION5(LHANDLE,OS2WSAAsyncGetHostByName,
    1382               HWND,hWnd,
    1383               u_int,wMsg,
    1384               const char *,name,
    1385               char *,buf,
    1386               int,buflen)
    1387 {
    1388   int   rc;
    1389   HWND  hwndOS2 = Win32ToOS2Handle(hWnd);
    1390   ULONG ulNewID;
    1391 
    1392   dprintf(("WSAAsyncGetHostByName %s", name));
    1393 
    1394   if (hwndRelay == NULL) // already initialized ?
    1395     hwndRelay = RelayInitialize(hwndOS2);
    1396 
    1397   // add entry to list, we need to store both our temp buffer and the apps buffer
    1398   ulNewID = RelayAlloc(hWnd,
    1399                        wMsg,
    1400                        ASYNCREQUEST_GETHOSTBYNAME,
    1401                        FALSE,
    1402                        (PVOID)buf, (PVOID)buflen);
    1403 
    1404   // call pmwsock function, will fill our temp buffer
    1405   rc = WSAAsyncGetHostByName(hwndRelay,
    1406                              ulNewID,
    1407                              name,
    1408                              buf,
    1409                              buflen);
    1410 
    1411   // if an error occurs, free the allocated relay entry
    1412   if (rc == SOCKET_ERROR)
    1413     RelayFree(ulNewID);
    1414 
    1415   return rc;
    1416 }
    1417 
    1418 
    1419 /*****************************************************************************
    1420  * Name      :
    1421  * Purpose   :
    1422  * Parameters:
    1423  * Variables :
    1424  * Result    :
    1425  * Remark    :
    1426  * Status    : UNTESTED STUB
    1427  *
    1428  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1429  *****************************************************************************/
    1430 
    1431 ODINFUNCTION7(LHANDLE,OS2WSAAsyncGetHostByAddr,
    1432               HWND,hWnd,
    1433               u_int,wMsg,
    1434               const char *,addr,
    1435               int,len,
    1436               int,type,
    1437               char *,buf,
    1438               int,buflen)
    1439 {
    1440   int   rc;
    1441   HWND  hwndOS2 = Win32ToOS2Handle(hWnd);
    1442   ULONG ulNewID;
    1443 
    1444   if (hwndRelay == NULL) // already initialized ?
    1445     hwndRelay = RelayInitialize(hwndOS2);
    1446 
    1447   // add entry to list, we need to store both our temp buffer and the apps buffer
    1448   ulNewID = RelayAlloc(hWnd,
    1449                        wMsg,
    1450                        ASYNCREQUEST_GETHOSTBYADDR,
    1451                        FALSE,
    1452                        buf);
    1453 
    1454   // call pmwsock function, will fill our temp buffer
    1455   rc = WSAAsyncGetHostByAddr(hwndRelay,
    1456                              ulNewID,
    1457                              addr,
    1458                              len,
    1459                              type,
    1460                              buf,
    1461                              buflen);
    1462 
    1463   // if an error occurs, free the allocated relay entry
    1464   if (rc == SOCKET_ERROR)
    1465     RelayFree(ulNewID);
    1466 
    1467   return (rc);
    1468 }
    1469 
    1470 
    1471 /*****************************************************************************
    1472  * Name      :
    1473  * Purpose   :
    1474  * Parameters:
    1475  * Variables :
    1476  * Result    :
    1477  * Remark    :
    1478  * Status    : UNTESTED STUB
    1479  *
    1480  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1481  *****************************************************************************/
    1482 
    1483 ODINFUNCTION1(int,OS2WSACancelAsyncRequest,
    1484               LHANDLE,hAsyncTaskHandle)
    1485 {
    1486   return(WSACancelAsyncRequest(hAsyncTaskHandle));
    1487 }
    1488 
    1489 
    1490 /*****************************************************************************
    1491  * Name      :
    1492  * Purpose   :
    1493  * Parameters:
    1494  * Variables :
    1495  * Result    :
    1496  * Remark    :
    1497  * Status    : UNTESTED STUB
    1498  *
    1499  * Author    : Patrick Haller [Thu, 1999/11/25 23:00]
    1500  *****************************************************************************/
    1501 
    1502 ODINFUNCTION4(int,OS2WSAAsyncSelect,
    1503               SOCKET,s,
    1504               HWND,hWnd,
    1505               u_int,wMsg,
    1506               long,lEvent)
    1507 {
    1508   int   rc;
    1509 //  int   iError;
    1510   HWND  hwndOS2 = Win32ToOS2Handle(hWnd);
    1511   ULONG ulNewID;
    1512 
    1513   if (hwndRelay == NULL) // already initialized ?
    1514     hwndRelay = RelayInitialize(hwndOS2);
    1515 
    1516   /* @@@PH: our source window doesn't seem to have an anchor block.
    1517             Docs suggest we've missed to call WinInitialize on the
    1518             caller thread.
    1519 
    1520             Cause however is the Open32 handle is (of course!) invalid
    1521             in plain PM Window Manager! -> use DAPWSOCK
    1522 
    1523             Unfortunately, DAPWSOCK calls WinQueryAnchorBlock(hOpen32), too.
    1524             So, we're stuck until I resolve hWnd to it's valid PM
    1525             counterpart.
    1526 
    1527             new problem: we've ultimately got to use PostMessageA instead
    1528             anything else. => create invisible msg relay window:
    1529             - hMsg = registerMessage(hWnd, wMsg)
    1530             - call WSAAsyncSelect with object window handle
    1531             - overwrite hWnd relay for "same handles"
    1532    */
    1533 
    1534   // add event to list or remove any list entry in case of WSAAsyncSelect(hwnd,0,0)
    1535   if ( (wMsg == 0) && (lEvent == 0) )
    1536   {
    1537     // remove entry from list
    1538     RelayFreeByHwnd(hWnd);
    1539   }
    1540   else
    1541     // add entry to list
    1542     ulNewID = RelayAlloc(hWnd,
    1543                          wMsg,
    1544                          ASYNCREQUEST_SELECT,
    1545                          FALSE); //SvL: allow multiple selects -> pmwsock should fail if it not allowed
    1546 //                         TRUE);
    1547 
    1548   rc = WSAAsyncSelect(s,
    1549                       hwndRelay,
    1550                       ulNewID,
    1551                       lEvent);
    1552 
    1553   // if an error occurs, free the allocated relay entry
    1554   if (rc == SOCKET_ERROR)
    1555     RelayFree(ulNewID);
    1556 
    1557   return (rc);
    1558 }
     1151    LPWSINFO pwsi = WINSOCK_GetIData();
     1152
     1153    if( pwsi )
     1154    {
     1155        struct protoent * proto;
     1156        if( (proto = getprotobyname((char *)name)) != NULL ) {
     1157                if(WS_dup_pe(pwsi, proto)) {
     1158                        WSASetLastError(NO_ERROR);
     1159                        return pwsi->pe;
     1160                }
     1161                else    WSASetLastError(WSAENOBUFS);
     1162        }
     1163        else    WSASetLastError((h_errno < 0) ? wsaErrno() : wsaHerrno());
     1164    }
     1165    else WSASetLastError(WSANOTINITIALISED);
     1166    return NULL;
     1167}
     1168//******************************************************************************
     1169//******************************************************************************
Note: See TracChangeset for help on using the changeset viewer.