When sending a internal packet(eg:window adjust packet),
even we may blocked in the last call, try to send it normally
Signed-off-by: liuzl <xieepp_at_gmail.com>
--- src/channel.c | 37 +++++++------------------------------ src/transport.c | 12 +++++++++++- 2 files changed, 18 insertions(+), 31 deletions(-) diff --git a/src/channel.c b/src/channel.c index be6a680..c1e6cb0 100644 --- a/src/channel.c +++ b/src/channel.c @@ -1585,7 +1585,6 @@ _libssh2_channel_receive_window_adjust(LIBSSH2_CHANNEL * channel, return rc; } else if (rc) { - channel->adjust_queue = adjustment; return _libssh2_error(channel->session, LIBSSH2_ERROR_SOCKET_SEND, "Unable to send transfer-window adjustment " "packet, deferring"); @@ -1746,6 +1745,13 @@ ssize_t _libssh2_channel_read(LIBSSH2_CHANNEL *channel, int stream_id, LIBSSH2_PACKET *read_packet; LIBSSH2_PACKET *read_next; + if(channel->remote.window_size < (LIBSSH2_CHANNEL_WINDOW_DEFAULT*30)) { + /* the window is getting too narrow, expand it! + Ignore all the sending errors since we are receiving. */ + _libssh2_channel_receive_window_adjust(channel, + (LIBSSH2_CHANNEL_WINDOW_DEFAULT*60), 0, NULL); + } + if (channel->read_state == libssh2_NB_state_idle) { _libssh2_debug(session, LIBSSH2_TRACE_CONN, "channel_read() wants %d bytes from channel %lu/%lu " @@ -1765,15 +1771,6 @@ ssize_t _libssh2_channel_read(LIBSSH2_CHANNEL *channel, int stream_id, if ((rc < 0) && (rc != LIBSSH2_ERROR_EAGAIN)) return _libssh2_error(session, rc, "transport read"); - /* - * =============================== NOTE =============================== - * I know this is very ugly and not a really good use of "goto", but - * this case statement would be even uglier to do it any other way - */ - if (channel->read_state == libssh2_NB_state_jump1) { - goto channel_read_ex_point1; - } - read_packet = _libssh2_list_first(&session->packets); while (read_packet && (bytes_read < (int) buflen)) { /* previously this loop condition also checked for @@ -1871,26 +1868,6 @@ ssize_t _libssh2_channel_read(LIBSSH2_CHANNEL *channel, int stream_id, more off the network again */ channel->read_state = libssh2_NB_state_created; - if(channel->remote.window_size < (LIBSSH2_CHANNEL_WINDOW_DEFAULT*30)) { - /* the window is getting too narrow, expand it! */ - - channel_read_ex_point1: - channel->read_state = libssh2_NB_state_jump1; - /* the actual window adjusting may not finish so we need to deal with - this special state here */ - rc = _libssh2_channel_receive_window_adjust(channel, - (LIBSSH2_CHANNEL_WINDOW_DEFAULT*60), 0, NULL); - if (rc == LIBSSH2_ERROR_EAGAIN) - return rc; - - _libssh2_debug(session, LIBSSH2_TRACE_CONN, - "channel_read() filled %d adjusted %d", - bytes_read, buflen); - /* continue in 'created' state to drain the already read packages - first before starting to empty the socket further */ - channel->read_state = libssh2_NB_state_created; - } - return bytes_read; } diff --git a/src/transport.c b/src/transport.c index 057dcf5..7eecd25 100644 --- a/src/transport.c +++ b/src/transport.c @@ -596,7 +596,12 @@ send_existing(LIBSSH2_SESSION *session, const unsigned char *data, } /* send as much as possible of the existing packet */ - if ((data != p->odata) || (data_len != p->olen)) { + /* Very common scene: We may send receive-window-adjust packet at any time, + if we just blocked in the last call, will lead to LIBSSH2_ERROR_BAD_USE. + So, if the caller is an internal function, we try to send normally. This + behavior will be modified in the future. */ + if (data[0] == SSH_MSG_CHANNEL_DATA && p->odata[0] == SSH_MSG_CHANNEL_DATA + && ((data != p->odata) || (data_len != p->olen))) { /* When we are about to complete the sending of a packet, it is vital that the caller doesn't try to send a new/different packet since we don't add this one up until the previous one has been sent. To @@ -624,6 +629,11 @@ send_existing(LIBSSH2_SESSION *session, const unsigned char *data, } if (rc == length) { + /* The existing data have been sent completely, tell parent to continue + sending the new data. */ + if ((data != p->odata) || (data_len != p->olen)) + *ret = 0; + /* the remainder of the package was sent */ p->ototal_num = 0; p->olen = 0; -- 1.7.4.msysgit.0 _______________________________________________ libssh2-devel http://cool.haxx.se/cgi-bin/mailman/listinfo/libssh2-develReceived on 2011-09-06