diff --git a/include/freerdp/transport_io.h b/include/freerdp/transport_io.h index 6a5726ebf..bfa55cb14 100644 --- a/include/freerdp/transport_io.h +++ b/include/freerdp/transport_io.h @@ -38,7 +38,10 @@ extern "C" * @param userContext user defined context passed by @ref freerdp_set_io_callback_context * @param data a buffer to read to * @param bytes the size of the buffer - * @return the number of bytes read or <0 for failures + * @return the number of bytes read. Negative numbers indicate an error + * occurred. \b errno is set accordingly (see man 2 read) + * @bug Before 3.18.0 the function did return \b -1 for transport closed and \b 0 for retry + * events. * @since version 3.9.0 */ typedef int (*pTransportLayerRead)(void* userContext, void* data, int bytes); @@ -48,7 +51,10 @@ extern "C" * @param userContext user defined context passed by @ref freerdp_set_io_callback_context * @param data a buffer to write * @param bytes the size of the buffer - * @return the number of bytes written or <0 for failures + * @return the number of bytes written. Negative numbers indicate an error + * occurred. \b errno is set accordingly (see man 2 send) + * @bug Before 3.18.0 the function did return \b -1 for transport closed and \b 0 for retry + * events. * @since version 3.9.0 */ typedef int (*pTransportLayerWrite)(void* userContext, const void* data, int bytes); @@ -109,14 +115,14 @@ extern "C" pTransportFkt TLSAccept; pTransportAttach TransportAttach; pTransportFkt TransportDisconnect; - pTransportRWFkt ReadPdu; /* Reads a whole PDU from the transport */ - pTransportRWFkt WritePdu; /* Writes a whole PDU to the transport */ - pTransportRead ReadBytes; /* Reads up to a requested amount of bytes */ + pTransportRWFkt ReadPdu; /* Reads a whole PDU from the transport */ + pTransportRWFkt WritePdu; /* Writes a whole PDU to the transport */ + pTransportRead ReadBytes; /* Reads up to a requested amount of bytes */ pTransportGetPublicKey GetPublicKey; /** @since version 3.2.0 */ pTransportSetBlockingMode SetBlockingMode; /** @since version 3.3.0 */ pTransportConnectLayer ConnectLayer; /** @since 3.9.0 */ pTransportAttachLayer AttachLayer; /** @since 3.9.0 */ - UINT64 reserved[64 - 12]; /* Reserve some space for ABI compatibility */ + UINT64 reserved[64 - 12]; /* Reserve some space for ABI compatibility */ }; typedef struct rdp_transport_io rdpTransportIo; diff --git a/libfreerdp/core/proxy.c b/libfreerdp/core/proxy.c index 03b1aeb08..76e2e2e14 100644 --- a/libfreerdp/core/proxy.c +++ b/libfreerdp/core/proxy.c @@ -696,12 +696,6 @@ static BOOL http_proxy_connect(rdpContext* context, BIO* bufferedBio, const char } Sleep(10); } - else - { - /* Error? */ - WLog_ERR(TAG, "Failed reading reply from HTTP proxy (BIO_read returned zero)"); - goto fail; - } resultsize += WINPR_ASSERTING_INT_CAST(size_t, status); } diff --git a/libfreerdp/core/tcp.c b/libfreerdp/core/tcp.c index 76e95cbf7..456ba84b6 100644 --- a/libfreerdp/core/tcp.c +++ b/libfreerdp/core/tcp.c @@ -1354,29 +1354,17 @@ static int freerdp_tcp_layer_read(void* userContext, void* data, int bytes) rdpTcpLayer* tcpLayer = (rdpTcpLayer*)userContext; - int error = 0; - int status = 0; - (void)WSAResetEvent(tcpLayer->hEvent); - status = _recv((SOCKET)tcpLayer->sockfd, data, bytes, 0); + const int status = _recv((SOCKET)tcpLayer->sockfd, data, bytes, 0); if (status > 0) return status; - if (status == 0) - return -1; /* socket closed */ - - error = WSAGetLastError(); + const int error = WSAGetLastError(); if ((error == WSAEWOULDBLOCK) || (error == WSAEINTR) || (error == WSAEINPROGRESS) || (error == WSAEALREADY)) - { - status = 0; - } - else - { - status = -1; - } + errno = EAGAIN; return status; } @@ -1390,25 +1378,15 @@ static int freerdp_tcp_layer_write(void* userContext, const void* data, int byte rdpTcpLayer* tcpLayer = (rdpTcpLayer*)userContext; - int error = 0; - int status = 0; + const int status = _send((SOCKET)tcpLayer->sockfd, data, bytes, 0); + if (status > 0) + return status; - status = _send((SOCKET)tcpLayer->sockfd, data, bytes, 0); + const int error = WSAGetLastError(); - if (status <= 0) - { - error = WSAGetLastError(); - - if ((error == WSAEWOULDBLOCK) || (error == WSAEINTR) || (error == WSAEINPROGRESS) || - (error == WSAEALREADY)) - { - status = 0; - } - else - { - status = -1; - } - } + if ((error == WSAEWOULDBLOCK) || (error == WSAEINTR) || (error == WSAEINPROGRESS) || + (error == WSAEALREADY)) + errno = EAGAIN; return status; } diff --git a/libfreerdp/core/transport.c b/libfreerdp/core/transport.c index 21523f2ae..b06e9f107 100644 --- a/libfreerdp/core/transport.c +++ b/libfreerdp/core/transport.c @@ -1961,11 +1961,21 @@ static int transport_layer_bio_write(BIO* bio, const char* buf, int size) BIO_clear_flags(bio, BIO_FLAGS_WRITE | BIO_FLAGS_SHOULD_RETRY); - int status = IFCALLRESULT(-1, layer->Write, layer->userContext, buf, size); + errno = 0; + const int status = IFCALLRESULT(-1, layer->Write, layer->userContext, buf, size); if (status >= 0 && status < size) BIO_set_flags(bio, (BIO_FLAGS_WRITE | BIO_FLAGS_SHOULD_RETRY)); + switch (errno) + { + case EAGAIN: + BIO_set_flags(bio, (BIO_FLAGS_WRITE | BIO_FLAGS_SHOULD_RETRY)); + break; + default: + break; + } + return status; } @@ -1983,11 +1993,17 @@ static int transport_layer_bio_read(BIO* bio, char* buf, int size) return -1; BIO_clear_flags(bio, BIO_FLAGS_READ | BIO_FLAGS_SHOULD_RETRY); + errno = 0; + const int status = IFCALLRESULT(-1, layer->Read, layer->userContext, buf, size); - int status = IFCALLRESULT(-1, layer->Read, layer->userContext, buf, size); - - if (status == 0) - BIO_set_flags(bio, (BIO_FLAGS_READ | BIO_FLAGS_SHOULD_RETRY)); + switch (errno) + { + case EAGAIN: + BIO_set_flags(bio, (BIO_FLAGS_READ | BIO_FLAGS_SHOULD_RETRY)); + break; + default: + break; + } return status; }