diff options
author | Andreas Schneider <mail@cynapses.org> | 2009-07-31 12:16:25 +0200 |
---|---|---|
committer | Andreas Schneider <mail@cynapses.org> | 2009-07-31 12:31:46 +0200 |
commit | 83f65031c0e2bfb5bca323e27eabadcc4823a754 (patch) | |
tree | 25f20bb1c0ed66a1f62ed1b2e98116d2dfca0b92 | |
parent | 63053541e6bc477f0260b81871c2e8bf08e77ddd (diff) | |
download | libssh-83f65031c0e2bfb5bca323e27eabadcc4823a754.tar.gz libssh-83f65031c0e2bfb5bca323e27eabadcc4823a754.tar.xz libssh-83f65031c0e2bfb5bca323e27eabadcc4823a754.zip |
Fixed libssh compilation without server support.
-rw-r--r-- | include/libssh/libssh.h | 46 | ||||
-rw-r--r-- | include/libssh/server.h | 37 | ||||
-rw-r--r-- | libssh/channels.c | 3 | ||||
-rw-r--r-- | libssh/messages.c | 356 | ||||
-rw-r--r-- | libssh/server.c | 330 | ||||
-rw-r--r-- | samplesshd.c | 12 |
6 files changed, 392 insertions, 392 deletions
diff --git a/include/libssh/libssh.h b/include/libssh/libssh.h index 5cf29235..ee8c7ff7 100644 --- a/include/libssh/libssh.h +++ b/include/libssh/libssh.h @@ -124,13 +124,36 @@ typedef int socket_t; #define SSH_AUTH_INFO 3 #define SSH_AUTH_ERROR -1 -#define SSH_AUTH_METHOD_PASSWORD 0x0001 -#define SSH_AUTH_METHOD_PUBLICKEY 0x0002 -#define SSH_AUTH_METHOD_HOSTBASED 0x0004 -#define SSH_AUTH_METHOD_INTERACTIVE 0x0008 +/* auth flags */ +#define SSH_AUTH_METHOD_UNKNOWN 0 +#define SSH_AUTH_METHOD_NONE 0x0001 +#define SSH_AUTH_METHOD_PASSWORD 0x0002 +#define SSH_AUTH_METHOD_PUBLICKEY 0x0004 +#define SSH_AUTH_METHOD_HOSTBASED 0x0008 +#define SSH_AUTH_METHOD_INTERACTIVE 0x0010 + +/* messages */ +#define SSH_REQUEST_AUTH 1 +#define SSH_REQUEST_CHANNEL_OPEN 2 +#define SSH_REQUEST_CHANNEL 3 +#define SSH_REQUEST_SERVICE 4 +#define SSH_REQUEST_GLOBAL 5 + +#define SSH_CHANNEL_UNKNOWN 0 +#define SSH_CHANNEL_SESSION 1 +#define SSH_CHANNEL_DIRECT_TCPIP 2 +#define SSH_CHANNEL_FORWARDED_TCPIP 3 +#define SSH_CHANNEL_X11 4 + +#define SSH_CHANNEL_REQUEST_UNKNOWN 0 +#define SSH_CHANNEL_REQUEST_PTY 1 +#define SSH_CHANNEL_REQUEST_EXEC 2 +#define SSH_CHANNEL_REQUEST_SHELL 3 +#define SSH_CHANNEL_REQUEST_ENV 4 +#define SSH_CHANNEL_REQUEST_SUBSYSTEM 5 +#define SSH_CHANNEL_REQUEST_WINDOW_CHANGE 6 /* status flags */ - #define SSH_CLOSED (1<<0) #define SSH_READ_PENDING (1<<1) #define SSH_CLOSED_ERROR (1<<2) @@ -389,6 +412,19 @@ int ssh_userauth_kbdint_setanswer(SSH_SESSION *session, unsigned int i, int ssh_init(void); int ssh_finalize(void); +/* messages.c */ +typedef struct ssh_message SSH_MESSAGE; + +SSH_MESSAGE *ssh_message_retrieve(SSH_SESSION *session, uint32_t packettype); +SSH_MESSAGE *ssh_message_get(SSH_SESSION *session); +int ssh_message_type(SSH_MESSAGE *msg); +int ssh_message_subtype(SSH_MESSAGE *msg); +void ssh_message_free(SSH_MESSAGE *msg); + +ssh_channel ssh_message_channel_request_open_reply_accept(SSH_MESSAGE *msg); +int ssh_message_channel_request_reply_success(SSH_MESSAGE *msg); + + #ifdef __cplusplus } #endif diff --git a/include/libssh/server.h b/include/libssh/server.h index e5a921d5..c72c0e78 100644 --- a/include/libssh/server.h +++ b/include/libssh/server.h @@ -124,41 +124,7 @@ int ssh_accept(SSH_SESSION *session); int channel_write_stderr(ssh_channel channel, const void *data, uint32_t len); /* messages.c */ - -#define SSH_AUTH_REQUEST 1 -#define SSH_CHANNEL_REQUEST_OPEN 2 -#define SSH_CHANNEL_REQUEST 3 -#define SSH_SERVICE_REQUEST 4 - -#define SSH_AUTH_NONE (1<<0) -#define SSH_AUTH_PASSWORD (1<<1) -#define SSH_AUTH_HOSTBASED (1<<2) -#define SSH_AUTH_PUBLICKEY (1<<3) -#define SSH_AUTH_KEYBINT (1<<4) -#define SSH_AUTH_UNKNOWN 0 - -#define SSH_CHANNEL_SESSION 1 -#define SSH_CHANNEL_DIRECT_TCPIP 2 -#define SSH_CHANNEL_FORWARDED_TCPIP 3 -#define SSH_CHANNEL_X11 4 -#define SSH_CHANNEL_UNKNOWN 5 - -#define SSH_CHANNEL_REQUEST_PTY 1 -#define SSH_CHANNEL_REQUEST_EXEC 2 -#define SSH_CHANNEL_REQUEST_SHELL 3 -#define SSH_CHANNEL_REQUEST_ENV 4 -#define SSH_CHANNEL_REQUEST_SUBSYSTEM 5 -#define SSH_CHANNEL_REQUEST_WINDOW_CHANGE 6 -#define SSH_CHANNEL_REQUEST_UNKNOWN 7 - -typedef struct ssh_message SSH_MESSAGE; - -SSH_MESSAGE *ssh_message_retrieve(SSH_SESSION *session, uint32_t packettype); -SSH_MESSAGE *ssh_message_get(SSH_SESSION *session); -int ssh_message_type(SSH_MESSAGE *msg); -int ssh_message_subtype(SSH_MESSAGE *msg); int ssh_message_reply_default(SSH_MESSAGE *msg); -void ssh_message_free(SSH_MESSAGE *msg); char *ssh_message_auth_user(SSH_MESSAGE *msg); char *ssh_message_auth_password(SSH_MESSAGE *msg); @@ -167,9 +133,6 @@ int ssh_message_auth_reply_success(SSH_MESSAGE *msg,int partial); int ssh_message_auth_reply_pk_ok(SSH_MESSAGE *msg, ssh_string algo, ssh_string pubkey); int ssh_message_auth_set_methods(SSH_MESSAGE *msg, int methods); -ssh_channel ssh_message_channel_request_open_reply_accept(SSH_MESSAGE *msg); -int ssh_message_channel_request_reply_success(SSH_MESSAGE *msg); - int ssh_message_service_reply_success(SSH_MESSAGE *msg); char *ssh_message_service_service(SSH_MESSAGE *msg); diff --git a/libssh/channels.c b/libssh/channels.c index cd10bc22..88169b7c 100644 --- a/libssh/channels.c +++ b/libssh/channels.c @@ -34,7 +34,6 @@ #include "libssh/priv.h" #include "libssh/ssh2.h" -#include "libssh/server.h" #define WINDOWBASE 128000 #define WINDOWLIMIT (WINDOWBASE/2) @@ -1360,7 +1359,7 @@ ssh_channel channel_accept_x11(ssh_channel channel, int timeout_ms) { iterator = ssh_list_get_iterator(session->ssh_message_list); while (iterator) { msg = (SSH_MESSAGE*)iterator->data; - if (ssh_message_type(msg) == SSH_CHANNEL_REQUEST_OPEN && + if (ssh_message_type(msg) == SSH_REQUEST_CHANNEL_OPEN && ssh_message_subtype(msg) == SSH_CHANNEL_X11) { ssh_list_remove(session->ssh_message_list, iterator); return ssh_message_channel_request_open_reply_accept(msg); diff --git a/libssh/messages.c b/libssh/messages.c index b20aef00..a2252534 100644 --- a/libssh/messages.c +++ b/libssh/messages.c @@ -41,7 +41,6 @@ #include "libssh/libssh.h" #include "libssh/priv.h" -#include "libssh/server.h" #include "libssh/ssh2.h" @@ -80,44 +79,13 @@ static SSH_MESSAGE *handle_service_request(SSH_SESSION *session) { SAFE_FREE(service_c); goto error; } - msg->type=SSH_SERVICE_REQUEST; + msg->type=SSH_REQUEST_SERVICE; msg->service_request.service=service_c; error: leave_function(); return msg; } -static int ssh_message_service_request_reply_default(SSH_MESSAGE *msg) { - /* The only return code accepted by specifications are success or disconnect */ - return ssh_message_service_reply_success(msg); -} -int ssh_message_service_reply_success(SSH_MESSAGE *msg) { - struct ssh_string_struct *service; - SSH_SESSION *session=msg->session; - if (msg == NULL) { - return SSH_ERROR; - } - ssh_log(session, SSH_LOG_PACKET, - "Sending a SERVICE_ACCEPT for service %s", msg->service_request.service); - if (buffer_add_u8(session->out_buffer, SSH2_MSG_SERVICE_ACCEPT) < 0) { - return -1; - } - service=string_from_char(msg->service_request.service); - if (buffer_add_ssh_string(session->out_buffer, service) < 0) { - string_free(service); - return -1; - } - string_free(service); - return packet_send(msg->session); -} - -char *ssh_message_service_service(SSH_MESSAGE *msg){ - if (msg == NULL) { - return NULL; - } - return msg->service_request.service; -} - static int handle_unimplemented(SSH_SESSION *session) { if (buffer_add_u32(session->out_buffer, htonl(session->recv_seq - 1)) < 0) { return -1; @@ -158,7 +126,7 @@ static SSH_MESSAGE *handle_userauth_request(SSH_SESSION *session){ goto error; } - msg->type = SSH_AUTH_REQUEST; + msg->type = SSH_REQUEST_AUTH; msg->auth_request.username = string_to_char(user); if (msg->auth_request.username == NULL) { goto error; @@ -187,7 +155,7 @@ static SSH_MESSAGE *handle_userauth_request(SSH_SESSION *session){ if (strcmp(method_c, "none") == 0) { - msg->auth_request.method = SSH_AUTH_NONE; + msg->auth_request.method = SSH_AUTH_METHOD_NONE; SAFE_FREE(service_c); SAFE_FREE(method_c); leave_function(); @@ -198,7 +166,7 @@ static SSH_MESSAGE *handle_userauth_request(SSH_SESSION *session){ ssh_string pass = NULL; uint8_t tmp; - msg->auth_request.method = SSH_AUTH_PASSWORD; + msg->auth_request.method = SSH_AUTH_METHOD_PASSWORD; SAFE_FREE(service_c); SAFE_FREE(method_c); buffer_get_u8(session->in_buffer, &tmp); @@ -222,7 +190,7 @@ static SSH_MESSAGE *handle_userauth_request(SSH_SESSION *session){ ssh_string publickey = NULL; uint8_t has_sign; - msg->auth_request.method = SSH_AUTH_PUBLICKEY; + msg->auth_request.method = SSH_AUTH_METHOD_PUBLICKEY; SAFE_FREE(method_c); buffer_get_u8(session->in_buffer, &has_sign); algo = buffer_get_ssh_string(session->in_buffer); @@ -277,7 +245,7 @@ static SSH_MESSAGE *handle_userauth_request(SSH_SESSION *session){ return msg; } - msg->auth_request.method = SSH_AUTH_UNKNOWN; + msg->auth_request.method = SSH_AUTH_METHOD_UNKNOWN; SAFE_FREE(method_c); leave_function(); @@ -296,133 +264,6 @@ error: return NULL; } -char *ssh_message_auth_user(SSH_MESSAGE *msg) { - if (msg == NULL) { - return NULL; - } - - return msg->auth_request.username; -} - -char *ssh_message_auth_password(SSH_MESSAGE *msg){ - if (msg == NULL) { - return NULL; - } - - return msg->auth_request.password; -} - -/* Get the publickey of an auth request */ -ssh_public_key ssh_message_auth_publickey(SSH_MESSAGE *msg){ - if (msg == NULL) { - return NULL; - } - - return msg->auth_request.public_key; -} - -int ssh_message_auth_set_methods(SSH_MESSAGE *msg, int methods) { - if (msg == NULL || msg->session == NULL) { - return -1; - } - - msg->session->auth_methods = methods; - - return 0; -} - -static int ssh_message_auth_reply_default(SSH_MESSAGE *msg,int partial) { - SSH_SESSION *session = msg->session; - char methods_c[128] = {0}; - ssh_string methods = NULL; - int rc = SSH_ERROR; - - enter_function(); - - if (buffer_add_u8(session->out_buffer, SSH2_MSG_USERAUTH_FAILURE) < 0) { - return rc; - } - - if (session->auth_methods == 0) { - session->auth_methods = SSH_AUTH_PUBLICKEY | SSH_AUTH_PASSWORD; - } - if (session->auth_methods & SSH_AUTH_PUBLICKEY) { - strcat(methods_c, "publickey,"); - } - if (session->auth_methods & SSH_AUTH_KEYBINT) { - strcat(methods_c, "keyboard-interactive,"); - } - if (session->auth_methods & SSH_AUTH_PASSWORD) { - strcat(methods_c, "password,"); - } - if (session->auth_methods & SSH_AUTH_HOSTBASED) { - strcat(methods_c, "hostbased,"); - } - - /* Strip the comma. */ - methods_c[strlen(methods_c) - 1] = '\0'; // strip the comma. We are sure there is at - - ssh_log(session, SSH_LOG_PACKET, - "Sending a auth failure. methods that can continue: %s", methods_c); - - methods = string_from_char(methods_c); - if (methods == NULL) { - goto error; - } - - if (buffer_add_ssh_string(msg->session->out_buffer, methods) < 0) { - goto error; - } - - if (partial) { - if (buffer_add_u8(session->out_buffer, 1) < 0) { - goto error; - } - } else { - if (buffer_add_u8(session->out_buffer, 0) < 0) { - goto error; - } - } - - rc = packet_send(msg->session); -error: - string_free(methods); - - leave_function(); - return rc; -} - -int ssh_message_auth_reply_success(SSH_MESSAGE *msg, int partial) { - if (msg == NULL) { - return SSH_ERROR; - } - - if (partial) { - return ssh_message_auth_reply_default(msg, partial); - } - - if (buffer_add_u8(msg->session->out_buffer,SSH2_MSG_USERAUTH_SUCCESS) < 0) { - return SSH_ERROR; - } - - return packet_send(msg->session); -} - -/* Answer OK to a pubkey auth request */ -int ssh_message_auth_reply_pk_ok(SSH_MESSAGE *msg, ssh_string algo, ssh_string pubkey) { - if (msg == NULL) { - return SSH_ERROR; - } - - if (buffer_add_u8(msg->session->out_buffer, SSH2_MSG_USERAUTH_PK_OK) < 0 || - buffer_add_ssh_string(msg->session->out_buffer, algo) < 0 || - buffer_add_ssh_string(msg->session->out_buffer, pubkey) < 0) { - return SSH_ERROR; - } - - return packet_send(msg->session); -} - static SSH_MESSAGE *handle_channel_request_open(SSH_SESSION *session) { SSH_MESSAGE *msg = NULL; ssh_string type = NULL, originator = NULL, destination = NULL; @@ -437,7 +278,7 @@ static SSH_MESSAGE *handle_channel_request_open(SSH_SESSION *session) { return NULL; } - msg->type = SSH_CHANNEL_REQUEST_OPEN; + msg->type = SSH_REQUEST_CHANNEL_OPEN; type = buffer_get_ssh_string(session->in_buffer); if (type == NULL) { @@ -629,35 +470,6 @@ error: return NULL; } -static int ssh_message_channel_request_open_reply_default(SSH_MESSAGE *msg) { - ssh_log(msg->session, SSH_LOG_FUNCTIONS, "Refusing a channel"); - - if (buffer_add_u8(msg->session->out_buffer - , SSH2_MSG_CHANNEL_OPEN_FAILURE) < 0) { - goto error; - } - if (buffer_add_u32(msg->session->out_buffer, - htonl(msg->channel_request_open.sender)) < 0) { - goto error; - } - if (buffer_add_u32(msg->session->out_buffer, - htonl(SSH2_OPEN_ADMINISTRATIVELY_PROHIBITED)) < 0) { - goto error; - } - /* reason is an empty string */ - if (buffer_add_u32(msg->session->out_buffer, 0) < 0) { - goto error; - } - /* language too */ - if (buffer_add_u32(msg->session->out_buffer, 0) < 0) { - goto error; - } - - return packet_send(msg->session); -error: - return SSH_ERROR; -} - static SSH_MESSAGE *handle_channel_request(SSH_SESSION *session) { SSH_MESSAGE *msg = NULL; ssh_string type = NULL; @@ -691,7 +503,7 @@ static SSH_MESSAGE *handle_channel_request(SSH_SESSION *session) { "Received a %s channel_request for channel %d (want_reply=%hhd)", type_c, channel, want_reply); - msg->type = SSH_CHANNEL_REQUEST; + msg->type = SSH_REQUEST_CHANNEL; msg->channel_request.channel = ssh_channel_from_local(session, channel); msg->channel_request.want_reply = want_reply; @@ -852,62 +664,6 @@ error: return NULL; } -char *ssh_message_channel_request_open_originator(SSH_MESSAGE *msg){ - return msg->channel_request_open.originator; -} - -int ssh_message_channel_request_open_originator_port(SSH_MESSAGE *msg){ - return msg->channel_request_open.originator_port; -} - -char *ssh_message_channel_request_open_destination(SSH_MESSAGE *msg){ - return msg->channel_request_open.destination; -} - -int ssh_message_channel_request_open_destination_port(SSH_MESSAGE *msg){ - return msg->channel_request_open.destination_port; -} - -CHANNEL *ssh_message_channel_request_channel(SSH_MESSAGE *msg){ - return msg->channel_request.channel; -} - -char *ssh_message_channel_request_pty_term(SSH_MESSAGE *msg){ - return msg->channel_request.TERM; -} - -int ssh_message_channel_request_pty_width(SSH_MESSAGE *msg){ - return msg->channel_request.width; -} - -int ssh_message_channel_request_pty_height(SSH_MESSAGE *msg){ - return msg->channel_request.height; -} - -int ssh_message_channel_request_pty_pxwidth(SSH_MESSAGE *msg){ - return msg->channel_request.pxwidth; -} - -int ssh_message_channel_request_pty_pxheight(SSH_MESSAGE *msg){ - return msg->channel_request.pxheight; -} - -char *ssh_message_channel_request_env_name(SSH_MESSAGE *msg){ - return msg->channel_request.var_name; -} - -char *ssh_message_channel_request_env_value(SSH_MESSAGE *msg){ - return msg->channel_request.var_value; -} - -char *ssh_message_channel_request_command(SSH_MESSAGE *msg){ - return msg->channel_request.command; -} - -char *ssh_message_channel_request_subsystem(SSH_MESSAGE *msg){ - return msg->channel_request.subsystem; -} - int ssh_message_channel_request_reply_success(SSH_MESSAGE *msg) { uint32_t channel; @@ -937,31 +693,6 @@ int ssh_message_channel_request_reply_success(SSH_MESSAGE *msg) { return SSH_OK; } -static int ssh_message_channel_request_reply_default(SSH_MESSAGE *msg) { - uint32_t channel; - - if (msg->channel_request.want_reply) { - channel = msg->channel_request.channel->remote_channel; - - ssh_log(msg->session, SSH_LOG_PACKET, - "Sending a default channel_request denied to channel %d", channel); - - if (buffer_add_u8(msg->session->out_buffer, SSH2_MSG_CHANNEL_FAILURE) < 0) { - return SSH_ERROR; - } - if (buffer_add_u32(msg->session->out_buffer, htonl(channel)) < 0) { - return SSH_ERROR; - } - - return packet_send(msg->session); - } - - ssh_log(msg->session, SSH_LOG_PACKET, - "The client doesn't want to know the request failed!"); - - return SSH_OK; -} - SSH_MESSAGE *ssh_message_retrieve(SSH_SESSION *session, uint32_t packettype){ SSH_MESSAGE *msg=NULL; enter_function(); @@ -1020,48 +751,24 @@ int ssh_message_subtype(SSH_MESSAGE *msg) { } switch(msg->type) { - case SSH_AUTH_REQUEST: + case SSH_REQUEST_AUTH: return msg->auth_request.method; - case SSH_CHANNEL_REQUEST_OPEN: + case SSH_REQUEST_CHANNEL_OPEN: return msg->channel_request_open.type; - case SSH_CHANNEL_REQUEST: + case SSH_REQUEST_CHANNEL: return msg->channel_request.type; } return -1; } -int ssh_message_reply_default(SSH_MESSAGE *msg) { - if (msg == NULL) { - return -1; - } - - switch(msg->type) { - case SSH_AUTH_REQUEST: - return ssh_message_auth_reply_default(msg, 0); - case SSH_CHANNEL_REQUEST_OPEN: - return ssh_message_channel_request_open_reply_default(msg); - case SSH_CHANNEL_REQUEST: - return ssh_message_channel_request_reply_default(msg); - case SSH_SERVICE_REQUEST: - return ssh_message_service_request_reply_default(msg); - default: - ssh_log(msg->session, SSH_LOG_PACKET, - "Don't know what to default reply to %d type", - msg->type); - break; - } - - return -1; -} - void ssh_message_free(SSH_MESSAGE *msg){ if (msg == NULL) { return; } switch(msg->type) { - case SSH_AUTH_REQUEST: + case SSH_REQUEST_AUTH: SAFE_FREE(msg->auth_request.username); if (msg->auth_request.password) { memset(msg->auth_request.password, 0, @@ -1069,11 +776,11 @@ void ssh_message_free(SSH_MESSAGE *msg){ SAFE_FREE(msg->auth_request.password); } break; - case SSH_CHANNEL_REQUEST_OPEN: + case SSH_REQUEST_CHANNEL_OPEN: SAFE_FREE(msg->channel_request_open.originator); SAFE_FREE(msg->channel_request_open.destination); break; - case SSH_CHANNEL_REQUEST: + case SSH_REQUEST_CHANNEL: SAFE_FREE(msg->channel_request.TERM); SAFE_FREE(msg->channel_request.modes); SAFE_FREE(msg->channel_request.var_name); @@ -1102,41 +809,6 @@ void message_handle(SSH_SESSION *session, uint32_t type){ } } -/** @brief defines the SSH_MESSAGE callback - * @param session the current ssh session - * @param ssh_message_callback a function pointer to a callback taking the - * current ssh session and received message as parameters. the function returns - * 0 if the message has been parsed and treated sucessfuly, 1 otherwise (libssh - * must take care of the response). - */ -void ssh_set_message_callback(SSH_SESSION *session, - int(*ssh_message_callback)(ssh_session session, struct ssh_message *msg)){ - session->ssh_message_callback=ssh_message_callback; -} - -int ssh_execute_message_callbacks(SSH_SESSION *session){ - SSH_MESSAGE *msg=NULL; - int ret; - if(!session->ssh_message_list) - return SSH_OK; - if(session->ssh_message_callback){ - while((msg=ssh_list_get_head(SSH_MESSAGE *, session->ssh_message_list)) != NULL){ - ret=session->ssh_message_callback(session,msg); - if(ret==1){ - ret = ssh_message_reply_default(msg); - if(ret != SSH_OK) - return ret; - } - } - } else { - while((msg=ssh_list_get_head(SSH_MESSAGE *, session->ssh_message_list)) != NULL){ - ret = ssh_message_reply_default(msg); - if(ret != SSH_OK) - return ret; - } - } - return SSH_OK; -} /** * @} */ diff --git a/libssh/server.c b/libssh/server.c index 3872849a..5625229d 100644 --- a/libssh/server.c +++ b/libssh/server.c @@ -526,6 +526,336 @@ int channel_write_stderr(ssh_channel channel, const void *data, uint32_t len) { return channel_write_common(channel, data, len, 1); } +/* messages */ + +static int ssh_message_auth_reply_default(SSH_MESSAGE *msg,int partial) { + SSH_SESSION *session = msg->session; + char methods_c[128] = {0}; + ssh_string methods = NULL; + int rc = SSH_ERROR; + + enter_function(); + + if (buffer_add_u8(session->out_buffer, SSH2_MSG_USERAUTH_FAILURE) < 0) { + return rc; + } + + if (session->auth_methods == 0) { + session->auth_methods = SSH_AUTH_METHOD_PUBLICKEY | SSH_AUTH_METHOD_PASSWORD; + } + if (session->auth_methods & SSH_AUTH_METHOD_PUBLICKEY) { + strcat(methods_c, "publickey,"); + } + if (session->auth_methods & SSH_AUTH_METHOD_INTERACTIVE) { + strcat(methods_c, "keyboard-interactive,"); + } + if (session->auth_methods & SSH_AUTH_METHOD_PASSWORD) { + strcat(methods_c, "password,"); + } + if (session->auth_methods & SSH_AUTH_METHOD_HOSTBASED) { + strcat(methods_c, "hostbased,"); + } + + /* Strip the comma. */ + methods_c[strlen(methods_c) - 1] = '\0'; // strip the comma. We are sure there is at + + ssh_log(session, SSH_LOG_PACKET, + "Sending a auth failure. methods that can continue: %s", methods_c); + + methods = string_from_char(methods_c); + if (methods == NULL) { + goto error; + } + + if (buffer_add_ssh_string(msg->session->out_buffer, methods) < 0) { + goto error; + } + + if (partial) { + if (buffer_add_u8(session->out_buffer, 1) < 0) { + goto error; + } + } else { + if (buffer_add_u8(session->out_buffer, 0) < 0) { + goto error; + } + } + + rc = packet_send(msg->session); +error: + string_free(methods); + + leave_function(); + return rc; +} + +static int ssh_message_channel_request_open_reply_default(SSH_MESSAGE *msg) { + ssh_log(msg->session, SSH_LOG_FUNCTIONS, "Refusing a channel"); + + if (buffer_add_u8(msg->session->out_buffer + , SSH2_MSG_CHANNEL_OPEN_FAILURE) < 0) { + goto error; + } + if (buffer_add_u32(msg->session->out_buffer, + htonl(msg->channel_request_open.sender)) < 0) { + goto error; + } + if (buffer_add_u32(msg->session->out_buffer, + htonl(SSH2_OPEN_ADMINISTRATIVELY_PROHIBITED)) < 0) { + goto error; + } + /* reason is an empty string */ + if (buffer_add_u32(msg->session->out_buffer, 0) < 0) { + goto error; + } + /* language too */ + if (buffer_add_u32(msg->session->out_buffer, 0) < 0) { + goto error; + } + + return packet_send(msg->session); +error: + return SSH_ERROR; +} + +static int ssh_message_channel_request_reply_default(SSH_MESSAGE *msg) { + uint32_t channel; + + if (msg->channel_request.want_reply) { + channel = msg->channel_request.channel->remote_channel; + + ssh_log(msg->session, SSH_LOG_PACKET, + "Sending a default channel_request denied to channel %d", channel); + + if (buffer_add_u8(msg->session->out_buffer, SSH2_MSG_CHANNEL_FAILURE) < 0) { + return SSH_ERROR; + } + if (buffer_add_u32(msg->session->out_buffer, htonl(channel)) < 0) { + return SSH_ERROR; + } + + return packet_send(msg->session); + } + + ssh_log(msg->session, SSH_LOG_PACKET, + "The client doesn't want to know the request failed!"); + + return SSH_OK; +} + +static int ssh_message_service_request_reply_default(SSH_MESSAGE *msg) { + /* The only return code accepted by specifications are success or disconnect */ + return ssh_message_service_reply_success(msg); +} + +int ssh_message_service_reply_success(SSH_MESSAGE *msg) { + struct ssh_string_struct *service; + SSH_SESSION *session=msg->session; + if (msg == NULL) { + return SSH_ERROR; + } + ssh_log(session, SSH_LOG_PACKET, + "Sending a SERVICE_ACCEPT for service %s", msg->service_request.service); + if (buffer_add_u8(session->out_buffer, SSH2_MSG_SERVICE_ACCEPT) < 0) { + return -1; + } + service=string_from_char(msg->service_request.service); + if (buffer_add_ssh_string(session->out_buffer, service) < 0) { + string_free(service); + return -1; + } + string_free(service); + return packet_send(msg->session); +} + +int ssh_message_reply_default(SSH_MESSAGE *msg) { + if (msg == NULL) { + return -1; + } + + switch(msg->type) { + case SSH_REQUEST_AUTH: + return ssh_message_auth_reply_default(msg, 0); + case SSH_REQUEST_CHANNEL_OPEN: + return ssh_message_channel_request_open_reply_default(msg); + case SSH_REQUEST_CHANNEL: + return ssh_message_channel_request_reply_default(msg); + case SSH_REQUEST_SERVICE: + return ssh_message_service_request_reply_default(msg); + default: + ssh_log(msg->session, SSH_LOG_PACKET, + "Don't know what to default reply to %d type", + msg->type); + break; + } + + return -1; +} + +char *ssh_message_service_service(SSH_MESSAGE *msg){ + if (msg == NULL) { + return NULL; + } + return msg->service_request.service; +} + +char *ssh_message_auth_user(SSH_MESSAGE *msg) { + if (msg == NULL) { + return NULL; + } + + return msg->auth_request.username; +} + +char *ssh_message_auth_password(SSH_MESSAGE *msg){ + if (msg == NULL) { + return NULL; + } + + return msg->auth_request.password; +} + +/* Get the publickey of an auth request */ +ssh_public_key ssh_message_auth_publickey(SSH_MESSAGE *msg){ + if (msg == NULL) { + return NULL; + } + + return msg->auth_request.public_key; +} + +int ssh_message_auth_set_methods(SSH_MESSAGE *msg, int methods) { + if (msg == NULL || msg->session == NULL) { + return -1; + } + + msg->session->auth_methods = methods; + + return 0; +} + +int ssh_message_auth_reply_success(SSH_MESSAGE *msg, int partial) { + if (msg == NULL) { + return SSH_ERROR; + } + + if (partial) { + return ssh_message_auth_reply_default(msg, partial); + } + + if (buffer_add_u8(msg->session->out_buffer,SSH2_MSG_USERAUTH_SUCCESS) < 0) { + return SSH_ERROR; + } + + return packet_send(msg->session); +} + +/* Answer OK to a pubkey auth request */ +int ssh_message_auth_reply_pk_ok(SSH_MESSAGE *msg, ssh_string algo, ssh_string pubkey) { + if (msg == NULL) { + return SSH_ERROR; + } + + if (buffer_add_u8(msg->session->out_buffer, SSH2_MSG_USERAUTH_PK_OK) < 0 || + buffer_add_ssh_string(msg->session->out_buffer, algo) < 0 || + buffer_add_ssh_string(msg->session->out_buffer, pubkey) < 0) { + return SSH_ERROR; + } + + return packet_send(msg->session); +} + +char *ssh_message_channel_request_open_originator(SSH_MESSAGE *msg){ + return msg->channel_request_open.originator; +} + +int ssh_message_channel_request_open_originator_port(SSH_MESSAGE *msg){ + return msg->channel_request_open.originator_port; +} + +char *ssh_message_channel_request_open_destination(SSH_MESSAGE *msg){ + return msg->channel_request_open.destination; +} + +int ssh_message_channel_request_open_destination_port(SSH_MESSAGE *msg){ + return msg->channel_request_open.destination_port; +} + +CHANNEL *ssh_message_channel_request_channel(SSH_MESSAGE *msg){ + return msg->channel_request.channel; +} + +char *ssh_message_channel_request_pty_term(SSH_MESSAGE *msg){ + return msg->channel_request.TERM; +} + +int ssh_message_channel_request_pty_width(SSH_MESSAGE *msg){ + return msg->channel_request.width; +} + +int ssh_message_channel_request_pty_height(SSH_MESSAGE *msg){ + return msg->channel_request.height; +} + +int ssh_message_channel_request_pty_pxwidth(SSH_MESSAGE *msg){ + return msg->channel_request.pxwidth; +} + +int ssh_message_channel_request_pty_pxheight(SSH_MESSAGE *msg){ + return msg->channel_request.pxheight; +} + +char *ssh_message_channel_request_env_name(SSH_MESSAGE *msg){ + return msg->channel_request.var_name; +} + +char *ssh_message_channel_request_env_value(SSH_MESSAGE *msg){ + return msg->channel_request.var_value; +} + +char *ssh_message_channel_request_command(SSH_MESSAGE *msg){ + return msg->channel_request.command; +} + +char *ssh_message_channel_request_subsystem(SSH_MESSAGE *msg){ + return msg->channel_request.subsystem; +} + +/** @brief defines the SSH_MESSAGE callback + * @param session the current ssh session + * @param ssh_message_callback a function pointer to a callback taking the + * current ssh session and received message as parameters. the function returns + * 0 if the message has been parsed and treated sucessfuly, 1 otherwise (libssh + * must take care of the response). + */ +void ssh_set_message_callback(SSH_SESSION *session, + int(*ssh_message_callback)(ssh_session session, struct ssh_message *msg)){ + session->ssh_message_callback=ssh_message_callback; +} + +int ssh_execute_message_callbacks(SSH_SESSION *session){ + SSH_MESSAGE *msg=NULL; + int ret; + if(!session->ssh_message_list) + return SSH_OK; + if(session->ssh_message_callback){ + while((msg=ssh_list_get_head(SSH_MESSAGE *, session->ssh_message_list)) != NULL){ + ret=session->ssh_message_callback(session,msg); + if(ret==1){ + ret = ssh_message_reply_default(msg); + if(ret != SSH_OK) + return ret; + } + } + } else { + while((msg=ssh_list_get_head(SSH_MESSAGE *, session->ssh_message_list)) != NULL){ + ret = ssh_message_reply_default(msg); + if(ret != SSH_OK) + return ret; + } + } + return SSH_OK; +} /** @} */ /* vim: set ts=2 sw=2 et cindent: */ diff --git a/samplesshd.c b/samplesshd.c index c5d6243f..25f802c0 100644 --- a/samplesshd.c +++ b/samplesshd.c @@ -73,9 +73,9 @@ int main(int argc, char **argv){ if(!message) break; switch(ssh_message_type(message)){ - case SSH_AUTH_REQUEST: + case SSH_REQUEST_AUTH: switch(ssh_message_subtype(message)){ - case SSH_AUTH_PASSWORD: + case SSH_AUTH_METHOD_PASSWORD: printf("User %s wants to auth with pass %s\n", ssh_message_auth_user(message), ssh_message_auth_password(message)); @@ -86,9 +86,9 @@ int main(int argc, char **argv){ break; } // not authenticated, send default message - case SSH_AUTH_NONE: + case SSH_AUTH_METHOD_NONE: default: - ssh_message_auth_set_methods(message,SSH_AUTH_PASSWORD); + ssh_message_auth_set_methods(message,SSH_AUTH_METHOD_PASSWORD); ssh_message_reply_default(message); break; } @@ -107,7 +107,7 @@ int main(int argc, char **argv){ message=ssh_message_get(session); if(message){ switch(ssh_message_type(message)){ - case SSH_CHANNEL_REQUEST_OPEN: + case SSH_REQUEST_CHANNEL_OPEN: if(ssh_message_subtype(message)==SSH_CHANNEL_SESSION){ chan=ssh_message_channel_request_open_reply_accept(message); break; @@ -125,7 +125,7 @@ int main(int argc, char **argv){ } do { message=ssh_message_get(session); - if(message && ssh_message_type(message)==SSH_CHANNEL_REQUEST && + if(message && ssh_message_type(message)==SSH_REQUEST_CHANNEL && ssh_message_subtype(message)==SSH_CHANNEL_REQUEST_SHELL){ // if(!strcmp(ssh_message_channel_request_subsystem(message),"sftp")){ sftp=1; |