Bruno Jesus : ws2_32/tests: Add more SIO_ADDRESS_LIST_CHANGE tests.
Alexandre Julliard
julliard at winehq.org
Tue Sep 13 11:33:57 CDT 2016
Module: wine
Branch: master
Commit: 77b391125ffc0d91d24e645177e16fb02844275e
URL: http://source.winehq.org/git/wine.git/?a=commit;h=77b391125ffc0d91d24e645177e16fb02844275e
Author: Bruno Jesus <00cpxxx at gmail.com>
Date: Fri Sep 9 00:28:52 2016 -0300
ws2_32/tests: Add more SIO_ADDRESS_LIST_CHANGE tests.
Signed-off-by: Bruno Jesus <00cpxxx at gmail.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>
---
dlls/ws2_32/tests/sock.c | 110 ++++++++++++++++++++++++++++++++++-------------
include/winsock2.h | 9 ++++
2 files changed, 90 insertions(+), 29 deletions(-)
diff --git a/dlls/ws2_32/tests/sock.c b/dlls/ws2_32/tests/sock.c
index be98691..d216542 100644
--- a/dlls/ws2_32/tests/sock.c
+++ b/dlls/ws2_32/tests/sock.c
@@ -8349,8 +8349,9 @@ static void test_sioAddressListChange(void)
struct in_addr net_address;
WSAOVERLAPPED overlapped;
struct hostent *h;
- DWORD num_bytes, error;
- SOCKET sock;
+ DWORD num_bytes, error, tick;
+ SOCKET sock, sock2, sock3;
+ WSAEVENT event2, event3;
int acount;
int ret;
@@ -8397,9 +8398,6 @@ todo_wine
sock = socket(AF_INET, 0, IPPROTO_TCP);
ok(sock != INVALID_SOCKET, "socket() failed\n");
- memset(&bindAddress, 0, sizeof(bindAddress));
- bindAddress.sin_family = AF_INET;
- bindAddress.sin_addr.s_addr = net_address.s_addr;
SetLastError(0xdeadbeef);
ret = bind(sock, (struct sockaddr*)&bindAddress, sizeof(bindAddress));
ok (!ret, "bind() failed with error %d\n", GetLastError());
@@ -8419,9 +8417,6 @@ todo_wine
sock = WSASocketW(AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, WSA_FLAG_OVERLAPPED);
ok(sock != INVALID_SOCKET, "socket() failed\n");
- memset(&bindAddress, 0, sizeof(bindAddress));
- bindAddress.sin_family = AF_INET;
- bindAddress.sin_addr.s_addr = net_address.s_addr;
SetLastError(0xdeadbeef);
ret = bind(sock, (struct sockaddr*)&bindAddress, sizeof(bindAddress));
ok (!ret, "bind() failed with error %d\n", GetLastError());
@@ -8442,9 +8437,6 @@ todo_wine
sock = WSASocketW(AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, WSA_FLAG_OVERLAPPED);
ok(sock != INVALID_SOCKET, "socket() failed\n");
- memset(&bindAddress, 0, sizeof(bindAddress));
- bindAddress.sin_family = AF_INET;
- bindAddress.sin_addr.s_addr = net_address.s_addr;
SetLastError(0xdeadbeef);
ret = bind(sock, (struct sockaddr*)&bindAddress, sizeof(bindAddress));
ok (!ret, "bind() failed with error %d\n", GetLastError());
@@ -8461,6 +8453,40 @@ todo_wine
CloseHandle(overlapped.hEvent);
closesocket(sock);
+ /* When the socket is overlapped non-blocking and the list change is requested without
+ * an overlapped structure the error will be different. */
+ sock = WSASocketW(AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, WSA_FLAG_OVERLAPPED);
+ ok(sock != INVALID_SOCKET, "socket() failed\n");
+
+ SetLastError(0xdeadbeef);
+ ret = bind(sock, (struct sockaddr*)&bindAddress, sizeof(bindAddress));
+ ok (!ret, "bind() failed with error %d\n", GetLastError());
+ set_blocking(sock, FALSE);
+
+ SetLastError(0xdeadbeef);
+ ret = WSAIoctl(sock, SIO_ADDRESS_LIST_CHANGE, NULL, 0, NULL, 0, &num_bytes, NULL, NULL);
+ error = GetLastError();
+ ok (ret == SOCKET_ERROR, "WSAIoctl(SIO_ADDRESS_LIST_CHANGE) failed with error %d\n", error);
+ ok (error == WSAEWOULDBLOCK, "expected 10035, got %d\n", error);
+
+ closesocket(sock);
+
+ /* Misuse of the API by using a blocking socket and not using an overlapped structure,
+ * this leads to a hang forever. */
+ if (0)
+ {
+ sock = WSASocketW(AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, WSA_FLAG_OVERLAPPED);
+
+ SetLastError(0xdeadbeef);
+ bind(sock, (struct sockaddr*)&bindAddress, sizeof(bindAddress));
+
+ set_blocking(sock, TRUE);
+ WSAIoctl(sock, SIO_ADDRESS_LIST_CHANGE, NULL, 0, NULL, 0, &num_bytes, NULL, NULL);
+ /* hang */
+
+ closesocket(sock);
+ }
+
if (!winetest_interactive)
{
skip("Cannot test SIO_ADDRESS_LIST_CHANGE, interactive tests must be enabled\n");
@@ -8470,35 +8496,61 @@ todo_wine
/* Bind an overlapped socket to the first found network interface */
sock = WSASocketW(AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, WSA_FLAG_OVERLAPPED);
ok(sock != INVALID_SOCKET, "Expected socket to return a valid socket\n");
- if (sock == INVALID_SOCKET)
- {
- skip("Cannot test SIO_ADDRESS_LIST_CHANGE, socket creation failed with %u\n",
- WSAGetLastError());
- return;
- }
- memset(&bindAddress, 0, sizeof(bindAddress));
- bindAddress.sin_family = AF_INET;
- bindAddress.sin_addr.s_addr = net_address.s_addr;
+ sock2 = WSASocketW(AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, WSA_FLAG_OVERLAPPED);
+ ok(sock2 != INVALID_SOCKET, "Expected socket to return a valid socket\n");
+ sock3 = WSASocketW(AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, WSA_FLAG_OVERLAPPED);
+ ok(sock3 != INVALID_SOCKET, "Expected socket to return a valid socket\n");
+
ret = bind(sock, (struct sockaddr*)&bindAddress, sizeof(bindAddress));
- if (ret != 0)
- {
- skip("Cannot test SIO_ADDRESS_LIST_CHANGE, failed to bind, error %u\n", WSAGetLastError());
- goto end;
- }
+ ok(!ret, "bind failed unexpectedly\n");
+ ret = bind(sock2, (struct sockaddr*)&bindAddress, sizeof(bindAddress));
+ ok(!ret, "bind failed unexpectedly\n");
+ ret = bind(sock3, (struct sockaddr*)&bindAddress, sizeof(bindAddress));
+ ok(!ret, "bind failed unexpectedly\n");
+
+ set_blocking(sock2, FALSE);
+ set_blocking(sock3, FALSE);
/* Wait for address changes, request that the user connects/disconnects an interface */
memset(&overlapped, 0, sizeof(overlapped));
overlapped.hEvent = CreateEventA(NULL, FALSE, FALSE, NULL);
ret = WSAIoctl(sock, SIO_ADDRESS_LIST_CHANGE, NULL, 0, NULL, 0, &num_bytes, &overlapped, NULL);
ok(ret == SOCKET_ERROR, "WSAIoctl succeeded unexpectedly\n");
- ok(WSAGetLastError() == WSA_IO_PENDING, "Expected pending last error %d\n", WSAGetLastError());
+ ok(WSAGetLastError() == WSA_IO_PENDING, "Expected pending last error, got %d\n", WSAGetLastError());
+
+ ret = WSAIoctl(sock2, SIO_ADDRESS_LIST_CHANGE, NULL, 0, NULL, 0, &num_bytes, NULL, NULL);
+ ok(ret == SOCKET_ERROR, "WSAIoctl succeeded unexpectedly\n");
+ ok(WSAGetLastError() == WSAEWOULDBLOCK, "Expected would block last error, got %d\n", WSAGetLastError());
+
+ event2 = WSACreateEvent();
+ event3 = WSACreateEvent();
+ ret = WSAEventSelect (sock2, event2, FD_ADDRESS_LIST_CHANGE);
+ ok(!ret, "WSAEventSelect failed with %d\n", WSAGetLastError());
+ /* sock3 did not request SIO_ADDRESS_LIST_CHANGE but it is trying to wait anyway */
+ ret = WSAEventSelect (sock3, event3, FD_ADDRESS_LIST_CHANGE);
+ ok(!ret, "WSAEventSelect failed with %d\n", WSAGetLastError());
+
trace("Testing socket-based ipv4 address list change notification. Please connect/disconnect or"
- " change the ipv4 address of any of the local network interfaces (10 second timeout).\n");
- ret = WaitForSingleObject(overlapped.hEvent, 10000);
+ " change the ipv4 address of any of the local network interfaces (15 second timeout).\n");
+ tick = GetTickCount();
+ ret = WaitForSingleObject(overlapped.hEvent, 15000);
ok(ret == WAIT_OBJECT_0, "failed to get overlapped event %u\n", ret);
-end:
+ ret = WaitForSingleObject(event2, 500);
+todo_wine
+ ok(ret == WAIT_OBJECT_0, "failed to get change event %u\n", ret);
+
+ ret = WaitForSingleObject(event3, 500);
+ ok(ret == WAIT_TIMEOUT, "unexpected change event\n");
+
+ trace("Spent %d ms waiting.\n", GetTickCount() - tick);
+
+ WSACloseEvent(event2);
+ WSACloseEvent(event3);
+
closesocket(sock);
+ closesocket(sock2);
+ closesocket(sock3);
}
static void test_synchronous_WSAIoctl(void)
diff --git a/include/winsock2.h b/include/winsock2.h
index 24f0ea3..a2563f4 100644
--- a/include/winsock2.h
+++ b/include/winsock2.h
@@ -101,6 +101,15 @@ extern "C" {
#define FD_ACCEPT_BIT 3
#define FD_CONNECT_BIT 4
#define FD_CLOSE_BIT 5
+#define FD_QOS_BIT 6
+#define FD_GROUP_QOS_BIT 7
+#define FD_ROUTING_INTERFACE_CHANGE_BIT 8
+#define FD_ADDRESS_LIST_CHANGE_BIT 9
+
+#define FD_QOS 0x00000040
+#define FD_GROUP_QOS 0x00000080
+#define FD_ROUTING_INTERFACE_CHANGE 0x00000100
+#define FD_ADDRESS_LIST_CHANGE 0x00000200
/* Constants for LPCONDITIONPROC */
#define CF_ACCEPT 0x0000
More information about the wine-cvs
mailing list