Loading CHANGES +4 −0 Original line number Diff line number Diff line Loading @@ -7,6 +7,10 @@ Changelog Daniel Fandrich (3 Jun 2008) - Fixed a problem where telnet data would be lost if an EWOULDBLOCK condition were encountered. Marty Kuhrt (1 Jun 2008) - Updated main.c to return CURLE_OK if PARAM_HELP_REQUESTED was returned from getparameter instead of CURLE_FAILED_INIT. No point in returning Loading RELEASE-NOTES +1 −0 Original line number Diff line number Diff line Loading @@ -40,6 +40,7 @@ This release includes the following bugfixes: o follow redirect with only a new query string o SCP and SFTP memory leaks on aborted transfers o curl_multi_socket() and HTTP pipelining transfer stalls o lost telnet data on an EWOULDBLOCK condition This release includes the following known bugs: Loading lib/telnet.c +58 −46 Original line number Diff line number Diff line Loading @@ -1117,6 +1117,46 @@ void telrcv(struct connectdata *conn, bufferflush(); } /* Escape and send a telnet data block */ /* TODO: write large chunks of data instead of one byte at a time */ static CURLcode send_telnet_data(struct connectdata *conn, char *buffer, ssize_t nread) { unsigned char outbuf[2]; ssize_t bytes_written, total_written; int out_count; CURLcode rc = CURLE_OK; while(rc == CURLE_OK && nread--) { outbuf[0] = *buffer++; out_count = 1; if(outbuf[0] == CURL_IAC) outbuf[out_count++] = CURL_IAC; total_written = 0; do { /* Make sure socket is writable to avoid EWOULDBLOCK condition */ struct pollfd pfd[1]; pfd[0].fd = conn->sock[FIRSTSOCKET]; pfd[0].events = POLLOUT; switch (Curl_poll(pfd, 1, -1)) { case -1: /* error, abort writing */ case 0: /* timeout (will never happen) */ rc = CURLE_SEND_ERROR; break; default: /* write! */ bytes_written = 0; rc = Curl_write(conn, conn->sock[FIRSTSOCKET], outbuf+total_written, out_count-total_written, &bytes_written); total_written += bytes_written; break; } /* handle partial write */ } while (rc == CURLE_OK && total_written < out_count); } return rc; } static CURLcode telnet_done(struct connectdata *conn, CURLcode status, bool premature) { Loading Loading @@ -1270,36 +1310,27 @@ static CURLcode telnet_do(struct connectdata *conn, bool *done) switch(waitret) { case WAIT_TIMEOUT: { unsigned char outbuf[2]; int out_count = 0; ssize_t bytes_written; char *buffer = buf; while(1) { if(!PeekNamedPipe(stdin_handle, NULL, 0, NULL, &readfile_read, NULL)) { keepon = FALSE; code = CURLE_READ_ERROR; break; } nread = readfile_read; if(!nread) if(!readfile_read) break; if(!ReadFile(stdin_handle, buf, sizeof(data->state.buffer), &readfile_read, NULL)) { keepon = FALSE; code = CURLE_READ_ERROR; break; } nread = readfile_read; while(nread--) { outbuf[0] = *buffer++; out_count = 1; if(outbuf[0] == CURL_IAC) outbuf[out_count++] = CURL_IAC; Curl_write(conn, conn->sock[FIRSTSOCKET], outbuf, out_count, &bytes_written); code = send_telnet_data(conn, buf, readfile_read); if(code) { keepon = FALSE; break; } } } Loading @@ -1307,26 +1338,17 @@ static CURLcode telnet_do(struct connectdata *conn, bool *done) case WAIT_OBJECT_0 + 1: { unsigned char outbuf[2]; int out_count = 0; ssize_t bytes_written; char *buffer = buf; if(!ReadFile(stdin_handle, buf, sizeof(data->state.buffer), &readfile_read, NULL)) { keepon = FALSE; code = CURLE_READ_ERROR; break; } nread = readfile_read; while(nread--) { outbuf[0] = *buffer++; out_count = 1; if(outbuf[0] == CURL_IAC) outbuf[out_count++] = CURL_IAC; Curl_write(conn, conn->sock[FIRSTSOCKET], outbuf, out_count, &bytes_written); code = send_telnet_data(conn, buf, readfile_read); if(code) { keepon = FALSE; break; } } break; Loading Loading @@ -1389,21 +1411,11 @@ static CURLcode telnet_do(struct connectdata *conn, bool *done) break; default: /* read! */ if(pfd[1].revents & POLLIN) { /* read from stdin */ unsigned char outbuf[2]; int out_count = 0; ssize_t bytes_written; char *buffer = buf; nread = read(0, buf, 255); while(nread--) { outbuf[0] = *buffer++; out_count = 1; if(outbuf[0] == CURL_IAC) outbuf[out_count++] = CURL_IAC; Curl_write(conn, conn->sock[FIRSTSOCKET], outbuf, out_count, &bytes_written); code = send_telnet_data(conn, buf, nread); if(code) { keepon = FALSE; break; } } Loading Loading
CHANGES +4 −0 Original line number Diff line number Diff line Loading @@ -7,6 +7,10 @@ Changelog Daniel Fandrich (3 Jun 2008) - Fixed a problem where telnet data would be lost if an EWOULDBLOCK condition were encountered. Marty Kuhrt (1 Jun 2008) - Updated main.c to return CURLE_OK if PARAM_HELP_REQUESTED was returned from getparameter instead of CURLE_FAILED_INIT. No point in returning Loading
RELEASE-NOTES +1 −0 Original line number Diff line number Diff line Loading @@ -40,6 +40,7 @@ This release includes the following bugfixes: o follow redirect with only a new query string o SCP and SFTP memory leaks on aborted transfers o curl_multi_socket() and HTTP pipelining transfer stalls o lost telnet data on an EWOULDBLOCK condition This release includes the following known bugs: Loading
lib/telnet.c +58 −46 Original line number Diff line number Diff line Loading @@ -1117,6 +1117,46 @@ void telrcv(struct connectdata *conn, bufferflush(); } /* Escape and send a telnet data block */ /* TODO: write large chunks of data instead of one byte at a time */ static CURLcode send_telnet_data(struct connectdata *conn, char *buffer, ssize_t nread) { unsigned char outbuf[2]; ssize_t bytes_written, total_written; int out_count; CURLcode rc = CURLE_OK; while(rc == CURLE_OK && nread--) { outbuf[0] = *buffer++; out_count = 1; if(outbuf[0] == CURL_IAC) outbuf[out_count++] = CURL_IAC; total_written = 0; do { /* Make sure socket is writable to avoid EWOULDBLOCK condition */ struct pollfd pfd[1]; pfd[0].fd = conn->sock[FIRSTSOCKET]; pfd[0].events = POLLOUT; switch (Curl_poll(pfd, 1, -1)) { case -1: /* error, abort writing */ case 0: /* timeout (will never happen) */ rc = CURLE_SEND_ERROR; break; default: /* write! */ bytes_written = 0; rc = Curl_write(conn, conn->sock[FIRSTSOCKET], outbuf+total_written, out_count-total_written, &bytes_written); total_written += bytes_written; break; } /* handle partial write */ } while (rc == CURLE_OK && total_written < out_count); } return rc; } static CURLcode telnet_done(struct connectdata *conn, CURLcode status, bool premature) { Loading Loading @@ -1270,36 +1310,27 @@ static CURLcode telnet_do(struct connectdata *conn, bool *done) switch(waitret) { case WAIT_TIMEOUT: { unsigned char outbuf[2]; int out_count = 0; ssize_t bytes_written; char *buffer = buf; while(1) { if(!PeekNamedPipe(stdin_handle, NULL, 0, NULL, &readfile_read, NULL)) { keepon = FALSE; code = CURLE_READ_ERROR; break; } nread = readfile_read; if(!nread) if(!readfile_read) break; if(!ReadFile(stdin_handle, buf, sizeof(data->state.buffer), &readfile_read, NULL)) { keepon = FALSE; code = CURLE_READ_ERROR; break; } nread = readfile_read; while(nread--) { outbuf[0] = *buffer++; out_count = 1; if(outbuf[0] == CURL_IAC) outbuf[out_count++] = CURL_IAC; Curl_write(conn, conn->sock[FIRSTSOCKET], outbuf, out_count, &bytes_written); code = send_telnet_data(conn, buf, readfile_read); if(code) { keepon = FALSE; break; } } } Loading @@ -1307,26 +1338,17 @@ static CURLcode telnet_do(struct connectdata *conn, bool *done) case WAIT_OBJECT_0 + 1: { unsigned char outbuf[2]; int out_count = 0; ssize_t bytes_written; char *buffer = buf; if(!ReadFile(stdin_handle, buf, sizeof(data->state.buffer), &readfile_read, NULL)) { keepon = FALSE; code = CURLE_READ_ERROR; break; } nread = readfile_read; while(nread--) { outbuf[0] = *buffer++; out_count = 1; if(outbuf[0] == CURL_IAC) outbuf[out_count++] = CURL_IAC; Curl_write(conn, conn->sock[FIRSTSOCKET], outbuf, out_count, &bytes_written); code = send_telnet_data(conn, buf, readfile_read); if(code) { keepon = FALSE; break; } } break; Loading Loading @@ -1389,21 +1411,11 @@ static CURLcode telnet_do(struct connectdata *conn, bool *done) break; default: /* read! */ if(pfd[1].revents & POLLIN) { /* read from stdin */ unsigned char outbuf[2]; int out_count = 0; ssize_t bytes_written; char *buffer = buf; nread = read(0, buf, 255); while(nread--) { outbuf[0] = *buffer++; out_count = 1; if(outbuf[0] == CURL_IAC) outbuf[out_count++] = CURL_IAC; Curl_write(conn, conn->sock[FIRSTSOCKET], outbuf, out_count, &bytes_written); code = send_telnet_data(conn, buf, nread); if(code) { keepon = FALSE; break; } } Loading