[PATCH 2/6] ws2_32: Validate address length in bind().
Zebediah Figura
zfigura at codeweavers.com
Wed Jul 21 20:34:51 CDT 2021
bind() returns WSAEFAULT for short length, but IOCTL_AFD_BIND returns
STATUS_INVALID_ADDRESS, which translates to WSAEADDRNOTAVAIL.
Signed-off-by: Zebediah Figura <zfigura at codeweavers.com>
---
dlls/ws2_32/socket.c | 42 +++++++++++++++++++++++++++++++++++++++-
dlls/ws2_32/tests/sock.c | 10 ++++------
2 files changed, 45 insertions(+), 7 deletions(-)
diff --git a/dlls/ws2_32/socket.c b/dlls/ws2_32/socket.c
index fac19355705..88d30cb2802 100644
--- a/dlls/ws2_32/socket.c
+++ b/dlls/ws2_32/socket.c
@@ -1775,12 +1775,52 @@ int WINAPI WS_bind( SOCKET s, const struct WS_sockaddr *addr, int len )
TRACE( "socket %#lx, addr %s\n", s, debugstr_sockaddr(addr) );
- if (!addr || (addr->sa_family && !supported_pf( addr->sa_family )))
+ if (!addr)
{
SetLastError( WSAEAFNOSUPPORT );
return -1;
}
+ switch (addr->sa_family)
+ {
+ case WS_AF_INET:
+ if (len < sizeof(struct WS_sockaddr_in))
+ {
+ SetLastError( WSAEFAULT );
+ return -1;
+ }
+ break;
+
+ case WS_AF_INET6:
+ if (len < sizeof(struct WS_sockaddr_in6))
+ {
+ SetLastError( WSAEFAULT );
+ return -1;
+ }
+ break;
+
+ case WS_AF_IPX:
+ if (len < sizeof(struct WS_sockaddr_ipx))
+ {
+ SetLastError( WSAEFAULT );
+ return -1;
+ }
+ break;
+
+ case WS_AF_IRDA:
+ if (len < sizeof(SOCKADDR_IRDA))
+ {
+ SetLastError( WSAEFAULT );
+ return -1;
+ }
+ break;
+
+ default:
+ FIXME( "unknown protocol %u\n", addr->sa_family );
+ SetLastError( WSAEAFNOSUPPORT );
+ return -1;
+ }
+
if (!(sync_event = get_sync_event())) return -1;
params = HeapAlloc( GetProcessHeap(), 0, sizeof(int) + len );
diff --git a/dlls/ws2_32/tests/sock.c b/dlls/ws2_32/tests/sock.c
index f5c5acf161e..dd880531047 100644
--- a/dlls/ws2_32/tests/sock.c
+++ b/dlls/ws2_32/tests/sock.c
@@ -10668,15 +10668,13 @@ static void test_bind(void)
ok(s != -1, "failed to create socket, error %u\n", WSAGetLastError());
ret = bind(s, unicast_addr->Address.lpSockaddr, sizeof(struct sockaddr_in6_old));
- todo_wine_if (!addr6.sin6_scope_id)
- {
- ok(ret == -1, "expected failure\n");
- ok(WSAGetLastError() == WSAEFAULT, "got error %u\n", WSAGetLastError());
- }
+ ok(ret == -1, "expected failure\n");
+ ok(WSAGetLastError() == WSAEFAULT, "got error %u\n", WSAGetLastError());
addr6.sin6_scope_id = 0xabacab;
ret = bind(s, (struct sockaddr *)&addr6, sizeof(addr6));
- ok(ret == -1, "expected failure\n");
+ todo_wine_if (!((const struct sockaddr_in6 *)unicast_addr->Address.lpSockaddr)->sin6_scope_id)
+ ok(ret == -1, "expected failure\n");
todo_wine ok(WSAGetLastError() == WSAEADDRNOTAVAIL, "got error %u\n", WSAGetLastError());
addr6.sin6_scope_id = 0;
--
2.30.2
More information about the wine-devel
mailing list