Fill WSAPROTOCOL_INFO structures instead of PROTOCOL_INFO structures.

Implement WSCEnumProtocols().
Add some tests.
This commit is contained in:
Hans Leidekker 2004-11-01 23:18:47 +00:00 committed by Alexandre Julliard
parent d3eb0550f5
commit bec06ad777
6 changed files with 422 additions and 197 deletions

View File

@ -2,6 +2,7 @@
* Protocol enumeration functions
*
* Copyright (C) 2001 Stefan Leichter
* Copyright (C) 2004 Hans Leidekker
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@ -46,166 +47,273 @@
WINE_DEFAULT_DEBUG_CHANNEL(winsock);
/* name of the protocols
*/
static const WCHAR NameIpx[] = {'I', 'P', 'X', '\0'};
static const WCHAR NameSpx[] = {'S', 'P', 'X', '\0'};
static const WCHAR NameSpxII[] = {'S', 'P', 'X', ' ', 'I', 'I', '\0'};
static const WCHAR NameTcp[] = {'T', 'C', 'P', '/', 'I', 'P', '\0'};
static const WCHAR NameUdp[] = {'U', 'D', 'P', '/', 'I', 'P', '\0'};
/* names of the protocols */
static const CHAR NameIpx[] = "IPX";
static const CHAR NameSpx[] = "SPX";
static const CHAR NameSpxII[] = "SPX II";
static const CHAR NameTcp[] = "TCP/IP";
static const CHAR NameUdp[] = "UDP/IP";
static const WCHAR NameIpxW[] = {'I', 'P', 'X', '\0'};
static const WCHAR NameSpxW[] = {'S', 'P', 'X', '\0'};
static const WCHAR NameSpxIIW[] = {'S', 'P', 'X', ' ', 'I', 'I', '\0'};
static const WCHAR NameTcpW[] = {'T', 'C', 'P', '/', 'I', 'P', '\0'};
static const WCHAR NameUdpW[] = {'U', 'D', 'P', '/', 'I', 'P', '\0'};
/* Taken from Win2k */
GUID ProviderId = { 0xe70f1aa0, 0xab8b, 0x11cf, { 0x8c, 0xa3, 0x00, 0x80, 0x5f, 0x48, 0xa1, 0x92 } };
/*****************************************************************************
* WINSOCK_EnterSingleProtocol [internal]
* WINSOCK_EnterSingleProtocolW [internal]
*
* enters the protocol informations of one given protocol into the
* given buffer. If the given buffer is too small only the required size for
* the protocols are returned.
* enters the protocol information of one given protocol into the given
* buffer.
*
* RETURNS
* The number of protocols entered into the buffer
* 1 if a protocol was entered into the buffer.
* SOCKET_ERROR otherwise.
*
* BUGS
* - only implemented for IPX, SPX, SPXII, TCP, UDP
* - there is no check that the operating system supports the returned
* protocols
*/
static INT WINSOCK_EnterSingleProtocol( INT iProtocol, PROTOCOL_INFOA* lpBuffer,
LPDWORD lpSize, BOOL unicode )
static INT WINSOCK_EnterSingleProtocolW( INT protocol, WSAPROTOCOL_INFOW* info )
{
DWORD dwLength = 0, dwOldSize = *lpSize;
INT iAnz = 1;
const WCHAR* lpProtName = NULL;
memset( info, 0, sizeof(WSAPROTOCOL_INFOW) );
info->iProtocol = protocol;
*lpSize = sizeof( PROTOCOL_INFOA);
switch (iProtocol) {
switch (protocol)
{
case WS_IPPROTO_TCP:
dwLength = (unicode) ? sizeof(WCHAR) * (strlenW(NameTcp)+1) :
WideCharToMultiByte( CP_ACP, 0, NameTcp, -1,
NULL, 0, NULL, NULL);
info->dwServiceFlags1 = XP1_PARTIAL_MESSAGE | XP1_EXPEDITED_DATA |
XP1_GRACEFUL_CLOSE | XP1_GUARANTEED_ORDER |
XP1_GUARANTEED_DELIVERY;
memcpy( &info->ProviderId, &ProviderId, sizeof(GUID) );
info->dwCatalogEntryId = 0x3e9;
info->ProtocolChain.ChainLen = 1;
info->iVersion = 2;
info->iAddressFamily = WS_AF_INET;
info->iMaxSockAddr = 0x10;
info->iMinSockAddr = 0x10;
info->iSocketType = WS_SOCK_STREAM;
strcpyW( info->szProtocol, NameTcpW );
break;
case WS_IPPROTO_UDP:
dwLength = (unicode) ? sizeof(WCHAR) * (strlenW(NameUdp)+1) :
WideCharToMultiByte( CP_ACP, 0, NameUdp, -1,
NULL, 0, NULL, NULL);
info->dwServiceFlags1 = XP1_PARTIAL_MESSAGE | XP1_SUPPORT_BROADCAST |
XP1_SUPPORT_MULTIPOINT | XP1_MESSAGE_ORIENTED |
XP1_CONNECTIONLESS;
memcpy( &info->ProviderId, &ProviderId, sizeof(GUID) );
info->dwCatalogEntryId = 0x3ea;
info->ProtocolChain.ChainLen = 1;
info->iVersion = 2;
info->iAddressFamily = WS_AF_INET;
info->iMaxSockAddr = 0x10;
info->iMinSockAddr = 0x10;
info->iSocketType = WS_SOCK_DGRAM;
info->dwMessageSize = 0xffbb;
strcpyW( info->szProtocol, NameUdpW );
break;
case NSPROTO_IPX:
dwLength = (unicode) ? sizeof(WCHAR) * (strlenW(NameIpx)+1) :
WideCharToMultiByte( CP_ACP, 0, NameIpx, -1,
NULL, 0, NULL, NULL);
info->dwServiceFlags1 = XP1_PARTIAL_MESSAGE | XP1_SUPPORT_BROADCAST |
XP1_SUPPORT_MULTIPOINT | XP1_MESSAGE_ORIENTED |
XP1_CONNECTIONLESS;
info->iAddressFamily = WS_AF_IPX;
info->iMaxSockAddr = 0x10;
info->iMinSockAddr = 0x0e;
info->iSocketType = WS_SOCK_DGRAM;
info->dwMessageSize = 576;
strcpyW( info->szProtocol, NameIpxW );
break;
case NSPROTO_SPX:
dwLength = (unicode) ? sizeof(WCHAR) * (strlenW(NameSpx)+1) :
WideCharToMultiByte( CP_ACP, 0, NameSpx, -1,
NULL, 0, NULL, NULL);
info->dwServiceFlags1 = XP1_PARTIAL_MESSAGE |
XP1_PSEUDO_STREAM | XP1_MESSAGE_ORIENTED |
XP1_GUARANTEED_ORDER | XP1_GUARANTEED_DELIVERY;
info->iAddressFamily = WS_AF_IPX;
info->iMaxSockAddr = 0x10;
info->iMinSockAddr = 0x0e;
info->iSocketType = 5;
info->dwMessageSize = -1;
strcpyW( info->szProtocol, NameSpxW );
break;
case NSPROTO_SPXII:
dwLength = (unicode) ? sizeof(WCHAR) * (strlenW(NameSpxII)+1) :
WideCharToMultiByte( CP_ACP, 0, NameSpxII, -1,
NULL, 0, NULL, NULL);
info->dwServiceFlags1 = XP1_PARTIAL_MESSAGE | XP1_GRACEFUL_CLOSE |
XP1_PSEUDO_STREAM | XP1_MESSAGE_ORIENTED |
XP1_GUARANTEED_ORDER | XP1_GUARANTEED_DELIVERY;
info->iAddressFamily = WS_AF_IPX;
info->iMaxSockAddr = 0x10;
info->iMinSockAddr = 0x0e;
info->iSocketType = 5;
info->dwMessageSize = -1;
strcpyW( info->szProtocol, NameSpxIIW );
break;
default:
*lpSize = 0;
if ((iProtocol == ISOPROTO_TP4) || (iProtocol == NSPROTO_SPX))
if ((protocol == ISOPROTO_TP4) || (protocol == NSPROTO_SPX))
FIXME("Protocol <%s> not implemented\n",
(iProtocol == ISOPROTO_TP4) ? "ISOPROTO_TP4" : "NSPROTO_SPX");
(protocol == ISOPROTO_TP4) ? "ISOPROTO_TP4" : "NSPROTO_SPX");
else
FIXME("unknown Protocol <0x%08x>\n", iProtocol);
break;
FIXME("unknown Protocol <0x%08x>\n", protocol);
return SOCKET_ERROR;
}
*lpSize += dwLength;
if ( !lpBuffer || !*lpSize || (*lpSize > dwOldSize))
return 0;
memset( lpBuffer, 0, dwOldSize);
lpBuffer->lpProtocol = (LPSTR) &lpBuffer[ iAnz];
lpBuffer->iProtocol = iProtocol;
switch (iProtocol) {
case WS_IPPROTO_TCP :
lpBuffer->dwServiceFlags = XP_FRAGMENTATION | XP_EXPEDITED_DATA |
XP_GRACEFUL_CLOSE | XP_GUARANTEED_ORDER |
XP_GUARANTEED_DELIVERY;
lpBuffer->iAddressFamily = WS_AF_INET;
lpBuffer->iMaxSockAddr = 0x10; /* NT4 SP5 */
lpBuffer->iMinSockAddr = 0x10; /* NT4 SP5 */
lpBuffer->iSocketType = WS_SOCK_STREAM;
lpBuffer->dwMessageSize = 0;
lpProtName = NameTcp;
break;
case WS_IPPROTO_UDP :
lpBuffer->dwServiceFlags = XP_FRAGMENTATION | XP_SUPPORTS_BROADCAST |
XP_SUPPORTS_MULTICAST | XP_MESSAGE_ORIENTED |
XP_CONNECTIONLESS;
lpBuffer->iAddressFamily = WS_AF_INET;
lpBuffer->iMaxSockAddr = 0x10; /* NT4 SP5 */
lpBuffer->iMinSockAddr = 0x10; /* NT4 SP5 */
lpBuffer->iSocketType = WS_SOCK_DGRAM;
lpBuffer->dwMessageSize = 65457; /* NT4 SP5 */
lpProtName = NameUdp;
break;
case NSPROTO_IPX :
lpBuffer->dwServiceFlags = XP_FRAGMENTATION | XP_SUPPORTS_BROADCAST |
XP_SUPPORTS_MULTICAST | XP_MESSAGE_ORIENTED |
XP_CONNECTIONLESS;
lpBuffer->iAddressFamily = WS_AF_IPX;
lpBuffer->iMaxSockAddr = 0x10; /* NT4 SP5 */
lpBuffer->iMinSockAddr = 0x0e; /* NT4 SP5 */
lpBuffer->iSocketType = WS_SOCK_DGRAM;
lpBuffer->dwMessageSize = 576; /* NT4 SP5 */
lpProtName = NameIpx;
break;
case NSPROTO_SPX :
lpBuffer->dwServiceFlags = XP_FRAGMENTATION |
XP_PSEUDO_STREAM | XP_MESSAGE_ORIENTED |
XP_GUARANTEED_ORDER | XP_GUARANTEED_DELIVERY;
lpBuffer->iAddressFamily = WS_AF_IPX;
lpBuffer->iMaxSockAddr = 0x10; /* NT4 SP5 */
lpBuffer->iMinSockAddr = 0x0e; /* NT4 SP5 */
lpBuffer->iSocketType = 5;
lpBuffer->dwMessageSize = -1; /* NT4 SP5 */
lpProtName = NameSpx;
break;
case NSPROTO_SPXII :
lpBuffer->dwServiceFlags = XP_FRAGMENTATION | XP_GRACEFUL_CLOSE |
XP_PSEUDO_STREAM | XP_MESSAGE_ORIENTED |
XP_GUARANTEED_ORDER | XP_GUARANTEED_DELIVERY;
lpBuffer->iAddressFamily = WS_AF_IPX;
lpBuffer->iMaxSockAddr = 0x10; /* NT4 SP5 */
lpBuffer->iMinSockAddr = 0x0e; /* NT4 SP5 */
lpBuffer->iSocketType = 5;
lpBuffer->dwMessageSize = -1; /* NT4 SP5 */
lpProtName = NameSpxII;
break;
}
if (unicode)
strcpyW( (LPWSTR)lpBuffer->lpProtocol, lpProtName);
else
WideCharToMultiByte( CP_ACP, 0, lpProtName, -1, lpBuffer->lpProtocol,
dwOldSize - iAnz * sizeof( PROTOCOL_INFOA), NULL, NULL);
return iAnz;
return 1;
}
/*****************************************************************************
* WINSOCK_EnumProtocol [internal]
* WINSOCK_EnterSingleProtocolA [internal]
*
* Enters the information about installed protocols into a given buffer
* see function WINSOCK_EnterSingleProtocolW
*
*/
static INT WINSOCK_EnterSingleProtocolA( INT protocol, WSAPROTOCOL_INFOA* info )
{
memset( info, 0, sizeof(WSAPROTOCOL_INFOA) );
info->iProtocol = protocol;
switch (protocol)
{
case WS_IPPROTO_TCP:
info->dwServiceFlags1 = XP1_IFS_HANDLES | XP1_EXPEDITED_DATA |
XP1_GRACEFUL_CLOSE | XP1_GUARANTEED_ORDER |
XP1_GUARANTEED_DELIVERY;
memcpy( &info->ProviderId, &ProviderId, sizeof(GUID) );
info->dwCatalogEntryId = 0x3e9;
info->ProtocolChain.ChainLen = 1;
info->iVersion = 2;
info->iAddressFamily = WS_AF_INET;
info->iMaxSockAddr = 0x10;
info->iMinSockAddr = 0x10;
info->iSocketType = WS_SOCK_STREAM;
strcpy( info->szProtocol, NameTcp );
break;
case WS_IPPROTO_UDP:
info->dwServiceFlags1 = XP1_IFS_HANDLES | XP1_SUPPORT_BROADCAST |
XP1_SUPPORT_MULTIPOINT | XP1_MESSAGE_ORIENTED |
XP1_CONNECTIONLESS;
memcpy( &info->ProviderId, &ProviderId, sizeof(GUID) );
info->dwCatalogEntryId = 0x3ea;
info->ProtocolChain.ChainLen = 1;
info->iVersion = 2;
info->iAddressFamily = WS_AF_INET;
info->iMaxSockAddr = 0x10;
info->iMinSockAddr = 0x10;
info->iSocketType = WS_SOCK_DGRAM;
info->dwMessageSize = 0xffbb;
strcpy( info->szProtocol, NameUdp );
break;
case NSPROTO_IPX:
info->dwServiceFlags1 = XP1_PARTIAL_MESSAGE | XP1_SUPPORT_BROADCAST |
XP1_SUPPORT_MULTIPOINT | XP1_MESSAGE_ORIENTED |
XP1_CONNECTIONLESS;
info->iAddressFamily = WS_AF_IPX;
info->iMaxSockAddr = 0x10;
info->iMinSockAddr = 0x0e;
info->iSocketType = WS_SOCK_DGRAM;
info->dwMessageSize = 576;
strcpy( info->szProtocol, NameIpx );
break;
case NSPROTO_SPX:
info->dwServiceFlags1 = XP1_PARTIAL_MESSAGE |
XP1_PSEUDO_STREAM | XP1_MESSAGE_ORIENTED |
XP1_GUARANTEED_ORDER | XP1_GUARANTEED_DELIVERY;
info->iAddressFamily = WS_AF_IPX;
info->iMaxSockAddr = 0x10;
info->iMinSockAddr = 0x0e;
info->iSocketType = 5;
info->dwMessageSize = -1;
strcpy( info->szProtocol, NameSpx );
break;
case NSPROTO_SPXII:
info->dwServiceFlags1 = XP1_PARTIAL_MESSAGE | XP1_GRACEFUL_CLOSE |
XP1_PSEUDO_STREAM | XP1_MESSAGE_ORIENTED |
XP1_GUARANTEED_ORDER | XP1_GUARANTEED_DELIVERY;
info->iAddressFamily = WS_AF_IPX;
info->iMaxSockAddr = 0x10;
info->iMinSockAddr = 0x0e;
info->iSocketType = 5;
info->dwMessageSize = -1;
strcpy( info->szProtocol, NameSpxII );
break;
default:
if ((protocol == ISOPROTO_TP4) || (protocol == NSPROTO_SPX))
FIXME("Protocol <%s> not implemented\n",
(protocol == ISOPROTO_TP4) ? "ISOPROTO_TP4" : "NSPROTO_SPX");
else
FIXME("unknown Protocol <0x%08x>\n", protocol);
return SOCKET_ERROR;
}
return 1;
}
/*****************************************************************************
* WSAEnumProtocolsA [WS2_32.@]
*
* see function WSAEnumProtocolsW
*/
INT WINAPI WSAEnumProtocolsA( LPINT protocols, LPWSAPROTOCOL_INFOA buffer, LPDWORD len )
{
INT i = 0;
DWORD size = 0;
INT local[] = { WS_IPPROTO_TCP, WS_IPPROTO_UDP, NSPROTO_IPX, NSPROTO_SPXII, 0 };
if (!buffer)
return SOCKET_ERROR;
if (!protocols) protocols = local;
while (protocols[i]) i++;
size = i * sizeof(WSAPROTOCOL_INFOA);
if (*len < size)
{
*len = size;
return SOCKET_ERROR;
}
for (i = 0; protocols[i]; i++)
{
if (WINSOCK_EnterSingleProtocolA( protocols[i], &buffer[i] ) == SOCKET_ERROR)
return i;
}
return i;
}
/*****************************************************************************
* WSAEnumProtocolsW [WS2_32.@]
*
* Retrieves information about specified set of active network protocols.
*
* PARAMS
* protocols [I] Pointer to null-terminated array of protocol id's. NULL
* retrieves information on all available protocols.
* buffer [I] Pointer to a buffer to be filled with WSAPROTOCOL_INFO
* structures.
* len [I/O] Pointer to a variable specifying buffer size. On output
* the variable holds the number of bytes needed when the
* specified size is too small.
*
* RETURNS
* SOCKET_ERROR if the buffer is to small for the requested protocol infos
* on success the number of protocols inside the buffer
* Success: number of WSAPROTOCOL_INFO structures in buffer.
* Failure: SOCKET_ERROR
*
* NOTE
* NOTES
* NT4SP5 does not return SPX if lpiProtocols == NULL
*
* BUGS
* - NT4SP5 returns in addition these list of NETBIOS protocols
* (address family 17), each entry two times one for socket type 2 and 5
*
* iProtocol lpProtocol
* iProtocol szProtocol
* 0x80000000 \Device\NwlnkNb
* 0xfffffffa \Device\NetBT_CBENT7
* 0xfffffffb \Device\Nbf_CBENT7
@ -217,76 +325,57 @@ static INT WINSOCK_EnterSingleProtocol( INT iProtocol, PROTOCOL_INFOA* lpBuffer,
* - there is no check that the operating system supports the returned
* protocols
*/
static INT WINSOCK_EnumProtocol( LPINT lpiProtocols, PROTOCOL_INFOA* lpBuffer,
LPDWORD lpdwLength, BOOL unicode )
INT WINAPI WSAEnumProtocolsW( LPINT protocols, LPWSAPROTOCOL_INFOW buffer, LPDWORD len )
{
DWORD dwCurSize, dwOldSize = *lpdwLength, dwTemp;
INT anz = 0, i;
INT iLocal[] = { WS_IPPROTO_TCP, WS_IPPROTO_UDP, NSPROTO_IPX, NSPROTO_SPXII, 0};
INT i = 0;
DWORD size = 0;
INT local[] = { WS_IPPROTO_TCP, WS_IPPROTO_UDP, NSPROTO_IPX, NSPROTO_SPXII, 0 };
if (!lpiProtocols) lpiProtocols = iLocal;
if (!buffer)
return SOCKET_ERROR;
*lpdwLength = 0;
while ( *lpiProtocols )
if (!protocols) protocols = local;
while (protocols[i]) i++;
size = i * sizeof(WSAPROTOCOL_INFOW);
if (*len < size)
{
dwCurSize = 0;
WINSOCK_EnterSingleProtocol( *lpiProtocols, NULL, &dwCurSize, unicode);
if ( lpBuffer && dwCurSize && ((*lpdwLength + dwCurSize) <= dwOldSize))
{ /* reserve the required space for the current protocol_info after the
* last protocol_info before the start of the string buffer and adjust
* the references into the string buffer
*/
memmove( &((char*)&lpBuffer[ anz])[dwCurSize],
&lpBuffer[ anz],
*lpdwLength - anz * sizeof( PROTOCOL_INFOA));
for (i=0; i < anz; i++)
lpBuffer[i].lpProtocol += dwCurSize;
dwTemp = dwCurSize;
anz += WINSOCK_EnterSingleProtocol( *lpiProtocols, &lpBuffer[anz],
&dwTemp, unicode);
*len = size;
return SOCKET_ERROR;
}
*lpdwLength += dwCurSize;
lpiProtocols++;
for (i = 0; protocols[i]; i++)
{
if (WINSOCK_EnterSingleProtocolW( protocols[i], &buffer[i] ) == SOCKET_ERROR)
return i;
}
if (dwOldSize < *lpdwLength) anz = SOCKET_ERROR;
return anz;
return i;
}
/*****************************************************************************
* WSAEnumProtocolsA [WSOCK32.1111]
*
* Retrieves information about specified set of active network protocols.
* WSCEnumProtocols [WS2_32.@]
*
* PARAMS
* lpiProtocols [I] Pointer to null-terminated array of protocol id's. NULL retrieves
* information on all available protocols.
* lpProtocolBuffer [I] Pointer to a buffer to be filled with PROTOCOL_INFO structures.
* lpdwBufferLength [I/O] Pointer to a variable specifying buffer size. On output the variable
* holds the number of bytes needed when the specified size is too small.
* protocols [I] Null-terminated array of iProtocol values.
* buffer [O] Buffer of WSAPROTOCOL_INFOW structures.
* len [I/O] Size of buffer on input/output.
* errno [O] Error code.
*
* RETURNS
* Success: number of PROTOCOL_INFO structures in buffer.
* Failure: SOCKET_ERROR
* Success: number of protocols to be reported on.
* Failure: SOCKET_ERROR. error is in errno.
*
* BUGS
* Doesn't supply info on layered protocols.
*
* NOTES
* see function WINSOCK_EnumProtocol for BUGS
*/
INT WINAPI WSAEnumProtocolsA( LPINT lpiProtocols, LPWSAPROTOCOL_INFOA lpBuffer, LPDWORD lpdwLength )
INT WINAPI WSCEnumProtocols( LPINT protocols, LPWSAPROTOCOL_INFOW buffer, LPDWORD len, LPINT errno )
{
return WINSOCK_EnumProtocol( lpiProtocols, (PROTOCOL_INFOA *)lpBuffer, lpdwLength, FALSE );
}
INT ret = WSAEnumProtocolsW( protocols, buffer, len );
/*****************************************************************************
* WSAEnumProtocolsW [WSOCK32.1112]
*
* see function WSAEnumProtocolsA
*/
INT WINAPI WSAEnumProtocolsW( LPINT lpiProtocols, LPWSAPROTOCOL_INFOW lpBuffer, LPDWORD lpdwLength )
{
return WINSOCK_EnumProtocol( lpiProtocols, (PROTOCOL_INFOA *)lpBuffer, lpdwLength, TRUE );
if (ret == SOCKET_ERROR) *errno = WSAENOBUFS;
return ret;
}

View File

@ -1,3 +1,4 @@
Makefile
protocol.ok
sock.ok
testlist.c

View File

@ -6,6 +6,7 @@ TESTDLL = ws2_32.dll
IMPORTS = ws2_32
CTESTS = \
protocol.c \
sock.c
@MAKE_TEST_RULES@

View File

@ -0,0 +1,109 @@
/*
* Unit test suite for protocol functions
*
* Copyright 2004 Hans Leidekker
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include <stdarg.h>
#include <windef.h>
#include <winbase.h>
#include <winsock2.h>
#include "wine/test.h"
#include "wine/debug.h"
static void test_WSAEnumProtocolsA()
{
INT ret;
DWORD len = 0;
WSAPROTOCOL_INFOA info, *buffer;
ret = WSAEnumProtocolsA( NULL, NULL, &len );
ok( ret == SOCKET_ERROR, "WSAEnumProtocolsA() succeeded unexpectedly: %d\n",
WSAGetLastError() );
len = 0;
ret = WSAEnumProtocolsA( NULL, &info, &len );
ok( ret == SOCKET_ERROR, "WSAEnumProtocolsA() succeeded unexpectedly: %d\n",
WSAGetLastError() );
buffer = HeapAlloc( GetProcessHeap(), 0, len );
if (buffer)
{
INT i;
ret = WSAEnumProtocolsA( NULL, buffer, &len );
ok( ret != SOCKET_ERROR, "WSAEnumProtocolsA() failed unexpectedly: %d\n",
WSAGetLastError() );
for (i = 0; i < ret; i++)
{
ok( strlen( buffer[i].szProtocol ), "No protocol name found\n" );
}
HeapFree( GetProcessHeap(), 0, buffer );
}
}
static void test_WSAEnumProtocolsW()
{
INT ret;
DWORD len = 0;
WSAPROTOCOL_INFOW info, *buffer;
ret = WSAEnumProtocolsW( NULL, NULL, &len );
ok( ret == SOCKET_ERROR, "WSAEnumProtocolsW() succeeded unexpectedly: %d\n",
WSAGetLastError() );
len = 0;
ret = WSAEnumProtocolsW( NULL, &info, &len );
ok( ret == SOCKET_ERROR, "WSAEnumProtocolsW() succeeded unexpectedly: %d\n",
WSAGetLastError() );
buffer = HeapAlloc( GetProcessHeap(), 0, len );
if (buffer)
{
INT i;
ret = WSAEnumProtocolsW( NULL, buffer, &len );
ok( ret != SOCKET_ERROR, "WSAEnumProtocolsW() failed unexpectedly: %d\n",
WSAGetLastError() );
for (i = 0; i < ret; i++)
{
ok( lstrlenW( buffer[i].szProtocol ), "No protocol name found\n" );
}
HeapFree( GetProcessHeap(), 0, buffer );
}
}
START_TEST( protocol )
{
WSADATA data;
WORD version = MAKEWORD( 2, 2 );
if (WSAStartup( version, &data )) return;
test_WSAEnumProtocolsA();
test_WSAEnumProtocolsW();
}

View File

@ -86,7 +86,7 @@
82 stdcall WSAWaitForMultipleEvents(long ptr long long long) kernel32.WaitForMultipleObjectsEx
83 stdcall WSCDeinstallProvider(ptr ptr)
84 stub WSCEnableNSProvider
85 stub WSCEnumProtocols
85 stdcall WSCEnumProtocols(ptr ptr ptr ptr)
86 stub WSCGetProviderPath
87 stub WSCInstallNameSpace
88 stdcall WSCInstallProvider(ptr wstr ptr long ptr)

View File

@ -176,6 +176,31 @@ typedef struct _WSAPROTOCOLCHAIN
DWORD ChainEntries[MAX_PROTOCOL_CHAIN]; /* a list of dwCatalogEntryIds */
} WSAPROTOCOLCHAIN, * LPWSAPROTOCOLCHAIN;
#define XP1_CONNECTIONLESS 0x00000001
#define XP1_GUARANTEED_DELIVERY 0x00000002
#define XP1_GUARANTEED_ORDER 0x00000004
#define XP1_MESSAGE_ORIENTED 0x00000008
#define XP1_PSEUDO_STREAM 0x00000010
#define XP1_GRACEFUL_CLOSE 0x00000020
#define XP1_EXPEDITED_DATA 0x00000040
#define XP1_CONNECT_DATA 0x00000080
#define XP1_DISCONNECT_DATA 0x00000100
#define XP1_SUPPORT_BROADCAST 0x00000200
#define XP1_SUPPORT_MULTIPOINT 0x00000400
#define XP1_MULTIPOINT_CONTROL_PLANE 0x00000800
#define XP1_MULTIPOINT_DATA_PLANE 0x00001000
#define XP1_QOS_SUPPORTED 0x00002000
#define XP1_INTERRUPT 0x00004000
#define XP1_UNI_SEND 0x00008000
#define XP1_UNI_RECV 0x00010000
#define XP1_IFS_HANDLES 0x00020000
#define XP1_PARTIAL_MESSAGE 0x00040000
#define BIGENDIAN 0x0000
#define LITTLEENDIAN 0x0001
#define SECURITY_PROTOCOL_NONE 0x0000
#define WSAPROTOCOL_LEN 255
typedef struct _WSAPROTOCOL_INFOA
{