@@ -909,8 +909,10 @@ WSPBind(SOCKET Handle,
909909 return SOCKET_ERROR ;
910910 }
911911
912+ int connectSize = FIELD_OFFSET (AFD_BIND_DATA , Address .Address [SocketAddressLength ]);
913+
912914 /* See below */
913- BindData = HeapAlloc (GlobalHeap , 0 , 0xA + SocketAddressLength );
915+ BindData = HeapAlloc (GlobalHeap , 0 , connectSize );
914916 if (!BindData )
915917 {
916918 return MsafdReturnWithErrno (STATUS_INSUFFICIENT_RESOURCES , lpErrno , 0 , NULL );
@@ -950,9 +952,9 @@ WSPBind(SOCKET Handle,
950952 & IOSB ,
951953 IOCTL_AFD_BIND ,
952954 BindData ,
953- 0xA + Socket -> SharedData -> SizeOfLocalAddress , /* Can't figure out a way to calculate this in C*/
955+ connectSize ,
954956 BindData ,
955- 0xA + Socket -> SharedData -> SizeOfLocalAddress ); /* Can't figure out a way to calculate this C */
957+ connectSize );
956958
957959 /* Wait for return */
958960 if (Status == STATUS_PENDING )
@@ -2173,6 +2175,115 @@ WSPConnect(SOCKET Handle,
21732175
21742176 return MsafdReturnWithErrno (Status , lpErrno , 0 , NULL );
21752177}
2178+
2179+ BOOL
2180+ WSPAPI
2181+ WSPConnectEx (
2182+ IN SOCKET Handle ,
2183+ IN const struct sockaddr * SocketAddress ,
2184+ IN int SocketAddressLength ,
2185+ IN PVOID lpSendBuffer ,
2186+ IN DWORD dwSendDataLength ,
2187+ OUT LPDWORD lpdwBytesSent ,
2188+ IN OUT LPOVERLAPPED lpOverlapped )
2189+ {
2190+ IO_STATUS_BLOCK DummyIOSB ;
2191+ PIO_STATUS_BLOCK IOSB = & DummyIOSB ;
2192+ PAFD_SUPER_CONNECT_INFO ConnectInfo = NULL ;
2193+ PSOCKET_INFORMATION Socket ;
2194+ NTSTATUS Status ;
2195+ int SocketDataLength ;
2196+ UCHAR Buffer [128 ];
2197+
2198+ FIXME ("WSPConnectEx(%x)\n" , Handle );
2199+
2200+ if (!lpOverlapped )
2201+ {
2202+ SetLastError (ERROR_INVALID_PARAMETER );
2203+ return FALSE;
2204+ }
2205+
2206+ if (!lpSendBuffer && dwSendDataLength )
2207+ {
2208+ SetLastError (ERROR_INVALID_PARAMETER );
2209+ return FALSE;
2210+ }
2211+
2212+ /* Get the Socket Structure associate to this Socket*/
2213+ Socket = GetSocketStructure (Handle );
2214+ if (!Socket )
2215+ {
2216+ SetLastError (WSAENOTSOCK );
2217+ return FALSE;
2218+ }
2219+
2220+ if (SocketAddressLength > 128 - sizeof (AFD_CONNECT_INFO ))
2221+ {
2222+ SetLastError (WSAEFAULT );
2223+ return SOCKET_ERROR ;
2224+ }
2225+
2226+ if (Socket -> SharedData -> ServiceFlags1 & XP1_CONNECTIONLESS )
2227+ {
2228+ // cannot call on connectionless socket
2229+ SetLastError (WSAEFAULT );
2230+ return SOCKET_ERROR ;
2231+ }
2232+
2233+ if (Socket -> SharedData -> State == SocketOpen )
2234+ {
2235+ // Socket already must be bound
2236+ SetLastError (WSAEINVAL );
2237+ return FALSE;
2238+ }
2239+
2240+ ConnectInfo = (PAFD_SUPER_CONNECT_INFO )Buffer ;
2241+ ConnectInfo -> SanActive = FALSE;
2242+
2243+ /* Calculate the size of SocketAddress->sa_data */
2244+ SocketDataLength = SocketAddressLength - FIELD_OFFSET (struct sockaddr , sa_data );
2245+
2246+ /* Set up Address in TDI Format */
2247+ ConnectInfo -> RemoteAddress .TAAddressCount = 1 ;
2248+ ConnectInfo -> RemoteAddress .Address [0 ].AddressLength = SocketDataLength ;
2249+ ConnectInfo -> RemoteAddress .Address [0 ].AddressType = SocketAddress -> sa_family ;
2250+ RtlCopyMemory (ConnectInfo -> RemoteAddress .Address [0 ].Address ,
2251+ SocketAddress -> sa_data ,
2252+ SocketDataLength );
2253+
2254+ /*
2255+ * Disable FD_WRITE and FD_CONNECT
2256+ * The latter fixes a race condition where the FD_CONNECT is re-enabled
2257+ * at the end of this function right after the Async Thread disables it.
2258+ * This should only happen at the *next* WSPConnect
2259+ */
2260+ if (Socket -> SharedData -> AsyncEvents & FD_CONNECT )
2261+ {
2262+ Socket -> SharedData -> AsyncDisabledEvents |= FD_CONNECT | FD_WRITE ;
2263+ }
2264+
2265+ IOSB = (PIO_STATUS_BLOCK )lpOverlapped ;
2266+ IOSB -> Status = STATUS_PENDING ;
2267+
2268+ /* Send IOCTL */
2269+ Status = NtDeviceIoControlFile ((HANDLE )Handle ,
2270+ lpOverlapped -> hEvent ,
2271+ NULL ,
2272+ lpOverlapped -> hEvent ? NULL : lpOverlapped ,
2273+ IOSB ,
2274+ IOCTL_AFD_SUPER_CONNECT ,
2275+ ConnectInfo ,
2276+ FIELD_OFFSET (AFD_SUPER_CONNECT_INFO , RemoteAddress .Address [0 ].Address [SocketDataLength ]),
2277+ lpSendBuffer ,
2278+ dwSendDataLength );
2279+
2280+ SetLastError (TranslateNtStatusError (Status ));
2281+
2282+ TRACE ("Ending %lx\n" , Status );
2283+
2284+ return Status == S_OK ? TRUE : FALSE;
2285+ }
2286+
21762287int
21772288WSPAPI
21782289WSPShutdown (SOCKET Handle ,
@@ -2902,7 +3013,7 @@ WSPSetSockOpt(
29023013 if (lpErrno ) * lpErrno = WSAENOTSOCK ;
29033014 return SOCKET_ERROR ;
29043015 }
2905- if (!optval )
3016+ if (!optval && optlen )
29063017 {
29073018 if (lpErrno ) * lpErrno = WSAEFAULT ;
29083019 return SOCKET_ERROR ;
0 commit comments