File: [local] / src / usr.bin / ssh / nchan.c (download)
Revision 1.1, Sat Oct 16 20:47:14 1999 UTC (24 years, 7 months ago) by markus
Branch: MAIN
support for SSH protocol 1.5 which is poorly documented, the RFC.troff lies.
interops (x11,agent,etc) with 1.2.27 and protocol 1.3
|
#include "includes.h"
#include "ssh.h"
#include "buffer.h"
#include "channels.h"
#include "packet.h"
#include "nchan.h"
void
dump_chan(Channel *c){
debug("chan %d type %d flags 0x%x", c->self, c->type, c->flags);
}
void
chan_rcvd_ieof(Channel *c){
dump_chan(c);
if(c->flags & CHAN_IEOF_RCVD){
debug("chan_rcvd_ieof twice: %d",c->self);
return;
}
debug("rcvd_CHAN_IEOF %d",c->self);
c->flags |= CHAN_IEOF_RCVD;
/* cannot clear input buffer. remaining data has to be sent to client */
chan_del_if_dead(c);
}
void
chan_rcvd_oclose(Channel *c){
dump_chan(c);
if(c->flags & CHAN_OCLOSE_RCVD){
debug("chan_rcvd_oclose twice: %d",c->self);
return;
}
debug("rcvd_CHAN_OCLOSE %d",c->self);
c->flags |= CHAN_OCLOSE_RCVD;
/* our peer can no longer consume, so there is not need to read */
chan_shutdown_read(c);
buffer_consume(&c->output, buffer_len(&c->output));
/* Note: for type==OPEN IEOF is sent by channel_output_poll() */
chan_del_if_dead(c);
}
void
chan_send_ieof(Channel *c){
if(c->flags & CHAN_IEOF_SENT){
debug("send_chan_ieof twice %d", c->self);
return;
}
debug("send_CHAN_IEOF %d", c->self);
packet_start(CHAN_IEOF);
packet_put_int(c->remote_id);
packet_send();
c->flags |= CHAN_IEOF_SENT;
dump_chan(c);
}
void
chan_send_oclose(Channel *c){
if(c->flags & CHAN_OCLOSE_SENT){
debug("send_chan_oclose twice %d", c->self);
return;
}
debug("send_CHAN_OCLOSE %d", c->self);
packet_start(CHAN_OCLOSE);
packet_put_int(c->remote_id);
packet_send();
c->flags |= CHAN_OCLOSE_SENT;
dump_chan(c);
}
void
chan_shutdown_write(Channel *c){
if(c->flags & CHAN_SHUT_WR){
debug("chan_shutdown_write twice %d",c->self);
return;
}
debug("chan_shutdown_write %d", c->self);
if(shutdown(c->sock, SHUT_WR)<0)
error("chan_shutdown_write failed %.100s", strerror(errno));
c->flags |= CHAN_SHUT_WR;
/* clear output buffer, since there is noone going to read the data
we just closed the output-socket */
// buffer_consume(&c->output, buffer_len(&c->output));
}
void
chan_shutdown_read(Channel *c){
if(c->flags & CHAN_SHUT_RD){
debug("chan_shutdown_read twice %d",c->self);
return;
}
debug("chan_shutdown_read %d", c->self);
if(shutdown(c->sock, SHUT_RD)<0)
error("chan_shutdown_read failed %.100s", strerror(errno));
c->flags |= CHAN_SHUT_RD;
}
void
chan_del_if_dead(Channel *c){
if(c->flags == CHAN_CLOSED){
debug("channel %d closing",c->self);
channel_free(c->self);
}
}