diff --git a/dlls/winsock/socket.c b/dlls/winsock/socket.c index f7ca20cf8c7..3d3ec3dac13 100644 --- a/dlls/winsock/socket.c +++ b/dlls/winsock/socket.c @@ -3470,3 +3470,63 @@ INT WINAPI WSCDeinstallProvider(LPGUID lpProviderId, LPINT lpErrno) *lpErrno = 0; return 0; } + + +SOCKET WINAPI WSAAccept( SOCKET s, struct WS_sockaddr *addr, LPINT addrlen, + LPCONDITIONPROC lpfnCondition, DWORD dwCallbackData) +{ + + int ret = 0, size = 0; + WSABUF CallerId, CallerData, CalleeId, CalleeData; + /* QOS SQOS, GQOS; */ + GROUP g; + SOCKET cs; + SOCKADDR s_addr, d_addr; + + TRACE("Socket %ui, sockaddr %p, addrlen %p, fnCondition %p, dwCallbackD ata %ld\n", + s, addr, addrlen, lpfnCondition, dwCallbackData); + + + size = sizeof(s_addr); + cs = WS_accept(s, &s_addr, &size); + + if (cs == SOCKET_ERROR) return SOCKET_ERROR; + + CallerId.buf = (char *)&s_addr; + CallerId.len = sizeof(s_addr); + + CallerData.buf = NULL; + CallerData.len = (ULONG)NULL; + + WS_getsockname(cs, &d_addr, &size); + + CalleeId.buf = (char *)&d_addr; + CalleeId.len = sizeof(d_addr); + + + ret = (*lpfnCondition)(&CallerId, &CallerData, NULL, NULL, + &CalleeId, &CalleeData, &g, dwCallbackData); + + switch (ret) + { + case CF_ACCEPT: + if (addr && addrlen) + addr = memcpy(addr, &s_addr, (*addrlen > size) ? size : *addrlen ); + return cs; + case CF_DEFER: + SetLastError(WSATRY_AGAIN); + return SOCKET_ERROR; + case CF_REJECT: + WS_closesocket(cs); + SetLastError(WSAECONNREFUSED); + return SOCKET_ERROR; + default: + FIXME("Unknown return type from Condition function\n"); + SetLastError(WSAENOTSOCK); + return SOCKET_ERROR; + } + + SetLastError(WSAENOTSOCK); + return SOCKET_ERROR; +} + diff --git a/dlls/winsock/ws2_32.spec b/dlls/winsock/ws2_32.spec index 8958ea7f4df..7946a4f55b8 100644 --- a/dlls/winsock/ws2_32.spec +++ b/dlls/winsock/ws2_32.spec @@ -38,7 +38,7 @@ debug_channels (winsock) 23 stdcall socket(long long long) WS_socket 24 stdcall WSApSetPostRoutine(ptr) WSApSetPostRoutine 25 stub WPUCompleteOverlappedRequest -26 stub WSAAccept +26 stdcall WSAAccept(long ptr ptr ptr long) WSAAccept 27 stub WSAAddressToStringA 28 stub WSAAddressToStringW 29 stdcall WSACloseEvent(long) WSACloseEvent diff --git a/include/winsock2.h b/include/winsock2.h index 4ee62425dc0..360151d1848 100644 --- a/include/winsock2.h +++ b/include/winsock2.h @@ -226,8 +226,28 @@ typedef unsigned int GROUP; #define SG_UNCONSTRAINED_GROUP 0x01 #define SG_CONSTRAINED_GROUP 0x02 -/* FIXME: We don't yet have qos.h */ -typedef DWORD QOS, *LPQOS; +/* + * FLOWSPEC and SERVICETYPE should eventually move to qos.h + */ + +typedef ULONG SERVICETYPE; + +typedef struct _FLOWSPEC { + unsigned int TokenRate; + unsigned int TokenBucketSize; + unsigned int PeakBandwidth; + unsigned int Latency; + unsigned int DelayVariation; + SERVICETYPE ServiceType; + unsigned int MaxSduSize; + unsigned int MinimumPolicedSize; + } FLOWSPEC, *PFLOWSPEC, *LPFLOWSPEC; + +typedef struct _QUALITYOFSERVICE { + FLOWSPEC SendingFlowspec; + FLOWSPEC ReceivingFlowspec; + WSABUF ProviderSpecific; + } QOS, *LPQOS; typedef int CALLBACK (*LPCONDITIONPROC) ( @@ -440,6 +460,11 @@ typedef DWORD (WINAPI *LPFN_WSAWAITFORMULTIPLEEVENTS)(DWORD,const WSAEVENT*,BOOL #endif /* WS_API_TYPEDEFS */ +/* Condition function return values */ +#define CF_ACCEPT 0x0000 +#define CF_REJECT 0x0001 +#define CF_DEFER 0x0002 + #include "poppack.h" #ifdef __cplusplus