mirror of
https://github.com/solemnwarning/ipxwrapper
synced 2024-12-30 16:45:37 +01:00
Bodge asynchronous connects to almost work as they should.
This commit is contained in:
parent
a930a972df
commit
3be40b6e63
@ -20,3 +20,4 @@ EXPORTS
|
||||
getpeername
|
||||
listen
|
||||
accept
|
||||
WSAAsyncSelect
|
||||
|
@ -47,6 +47,7 @@
|
||||
#define IPX_IS_SPX (int)(1<<10)
|
||||
#define IPX_IS_SPXII (int)(1<<11)
|
||||
#define IPX_LISTENING (int)(1<<12)
|
||||
#define IPX_CONNECT_OK (int)(1<<13)
|
||||
|
||||
typedef struct ipx_socket ipx_socket;
|
||||
typedef struct ipx_packet ipx_packet;
|
||||
@ -152,5 +153,6 @@ int PASCAL r_send(SOCKET fd, const char *buf, int len, int flags);
|
||||
int PASCAL r_getpeername(SOCKET fd, struct sockaddr *addr, int *addrlen);
|
||||
int PASCAL r_listen(SOCKET s, int backlog);
|
||||
SOCKET PASCAL r_accept(SOCKET s, struct sockaddr *addr, int *addrlen);
|
||||
int PASCAL r_WSAAsyncSelect(SOCKET s, HWND hWnd, unsigned int wMsg, long lEvent);
|
||||
|
||||
#endif /* !IPXWRAPPER_H */
|
||||
|
@ -33,3 +33,5 @@ r_connect:4
|
||||
r_send:4
|
||||
r_getpeername:4
|
||||
inet_ntoa:4
|
||||
__WSAFDIsSet:4
|
||||
r_WSAAsyncSelect:4
|
||||
|
@ -1724,12 +1724,57 @@ static int _connect_spx(ipx_socket *sock, struct sockaddr_ipx *ipxaddr)
|
||||
|
||||
if(r_connect(sock->fd, (struct sockaddr*)(&in_addr), sizeof(in_addr)) == -1)
|
||||
{
|
||||
if(WSAGetLastError() == WSAEWOULDBLOCK)
|
||||
{
|
||||
/* The socket is in non-blocking mode, so we wait for
|
||||
* the asynchronous connect call to complete.
|
||||
*
|
||||
* Keeping it synchronous until it is proven this breaks
|
||||
* something for simplicity.
|
||||
*/
|
||||
|
||||
fd_set w_fdset;
|
||||
FD_ZERO(&w_fdset);
|
||||
FD_SET(sock->fd, &w_fdset);
|
||||
|
||||
fd_set e_fdset;
|
||||
FD_ZERO(&e_fdset);
|
||||
FD_SET(sock->fd, &e_fdset);
|
||||
|
||||
if(select(1, NULL, &w_fdset, &e_fdset, NULL) == 1 && FD_ISSET(sock->fd, &w_fdset))
|
||||
{
|
||||
goto CONNECTED;
|
||||
}
|
||||
|
||||
int errnum, len = sizeof(int);
|
||||
getsockopt(sock->fd, SOL_SOCKET, SO_ERROR, (char*)(&errnum), &len);
|
||||
|
||||
log_printf(LOG_DEBUG, "Connection failed: %s", w32_error(errnum));
|
||||
|
||||
unlock_sockets();
|
||||
|
||||
WSASetLastError(WSAEWOULDBLOCK);
|
||||
return -1;
|
||||
}
|
||||
|
||||
unlock_sockets();
|
||||
return -1;
|
||||
}
|
||||
|
||||
CONNECTED:
|
||||
|
||||
log_printf(LOG_DEBUG, "Connection succeeded");
|
||||
|
||||
/* Set the IPX_CONNECT_OK bit which indicates the next WSAAsyncSelect
|
||||
* call with FD_CONNECT set should send a message indicating the
|
||||
* connection succeeded and then clear this bit.
|
||||
*
|
||||
* This is a hack to make asynchronous connect calls vaguely work as
|
||||
* they should.
|
||||
*/
|
||||
|
||||
sock->flags |= IPX_CONNECT_OK;
|
||||
|
||||
/* The TCP connection is up!
|
||||
*
|
||||
* Store the remote IPX address in remote_addr and mark the socket as
|
||||
@ -2145,3 +2190,26 @@ SOCKET PASCAL accept(SOCKET s, struct sockaddr *addr, int *addrlen)
|
||||
return r_accept(s, addr, addrlen);
|
||||
}
|
||||
}
|
||||
|
||||
int PASCAL WSAAsyncSelect(SOCKET s, HWND hWnd, unsigned int wMsg, long lEvent)
|
||||
{
|
||||
if(lEvent & FD_CONNECT)
|
||||
{
|
||||
ipx_socket *sock = get_socket(s);
|
||||
|
||||
if(sock)
|
||||
{
|
||||
if(sock->flags & IPX_CONNECT_OK)
|
||||
{
|
||||
log_printf(LOG_DEBUG, "Posting message %u for FD_CONNECT on socket %d", wMsg, sock->fd);
|
||||
|
||||
PostMessage(hWnd, wMsg, sock->fd, MAKEWORD(FD_CONNECT, 0));
|
||||
sock->flags &= ~IPX_CONNECT_OK;
|
||||
}
|
||||
|
||||
unlock_sockets();
|
||||
}
|
||||
}
|
||||
|
||||
return r_WSAAsyncSelect(s, hWnd, wMsg, lEvent);
|
||||
}
|
||||
|
@ -29,7 +29,7 @@ getprotobynumber
|
||||
getservbyname
|
||||
getservbyport
|
||||
gethostname
|
||||
WSAAsyncSelect
|
||||
WSAAsyncSelect:0
|
||||
WSAAsyncGetHostByAddr
|
||||
WSAAsyncGetHostByName
|
||||
WSAAsyncGetProtoByNumber
|
||||
|
Loading…
x
Reference in New Issue
Block a user