wininet: Use blocking_mode_t instead of flags in NETCON_recv.

This commit is contained in:
Jacek Caban 2014-03-05 18:27:36 +01:00 committed by Alexandre Julliard
parent ac58c3e8bc
commit 0767e06044
3 changed files with 49 additions and 17 deletions

View File

@ -379,12 +379,6 @@ static LPHTTPHEADERW HTTP_GetHeader(http_request_t *req, LPCWSTR head)
return &req->custHeaders[HeaderIndex];
}
typedef enum {
BLOCKING_ALLOW,
BLOCKING_DISALLOW,
BLOCKING_WAITALL
} blocking_mode_t;
struct data_stream_vtbl_t {
DWORD (*get_avail_data)(data_stream_t*,http_request_t*);
BOOL (*end_of_data)(data_stream_t*,http_request_t*);
@ -2497,7 +2491,7 @@ static DWORD read_more_data( http_request_t *req, int maxlen )
if (maxlen == -1) maxlen = sizeof(req->read_buf);
res = NETCON_recv( req->netconn, req->read_buf + req->read_size,
maxlen - req->read_size, 0, &len );
maxlen - req->read_size, BLOCKING_ALLOW, &len );
if(res == ERROR_SUCCESS)
req->read_size += len;
@ -2654,10 +2648,15 @@ static DWORD netconn_read(data_stream_t *stream, http_request_t *req, BYTE *buf,
}
if(size && is_valid_netconn(req->netconn)) {
if((res = NETCON_recv(req->netconn, buf, size, blocking_mode == BLOCKING_WAITALL ? MSG_WAITALL : 0, &len)))
if((res = NETCON_recv(req->netconn, buf, size, blocking_mode, &len))) {
len = 0;
if(!len)
if(blocking_mode == BLOCKING_DISALLOW && res == WSAEWOULDBLOCK)
res = ERROR_SUCCESS;
else
netconn_stream->content_length = netconn_stream->content_read;
}else if(!len) {
netconn_stream->content_length = netconn_stream->content_read;
}
}
netconn_stream->content_read += *read = len;
@ -2680,7 +2679,7 @@ static BOOL netconn_drain_content(data_stream_t *stream, http_request_t *req)
if(!avail)
return FALSE;
if(NETCON_recv(req->netconn, buf, min(avail, sizeof(buf)), 0, &len) != ERROR_SUCCESS)
if(NETCON_recv(req->netconn, buf, min(avail, sizeof(buf)), BLOCKING_ALLOW, &len) != ERROR_SUCCESS)
return FALSE;
netconn_stream->content_read += len;
@ -2720,7 +2719,7 @@ static DWORD read_more_chunked_data(chunked_stream_t *stream, http_request_t *re
if (maxlen == -1) maxlen = sizeof(stream->buf);
res = NETCON_recv( req->netconn, stream->buf + stream->buf_size,
maxlen - stream->buf_size, 0, &len );
maxlen - stream->buf_size, BLOCKING_ALLOW, &len );
if(res == ERROR_SUCCESS)
stream->buf_size += len;
@ -2845,7 +2844,7 @@ static DWORD chunked_read(data_stream_t *stream, http_request_t *req, BYTE *buf,
break;
}
res = NETCON_recv(req->netconn, (char *)buf+ret_read, read_bytes, 0, (int*)&read_bytes);
res = NETCON_recv(req->netconn, (char *)buf+ret_read, read_bytes, BLOCKING_ALLOW, (int*)&read_bytes);
if(res != ERROR_SUCCESS)
break;
}

View File

@ -438,14 +438,19 @@ VOID INTERNET_SendCallback(object_header_t *hdr, DWORD_PTR dwContext,
DWORD dwStatusInfoLength) DECLSPEC_HIDDEN;
BOOL INTERNET_FindProxyForProtocol(LPCWSTR szProxy, LPCWSTR proto, WCHAR *foundProxy, DWORD *foundProxyLen) DECLSPEC_HIDDEN;
typedef enum {
BLOCKING_ALLOW,
BLOCKING_DISALLOW,
BLOCKING_WAITALL
} blocking_mode_t;
DWORD create_netconn(BOOL,server_t*,DWORD,BOOL,DWORD,netconn_t**) DECLSPEC_HIDDEN;
void free_netconn(netconn_t*) DECLSPEC_HIDDEN;
void NETCON_unload(void) DECLSPEC_HIDDEN;
DWORD NETCON_secure_connect(netconn_t*,server_t*) DECLSPEC_HIDDEN;
DWORD NETCON_send(netconn_t *connection, const void *msg, size_t len, int flags,
int *sent /* out */) DECLSPEC_HIDDEN;
DWORD NETCON_recv(netconn_t *connection, void *buf, size_t len, int flags,
int *recvd /* out */) DECLSPEC_HIDDEN;
DWORD NETCON_recv(netconn_t*,void*,size_t,blocking_mode_t,int*) DECLSPEC_HIDDEN;
BOOL NETCON_query_data_available(netconn_t *connection, DWORD *available) DECLSPEC_HIDDEN;
BOOL NETCON_is_alive(netconn_t*) DECLSPEC_HIDDEN;
LPCVOID NETCON_GetCert(netconn_t *connection) DECLSPEC_HIDDEN;

View File

@ -491,6 +491,14 @@ int sock_get_error( int err )
return err;
}
static void set_socket_blocking(int socket, blocking_mode_t mode)
{
#if defined(__MINGW32__) || defined (_MSC_VER)
ULONG arg = mode == BLOCKING_DISALLOW;
ioctlsocket(socket, FIONBIO, &arg);
#endif
}
static DWORD netcon_secure_connect_setup(netconn_t *connection, BOOL compat_mode)
{
SecBuffer out_buf = {0, SECBUFFER_TOKEN, NULL}, in_bufs[2] = {{0, SECBUFFER_TOKEN}, {0, SECBUFFER_EMPTY}};
@ -845,7 +853,7 @@ static BOOL read_ssl_chunk(netconn_t *conn, void *buf, SIZE_T buf_size, SIZE_T *
* Basically calls 'recv()' unless we should use SSL
* number of chars received is put in *recvd
*/
DWORD NETCON_recv(netconn_t *connection, void *buf, size_t len, int flags, int *recvd)
DWORD NETCON_recv(netconn_t *connection, void *buf, size_t len, blocking_mode_t mode, int *recvd)
{
*recvd = 0;
if (!len)
@ -853,6 +861,22 @@ DWORD NETCON_recv(netconn_t *connection, void *buf, size_t len, int flags, int *
if (!connection->secure)
{
int flags = 0;
switch(mode) {
case BLOCKING_ALLOW:
break;
case BLOCKING_DISALLOW:
#ifdef MSG_DONTWAIT
flags = MSG_DONTWAIT;
#endif
break;
case BLOCKING_WAITALL:
flags = MSG_WAITALL;
break;
}
set_socket_blocking(connection->socket, mode);
*recvd = recv(connection->socket, buf, len, flags);
return *recvd == -1 ? sock_get_error(errno) : ERROR_SUCCESS;
}
@ -872,12 +896,16 @@ DWORD NETCON_recv(netconn_t *connection, void *buf, size_t len, int flags, int *
connection->peek_msg_mem = connection->peek_msg = NULL;
}
/* check if we have enough data from the peek buffer */
if(!(flags & MSG_WAITALL) || size == len) {
if(mode != BLOCKING_WAITALL || size == len) {
*recvd = size;
return ERROR_SUCCESS;
}
}
if(mode == BLOCKING_DISALLOW)
return WSAEWOULDBLOCK; /* FIXME: We can do better */
set_socket_blocking(connection->socket, BLOCKING_ALLOW);
do {
res = read_ssl_chunk(connection, (BYTE*)buf+size, len-size, &cread, &eof);
if(!res) {
@ -893,7 +921,7 @@ DWORD NETCON_recv(netconn_t *connection, void *buf, size_t len, int flags, int *
}
size += cread;
}while(!size || ((flags & MSG_WAITALL) && size < len));
}while(!size || (mode == BLOCKING_WAITALL && size < len));
TRACE("received %ld bytes\n", size);
*recvd = size;