diff -u -r mysql-4.1.13-nightly-20050706.orig/include/violite.h mysql-4.1.13-nightly-20050706/include/violite.h --- mysql-4.1.13-nightly-20050706.orig/include/violite.h 2005-07-06 13:50:35.176417456 +0200 +++ mysql-4.1.13-nightly-20050706/include/violite.h 2005-07-06 13:51:13.854537488 +0200 @@ -37,6 +37,12 @@ VIO_TYPE_SSL, VIO_TYPE_SHARED_MEMORY }; +typedef enum enum_timeout_type +{ + VIO_READ_TIMEOUT, + VIO_WRITE_TIMEOUT +} timeout_type; + Vio* vio_new(my_socket sd, enum enum_vio_type type, my_bool localhost); #ifdef __WIN__ Vio* vio_new_win32pipe(HANDLE hPipe); @@ -81,7 +87,7 @@ /* Remotes in_addr */ void vio_in_addr(Vio *vio, struct in_addr *in); my_bool vio_poll_read(Vio *vio,uint timeout); -void vio_timeout(Vio *vio,uint which, uint timeout); +void vio_timeout(Vio *vio, timeout_type which, uint milliseconds); #ifdef HAVE_OPENSSL #include @@ -149,7 +155,7 @@ #define vio_close(vio) ((vio)->vioclose)(vio) #define vio_peer_addr(vio, buf, prt) (vio)->peer_addr(vio, buf, prt) #define vio_in_addr(vio, in) (vio)->in_addr(vio, in) -#define vio_timeout(vio, which, seconds) (vio)->timeout(vio, which, seconds) +#define vio_timeout(vio, which, milliseconds) (vio)->timeout((vio), (which), (milliseconds)) #endif /* defined(HAVE_VIO) && !defined(DONT_MAP_VIO) */ /* This enumerator is used in parser - should be always visible */ @@ -189,7 +195,7 @@ void (*in_addr)(Vio*, struct in_addr*); my_bool (*should_retry)(Vio*); int (*vioclose)(Vio*); - void (*timeout)(Vio*, unsigned int which, unsigned int timeout); + void (*timeout)(Vio*, timeout_type which, uint milliseconds); void *ssl_arg; #ifdef HAVE_SMEM HANDLE handle_file_map; diff -u -r mysql-4.1.13-nightly-20050706.orig/sql/net_serv.cc mysql-4.1.13-nightly-20050706/sql/net_serv.cc --- mysql-4.1.13-nightly-20050706.orig/sql/net_serv.cc 2005-07-06 13:50:39.429770848 +0200 +++ mysql-4.1.13-nightly-20050706/sql/net_serv.cc 2005-07-06 13:51:13.855537336 +0200 @@ -485,13 +485,10 @@ #endif /* HAVE_COMPRESS */ /* DBUG_DUMP("net",packet,len); */ -#ifndef NO_ALARM thr_alarm_init(&alarmed); +#ifndef NO_ALARM if (net_blocking) thr_alarm(&alarmed,(uint) net->write_timeout,&alarm_buff); -#else - alarmed=0; - vio_timeout(net->vio, 1, net->write_timeout); #endif /* NO_ALARM */ pos=(char*) packet; end=pos+len; @@ -506,9 +503,10 @@ if (!thr_alarm(&alarmed,(uint) net->write_timeout,&alarm_buff)) { /* Always true for client */ my_bool old_mode; + uint retry_fcntl = 0; while (vio_blocking(net->vio, TRUE, &old_mode) < 0) { - if (vio_should_retry(net->vio) && retry_count++ < net->retry_count) + if (vio_should_retry(net->vio) && retry_fcntl++ < net->retry_count) continue; #ifdef EXTRA_DEBUG fprintf(stderr, @@ -522,8 +520,8 @@ net->report_error= 1; goto end; } - retry_count=0; - continue; + if (retry_count++ < net->retry_count) + continue; } } else @@ -539,7 +537,7 @@ #endif /* EXTRA_DEBUG */ } #if defined(THREAD_SAFE_CLIENT) && !defined(MYSQL_SERVER) - if (vio_errno(net->vio) == SOCKET_EINTR) + if (interrupted && retry_count++ < net->retry_count) { DBUG_PRINT("warning",("Interrupted write. Retrying...")); continue; @@ -683,8 +681,6 @@ #ifndef NO_ALARM if (net_blocking) thr_alarm(&alarmed,net->read_timeout,&alarm_buff); -#else - vio_timeout(net->vio, 0, net->read_timeout); #endif /* NO_ALARM */ pos = net->buff + net->where_b; /* net->packet -4 */ @@ -710,10 +706,11 @@ if (!thr_alarm(&alarmed,net->read_timeout,&alarm_buff)) /* Don't wait too long */ { my_bool old_mode; + uint retry_fcntl = 0; while (vio_blocking(net->vio, TRUE, &old_mode) < 0) { if (vio_should_retry(net->vio) && - retry_count++ < net->retry_count) + retry_fcntl++ < net->retry_count) continue; DBUG_PRINT("error", ("fcntl returned error %d, aborting thread", @@ -731,8 +728,8 @@ #endif goto end; } - retry_count=0; - continue; + if (retry_count++ < net->retry_count) + continue; } } #endif /* (!defined(__WIN__) && !defined(__EMX__)) || defined(MYSQL_SERVER) */ @@ -747,7 +744,7 @@ #endif /* EXTRA_DEBUG */ } #if defined(THREAD_SAFE_CLIENT) && !defined(MYSQL_SERVER) - if (vio_should_retry(net->vio)) + if (interrupted && retry_count++ < net->retry_count) { DBUG_PRINT("warning",("Interrupted read. Retrying...")); continue; diff -u -r mysql-4.1.13-nightly-20050706.orig/sql-common/client.c mysql-4.1.13-nightly-20050706/sql-common/client.c --- mysql-4.1.13-nightly-20050706.orig/sql-common/client.c 2005-07-06 13:50:37.151117256 +0200 +++ mysql-4.1.13-nightly-20050706/sql-common/client.c 2005-07-06 13:51:13.857537032 +0200 @@ -1800,9 +1800,17 @@ vio_keepalive(net->vio,TRUE); /* Override local client variables */ if (mysql->options.read_timeout) - net->read_timeout= mysql->options.read_timeout; + { + net->read_timeout = mysql->options.read_timeout; + vio_timeout(net->vio, VIO_READ_TIMEOUT, + net->read_timeout * 1000 / (net->retry_count + 1)); + } if (mysql->options.write_timeout) - net->write_timeout= mysql->options.write_timeout; + { + net->write_timeout = mysql->options.write_timeout; + vio_timeout(net->vio, VIO_WRITE_TIMEOUT, + net->write_timeout * 1000 / (net->retry_count + 1)); + } if (mysql->options.max_allowed_packet) net->max_packet_size= mysql->options.max_allowed_packet; diff -u -r mysql-4.1.13-nightly-20050706.orig/vio/viosocket.c mysql-4.1.13-nightly-20050706/vio/viosocket.c --- mysql-4.1.13-nightly-20050706.orig/vio/viosocket.c 2005-07-06 13:50:39.336784984 +0200 +++ mysql-4.1.13-nightly-20050706/vio/viosocket.c 2005-07-06 13:51:13.857537032 +0200 @@ -34,13 +34,7 @@ int r; DBUG_ENTER("vio_read"); DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size)); - -#ifdef __WIN__ - r = recv(vio->sd, buf, size,0); -#else - errno=0; /* For linux */ - r = read(vio->sd, buf, size); -#endif /* __WIN__ */ + r = recv(vio->sd, buf, size, 0); #ifndef DBUG_OFF if (r < 0) { @@ -57,11 +51,7 @@ int r; DBUG_ENTER("vio_write"); DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size)); -#ifdef __WIN__ - r = send(vio->sd, buf, size,0); -#else - r = write(vio->sd, buf, size); -#endif /* __WIN__ */ + r = send(vio->sd, buf, size, 0); #ifndef DBUG_OFF if (r < 0) { @@ -317,15 +307,33 @@ } -void vio_timeout(Vio *vio __attribute__((unused)), - uint which __attribute__((unused)), - uint timeout __attribute__((unused))) +void vio_timeout(Vio *vio, timeout_type which, uint milliseconds) { #ifdef __WIN__ - ulong wait_timeout= (ulong) timeout * 1000; - (void) setsockopt(vio->sd, SOL_SOCKET, - which ? SO_SNDTIMEO : SO_RCVTIMEO, (char*) &wait_timeout, - sizeof(wait_timeout)); + ulong wait_timeout; +#else + struct timeval tv; +#endif /* __WIN__ */ + int optname; + switch (which) + { + case VIO_READ_TIMEOUT: + optname = SO_RCVTIMEO; + break; + case VIO_WRITE_TIMEOUT: + optname = SO_SNDTIMEO; + break; + default: + return; + } +#ifdef __WIN__ + wait_timeout= (ulong) milliseconds; + setsockopt(vio->sd, SOL_SOCKET, optname, (char*) &wait_timeout, + sizeof(wait_timeout)); +#else + tv.tv_sec = milliseconds / 1000; + tv.tv_usec = milliseconds % 1000 * 1000; + setsockopt(vio->sd, SOL_SOCKET, optname, &tv, sizeof(tv)); #endif /* __WIN__ */ }