summaryrefslogtreecommitdiff
path: root/clientloop.c
diff options
context:
space:
mode:
authorColin Watson <cjwatson@debian.org>2009-12-29 21:38:40 +0000
committerColin Watson <cjwatson@debian.org>2009-12-29 21:38:40 +0000
commit1b816ea846aca3ee89e7995373ace609e9518424 (patch)
treeb41cdc8495cae7fa9c2e0f98a5f2e71656b61f9a /clientloop.c
parentfa585019a79ebcb4e0202b1c33f87ff1c5c9ce1c (diff)
parent086ea76990b1e6287c24b6db74adffd4605eb3b0 (diff)
import openssh-4.6p1-gsskex-20070312.patch
Diffstat (limited to 'clientloop.c')
-rw-r--r--clientloop.c107
1 files changed, 73 insertions, 34 deletions
diff --git a/clientloop.c b/clientloop.c
index b76f7cfe0..c7362caa8 100644
--- a/clientloop.c
+++ b/clientloop.c
@@ -1,3 +1,4 @@
1/* $OpenBSD: clientloop.c,v 1.178 2007/02/20 10:25:14 djm Exp $ */
1/* 2/*
2 * Author: Tatu Ylonen <ylo@cs.hut.fi> 3 * Author: Tatu Ylonen <ylo@cs.hut.fi>
3 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland 4 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
@@ -59,20 +60,43 @@
59 */ 60 */
60 61
61#include "includes.h" 62#include "includes.h"
62RCSID("$OpenBSD: clientloop.c,v 1.149 2005/12/30 15:56:37 reyk Exp $");
63 63
64#include <sys/types.h>
65#include <sys/ioctl.h>
66#include <sys/param.h>
67#ifdef HAVE_SYS_STAT_H
68# include <sys/stat.h>
69#endif
70#ifdef HAVE_SYS_TIME_H
71# include <sys/time.h>
72#endif
73#include <sys/socket.h>
74
75#include <ctype.h>
76#include <errno.h>
77#ifdef HAVE_PATHS_H
78#include <paths.h>
79#endif
80#include <signal.h>
81#include <stdarg.h>
82#include <stdio.h>
83#include <stdlib.h>
84#include <string.h>
85#include <termios.h>
86#include <pwd.h>
87#include <unistd.h>
88
89#include "xmalloc.h"
64#include "ssh.h" 90#include "ssh.h"
65#include "ssh1.h" 91#include "ssh1.h"
66#include "ssh2.h" 92#include "ssh2.h"
67#include "xmalloc.h"
68#include "packet.h" 93#include "packet.h"
69#include "buffer.h" 94#include "buffer.h"
70#include "compat.h" 95#include "compat.h"
71#include "channels.h" 96#include "channels.h"
72#include "dispatch.h" 97#include "dispatch.h"
73#include "buffer.h"
74#include "bufaux.h"
75#include "key.h" 98#include "key.h"
99#include "cipher.h"
76#include "kex.h" 100#include "kex.h"
77#include "log.h" 101#include "log.h"
78#include "readconf.h" 102#include "readconf.h"
@@ -118,7 +142,7 @@ static volatile sig_atomic_t received_signal = 0;
118static int in_non_blocking_mode = 0; 142static int in_non_blocking_mode = 0;
119 143
120/* Common data for the client loop code. */ 144/* Common data for the client loop code. */
121static int quit_pending; /* Set to non-zero to quit the client loop. */ 145static volatile sig_atomic_t quit_pending; /* Set non-zero to quit the loop. */
122static int escape_char; /* Escape character. */ 146static int escape_char; /* Escape character. */
123static int escape_pending; /* Last character was the escape character */ 147static int escape_pending; /* Last character was the escape character */
124static int last_was_cr; /* Last character was a newline. */ 148static int last_was_cr; /* Last character was a newline. */
@@ -178,7 +202,7 @@ enter_non_blocking(void)
178 * Signal handler for the window change signal (SIGWINCH). This just sets a 202 * Signal handler for the window change signal (SIGWINCH). This just sets a
179 * flag indicating that the window has changed. 203 * flag indicating that the window has changed.
180 */ 204 */
181 205/*ARGSUSED */
182static void 206static void
183window_change_handler(int sig) 207window_change_handler(int sig)
184{ 208{
@@ -190,7 +214,7 @@ window_change_handler(int sig)
190 * Signal handler for signals that cause the program to terminate. These 214 * Signal handler for signals that cause the program to terminate. These
191 * signals must be trapped to restore terminal modes. 215 * signals must be trapped to restore terminal modes.
192 */ 216 */
193 217/*ARGSUSED */
194static void 218static void
195signal_handler(int sig) 219signal_handler(int sig)
196{ 220{
@@ -422,10 +446,10 @@ client_check_window_change(void)
422 if (ioctl(fileno(stdin), TIOCGWINSZ, &ws) < 0) 446 if (ioctl(fileno(stdin), TIOCGWINSZ, &ws) < 0)
423 return; 447 return;
424 packet_start(SSH_CMSG_WINDOW_SIZE); 448 packet_start(SSH_CMSG_WINDOW_SIZE);
425 packet_put_int(ws.ws_row); 449 packet_put_int((u_int)ws.ws_row);
426 packet_put_int(ws.ws_col); 450 packet_put_int((u_int)ws.ws_col);
427 packet_put_int(ws.ws_xpixel); 451 packet_put_int((u_int)ws.ws_xpixel);
428 packet_put_int(ws.ws_ypixel); 452 packet_put_int((u_int)ws.ws_ypixel);
429 packet_send(); 453 packet_send();
430 } 454 }
431} 455}
@@ -440,8 +464,10 @@ client_global_request_reply(int type, u_int32_t seq, void *ctxt)
440static void 464static void
441server_alive_check(void) 465server_alive_check(void)
442{ 466{
443 if (++server_alive_timeouts > options.server_alive_count_max) 467 if (++server_alive_timeouts > options.server_alive_count_max) {
444 packet_disconnect("Timeout, server not responding."); 468 logit("Timeout, server not responding.");
469 cleanup_exit(255);
470 }
445 packet_start(SSH2_MSG_GLOBAL_REQUEST); 471 packet_start(SSH2_MSG_GLOBAL_REQUEST);
446 packet_put_cstring("keepalive@openssh.com"); 472 packet_put_cstring("keepalive@openssh.com");
447 packet_put_char(1); /* boolean: want reply */ 473 packet_put_char(1); /* boolean: want reply */
@@ -569,7 +595,7 @@ client_suspend_self(Buffer *bin, Buffer *bout, Buffer *berr)
569} 595}
570 596
571static void 597static void
572client_process_net_input(fd_set * readset) 598client_process_net_input(fd_set *readset)
573{ 599{
574 int len; 600 int len;
575 char buf[8192]; 601 char buf[8192];
@@ -677,11 +703,11 @@ client_extra_session2_setup(int id, void *arg)
677} 703}
678 704
679static void 705static void
680client_process_control(fd_set * readset) 706client_process_control(fd_set *readset)
681{ 707{
682 Buffer m; 708 Buffer m;
683 Channel *c; 709 Channel *c;
684 int client_fd, new_fd[3], ver, allowed; 710 int client_fd, new_fd[3], ver, allowed, window, packetmax;
685 socklen_t addrlen; 711 socklen_t addrlen;
686 struct sockaddr_storage addr; 712 struct sockaddr_storage addr;
687 struct confirm_ctx *cctx; 713 struct confirm_ctx *cctx;
@@ -808,8 +834,7 @@ client_process_control(fd_set * readset)
808 return; 834 return;
809 } 835 }
810 836
811 cctx = xmalloc(sizeof(*cctx)); 837 cctx = xcalloc(1, sizeof(*cctx));
812 memset(cctx, 0, sizeof(*cctx));
813 cctx->want_tty = (flags & SSHMUX_FLAG_TTY) != 0; 838 cctx->want_tty = (flags & SSHMUX_FLAG_TTY) != 0;
814 cctx->want_subsys = (flags & SSHMUX_FLAG_SUBSYS) != 0; 839 cctx->want_subsys = (flags & SSHMUX_FLAG_SUBSYS) != 0;
815 cctx->want_x_fwd = (flags & SSHMUX_FLAG_X11_FWD) != 0; 840 cctx->want_x_fwd = (flags & SSHMUX_FLAG_X11_FWD) != 0;
@@ -824,7 +849,7 @@ client_process_control(fd_set * readset)
824 env_len = MIN(env_len, 4096); 849 env_len = MIN(env_len, 4096);
825 debug3("%s: receiving %d env vars", __func__, env_len); 850 debug3("%s: receiving %d env vars", __func__, env_len);
826 if (env_len != 0) { 851 if (env_len != 0) {
827 cctx->env = xmalloc(sizeof(*cctx->env) * (env_len + 1)); 852 cctx->env = xcalloc(env_len + 1, sizeof(*cctx->env));
828 for (i = 0; i < env_len; i++) 853 for (i = 0; i < env_len; i++)
829 cctx->env[i] = buffer_get_string(&m, &len); 854 cctx->env[i] = buffer_get_string(&m, &len);
830 cctx->env[i] = NULL; 855 cctx->env[i] = NULL;
@@ -832,6 +857,7 @@ client_process_control(fd_set * readset)
832 857
833 debug2("%s: accepted tty %d, subsys %d, cmd %s", __func__, 858 debug2("%s: accepted tty %d, subsys %d, cmd %s", __func__,
834 cctx->want_tty, cctx->want_subsys, cmd); 859 cctx->want_tty, cctx->want_subsys, cmd);
860 xfree(cmd);
835 861
836 /* Gather fds from client */ 862 /* Gather fds from client */
837 new_fd[0] = mm_receive_fd(client_fd); 863 new_fd[0] = mm_receive_fd(client_fd);
@@ -874,9 +900,15 @@ client_process_control(fd_set * readset)
874 900
875 set_nonblock(client_fd); 901 set_nonblock(client_fd);
876 902
903 window = CHAN_SES_WINDOW_DEFAULT;
904 packetmax = CHAN_SES_PACKET_DEFAULT;
905 if (cctx->want_tty) {
906 window >>= 1;
907 packetmax >>= 1;
908 }
909
877 c = channel_new("session", SSH_CHANNEL_OPENING, 910 c = channel_new("session", SSH_CHANNEL_OPENING,
878 new_fd[0], new_fd[1], new_fd[2], 911 new_fd[0], new_fd[1], new_fd[2], window, packetmax,
879 CHAN_SES_WINDOW_DEFAULT, CHAN_SES_PACKET_DEFAULT,
880 CHAN_EXTENDED_WRITE, "client-session", /*nonblock*/0); 912 CHAN_EXTENDED_WRITE, "client-session", /*nonblock*/0);
881 913
882 /* XXX */ 914 /* XXX */
@@ -912,12 +944,16 @@ process_cmdline(void)
912 944
913 if (*s == 'h' || *s == 'H' || *s == '?') { 945 if (*s == 'h' || *s == 'H' || *s == '?') {
914 logit("Commands:"); 946 logit("Commands:");
915 logit(" -Lport:host:hostport Request local forward"); 947 logit(" -L[bind_address:]port:host:hostport "
916 logit(" -Rport:host:hostport Request remote forward"); 948 "Request local forward");
917 logit(" -KRhostport Cancel remote forward"); 949 logit(" -R[bind_address:]port:host:hostport "
950 "Request remote forward");
951 logit(" -KR[bind_address:]port "
952 "Cancel remote forward");
918 if (!options.permit_local_command) 953 if (!options.permit_local_command)
919 goto out; 954 goto out;
920 logit(" !args Execute local command"); 955 logit(" !args "
956 "Execute local command");
921 goto out; 957 goto out;
922 } 958 }
923 959
@@ -978,9 +1014,12 @@ process_cmdline(void)
978 goto out; 1014 goto out;
979 } 1015 }
980 } else { 1016 } else {
981 channel_request_remote_forwarding(fwd.listen_host, 1017 if (channel_request_remote_forwarding(fwd.listen_host,
982 fwd.listen_port, fwd.connect_host, 1018 fwd.listen_port, fwd.connect_host,
983 fwd.connect_port); 1019 fwd.connect_port) < 0) {
1020 logit("Port forwarding failed.");
1021 goto out;
1022 }
984 } 1023 }
985 1024
986 logit("Forwarding port."); 1025 logit("Forwarding port.");
@@ -1172,7 +1211,7 @@ Supported escape sequences:\r\n\
1172} 1211}
1173 1212
1174static void 1213static void
1175client_process_input(fd_set * readset) 1214client_process_input(fd_set *readset)
1176{ 1215{
1177 int len; 1216 int len;
1178 char buf[8192]; 1217 char buf[8192];
@@ -1225,7 +1264,7 @@ client_process_input(fd_set * readset)
1225} 1264}
1226 1265
1227static void 1266static void
1228client_process_output(fd_set * writeset) 1267client_process_output(fd_set *writeset)
1229{ 1268{
1230 int len; 1269 int len;
1231 char buf[100]; 1270 char buf[100];
@@ -1724,7 +1763,7 @@ client_request_agent(const char *request_type, int rchan)
1724 error("Warning: this is probably a break-in attempt by a malicious server."); 1763 error("Warning: this is probably a break-in attempt by a malicious server.");
1725 return NULL; 1764 return NULL;
1726 } 1765 }
1727 sock = ssh_get_authentication_socket(); 1766 sock = ssh_get_authentication_socket();
1728 if (sock < 0) 1767 if (sock < 0)
1729 return NULL; 1768 return NULL;
1730 c = channel_new("authentication agent connection", 1769 c = channel_new("authentication agent connection",
@@ -1869,10 +1908,10 @@ client_session2_setup(int id, int want_tty, int want_subsystem,
1869 1908
1870 channel_request_start(id, "pty-req", 0); 1909 channel_request_start(id, "pty-req", 0);
1871 packet_put_cstring(term != NULL ? term : ""); 1910 packet_put_cstring(term != NULL ? term : "");
1872 packet_put_int(ws.ws_col); 1911 packet_put_int((u_int)ws.ws_col);
1873 packet_put_int(ws.ws_row); 1912 packet_put_int((u_int)ws.ws_row);
1874 packet_put_int(ws.ws_xpixel); 1913 packet_put_int((u_int)ws.ws_xpixel);
1875 packet_put_int(ws.ws_ypixel); 1914 packet_put_int((u_int)ws.ws_ypixel);
1876 tio = get_saved_tio(); 1915 tio = get_saved_tio();
1877 tty_make_modes(-1, tiop != NULL ? tiop : &tio); 1916 tty_make_modes(-1, tiop != NULL ? tiop : &tio);
1878 packet_send(); 1917 packet_send();