mirror of
https://git.libssh.org/projects/libssh.git
synced 2025-08-07 08:02:55 +03:00
callbacks: Implement list of callbacks for channels
Signed-off-by: Aris Adamantiadis <aris@0xbadc0de.be> Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
This commit is contained in:
committed by
Andreas Schneider
parent
5c67530f1e
commit
bbe437dbb1
@@ -867,10 +867,46 @@ typedef struct ssh_channel_callbacks_struct *ssh_channel_callbacks;
|
|||||||
* @param cb The callback structure itself.
|
* @param cb The callback structure itself.
|
||||||
*
|
*
|
||||||
* @return SSH_OK on success, SSH_ERROR on error.
|
* @return SSH_OK on success, SSH_ERROR on error.
|
||||||
|
* @warning this function will not replace existing callbacks but set the
|
||||||
|
* new one atop of them.
|
||||||
*/
|
*/
|
||||||
LIBSSH_API int ssh_set_channel_callbacks(ssh_channel channel,
|
LIBSSH_API int ssh_set_channel_callbacks(ssh_channel channel,
|
||||||
ssh_channel_callbacks cb);
|
ssh_channel_callbacks cb);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Add channel callback functions
|
||||||
|
*
|
||||||
|
* This function will add channel callback functions to the channel callback
|
||||||
|
* list.
|
||||||
|
* Callbacks missing from a callback structure will be probed in the next
|
||||||
|
* on the list.
|
||||||
|
*
|
||||||
|
* @param channel The channel to set the callback structure.
|
||||||
|
*
|
||||||
|
* @param cb The callback structure itself.
|
||||||
|
*
|
||||||
|
* @return SSH_OK on success, SSH_ERROR on error.
|
||||||
|
*
|
||||||
|
* @see ssh_set_channel_callbacks
|
||||||
|
*/
|
||||||
|
LIBSSH_API int ssh_add_channel_callbacks(ssh_channel channel,
|
||||||
|
ssh_channel_callbacks cb);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Remove a channel callback.
|
||||||
|
*
|
||||||
|
* The channel has been added with ssh_add_channel_callbacks or
|
||||||
|
* ssh_set_channel_callbacks in this case.
|
||||||
|
*
|
||||||
|
* @param channel The channel to remove the callback structure from.
|
||||||
|
*
|
||||||
|
* @param cb The callback structure to remove
|
||||||
|
*
|
||||||
|
* @returns SSH_OK on success, SSH_ERROR on error.
|
||||||
|
*/
|
||||||
|
LIBSSH_API int ssh_remove_channel_callbacks(ssh_channel channel,
|
||||||
|
ssh_channel_callbacks cb);
|
||||||
|
|
||||||
/** @} */
|
/** @} */
|
||||||
|
|
||||||
/** @group libssh_threads
|
/** @group libssh_threads
|
||||||
|
@@ -74,7 +74,8 @@ struct ssh_channel_struct {
|
|||||||
int version;
|
int version;
|
||||||
int exit_status;
|
int exit_status;
|
||||||
enum ssh_channel_request_state_e request_state;
|
enum ssh_channel_request_state_e request_state;
|
||||||
ssh_channel_callbacks callbacks;
|
struct ssh_list *callbacks; /* list of ssh_channel_callbacks */
|
||||||
|
|
||||||
/* counters */
|
/* counters */
|
||||||
ssh_counter counter;
|
ssh_counter counter;
|
||||||
};
|
};
|
||||||
|
@@ -25,7 +25,10 @@
|
|||||||
|
|
||||||
#include "libssh/callbacks.h"
|
#include "libssh/callbacks.h"
|
||||||
#include "libssh/session.h"
|
#include "libssh/session.h"
|
||||||
|
#include "libssh/misc.h"
|
||||||
|
|
||||||
|
#define is_callback_valid(session, cb) \
|
||||||
|
(cb->size <= 0 || cb->size > 1024 * sizeof(void *))
|
||||||
|
|
||||||
/* LEGACY */
|
/* LEGACY */
|
||||||
static void ssh_legacy_log_callback(int priority,
|
static void ssh_legacy_log_callback(int priority,
|
||||||
@@ -47,12 +50,12 @@ int ssh_set_callbacks(ssh_session session, ssh_callbacks cb) {
|
|||||||
return SSH_ERROR;
|
return SSH_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(cb->size <= 0 || cb->size > 1024 * sizeof(void *)){
|
if (is_callback_valid(session, cb)) {
|
||||||
ssh_set_error(session,SSH_FATAL,
|
ssh_set_error(session,
|
||||||
"Invalid callback passed in (badly initialized)");
|
SSH_FATAL,
|
||||||
|
"Invalid callback passed in (badly initialized)");
|
||||||
return SSH_ERROR;
|
return SSH_ERROR;
|
||||||
}
|
};
|
||||||
session->common.callbacks = cb;
|
session->common.callbacks = cb;
|
||||||
|
|
||||||
/* LEGACY */
|
/* LEGACY */
|
||||||
@@ -64,35 +67,80 @@ int ssh_set_callbacks(ssh_session session, ssh_callbacks cb) {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ssh_set_channel_callbacks(ssh_channel channel, ssh_channel_callbacks cb) {
|
static int ssh_add_set_channel_callbacks(ssh_channel channel,
|
||||||
ssh_session session = NULL;
|
ssh_channel_callbacks cb,
|
||||||
if (channel == NULL || cb == NULL) {
|
int prepend)
|
||||||
return SSH_ERROR;
|
{
|
||||||
}
|
ssh_session session = NULL;
|
||||||
session = channel->session;
|
int rc;
|
||||||
|
|
||||||
if(cb->size <= 0 || cb->size > 1024 * sizeof(void *)){
|
if (channel == NULL || cb == NULL) {
|
||||||
ssh_set_error(session,SSH_FATAL,
|
return SSH_ERROR;
|
||||||
"Invalid channel callback passed in (badly initialized)");
|
}
|
||||||
|
session = channel->session;
|
||||||
|
|
||||||
return SSH_ERROR;
|
if (is_callback_valid(session, cb)) {
|
||||||
}
|
ssh_set_error(session,
|
||||||
channel->callbacks = cb;
|
SSH_FATAL,
|
||||||
|
"Invalid callback passed in (badly initialized)");
|
||||||
|
return SSH_ERROR;
|
||||||
|
};
|
||||||
|
if (channel->callbacks == NULL) {
|
||||||
|
channel->callbacks = ssh_list_new();
|
||||||
|
if (channel->callbacks == NULL){
|
||||||
|
ssh_set_error_oom(session);
|
||||||
|
return SSH_ERROR;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (prepend) {
|
||||||
|
rc = ssh_list_prepend(channel->callbacks, cb);
|
||||||
|
} else {
|
||||||
|
rc = ssh_list_append(channel->callbacks, cb);
|
||||||
|
}
|
||||||
|
|
||||||
return 0;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int ssh_set_channel_callbacks(ssh_channel channel, ssh_channel_callbacks cb)
|
||||||
|
{
|
||||||
|
return ssh_add_set_channel_callbacks(channel, cb, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
int ssh_add_channel_callbacks(ssh_channel channel, ssh_channel_callbacks cb)
|
||||||
|
{
|
||||||
|
return ssh_add_set_channel_callbacks(channel, cb, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
int ssh_remove_channel_callbacks(ssh_channel channel, ssh_channel_callbacks cb)
|
||||||
|
{
|
||||||
|
struct ssh_iterator *it;
|
||||||
|
|
||||||
|
if (channel == NULL || channel->callbacks == NULL){
|
||||||
|
return SSH_ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
|
it = ssh_list_find(channel->callbacks, cb);
|
||||||
|
if (it == NULL){
|
||||||
|
return SSH_ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
|
ssh_list_remove(channel->callbacks, it);
|
||||||
|
|
||||||
|
return SSH_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
int ssh_set_server_callbacks(ssh_session session, ssh_server_callbacks cb){
|
int ssh_set_server_callbacks(ssh_session session, ssh_server_callbacks cb){
|
||||||
if (session == NULL || cb == NULL) {
|
if (session == NULL || cb == NULL) {
|
||||||
return SSH_ERROR;
|
return SSH_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(cb->size <= 0 || cb->size > 1024 * sizeof(void *)){
|
if (is_callback_valid(session, cb)) {
|
||||||
ssh_set_error(session,SSH_FATAL,
|
ssh_set_error(session,
|
||||||
"Invalid callback passed in (badly initialized)");
|
SSH_FATAL,
|
||||||
|
"Invalid callback passed in (badly initialized)");
|
||||||
return SSH_ERROR;
|
return SSH_ERROR;
|
||||||
}
|
};
|
||||||
session->server_callbacks = cb;
|
session->server_callbacks = cb;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
126
src/channels.c
126
src/channels.c
@@ -538,31 +538,37 @@ SSH_PACKET_CALLBACK(channel_rcv_data){
|
|||||||
|
|
||||||
ssh_string_free(str);
|
ssh_string_free(str);
|
||||||
|
|
||||||
if(ssh_callbacks_exists(channel->callbacks, channel_data_function)) {
|
if (is_stderr) {
|
||||||
if(is_stderr) {
|
buf = channel->stderr_buffer;
|
||||||
buf = channel->stderr_buffer;
|
} else {
|
||||||
} else {
|
buf = channel->stdout_buffer;
|
||||||
buf = channel->stdout_buffer;
|
|
||||||
}
|
|
||||||
rest = channel->callbacks->channel_data_function(channel->session,
|
|
||||||
channel,
|
|
||||||
ssh_buffer_get(buf),
|
|
||||||
ssh_buffer_get_len(buf),
|
|
||||||
is_stderr,
|
|
||||||
channel->callbacks->userdata);
|
|
||||||
if(rest > 0) {
|
|
||||||
if (channel->counter != NULL) {
|
|
||||||
channel->counter->in_bytes += rest;
|
|
||||||
}
|
|
||||||
ssh_buffer_pass_bytes(buf, rest);
|
|
||||||
}
|
|
||||||
if (channel->local_window + ssh_buffer_get_len(buf) < WINDOWLIMIT) {
|
|
||||||
if (grow_window(session, channel, 0) < 0) {
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ssh_callbacks_iterate(channel->callbacks,
|
||||||
|
ssh_channel_callbacks,
|
||||||
|
channel_data_function) {
|
||||||
|
if (ssh_buffer_get(buf) == 0) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
rest = ssh_callbacks_iterate_exec(channel->session,
|
||||||
|
channel,
|
||||||
|
ssh_buffer_get(buf),
|
||||||
|
ssh_buffer_get_len(buf),
|
||||||
|
is_stderr);
|
||||||
|
if (rest > 0) {
|
||||||
|
if (channel->counter != NULL) {
|
||||||
|
channel->counter->in_bytes += rest;
|
||||||
|
}
|
||||||
|
ssh_buffer_pass_bytes(buf, rest);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ssh_callbacks_iterate_end();
|
||||||
|
|
||||||
|
if (channel->local_window + ssh_buffer_get_len(buf) < WINDOWLIMIT) {
|
||||||
|
if (grow_window(session, channel, 0) < 0) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
return SSH_PACKET_USED;
|
return SSH_PACKET_USED;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -585,11 +591,11 @@ SSH_PACKET_CALLBACK(channel_rcv_eof) {
|
|||||||
/* channel->remote_window = 0; */
|
/* channel->remote_window = 0; */
|
||||||
channel->remote_eof = 1;
|
channel->remote_eof = 1;
|
||||||
|
|
||||||
if(ssh_callbacks_exists(channel->callbacks, channel_eof_function)) {
|
ssh_callbacks_execute_list(channel->callbacks,
|
||||||
channel->callbacks->channel_eof_function(channel->session,
|
ssh_channel_callbacks,
|
||||||
channel,
|
channel_eof_function,
|
||||||
channel->callbacks->userdata);
|
channel->session,
|
||||||
}
|
channel);
|
||||||
|
|
||||||
return SSH_PACKET_USED;
|
return SSH_PACKET_USED;
|
||||||
}
|
}
|
||||||
@@ -629,11 +635,12 @@ SSH_PACKET_CALLBACK(channel_rcv_close) {
|
|||||||
* buffer because the eof is ignored until the buffer is empty.
|
* buffer because the eof is ignored until the buffer is empty.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
if(ssh_callbacks_exists(channel->callbacks, channel_close_function)) {
|
ssh_callbacks_execute_list(channel->callbacks,
|
||||||
channel->callbacks->channel_close_function(channel->session,
|
ssh_channel_callbacks,
|
||||||
channel,
|
channel_close_function,
|
||||||
channel->callbacks->userdata);
|
channel->session,
|
||||||
}
|
channel);
|
||||||
|
|
||||||
channel->flags |= SSH_CHANNEL_FLAG_CLOSED_REMOTE;
|
channel->flags |= SSH_CHANNEL_FLAG_CLOSED_REMOTE;
|
||||||
if(channel->flags & SSH_CHANNEL_FLAG_FREED_LOCAL)
|
if(channel->flags & SSH_CHANNEL_FLAG_FREED_LOCAL)
|
||||||
ssh_channel_do_free(channel);
|
ssh_channel_do_free(channel);
|
||||||
@@ -668,12 +675,12 @@ SSH_PACKET_CALLBACK(channel_rcv_request) {
|
|||||||
rc = ssh_buffer_unpack(packet, "d", &channel->exit_status);
|
rc = ssh_buffer_unpack(packet, "d", &channel->exit_status);
|
||||||
SSH_LOG(SSH_LOG_PACKET, "received exit-status %d", channel->exit_status);
|
SSH_LOG(SSH_LOG_PACKET, "received exit-status %d", channel->exit_status);
|
||||||
|
|
||||||
if(ssh_callbacks_exists(channel->callbacks, channel_exit_status_function)) {
|
ssh_callbacks_execute_list(channel->callbacks,
|
||||||
channel->callbacks->channel_exit_status_function(channel->session,
|
ssh_channel_callbacks,
|
||||||
channel,
|
channel_exit_status_function,
|
||||||
channel->exit_status,
|
channel->session,
|
||||||
channel->callbacks->userdata);
|
channel,
|
||||||
}
|
channel->exit_status);
|
||||||
|
|
||||||
return SSH_PACKET_USED;
|
return SSH_PACKET_USED;
|
||||||
}
|
}
|
||||||
@@ -692,13 +699,13 @@ SSH_PACKET_CALLBACK(channel_rcv_request) {
|
|||||||
|
|
||||||
SSH_LOG(SSH_LOG_PACKET,
|
SSH_LOG(SSH_LOG_PACKET,
|
||||||
"Remote connection sent a signal SIG %s", sig);
|
"Remote connection sent a signal SIG %s", sig);
|
||||||
if(ssh_callbacks_exists(channel->callbacks, channel_signal_function)) {
|
ssh_callbacks_execute_list(channel->callbacks,
|
||||||
channel->callbacks->channel_signal_function(channel->session,
|
ssh_channel_callbacks,
|
||||||
channel,
|
channel_signal_function,
|
||||||
sig,
|
channel->session,
|
||||||
channel->callbacks->userdata);
|
channel,
|
||||||
}
|
sig);
|
||||||
SAFE_FREE(sig);
|
SAFE_FREE(sig);
|
||||||
|
|
||||||
return SSH_PACKET_USED;
|
return SSH_PACKET_USED;
|
||||||
}
|
}
|
||||||
@@ -728,12 +735,15 @@ SSH_PACKET_CALLBACK(channel_rcv_request) {
|
|||||||
|
|
||||||
SSH_LOG(SSH_LOG_PACKET,
|
SSH_LOG(SSH_LOG_PACKET,
|
||||||
"Remote connection closed by signal SIG %s %s", sig, core);
|
"Remote connection closed by signal SIG %s %s", sig, core);
|
||||||
if(ssh_callbacks_exists(channel->callbacks, channel_exit_signal_function)) {
|
ssh_callbacks_execute_list(channel->callbacks,
|
||||||
channel->callbacks->channel_exit_signal_function(channel->session,
|
ssh_channel_callbacks,
|
||||||
channel,
|
channel_exit_signal_function,
|
||||||
sig, core_dumped, errmsg, lang,
|
channel->session,
|
||||||
channel->callbacks->userdata);
|
channel,
|
||||||
}
|
sig,
|
||||||
|
core_dumped,
|
||||||
|
errmsg,
|
||||||
|
lang);
|
||||||
|
|
||||||
SAFE_FREE(lang);
|
SAFE_FREE(lang);
|
||||||
SAFE_FREE(errmsg);
|
SAFE_FREE(errmsg);
|
||||||
@@ -760,10 +770,11 @@ SSH_PACKET_CALLBACK(channel_rcv_request) {
|
|||||||
if (strcmp(request, "auth-agent-req@openssh.com") == 0) {
|
if (strcmp(request, "auth-agent-req@openssh.com") == 0) {
|
||||||
SAFE_FREE(request);
|
SAFE_FREE(request);
|
||||||
SSH_LOG(SSH_LOG_PROTOCOL, "Received an auth-agent-req request");
|
SSH_LOG(SSH_LOG_PROTOCOL, "Received an auth-agent-req request");
|
||||||
if(ssh_callbacks_exists(channel->callbacks, channel_auth_agent_req_function)) {
|
ssh_callbacks_execute_list(channel->callbacks,
|
||||||
channel->callbacks->channel_auth_agent_req_function(channel->session, channel,
|
ssh_channel_callbacks,
|
||||||
channel->callbacks->userdata);
|
channel_auth_agent_req_function,
|
||||||
}
|
channel->session,
|
||||||
|
channel);
|
||||||
|
|
||||||
return SSH_PACKET_USED;
|
return SSH_PACKET_USED;
|
||||||
}
|
}
|
||||||
@@ -1028,6 +1039,9 @@ void ssh_channel_do_free(ssh_channel channel){
|
|||||||
}
|
}
|
||||||
ssh_buffer_free(channel->stdout_buffer);
|
ssh_buffer_free(channel->stdout_buffer);
|
||||||
ssh_buffer_free(channel->stderr_buffer);
|
ssh_buffer_free(channel->stderr_buffer);
|
||||||
|
if (channel->callbacks != NULL){
|
||||||
|
ssh_list_free(channel->callbacks);
|
||||||
|
}
|
||||||
|
|
||||||
/* debug trick to catch use after frees */
|
/* debug trick to catch use after frees */
|
||||||
memset(channel, 'X', sizeof(struct ssh_channel_struct));
|
memset(channel, 'X', sizeof(struct ssh_channel_struct));
|
||||||
|
175
src/messages.c
175
src/messages.c
@@ -166,90 +166,113 @@ static int ssh_execute_server_request(ssh_session session, ssh_message msg)
|
|||||||
case SSH_REQUEST_CHANNEL:
|
case SSH_REQUEST_CHANNEL:
|
||||||
channel = msg->channel_request.channel;
|
channel = msg->channel_request.channel;
|
||||||
|
|
||||||
if (msg->channel_request.type == SSH_CHANNEL_REQUEST_PTY &&
|
if (msg->channel_request.type == SSH_CHANNEL_REQUEST_PTY){
|
||||||
ssh_callbacks_exists(channel->callbacks, channel_pty_request_function)) {
|
ssh_callbacks_iterate(channel->callbacks,
|
||||||
rc = channel->callbacks->channel_pty_request_function(session, channel,
|
ssh_channel_callbacks,
|
||||||
msg->channel_request.TERM,
|
channel_pty_request_function) {
|
||||||
msg->channel_request.width, msg->channel_request.height,
|
rc = ssh_callbacks_iterate_exec(session,
|
||||||
msg->channel_request.pxwidth, msg->channel_request.pxheight,
|
channel,
|
||||||
channel->callbacks->userdata);
|
msg->channel_request.TERM,
|
||||||
if (rc == 0) {
|
msg->channel_request.width,
|
||||||
ssh_message_channel_request_reply_success(msg);
|
msg->channel_request.height,
|
||||||
} else {
|
msg->channel_request.pxwidth,
|
||||||
ssh_message_reply_default(msg);
|
msg->channel_request.pxheight);
|
||||||
|
if (rc == 0) {
|
||||||
|
ssh_message_channel_request_reply_success(msg);
|
||||||
|
} else {
|
||||||
|
ssh_message_reply_default(msg);
|
||||||
|
}
|
||||||
|
return SSH_OK;
|
||||||
}
|
}
|
||||||
|
ssh_callbacks_iterate_end();
|
||||||
return SSH_OK;
|
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_SHELL){
|
||||||
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_SHELL &&
|
ssh_callbacks_iterate(channel->callbacks,
|
||||||
ssh_callbacks_exists(channel->callbacks, channel_shell_request_function)) {
|
ssh_channel_callbacks,
|
||||||
rc = channel->callbacks->channel_shell_request_function(session,
|
channel_shell_request_function) {
|
||||||
channel,
|
rc = ssh_callbacks_iterate_exec(session, channel);
|
||||||
channel->callbacks->userdata);
|
if (rc == 0) {
|
||||||
if (rc == 0) {
|
ssh_message_channel_request_reply_success(msg);
|
||||||
ssh_message_channel_request_reply_success(msg);
|
} else {
|
||||||
} else {
|
ssh_message_reply_default(msg);
|
||||||
ssh_message_reply_default(msg);
|
}
|
||||||
|
return SSH_OK;
|
||||||
}
|
}
|
||||||
|
ssh_callbacks_iterate_end();
|
||||||
return SSH_OK;
|
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_X11){
|
||||||
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_X11 &&
|
ssh_callbacks_iterate(channel->callbacks,
|
||||||
ssh_callbacks_exists(channel->callbacks, channel_x11_req_function)) {
|
ssh_channel_callbacks,
|
||||||
channel->callbacks->channel_x11_req_function(session,
|
channel_x11_req_function) {
|
||||||
channel,
|
ssh_callbacks_iterate_exec(session,
|
||||||
msg->channel_request.x11_single_connection,
|
channel,
|
||||||
msg->channel_request.x11_auth_protocol,
|
msg->channel_request.x11_single_connection,
|
||||||
msg->channel_request.x11_auth_cookie,
|
msg->channel_request.x11_auth_protocol,
|
||||||
msg->channel_request.x11_screen_number,
|
msg->channel_request.x11_auth_cookie,
|
||||||
channel->callbacks->userdata);
|
msg->channel_request.x11_screen_number);
|
||||||
ssh_message_channel_request_reply_success(msg);
|
|
||||||
|
|
||||||
return SSH_OK;
|
|
||||||
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_WINDOW_CHANGE &&
|
|
||||||
ssh_callbacks_exists(channel->callbacks, channel_pty_window_change_function)) {
|
|
||||||
rc = channel->callbacks->channel_pty_window_change_function(session,
|
|
||||||
channel,
|
|
||||||
msg->channel_request.width, msg->channel_request.height,
|
|
||||||
msg->channel_request.pxwidth, msg->channel_request.pxheight,
|
|
||||||
channel->callbacks->userdata);
|
|
||||||
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_EXEC &&
|
|
||||||
ssh_callbacks_exists(channel->callbacks, channel_exec_request_function)) {
|
|
||||||
rc = channel->callbacks->channel_exec_request_function(session,
|
|
||||||
channel,
|
|
||||||
msg->channel_request.command,
|
|
||||||
channel->callbacks->userdata);
|
|
||||||
if (rc == 0) {
|
|
||||||
ssh_message_channel_request_reply_success(msg);
|
ssh_message_channel_request_reply_success(msg);
|
||||||
} else {
|
return SSH_OK;
|
||||||
ssh_message_reply_default(msg);
|
|
||||||
}
|
}
|
||||||
|
ssh_callbacks_iterate_end();
|
||||||
return SSH_OK;
|
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_WINDOW_CHANGE){
|
||||||
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_ENV &&
|
ssh_callbacks_iterate(channel->callbacks,
|
||||||
ssh_callbacks_exists(channel->callbacks, channel_env_request_function)) {
|
ssh_channel_callbacks,
|
||||||
rc = channel->callbacks->channel_env_request_function(session,
|
channel_pty_window_change_function) {
|
||||||
channel,
|
rc = ssh_callbacks_iterate_exec(session,
|
||||||
msg->channel_request.var_name, msg->channel_request.var_value,
|
channel,
|
||||||
channel->callbacks->userdata);
|
msg->channel_request.width,
|
||||||
if (rc == 0) {
|
msg->channel_request.height,
|
||||||
ssh_message_channel_request_reply_success(msg);
|
msg->channel_request.pxwidth,
|
||||||
} else {
|
msg->channel_request.pxheight);
|
||||||
ssh_message_reply_default(msg);
|
return SSH_OK;
|
||||||
}
|
}
|
||||||
|
ssh_callbacks_iterate_end();
|
||||||
|
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_EXEC){
|
||||||
|
ssh_callbacks_iterate(channel->callbacks,
|
||||||
|
ssh_channel_callbacks,
|
||||||
|
channel_exec_request_function) {
|
||||||
|
rc = ssh_callbacks_iterate_exec(session,
|
||||||
|
channel,
|
||||||
|
msg->channel_request.command);
|
||||||
|
if (rc == 0) {
|
||||||
|
ssh_message_channel_request_reply_success(msg);
|
||||||
|
} else {
|
||||||
|
ssh_message_reply_default(msg);
|
||||||
|
}
|
||||||
|
|
||||||
return SSH_OK;
|
return SSH_OK;
|
||||||
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_SUBSYSTEM &&
|
|
||||||
ssh_callbacks_exists(channel->callbacks, channel_subsystem_request_function)) {
|
|
||||||
rc = channel->callbacks->channel_subsystem_request_function(session,
|
|
||||||
channel,
|
|
||||||
msg->channel_request.subsystem,
|
|
||||||
channel->callbacks->userdata);
|
|
||||||
if (rc == 0) {
|
|
||||||
ssh_message_channel_request_reply_success(msg);
|
|
||||||
} else {
|
|
||||||
ssh_message_reply_default(msg);
|
|
||||||
}
|
}
|
||||||
|
ssh_callbacks_iterate_end();
|
||||||
|
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_ENV){
|
||||||
|
ssh_callbacks_iterate(channel->callbacks,
|
||||||
|
ssh_channel_callbacks,
|
||||||
|
channel_env_request_function) {
|
||||||
|
rc = ssh_callbacks_iterate_exec(session,
|
||||||
|
channel,
|
||||||
|
msg->channel_request.var_name,
|
||||||
|
msg->channel_request.var_value);
|
||||||
|
if (rc == 0) {
|
||||||
|
ssh_message_channel_request_reply_success(msg);
|
||||||
|
} else {
|
||||||
|
ssh_message_reply_default(msg);
|
||||||
|
}
|
||||||
|
return SSH_OK;
|
||||||
|
}
|
||||||
|
ssh_callbacks_iterate_end();
|
||||||
|
} else if (msg->channel_request.type == SSH_CHANNEL_REQUEST_SUBSYSTEM){
|
||||||
|
ssh_callbacks_iterate(channel->callbacks,
|
||||||
|
ssh_channel_callbacks,
|
||||||
|
channel_subsystem_request_function) {
|
||||||
|
rc = ssh_callbacks_iterate_exec(session,
|
||||||
|
channel,
|
||||||
|
msg->channel_request.subsystem);
|
||||||
|
if (rc == 0) {
|
||||||
|
ssh_message_channel_request_reply_success(msg);
|
||||||
|
} else {
|
||||||
|
ssh_message_reply_default(msg);
|
||||||
|
}
|
||||||
|
|
||||||
return SSH_OK;
|
return SSH_OK;
|
||||||
|
}
|
||||||
|
ssh_callbacks_iterate_end();
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case SSH_REQUEST_SERVICE:
|
case SSH_REQUEST_SERVICE:
|
||||||
|
14
src/packet.c
14
src/packet.c
@@ -371,14 +371,12 @@ static void ssh_packet_socket_controlflow_callback(int code, void *userdata)
|
|||||||
it = ssh_list_get_iterator(session->channels);
|
it = ssh_list_get_iterator(session->channels);
|
||||||
while (it != NULL) {
|
while (it != NULL) {
|
||||||
channel = ssh_iterator_value(ssh_channel, it);
|
channel = ssh_iterator_value(ssh_channel, it);
|
||||||
if (ssh_callbacks_exists(channel->callbacks,
|
ssh_callbacks_execute_list(channel->callbacks,
|
||||||
channel_write_wontblock_function)) {
|
ssh_channel_callbacks,
|
||||||
SSH_LOG(SSH_LOG_TRACE, "Executing write_wontblock callback for channel");
|
channel_write_wontblock_function,
|
||||||
channel->callbacks->channel_write_wontblock_function(session,
|
session,
|
||||||
channel,
|
channel,
|
||||||
channel->remote_window,
|
channel->remote_window);
|
||||||
channel->callbacks->userdata);
|
|
||||||
}
|
|
||||||
it = it->next;
|
it = it->next;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user