1
1

move over lots of code to the _libssh2_list_* functions

and I fixed a few minor bugs at the same time
Этот коммит содержится в:
Daniel Stenberg 2009-08-20 00:56:05 +02:00
родитель a871f0b214
Коммит d8b6f3c7b8
6 изменённых файлов: 150 добавлений и 281 удалений

Просмотреть файл

@ -61,13 +61,13 @@ _libssh2_channel_nextid(LIBSSH2_SESSION * session)
unsigned long id = session->next_channel;
LIBSSH2_CHANNEL *channel;
channel = session->channels.head;
channel = _libssh2_list_first(&session->channels);
while (channel) {
if (channel->local.id > id) {
id = channel->local.id;
}
channel = channel->next;
channel = _libssh2_list_next(&channel->node);
}
/* This is a shortcut to avoid waiting for close packets on channels we've
@ -94,16 +94,21 @@ _libssh2_channel_locate(LIBSSH2_SESSION *session, unsigned long channel_id)
LIBSSH2_CHANNEL *channel;
LIBSSH2_LISTENER *l;
for(channel = session->channels.head; channel; channel = channel->next) {
for(channel = _libssh2_list_first(&session->channels);
channel;
channel = _libssh2_list_next(&channel->node)) {
if (channel->local.id == channel_id)
return channel;
}
/* We didn't find the channel in the session, let's then check its
listeners... */
listeners since each listener may have its own set of pending channels
*/
for(l = _libssh2_list_first(&session->listeners); l;
l = _libssh2_list_next(&l->node)) {
for(channel = l->queue; channel; channel = channel->next) {
for(channel = _libssh2_list_first(&l->queue);
channel;
channel = _libssh2_list_next(&channel->node)) {
if (channel->local.id == channel_id)
return channel;
}
@ -112,20 +117,6 @@ _libssh2_channel_locate(LIBSSH2_SESSION *session, unsigned long channel_id)
return NULL;
}
#define CHANNEL_ADD(session, channel) \
{ \
if ((session)->channels.tail) { \
(session)->channels.tail->next = (channel); \
(channel)->prev = (session)->channels.tail; \
} else { \
(session)->channels.head = (channel); \
(channel)->prev = NULL; \
} \
(channel)->next = NULL; \
(session)->channels.tail = (channel); \
(channel)->session = (session); \
}
/*
* _libssh2_channel_open
*
@ -188,8 +179,10 @@ _libssh2_channel_open(LIBSSH2_SESSION * session, const char *channel_type,
session->open_channel->remote.window_size = window_size;
session->open_channel->remote.window_size_initial = window_size;
session->open_channel->remote.packet_size = packet_size;
session->open_channel->session = session;
CHANNEL_ADD(session, session->open_channel);
_libssh2_list_add(&session->channels,
&session->open_channel->node);
s = session->open_packet =
LIBSSH2_ALLOC(session, session->open_packet_len);
@ -299,18 +292,7 @@ _libssh2_channel_open(LIBSSH2_SESSION * session, const char *channel_type,
unsigned char channel_id[4];
LIBSSH2_FREE(session, session->open_channel->channel_type);
if (session->open_channel->next) {
session->open_channel->next->prev = session->open_channel->prev;
}
if (session->open_channel->prev) {
session->open_channel->prev->next = session->open_channel->next;
}
if (session->channels.head == session->open_channel) {
session->channels.head = session->open_channel->next;
}
if (session->channels.tail == session->open_channel) {
session->channels.tail = session->open_channel->prev;
}
_libssh2_list_remove(&session->open_channel->node);
/* Clear out packets meant for this channel */
_libssh2_htonu32(channel_id, session->open_channel->local.id);
@ -639,7 +621,7 @@ libssh2_channel_forward_listen_ex(LIBSSH2_SESSION *session, const char *host,
static int channel_forward_cancel(LIBSSH2_LISTENER *listener)
{
LIBSSH2_SESSION *session = listener->session;
LIBSSH2_CHANNEL *queued = listener->queue;
LIBSSH2_CHANNEL *queued;
unsigned char *packet, *s;
unsigned long host_len = strlen(listener->host);
/* 14 = packet_type(1) + request_len(4) + want_replay(1) + host_len(4) +
@ -699,8 +681,9 @@ static int channel_forward_cancel(LIBSSH2_LISTENER *listener)
listener->chanFwdCncl_state = libssh2_NB_state_sent;
}
queued = _libssh2_list_first(&listener->queue);
while (queued) {
LIBSSH2_CHANNEL *next = queued->next;
LIBSSH2_CHANNEL *next = _libssh2_list_next(&queued->node);
rc = libssh2_channel_free(queued);
if (rc == PACKET_EAGAIN) {
@ -755,28 +738,17 @@ channel_forward_accept(LIBSSH2_LISTENER *listener)
}
} while (rc > 0);
if (listener->queue) {
LIBSSH2_SESSION *session = listener->session;
LIBSSH2_CHANNEL *channel;
if (_libssh2_list_first(&listener->queue)) {
LIBSSH2_CHANNEL *channel = _libssh2_list_first(&listener->queue);
channel = listener->queue;
/* detach channel from listener's queue */
_libssh2_list_remove(&channel->node);
listener->queue = listener->queue->next;
if (listener->queue) {
listener->queue->prev = NULL;
}
channel->prev = NULL;
channel->next = session->channels.head;
session->channels.head = channel;
if (channel->next) {
channel->next->prev = channel;
} else {
session->channels.tail = channel;
}
listener->queue_size--;
/* add channel to session's channel list */
_libssh2_list_add(&channel->session->channels, &channel->node);
return channel;
}
@ -1455,14 +1427,14 @@ libssh2_channel_set_blocking(LIBSSH2_CHANNEL * channel, int blocking)
int
_libssh2_channel_flush(LIBSSH2_CHANNEL *channel, int streamid)
{
LIBSSH2_PACKET *packet = channel->session->packets.head;
if (channel->flush_state == libssh2_NB_state_idle) {
LIBSSH2_PACKET *packet =
_libssh2_list_first(&channel->session->packets);
channel->flush_refund_bytes = 0;
channel->flush_flush_bytes = 0;
while (packet) {
LIBSSH2_PACKET *next = packet->next;
LIBSSH2_PACKET *next = _libssh2_list_next(&packet->node);
unsigned char packet_type = packet->data[0];
if (((packet_type == SSH_MSG_CHANNEL_DATA)
@ -1470,9 +1442,8 @@ _libssh2_channel_flush(LIBSSH2_CHANNEL *channel, int streamid)
&& (_libssh2_ntohu32(packet->data + 1) == channel->local.id)) {
/* It's our channel at least */
long packet_stream_id =
(packet_type ==
SSH_MSG_CHANNEL_DATA) ? 0 : _libssh2_ntohu32(packet->data +
5);
(packet_type == SSH_MSG_CHANNEL_DATA) ? 0 :
_libssh2_ntohu32(packet->data + 5);
if ((streamid == LIBSSH2_CHANNEL_FLUSH_ALL)
|| ((packet_type == SSH_MSG_CHANNEL_EXTENDED_DATA)
&& ((streamid == LIBSSH2_CHANNEL_FLUSH_EXTENDED_DATA)
@ -1492,16 +1463,9 @@ _libssh2_channel_flush(LIBSSH2_CHANNEL *channel, int streamid)
channel->flush_flush_bytes += bytes_to_flush;
LIBSSH2_FREE(channel->session, packet->data);
if (packet->prev) {
packet->prev->next = packet->next;
} else {
channel->session->packets.head = packet->next;
}
if (packet->next) {
packet->next->prev = packet->prev;
} else {
channel->session->packets.tail = packet->prev;
}
/* remove this packet from the parent's list */
_libssh2_list_remove(&packet->node);
LIBSSH2_FREE(channel->session, packet);
}
}
@ -1754,6 +1718,8 @@ static ssize_t channel_read(LIBSSH2_CHANNEL *channel, int stream_id,
int bytes_read = 0;
int bytes_want;
int unlink_packet;
LIBSSH2_PACKET *read_packet;
LIBSSH2_PACKET *read_next;
if (channel->read_state == libssh2_NB_state_idle) {
_libssh2_debug(session, LIBSSH2_DBG_CONN,
@ -1785,9 +1751,8 @@ static ssize_t channel_read(LIBSSH2_CHANNEL *channel, int stream_id,
rc = 0;
channel->read_packet = session->packets.head;
while (channel->read_packet &&
(bytes_read < (int) buflen)) {
read_packet = _libssh2_list_first(&session->packets);
while (read_packet && (bytes_read < (int) buflen)) {
/* previously this loop condition also checked for
!channel->remote.close but we cannot let it do this:
@ -1796,10 +1761,10 @@ static ssize_t channel_read(LIBSSH2_CHANNEL *channel, int stream_id,
makes us flush buffers prematurely and loose data.
*/
LIBSSH2_PACKET *readpkt = channel->read_packet;
LIBSSH2_PACKET *readpkt = read_packet;
/* In case packet gets destroyed during this iteration */
channel->read_next = readpkt->next;
read_next = _libssh2_list_next(&readpkt->node);
channel->read_local_id =
_libssh2_ntohu32(readpkt->data + 1);
@ -1850,23 +1815,16 @@ static ssize_t channel_read(LIBSSH2_CHANNEL *channel, int stream_id,
/* if drained, remove from list */
if (unlink_packet) {
if (readpkt->prev) {
readpkt->prev->next = readpkt->next;
} else {
session->packets.head = readpkt->next;
}
if (readpkt->next) {
readpkt->next->prev = readpkt->prev;
} else {
session->packets.tail = readpkt->prev;
}
/* detach readpkt from session->packets list */
_libssh2_list_remove(&readpkt->node);
LIBSSH2_FREE(session, readpkt->data);
LIBSSH2_FREE(session, readpkt);
}
}
/* check the next struct in the chain */
channel->read_packet = channel->read_next;
read_packet = read_next;
}
if (bytes_read == 0) {
@ -1949,9 +1907,9 @@ _libssh2_channel_packet_data_len(LIBSSH2_CHANNEL * channel, int stream_id)
LIBSSH2_PACKET *read_packet;
uint32_t read_local_id;
if ((read_packet = session->packets.head) == NULL) {
read_packet = _libssh2_list_first(&session->packets);
if (read_packet == NULL)
return 0;
}
while (read_packet) {
read_local_id = _libssh2_ntohu32(read_packet->data + 1);
@ -1980,7 +1938,7 @@ _libssh2_channel_packet_data_len(LIBSSH2_CHANNEL * channel, int stream_id)
{
return (read_packet->data_len - read_packet->data_head);
}
read_packet = read_packet->next;
read_packet = _libssh2_list_next(&read_packet->node);
}
return 0;
@ -2205,7 +2163,7 @@ LIBSSH2_API int
libssh2_channel_eof(LIBSSH2_CHANNEL * channel)
{
LIBSSH2_SESSION *session = channel->session;
LIBSSH2_PACKET *packet = session->packets.head;
LIBSSH2_PACKET *packet = _libssh2_list_first(&session->packets);
while (packet) {
if (((packet->data[0] == SSH_MSG_CHANNEL_DATA)
@ -2214,7 +2172,7 @@ libssh2_channel_eof(LIBSSH2_CHANNEL * channel)
/* There's data waiting to be read yet, mask the EOF status */
return 0;
}
packet = packet->next;
packet = _libssh2_list_next(&packet->node);
}
return channel->remote.eof;
@ -2473,17 +2431,8 @@ int _libssh2_channel_free(LIBSSH2_CHANNEL *channel)
LIBSSH2_FREE(session, channel->channel_type);
}
/* Unlink from channel brigade */
if (channel->prev) {
channel->prev->next = channel->next;
} else {
session->channels.head = channel->next;
}
if (channel->next) {
channel->next->prev = channel->prev;
} else {
session->channels.tail = channel->prev;
}
/* Unlink from channel list */
_libssh2_list_remove(&channel->node);
/*
* Make sure all memory used in the state variables are free
@ -2544,7 +2493,8 @@ libssh2_channel_window_read_ex(LIBSSH2_CHANNEL * channel,
if (read_avail) {
unsigned long bytes_queued = 0;
LIBSSH2_PACKET *packet = channel->session->packets.head;
LIBSSH2_PACKET *packet =
_libssh2_list_first(&channel->session->packets);
while (packet) {
unsigned char packet_type = packet->data[0];
@ -2555,7 +2505,7 @@ libssh2_channel_window_read_ex(LIBSSH2_CHANNEL * channel,
bytes_queued += packet->data_len - packet->data_head;
}
packet = packet->next;
packet = _libssh2_list_next(&packet->node);
}
*read_avail = bytes_queued;

Просмотреть файл

@ -188,8 +188,6 @@ typedef struct _LIBSSH2_CRYPT_METHOD LIBSSH2_CRYPT_METHOD;
typedef struct _LIBSSH2_COMP_METHOD LIBSSH2_COMP_METHOD;
typedef struct _LIBSSH2_PACKET LIBSSH2_PACKET;
typedef struct _LIBSSH2_PACKET_BRIGADE LIBSSH2_PACKET_BRIGADE;
typedef struct _LIBSSH2_CHANNEL_BRIGADE LIBSSH2_CHANNEL_BRIGADE;
typedef int libssh2pack_t;
@ -289,6 +287,7 @@ typedef struct packet_queue_listener_state_t
uint32_t sport;
uint32_t host_len;
uint32_t shost_len;
LIBSSH2_CHANNEL *channel;
} packet_queue_listener_state_t;
#define X11FwdUnAvil "X11 Forward Unavailable"
@ -303,10 +302,13 @@ typedef struct packet_x11_open_state_t
uint32_t packet_size;
uint32_t sport;
uint32_t shost_len;
LIBSSH2_CHANNEL *channel;
} packet_x11_open_state_t;
struct _LIBSSH2_PACKET
{
struct list_node node; /* linked list header */
unsigned char type;
/* Unencrypted Payload (no type byte, no padding, just the facts ma'am) */
@ -319,15 +321,6 @@ struct _LIBSSH2_PACKET
/* Can the message be confirmed? */
int mac;
LIBSSH2_PACKET_BRIGADE *brigade;
LIBSSH2_PACKET *next, *prev;
};
struct _LIBSSH2_PACKET_BRIGADE
{
LIBSSH2_PACKET *head, *tail;
};
typedef struct _libssh2_channel_data
@ -344,6 +337,8 @@ typedef struct _libssh2_channel_data
struct _LIBSSH2_CHANNEL
{
struct list_node node;
unsigned char *channel_type;
unsigned channel_type_len;
@ -356,8 +351,6 @@ struct _LIBSSH2_CHANNEL
LIBSSH2_SESSION *session;
LIBSSH2_CHANNEL *next, *prev;
void *abstract;
LIBSSH2_CHANNEL_CLOSE_FUNC((*close_cb));
@ -400,8 +393,6 @@ struct _LIBSSH2_CHANNEL
/* State variables used in libssh2_channel_read_ex() */
libssh2_nonblocking_states read_state;
LIBSSH2_PACKET *read_packet;
LIBSSH2_PACKET *read_next;
uint32_t read_local_id;
@ -430,11 +421,6 @@ struct _LIBSSH2_CHANNEL
libssh2_nonblocking_states extData2_state;
};
struct _LIBSSH2_CHANNEL_BRIGADE
{
LIBSSH2_CHANNEL *head, *tail;
};
struct _LIBSSH2_LISTENER
{
struct list_node node; /* linked list header */
@ -444,7 +430,9 @@ struct _LIBSSH2_LISTENER
char *host;
int port;
LIBSSH2_CHANNEL *queue;
/* a list of CHANNELs for this listener */
struct list_head queue;
int queue_size;
int queue_maxsize;
@ -588,7 +576,7 @@ struct _LIBSSH2_SFTP
unsigned long request_id, version;
LIBSSH2_PACKET_BRIGADE packets;
struct list_head packets;
/* a list of _LIBSSH2_SFTP_HANDLE structs */
struct list_head sftp_handles;
@ -716,12 +704,13 @@ struct _LIBSSH2_SESSION
/* (local as source of data -- packet_write ) */
libssh2_endpoint_data local;
/* Inbound Data buffer -- Sometimes the packet that comes in isn't the
/* Inbound Data linked list -- Sometimes the packet that comes in isn't the
packet we're ready for */
LIBSSH2_PACKET_BRIGADE packets;
struct list_head packets;
/* Active connection channels */
LIBSSH2_CHANNEL_BRIGADE channels;
struct list_head channels;
unsigned long next_channel;
struct list_head listeners; /* list of LIBSSH2_LISTENER structs */
@ -814,7 +803,7 @@ struct _LIBSSH2_SESSION
unsigned char *userauth_pblc_b;
packet_requirev_state_t userauth_pblc_packet_requirev_state;
/* State variables used in llibssh2_userauth_keyboard_interactive_ex() */
/* State variables used in libssh2_userauth_keyboard_interactive_ex() */
libssh2_nonblocking_states userauth_kybd_state;
unsigned char *userauth_kybd_data;
unsigned long userauth_kybd_data_len;
@ -863,7 +852,6 @@ struct _LIBSSH2_SESSION
/* State variables used in libssh2_packet_add() */
libssh2_nonblocking_states packAdd_state;
LIBSSH2_PACKET *packAdd_packet;
LIBSSH2_CHANNEL *packAdd_channel;
unsigned long packAdd_data_head;
key_exchange_state_t packAdd_key_state;

Просмотреть файл

@ -69,7 +69,7 @@
static inline int
packet_queue_listener(LIBSSH2_SESSION * session, unsigned char *data,
unsigned long datalen,
packet_queue_listener_state_t * listen_state)
packet_queue_listener_state_t *listen_state)
{
/*
* Look for a matching listener
@ -119,13 +119,12 @@ packet_queue_listener(LIBSSH2_SESSION * session, unsigned char *data,
while (listen) {
if ((listen->port == (int) listen_state->port) &&
(strlen(listen->host) == listen_state->host_len) &&
(memcmp
(listen->host, listen_state->host,
(memcmp (listen->host, listen_state->host,
listen_state->host_len) == 0)) {
/* This is our listener */
LIBSSH2_CHANNEL *channel = NULL, *last_queued = listen->queue;
LIBSSH2_CHANNEL *channel = NULL;
listen_state->channel = NULL;
last_queued = listen->queue;
if (listen_state->state == libssh2_NB_state_allocated) {
if (listen->queue_maxsize &&
(listen->queue_maxsize <= listen->queue_size)) {
@ -206,9 +205,9 @@ packet_queue_listener(LIBSSH2_SESSION * session, unsigned char *data,
if (listen_state->state == libssh2_NB_state_created) {
rc = _libssh2_transport_write(session, listen_state->packet,
17);
if (rc == PACKET_EAGAIN) {
if (rc == PACKET_EAGAIN)
return PACKET_EAGAIN;
} else if (rc) {
else if (rc) {
libssh2_error(session, LIBSSH2_ERROR_SOCKET_SEND,
"Unable to send channel open confirmation",
0);
@ -217,20 +216,8 @@ packet_queue_listener(LIBSSH2_SESSION * session, unsigned char *data,
}
/* Link the channel into the end of the queue list */
if (!last_queued) {
listen->queue = channel;
listen_state->state = libssh2_NB_state_idle;
return 0;
}
while (last_queued->next) {
last_queued = last_queued->next;
}
last_queued->next = channel;
channel->prev = last_queued;
_libssh2_list_add(&listen->queue,
&listen_state->channel->node);
listen->queue_size++;
listen_state->state = libssh2_NB_state_idle;
@ -245,7 +232,6 @@ packet_queue_listener(LIBSSH2_SESSION * session, unsigned char *data,
}
/* We're not listening to you */
{
p = listen_state->packet;
*(p++) = SSH_MSG_CHANNEL_OPEN_FAILURE;
_libssh2_htonu32(p, listen_state->sender_channel);
@ -270,7 +256,6 @@ packet_queue_listener(LIBSSH2_SESSION * session, unsigned char *data,
}
listen_state->state = libssh2_NB_state_idle;
return 0;
}
}
/*
@ -281,14 +266,14 @@ packet_queue_listener(LIBSSH2_SESSION * session, unsigned char *data,
static inline int
packet_x11_open(LIBSSH2_SESSION * session, unsigned char *data,
unsigned long datalen,
packet_x11_open_state_t * x11open_state)
packet_x11_open_state_t *x11open_state)
{
int failure_code = 2; /* SSH_OPEN_CONNECT_FAILED */
unsigned char *s = data + (sizeof("x11") - 1) + 5;
/* 17 = packet_type(1) + channel(4) + reason(4) + descr(4) + lang(4) */
unsigned long packet_len = 17 + (sizeof(X11FwdUnAvil) - 1);
unsigned char *p;
LIBSSH2_CHANNEL *channel = NULL;
LIBSSH2_CHANNEL *channel = x11open_state->channel;
int rc;
(void) datalen;
@ -388,21 +373,13 @@ packet_x11_open(LIBSSH2_SESSION * session, unsigned char *data,
}
/* Link the channel into the session */
if (session->channels.tail) {
session->channels.tail->next = channel;
channel->prev = session->channels.tail;
} else {
session->channels.head = channel;
channel->prev = NULL;
}
channel->next = NULL;
session->channels.tail = channel;
_libssh2_list_add(&session->channels, &channel->node);
/*
* Pass control to the callback, they may turn right around and
* free the channel, or actually use it
*/
LIBSSH2_X11_OPEN(channel, (char *) x11open_state->shost,
LIBSSH2_X11_OPEN(channel, (char *)x11open_state->shost,
x11open_state->sport);
x11open_state->state = libssh2_NB_state_idle;
@ -813,19 +790,15 @@ _libssh2_packet_add(LIBSSH2_SESSION * session, unsigned char *data,
if ((datalen >= (sizeof("forwarded-tcpip") + 4)) &&
((sizeof("forwarded-tcpip") - 1) == _libssh2_ntohu32(data + 1))
&&
(memcmp
(data + 5, "forwarded-tcpip",
(memcmp(data + 5, "forwarded-tcpip",
sizeof("forwarded-tcpip") - 1) == 0)) {
libssh2_packet_add_jump_point2:
session->packAdd_state = libssh2_NB_state_jump2;
rc = packet_queue_listener(session, data, datalen,
&session->packAdd_Qlstn_state);
if (rc == PACKET_EAGAIN) {
session->socket_block_directions =
LIBSSH2_SESSION_BLOCK_OUTBOUND;
if (rc == PACKET_EAGAIN)
return PACKET_EAGAIN;
}
LIBSSH2_FREE(session, data);
session->packAdd_state = libssh2_NB_state_idle;
@ -839,11 +812,8 @@ _libssh2_packet_add(LIBSSH2_SESSION * session, unsigned char *data,
session->packAdd_state = libssh2_NB_state_jump3;
rc = packet_x11_open(session, data, datalen,
&session->packAdd_x11open_state);
if (rc == PACKET_EAGAIN) {
session->socket_block_directions =
LIBSSH2_SESSION_BLOCK_OUTBOUND;
if (rc == PACKET_EAGAIN)
return PACKET_EAGAIN;
}
LIBSSH2_FREE(session, data);
session->packAdd_state = libssh2_NB_state_idle;
@ -879,33 +849,23 @@ _libssh2_packet_add(LIBSSH2_SESSION * session, unsigned char *data,
}
if (session->packAdd_state == libssh2_NB_state_sent) {
session->packAdd_packet =
LIBSSH2_PACKET *packAdd_packet;
packAdd_packet =
LIBSSH2_ALLOC(session, sizeof(LIBSSH2_PACKET));
if (!session->packAdd_packet) {
if (!packAdd_packet) {
_libssh2_debug(session, LIBSSH2_ERROR_ALLOC,
"Unable to allocate memory for LIBSSH2_PACKET");
LIBSSH2_FREE(session, data);
session->packAdd_state = libssh2_NB_state_idle;
return -1;
}
memset(session->packAdd_packet, 0, sizeof(LIBSSH2_PACKET));
memset(packAdd_packet, 0, sizeof(LIBSSH2_PACKET));
session->packAdd_packet->data = data;
session->packAdd_packet->data_len = datalen;
session->packAdd_packet->data_head = session->packAdd_data_head;
session->packAdd_packet->mac = macstate;
session->packAdd_packet->brigade = &session->packets;
session->packAdd_packet->next = NULL;
packAdd_packet->data = data;
packAdd_packet->data_len = datalen;
packAdd_packet->data_head = session->packAdd_data_head;
packAdd_packet->mac = macstate;
if (session->packets.tail) {
session->packAdd_packet->prev = session->packets.tail;
session->packAdd_packet->prev->next = session->packAdd_packet;
session->packets.tail = session->packAdd_packet;
} else {
session->packets.head = session->packAdd_packet;
session->packets.tail = session->packAdd_packet;
session->packAdd_packet->prev = NULL;
}
_libssh2_list_add(&session->packets, &packAdd_packet->node);
session->packAdd_state = libssh2_NB_state_sent1;
}
@ -968,7 +928,7 @@ _libssh2_packet_ask(LIBSSH2_SESSION * session, unsigned char packet_type,
unsigned long match_ofs, const unsigned char *match_buf,
unsigned long match_len)
{
LIBSSH2_PACKET *packet = session->packets.head;
LIBSSH2_PACKET *packet = _libssh2_list_first(&session->packets);
_libssh2_debug(session, LIBSSH2_DBG_TRANS,
"Looking for packet of type: %d", (int) packet_type);
@ -982,24 +942,14 @@ _libssh2_packet_ask(LIBSSH2_SESSION * session, unsigned char packet_type,
*data = packet->data;
*data_len = packet->data_len;
/* unlink struct */
if (packet->prev) {
packet->prev->next = packet->next;
} else {
session->packets.head = packet->next;
}
if (packet->next) {
packet->next->prev = packet->prev;
} else {
session->packets.tail = packet->prev;
}
/* unlink struct from session->packets */
_libssh2_list_remove(&packet->node);
LIBSSH2_FREE(session, packet);
return 0;
}
packet = packet->next;
packet = _libssh2_list_next(&packet->node);
}
return -1;
}

Просмотреть файл

@ -699,6 +699,9 @@ static int
session_free(LIBSSH2_SESSION *session)
{
int rc;
LIBSSH2_PACKET *pkg;
LIBSSH2_CHANNEL *ch;
LIBSSH2_LISTENER *l;
if (session->free_state == libssh2_NB_state_idle) {
_libssh2_debug(session, LIBSSH2_DBG_TRANS, "Freeing session resource",
@ -708,13 +711,15 @@ session_free(LIBSSH2_SESSION *session)
}
if (session->free_state == libssh2_NB_state_created) {
while (session->channels.head) {
LIBSSH2_CHANNEL *tmp = session->channels.head;
while ((ch = _libssh2_list_first(&session->channels))) {
rc = libssh2_channel_free(session->channels.head);
if (rc == PACKET_EAGAIN) {
rc = libssh2_channel_free(ch);
if (rc == PACKET_EAGAIN)
return PACKET_EAGAIN;
}
#if 0
/* Daniel's note: I'm leaving this code here right now since it
looks so weird I'm stumped. Why would libssh2_channel_free()
fail and forces this to be done? */
if (tmp == session->channels.head) {
/* channel_free couldn't do it's job, perform a messy cleanup */
tmp = session->channels.head;
@ -728,14 +733,14 @@ session_free(LIBSSH2_SESSION *session)
/* reverse linking isn't important here, we're killing the
* structure */
}
#endif
}
session->state = libssh2_NB_state_sent;
}
if (session->state == libssh2_NB_state_sent) {
LIBSSH2_LISTENER *l;
while (l = _libssh2_list_first(&session->listeners)) {
while ((l = _libssh2_list_first(&session->listeners))) {
rc = libssh2_channel_forward_cancel(l);
if (rc == PACKET_EAGAIN)
return PACKET_EAGAIN;
@ -908,16 +913,14 @@ session_free(LIBSSH2_SESSION *session)
LIBSSH2_FREE(session, session->err_msg);
}
/* Cleanup any remaining packets */
while (session->packets.head) {
LIBSSH2_PACKET *tmp = session->packets.head;
/* unlink */
session->packets.head = tmp->next;
/* Cleanup all remaining packets */
while ((pkg = _libssh2_list_first(&session->packets))) {
/* unlink the node */
_libssh2_list_remove(&pkg->node);
/* free */
LIBSSH2_FREE(session, tmp->data);
LIBSSH2_FREE(session, tmp);
LIBSSH2_FREE(session, pkg->data);
LIBSSH2_FREE(session, pkg);
}
if(session->socket_prev_blockstate)
@ -1245,7 +1248,7 @@ LIBSSH2_API int
libssh2_poll_channel_read(LIBSSH2_CHANNEL * channel, int extended)
{
LIBSSH2_SESSION *session = channel->session;
LIBSSH2_PACKET *packet = session->packets.head;
LIBSSH2_PACKET *packet = _libssh2_list_first(&session->packets);
while (packet) {
if ( channel->local.id == _libssh2_ntohu32(packet->data + 1)) {
@ -1259,7 +1262,7 @@ libssh2_poll_channel_read(LIBSSH2_CHANNEL * channel, int extended)
}
/* else - no data of any type is ready to be read */
}
packet = packet->next;
packet = _libssh2_list_next(&packet->node);
}
return 0;
@ -1285,7 +1288,7 @@ poll_channel_write(LIBSSH2_CHANNEL * channel)
static inline int
poll_listener_queued(LIBSSH2_LISTENER * listener)
{
return listener->queue ? 1 : 0;
return _libssh2_list_first(&listener->queue) ? 1 : 0;
}
/*
@ -1456,8 +1459,7 @@ libssh2_poll(LIBSSH2_POLLFD * fds, unsigned int nfds, long timeout)
((fds[i].revents & LIBSSH2_POLLFD_POLLIN) == 0)) {
/* No connections known of yet */
fds[i].revents |=
poll_listener_queued(fds[i].fd.
listener) ?
poll_listener_queued(fds[i].fd. listener) ?
LIBSSH2_POLLFD_POLLIN : 0;
}
if (fds[i].fd.listener->session->socket_state ==

Просмотреть файл

@ -131,15 +131,8 @@ sftp_packet_add(LIBSSH2_SFTP *sftp, unsigned char *data,
packet->data = data;
packet->data_len = data_len;
packet->data_head = 5;
packet->brigade = &sftp->packets;
packet->next = NULL;
packet->prev = sftp->packets.tail;
if (packet->prev) {
packet->prev->next = packet;
} else {
sftp->packets.head = packet;
}
sftp->packets.tail = packet;
_libssh2_list_add(&sftp->packets, &packet->node);
return 0;
}
@ -253,7 +246,7 @@ sftp_packet_ask(LIBSSH2_SFTP *sftp, unsigned char packet_type,
unsigned long *data_len)
{
LIBSSH2_SESSION *session = sftp->channel->session;
LIBSSH2_PACKET *packet = sftp->packets.head;
LIBSSH2_PACKET *packet = _libssh2_list_first(&sftp->packets);
unsigned char match_buf[5];
int match_len;
@ -277,24 +270,13 @@ sftp_packet_ask(LIBSSH2_SFTP *sftp, unsigned char packet_type,
*data_len = packet->data_len;
/* unlink and free this struct */
if (packet->prev) {
packet->prev->next = packet->next;
} else {
sftp->packets.head = packet->next;
}
if (packet->next) {
packet->next->prev = packet->prev;
} else {
sftp->packets.tail = packet->prev;
}
_libssh2_list_remove(&packet->node);
LIBSSH2_FREE(session, packet);
return 0;
}
/* check next struct in the list */
packet = packet->next;
packet = _libssh2_list_next(&packet->node);
}
return -1;
}

Просмотреть файл

@ -259,6 +259,8 @@ fullpacket(LIBSSH2_SESSION * session, int encrypted /* 1 or 0 */ )
/*
* This function reads the binary stream as specified in chapter 6 of RFC4253
* "The Secure Shell (SSH) Transport Layer Protocol"
*
* DOES NOT call libssh2_error() for ANY error case.
*/
libssh2pack_t
_libssh2_transport_read(LIBSSH2_SESSION * session)
@ -298,16 +300,11 @@ _libssh2_transport_read(LIBSSH2_SESSION * session)
_libssh2_debug(session, LIBSSH2_DBG_TRANS, "Redirecting into the"
" key re-exchange");
status = libssh2_kex_exchange(session, 1, &session->startup_key_state);
if (status == PACKET_EAGAIN) {
libssh2_error(session, LIBSSH2_ERROR_EAGAIN,
"Would block exchanging encryption keys", 0);
if (status == PACKET_EAGAIN)
return PACKET_EAGAIN;
} else if (status) {
libssh2_error(session, LIBSSH2_ERROR_KEX_FAILURE,
"Unable to exchange encryption keys",0);
else if (status)
return LIBSSH2_ERROR_KEX_FAILURE;
}
}
/*
* =============================== NOTE ===============================