mirror of
https://github.com/reactos/reactos.git
synced 2025-01-03 21:09:19 +00:00
[WS2_32_APITESTS] Add tests for SIO_GET_INTERFACE_LIST. Brought to you by Andreas Maier. Thanks.
Minor modifications by me on comparison and expected flags. ROSTESTS-246 svn path=/trunk/; revision=73011
This commit is contained in:
parent
3315eae709
commit
08744dfc42
3 changed files with 236 additions and 1 deletions
|
@ -9,6 +9,7 @@ list(APPEND SOURCE
|
|||
nostartup.c
|
||||
recv.c
|
||||
send.c
|
||||
WSAIoctl.c
|
||||
WSARecv.c
|
||||
WSAStartup.c
|
||||
testlist.c)
|
||||
|
@ -16,5 +17,5 @@ list(APPEND SOURCE
|
|||
add_executable(ws2_32_apitest ${SOURCE})
|
||||
target_link_libraries(ws2_32_apitest wine ${PSEH_LIB})
|
||||
set_module_type(ws2_32_apitest win32cui)
|
||||
add_importlibs(ws2_32_apitest ws2_32 msvcrt kernel32 ntdll)
|
||||
add_importlibs(ws2_32_apitest ws2_32 msvcrt iphlpapi kernel32 ntdll)
|
||||
add_cd_file(TARGET ws2_32_apitest DESTINATION reactos/bin FOR all)
|
||||
|
|
232
rostests/apitests/ws2_32/WSAIoctl.c
Normal file
232
rostests/apitests/ws2_32/WSAIoctl.c
Normal file
|
@ -0,0 +1,232 @@
|
|||
/*
|
||||
* PROJECT: ReactOS api tests
|
||||
* LICENSE: GPL - See COPYING in the top level directory
|
||||
* PURPOSE: Test for WSHIoctl:
|
||||
* - SIO_GET_INTERFACE_LIST
|
||||
* PROGRAMMERS: Andreas Maier
|
||||
*/
|
||||
|
||||
#include <apitest.h>
|
||||
|
||||
#include <stdio.h>
|
||||
#include "ws2tcpip.h"
|
||||
#include "iphlpapi.h"
|
||||
|
||||
void traceaddr(char* txt, sockaddr_gen a)
|
||||
{
|
||||
trace(" %s.AddressIn.sin_family %x\n", txt, a.AddressIn.sin_family);
|
||||
trace(" %s.AddressIn.sin_port %x\n", txt, a.AddressIn.sin_port);
|
||||
trace(" %s.AddressIn.sin_addr.s_addr %lx\n", txt, a.AddressIn.sin_addr.s_addr);
|
||||
}
|
||||
|
||||
BOOL Test_WSAIoctl_InitTest(
|
||||
OUT PMIB_IPADDRTABLE* ppTable)
|
||||
{
|
||||
PMIB_IPADDRROW pRow;
|
||||
DWORD ret, i1;
|
||||
ULONG TableSize;
|
||||
PMIB_IPADDRTABLE pTable;
|
||||
|
||||
TableSize = 0;
|
||||
*ppTable = NULL;
|
||||
ret = GetIpAddrTable(NULL, &TableSize, FALSE);
|
||||
if (ret != ERROR_INSUFFICIENT_BUFFER)
|
||||
{
|
||||
skip("GetIpAddrTable failed with %ld. Abort Testing.\n", ret);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* get sorted ip-address table. Sort order is the ip-address. */
|
||||
pTable = (PMIB_IPADDRTABLE)malloc(TableSize);
|
||||
*ppTable = pTable;
|
||||
ret = GetIpAddrTable(pTable, &TableSize, TRUE);
|
||||
if (ret != NO_ERROR)
|
||||
{
|
||||
skip("GetIpAddrTable failed with %ld. Abort Testing.\n", ret);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (winetest_debug >= 2)
|
||||
{
|
||||
trace("Result of GetIpAddrTable:\n");
|
||||
trace("Count: %ld\n", pTable->dwNumEntries);
|
||||
pRow = pTable->table;
|
||||
for (i1 = 0; i1 < pTable->dwNumEntries; i1++)
|
||||
{
|
||||
trace("** Entry %ld **\n", i1);
|
||||
trace(" dwAddr %lx\n", pRow->dwAddr);
|
||||
trace(" dwIndex %lx\n", pRow->dwIndex);
|
||||
trace(" dwMask %lx\n", pRow->dwMask);
|
||||
trace(" dwBCastAddr %lx\n", pRow->dwBCastAddr);
|
||||
trace(" dwReasmSize %lx\n", pRow->dwReasmSize);
|
||||
trace(" wType %x\n", pRow->wType);
|
||||
pRow++;
|
||||
}
|
||||
trace("END\n");
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void Test_WSAIoctl_GetInterfaceList()
|
||||
{
|
||||
WSADATA wdata;
|
||||
INT iResult;
|
||||
SOCKET sck;
|
||||
ULONG buflen, BytesReturned, BCastAddr;
|
||||
ULONG infoCount, i1, j1, iiFlagsExpected;
|
||||
BYTE* buf = NULL;
|
||||
LPINTERFACE_INFO ifInfo;
|
||||
PMIB_IPADDRTABLE pTable = NULL;
|
||||
PMIB_IPADDRROW pRow;
|
||||
|
||||
/* Get PMIB_IPADDRTABE - these results we should get from wshtcpip.dll too. */
|
||||
/* pTable is allocated by Test_WSAIoctl_InitTest! */
|
||||
if (!Test_WSAIoctl_InitTest(&pTable))
|
||||
goto cleanup;
|
||||
|
||||
/* Start up Winsock */
|
||||
iResult = WSAStartup(MAKEWORD(2, 2), &wdata);
|
||||
ok(iResult == 0, "WSAStartup failed. iResult = %d\n", iResult);
|
||||
|
||||
/* Create the socket */
|
||||
sck = WSASocket(AF_INET, SOCK_STREAM, IPPROTO_IP, 0, 0, 0);
|
||||
ok(sck != INVALID_SOCKET, "WSASocket failed. sck = %d\n", (INT)sck);
|
||||
if (sck == INVALID_SOCKET)
|
||||
{
|
||||
skip("Failed to create socket!\n");
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
/* Do the Ioctl (buffer to small) */
|
||||
buflen = sizeof(INTERFACE_INFO)-1;
|
||||
buf = (BYTE*)HeapAlloc(GetProcessHeap(), 0, buflen);
|
||||
if (buf == NULL)
|
||||
{
|
||||
skip("Failed to allocate memory!\n");
|
||||
goto cleanup;
|
||||
}
|
||||
BytesReturned = 0;
|
||||
iResult = WSAIoctl(sck, SIO_GET_INTERFACE_LIST, 0, 0,
|
||||
buf, buflen, &BytesReturned, 0, 0);
|
||||
ok(iResult == -1, "WSAIoctl/SIO_GET_INTERFACE_LIST did not fail! iResult = %d.\n", iResult);
|
||||
ok_hex(WSAGetLastError(), WSAEFAULT);
|
||||
ok(BytesReturned == 0, "WSAIoctl/SIO_GET_INTERFACE_LIST: BytesReturned should be 0, not %ld.\n", BytesReturned);
|
||||
HeapFree(GetProcessHeap(), 0, buf);
|
||||
buf = NULL;
|
||||
|
||||
/* Do the Ioctl
|
||||
In most cases no loop is done.
|
||||
Only if WSAIoctl fails with WSAEFAULT (buffer to small) we need to retry with a
|
||||
larger buffer */
|
||||
i1 = 0;
|
||||
while (TRUE)
|
||||
{
|
||||
if (buf != NULL)
|
||||
{
|
||||
HeapFree(GetProcessHeap(), 0, buf);
|
||||
buf = NULL;
|
||||
}
|
||||
|
||||
buflen = sizeof(INTERFACE_INFO) * (i1+1) * 32;
|
||||
buf = (BYTE*)HeapAlloc(GetProcessHeap(), 0, buflen);
|
||||
if (buf == NULL)
|
||||
{
|
||||
skip("Failed to allocate memory!\n");
|
||||
goto cleanup;
|
||||
}
|
||||
BytesReturned = 0;
|
||||
iResult = WSAIoctl(sck, SIO_GET_INTERFACE_LIST, 0, 0,
|
||||
buf, buflen, &BytesReturned, 0, 0);
|
||||
/* we have what we want ... leave loop */
|
||||
if (iResult == NO_ERROR)
|
||||
break;
|
||||
/* only retry if buffer was to small */
|
||||
/* to avoid infinite loop we maximum retry count is 4 */
|
||||
if ((i1 >= 4) || (WSAGetLastError() != WSAEFAULT))
|
||||
{
|
||||
ok_hex(iResult, NO_ERROR);
|
||||
skip("WSAIoctl / SIO_GET_INTERFACE_LIST\n");
|
||||
goto cleanup;
|
||||
}
|
||||
/* buffer to small -> retry */
|
||||
i1++;
|
||||
}
|
||||
|
||||
ok_dec(BytesReturned % sizeof(INTERFACE_INFO), 0);
|
||||
|
||||
/* Calculate how many INTERFACE_INFO we got */
|
||||
infoCount = BytesReturned / sizeof(INTERFACE_INFO);
|
||||
ok(infoCount == pTable->dwNumEntries,
|
||||
"Wrong count of entries! Got %ld, expected %ld.\n", pTable->dwNumEntries, infoCount);
|
||||
|
||||
if (winetest_debug >= 2)
|
||||
{
|
||||
trace("WSAIoctl\n");
|
||||
trace(" BytesReturned %ld - InfoCount %ld\n ", BytesReturned, infoCount);
|
||||
ifInfo = (LPINTERFACE_INFO)buf;
|
||||
for (i1 = 0; i1 < infoCount; i1++)
|
||||
{
|
||||
trace("entry-index %ld\n", i1);
|
||||
trace(" iiFlags %ld\n", ifInfo->iiFlags);
|
||||
traceaddr("ifInfo^.iiAddress", ifInfo->iiAddress);
|
||||
traceaddr("ifInfo^.iiBroadcastAddress", ifInfo->iiBroadcastAddress);
|
||||
traceaddr("ifInfo^.iiNetmask", ifInfo->iiNetmask);
|
||||
ifInfo++;
|
||||
}
|
||||
}
|
||||
|
||||
/* compare entries */
|
||||
ifInfo = (LPINTERFACE_INFO)buf;
|
||||
for (i1 = 0; i1 < infoCount; i1++)
|
||||
{
|
||||
if (winetest_debug >= 2)
|
||||
trace("Entry %ld\n", i1);
|
||||
for (j1 = 0; j1 < pTable->dwNumEntries; j1++)
|
||||
{
|
||||
if (ifInfo[i1].iiAddress.AddressIn.sin_addr.s_addr == pTable->table[j1].dwAddr)
|
||||
{
|
||||
pRow = &pTable->table[j1];
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (j1 == pTable->dwNumEntries)
|
||||
{
|
||||
skip("Skipping interface\n");
|
||||
continue;
|
||||
}
|
||||
|
||||
/* iiFlags
|
||||
* Don't know if this value is fix for SIO_GET_INTERFACE_LIST! */
|
||||
iiFlagsExpected = IFF_BROADCAST | IFF_MULTICAST;
|
||||
if ((pRow->wType & MIB_IPADDR_DISCONNECTED) == 0)
|
||||
iiFlagsExpected |= IFF_UP;
|
||||
if (pRow->dwAddr == ntohl(INADDR_LOOPBACK))
|
||||
{
|
||||
iiFlagsExpected |= IFF_LOOPBACK;
|
||||
/* on Windows 7 loopback has broadcast flag cleared */
|
||||
//iiFlagsExpected &= ~IFF_BROADCAST;
|
||||
}
|
||||
|
||||
ok_hex(ifInfo[i1].iiFlags, iiFlagsExpected);
|
||||
ok_hex(ifInfo[i1].iiAddress.AddressIn.sin_addr.s_addr, pRow->dwAddr);
|
||||
// dwBCastAddr is not the "real" Broadcast-Address.
|
||||
BCastAddr = (pRow->dwBCastAddr == 1 && (iiFlagsExpected & IFF_BROADCAST) != 0) ? 0xFFFFFFFF : 0x0;
|
||||
ok_hex(ifInfo[i1].iiBroadcastAddress.AddressIn.sin_addr.s_addr, BCastAddr);
|
||||
ok_hex(ifInfo[i1].iiNetmask.AddressIn.sin_addr.s_addr, pRow->dwMask);
|
||||
}
|
||||
|
||||
cleanup:
|
||||
if (sck != 0)
|
||||
closesocket(sck);
|
||||
if (pTable != NULL)
|
||||
free(pTable);
|
||||
if (buf != NULL)
|
||||
HeapFree(GetProcessHeap(), 0, buf);
|
||||
WSACleanup();
|
||||
}
|
||||
|
||||
START_TEST(WSAIoctl)
|
||||
{
|
||||
Test_WSAIoctl_GetInterfaceList();
|
||||
}
|
|
@ -11,6 +11,7 @@ extern void func_ioctlsocket(void);
|
|||
extern void func_nostartup(void);
|
||||
extern void func_recv(void);
|
||||
extern void func_send(void);
|
||||
extern void func_WSAIoctl(void);
|
||||
extern void func_WSARecv(void);
|
||||
extern void func_WSAStartup(void);
|
||||
|
||||
|
@ -24,6 +25,7 @@ const struct test winetest_testlist[] =
|
|||
{ "nostartup", func_nostartup },
|
||||
{ "recv", func_recv },
|
||||
{ "send", func_send },
|
||||
{ "WSAIoctl", func_WSAIoctl },
|
||||
{ "WSARecv", func_WSARecv },
|
||||
{ "WSAStartup", func_WSAStartup },
|
||||
{ 0, 0 }
|
||||
|
|
Loading…
Reference in a new issue