summaryrefslogtreecommitdiffstats
path: root/libssh/channels.c
diff options
context:
space:
mode:
authorAndreas Schneider <mail@cynapses.org>2009-04-04 14:27:59 +0000
committerAndreas Schneider <mail@cynapses.org>2009-04-04 14:27:59 +0000
commit226e48b4b7ac98a26259ee8f968a2cf64132b4ac (patch)
tree945dbedec51a3bf6946ad94f9375ce2349803f85 /libssh/channels.c
parenta7fbedf8d61a65c06a2d6f7d9c2f164340e510f9 (diff)
downloadlibssh-226e48b4b7ac98a26259ee8f968a2cf64132b4ac.tar.gz
libssh-226e48b4b7ac98a26259ee8f968a2cf64132b4ac.tar.xz
libssh-226e48b4b7ac98a26259ee8f968a2cf64132b4ac.zip
Improve channel_free().
git-svn-id: svn+ssh://svn.berlios.de/svnroot/repos/libssh/trunk@388 7dcaeef0-15fb-0310-b436-a5af3365683c
Diffstat (limited to 'libssh/channels.c')
-rw-r--r--libssh/channels.c54
1 files changed, 32 insertions, 22 deletions
diff --git a/libssh/channels.c b/libssh/channels.c
index 1fe7388..ae45c7f 100644
--- a/libssh/channels.c
+++ b/libssh/channels.c
@@ -482,29 +482,39 @@ int channel_open_forward(CHANNEL *channel,char *remotehost, int remoteport, char
* \param channel channel to free
* \warning any data unread on channel will be lost
*/
-void channel_free(CHANNEL *channel){
- SSH_SESSION *session=channel->session;
- enter_function();
- if(session->alive && channel->open)
- channel_close(channel);
- /* handle the "my channel is first on session list" case */
- if(session->channels==channel)
- session->channels=channel->next;
- /* handle the "my channel is the only on session list" case */
- if(channel->next == channel){
- session->channels=NULL;
- } else {
- channel->prev->next=channel->next;
- channel->next->prev=channel->prev;
- }
- if(channel->stdout_buffer)
- buffer_free(channel->stdout_buffer);
- if(channel->stderr_buffer)
- buffer_free(channel->stderr_buffer);
- /* debug trick to catch use after frees */
- memset(channel,'X',sizeof(CHANNEL));
- free(channel);
+void channel_free(CHANNEL *channel) {
+ SSH_SESSION *session = channel->session;
+ enter_function();
+
+ if (channel == NULL) {
leave_function();
+ return;
+ }
+
+ if (session->alive && channel->open) {
+ channel_close(channel);
+ }
+
+ /* handle the "my channel is first on session list" case */
+ if (session->channels == channel) {
+ session->channels = channel->next;
+ }
+
+ /* handle the "my channel is the only on session list" case */
+ if (channel->next == channel) {
+ session->channels = NULL;
+ } else {
+ channel->prev->next = channel->next;
+ channel->next->prev = channel->prev;
+ }
+
+ buffer_free(channel->stdout_buffer);
+ buffer_free(channel->stderr_buffer);
+
+ /* debug trick to catch use after frees */
+ memset(channel, 'X', sizeof(CHANNEL));
+ SAFE_FREE(channel);
+ leave_function();
}
/** it doesn't close the channel. You may still read from it but not write.