Changelog: Peter Hunnisett <peter@transgaming.com> Ove Kaaven <ovek@transgaming.com> - check for sockaddr being NULL. - hackish implementation of WSADuplicateSocket. -- Lionel Ulmer - http://www.bbrox.org/
Index: dlls/winsock/socket.c =================================================================== RCS file: /home/wine/wine/dlls/winsock/socket.c,v retrieving revision 1.97 diff -u -r1.97 socket.c --- dlls/winsock/socket.c 31 May 2002 23:40:57 -0000 1.97 +++ dlls/winsock/socket.c 10 Jun 2002 20:23:27 -0000 @@ -902,11 +902,19 @@ return NULL; } -/* allocates a Unix sockaddr structure to receive the data */ +/* Allocates a Unix sockaddr structure to receive the data */ inline struct sockaddr* ws_sockaddr_alloc(const struct WS_sockaddr* wsaddr, int* wsaddrlen, int* uaddrlen) { if (wsaddr==NULL) - return NULL; + { + ERR( "WINE shouldn't pass a NULL wsaddr! Attempting to continue\n" ); + + /* This is not strictly the right thing to do. Hope it works however */ + *uaddrlen=0; + + return NULL; + } + if (*wsaddrlen==0) *uaddrlen=0; else @@ -1640,12 +1648,21 @@ */ int WINAPI WS_getpeername(SOCKET s, struct WS_sockaddr *name, int *namelen) { - int fd = _get_sock_fd(s); + int fd; int res; TRACE("socket: %04x, ptr %p, len %8x\n", s, name, *namelen); - res=SOCKET_ERROR; + /* Check if what we've received is valid. Should we use IsBadReadPtr? */ + if( (name == NULL) || (namelen == NULL) ) + { + SetLastError( WSAEFAULT ); + return SOCKET_ERROR; + } + + fd = _get_sock_fd(s); + res = SOCKET_ERROR; + if (fd != -1) { struct sockaddr* uaddr; @@ -1697,12 +1714,21 @@ */ int WINAPI WS_getsockname(SOCKET s, struct WS_sockaddr *name, int *namelen) { - int fd = _get_sock_fd(s); + int fd; int res; TRACE("socket: %04x, ptr %p, len %8x\n", s, name, *namelen); - res=SOCKET_ERROR; + /* Check if what we've received is valid. Should we use IsBadReadPtr? */ + if( (name == NULL) || (namelen == NULL) ) + { + SetLastError( WSAEFAULT ); + return SOCKET_ERROR; + } + + fd = _get_sock_fd(s); + res = SOCKET_ERROR; + if (fd != -1) { struct sockaddr* uaddr; @@ -3337,6 +3363,13 @@ TRACE("af=%d type=%d protocol=%d protocol_info=%p group=%d flags=0x%lx\n", af, type, protocol, lpProtocolInfo, g, dwFlags ); + /* hack for WSADuplicateSocket */ + if (lpProtocolInfo && lpProtocolInfo->dwServiceFlags4 == 0xff00ff00) { + ret = lpProtocolInfo->dwCatalogEntryId; + TRACE("\tgot duplicate %04x\n", ret); + return ret; + } + /* check the socket family */ switch(af) { @@ -4072,4 +4105,25 @@ return 0; } +/*********************************************************************** + * WSADuplicateSocketA (WS2_32.32) + */ +int WINAPI WSADuplicateSocketA( SOCKET s, DWORD dwProcessId, LPWSAPROTOCOL_INFOA lpProtocolInfo ) +{ + HANDLE hProcess; + TRACE("(%d,%lx,%p)\n", s, dwProcessId, lpProtocolInfo); + memset(lpProtocolInfo, 0, sizeof(*lpProtocolInfo)); + /* FIXME: WS_getsockopt(s, WS_SOL_SOCKET, SO_PROTOCOL_INFO, lpProtocolInfo, sizeof(*lpProtocolInfo)); */ + /* I don't know what the real Windoze does next, this is a hack */ + /* ...we could duplicate and then use ConvertToGlobalHandle on the duplicate, then let + * the target use the global duplicate, or we could copy a reference to us to the structure + * and let the target duplicate it from us, but let's do it as simple as possible */ + hProcess = OpenProcess(PROCESS_DUP_HANDLE, FALSE, dwProcessId); + DuplicateHandle(GetCurrentProcess(), s, + hProcess, (LPHANDLE)&lpProtocolInfo->dwCatalogEntryId, + 0, FALSE, DUPLICATE_SAME_ACCESS); + CloseHandle(hProcess); + lpProtocolInfo->dwServiceFlags4 = 0xff00ff00; /* magic */ + return 0; +} Index: dlls/winsock/ws2_32.spec =================================================================== RCS file: /home/wine/wine/dlls/winsock/ws2_32.spec,v retrieving revision 1.23 diff -u -r1.23 ws2_32.spec --- dlls/winsock/ws2_32.spec 1 Jun 2002 02:55:51 -0000 1.23 +++ dlls/winsock/ws2_32.spec 10 Jun 2002 20:23:27 -0000 @@ -37,7 +37,7 @@ 29 stdcall WSACloseEvent(long) WSACloseEvent 30 stdcall WSAConnect(long ptr long ptr ptr ptr ptr) WSAConnect 31 stdcall WSACreateEvent () WSACreateEvent -32 stub WSADuplicateSocketA +32 stdcall WSADuplicateSocketA(long long ptr) WSADuplicateSocketA 33 stub WSADuplicateSocketW 34 stub WSAEnumNameSpaceProvidersA 35 stub WSAEnumNameSpaceProvidersW