OpenCoverage

clientloop.c

Absolute File Name:/home/opencoverage/opencoverage/guest-scripts/openssh/src/clientloop.c
Source codeSwitch to Preprocessed file
LineSourceCount
1/* $OpenBSD: clientloop.c,v 1.318 2018/09/21 12:46:22 djm Exp $ */-
2/*-
3 * Author: Tatu Ylonen <ylo@cs.hut.fi>-
4 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland-
5 * All rights reserved-
6 * The main loop for the interactive session (client side).-
7 *-
8 * As far as I am concerned, the code I have written for this software-
9 * can be used freely for any purpose. Any derived versions of this-
10 * software must be clearly marked as such, and if the derived work is-
11 * incompatible with the protocol description in the RFC file, it must be-
12 * called by a name other than "ssh" or "Secure Shell".-
13 *-
14 *-
15 * Copyright (c) 1999 Theo de Raadt. All rights reserved.-
16 *-
17 * Redistribution and use in source and binary forms, with or without-
18 * modification, are permitted provided that the following conditions-
19 * are met:-
20 * 1. Redistributions of source code must retain the above copyright-
21 * notice, this list of conditions and the following disclaimer.-
22 * 2. Redistributions in binary form must reproduce the above copyright-
23 * notice, this list of conditions and the following disclaimer in the-
24 * documentation and/or other materials provided with the distribution.-
25 *-
26 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR-
27 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES-
28 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.-
29 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,-
30 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT-
31 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,-
32 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY-
33 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT-
34 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF-
35 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.-
36 *-
37 *-
38 * SSH2 support added by Markus Friedl.-
39 * Copyright (c) 1999, 2000, 2001 Markus Friedl. All rights reserved.-
40 *-
41 * Redistribution and use in source and binary forms, with or without-
42 * modification, are permitted provided that the following conditions-
43 * are met:-
44 * 1. Redistributions of source code must retain the above copyright-
45 * notice, this list of conditions and the following disclaimer.-
46 * 2. Redistributions in binary form must reproduce the above copyright-
47 * notice, this list of conditions and the following disclaimer in the-
48 * documentation and/or other materials provided with the distribution.-
49 *-
50 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR-
51 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES-
52 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.-
53 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,-
54 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT-
55 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,-
56 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY-
57 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT-
58 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF-
59 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.-
60 */-
61-
62#include "includes.h"-
63-
64#include <sys/types.h>-
65#include <sys/ioctl.h>-
66#ifdef HAVE_SYS_STAT_H-
67# include <sys/stat.h>-
68#endif-
69#ifdef HAVE_SYS_TIME_H-
70# include <sys/time.h>-
71#endif-
72#include <sys/socket.h>-
73-
74#include <ctype.h>-
75#include <errno.h>-
76#ifdef HAVE_PATHS_H-
77#include <paths.h>-
78#endif-
79#include <signal.h>-
80#include <stdarg.h>-
81#include <stdio.h>-
82#include <stdlib.h>-
83#include <string.h>-
84#include <termios.h>-
85#include <pwd.h>-
86#include <unistd.h>-
87#include <limits.h>-
88-
89#include "openbsd-compat/sys-queue.h"-
90#include "xmalloc.h"-
91#include "ssh.h"-
92#include "ssh2.h"-
93#include "packet.h"-
94#include "sshbuf.h"-
95#include "compat.h"-
96#include "channels.h"-
97#include "dispatch.h"-
98#include "sshkey.h"-
99#include "cipher.h"-
100#include "kex.h"-
101#include "myproposal.h"-
102#include "log.h"-
103#include "misc.h"-
104#include "readconf.h"-
105#include "clientloop.h"-
106#include "sshconnect.h"-
107#include "authfd.h"-
108#include "atomicio.h"-
109#include "sshpty.h"-
110#include "match.h"-
111#include "msg.h"-
112#include "ssherr.h"-
113#include "hostfile.h"-
114-
115/* import options */-
116extern Options options;-
117-
118/* Flag indicating that stdin should be redirected from /dev/null. */-
119extern int stdin_null_flag;-
120-
121/* Flag indicating that no shell has been requested */-
122extern int no_shell_flag;-
123-
124/* Flag indicating that ssh should daemonise after authentication is complete */-
125extern int fork_after_authentication_flag;-
126-
127/* Control socket */-
128extern int muxserver_sock; /* XXX use mux_client_cleanup() instead */-
129-
130/*-
131 * Name of the host we are connecting to. This is the name given on the-
132 * command line, or the HostName specified for the user-supplied name in a-
133 * configuration file.-
134 */-
135extern char *host;-
136-
137/*-
138 * Flag to indicate that we have received a window change signal which has-
139 * not yet been processed. This will cause a message indicating the new-
140 * window size to be sent to the server a little later. This is volatile-
141 * because this is updated in a signal handler.-
142 */-
143static volatile sig_atomic_t received_window_change_signal = 0;-
144static volatile sig_atomic_t received_signal = 0;-
145-
146/* Flag indicating whether the user's terminal is in non-blocking mode. */-
147static int in_non_blocking_mode = 0;-
148-
149/* Time when backgrounded control master using ControlPersist should exit */-
150static time_t control_persist_exit_time = 0;-
151-
152/* Common data for the client loop code. */-
153volatile sig_atomic_t quit_pending; /* Set non-zero to quit the loop. */-
154static int last_was_cr; /* Last character was a newline. */-
155static int exit_status; /* Used to store the command exit status. */-
156static struct sshbuf *stderr_buffer; /* Used for final exit message. */-
157static int connection_in; /* Connection to server (input). */-
158static int connection_out; /* Connection to server (output). */-
159static int need_rekeying; /* Set to non-zero if rekeying is requested. */-
160static int session_closed; /* In SSH2: login session closed. */-
161static u_int x11_refuse_time; /* If >0, refuse x11 opens after this time. */-
162-
163static void client_init_dispatch(void);-
164int session_ident = -1;-
165-
166/* Track escape per proto2 channel */-
167struct escape_filter_ctx {-
168 int escape_pending;-
169 int escape_char;-
170};-
171-
172/* Context for channel confirmation replies */-
173struct channel_reply_ctx {-
174 const char *request_type;-
175 int id;-
176 enum confirm_action action;-
177};-
178-
179/* Global request success/failure callbacks */-
180/* XXX move to struct ssh? */-
181struct global_confirm {-
182 TAILQ_ENTRY(global_confirm) entry;-
183 global_confirm_cb *cb;-
184 void *ctx;-
185 int ref_count;-
186};-
187TAILQ_HEAD(global_confirms, global_confirm);-
188static struct global_confirms global_confirms =-
189 TAILQ_HEAD_INITIALIZER(global_confirms);-
190-
191void ssh_process_session2_setup(int, int, int, struct sshbuf *);-
192-
193/* Restores stdin to blocking mode. */-
194-
195static void-
196leave_non_blocking(void)-
197{-
198 if (in_non_blocking_mode) {
in_non_blocking_modeDescription
TRUEnever evaluated
FALSEnever evaluated
0
199 unset_nonblock(fileno(stdin));-
200 in_non_blocking_mode = 0;-
201 }
never executed: end of block
0
202}
never executed: end of block
0
203-
204/*-
205 * Signal handler for the window change signal (SIGWINCH). This just sets a-
206 * flag indicating that the window has changed.-
207 */-
208/*ARGSUSED */-
209static void-
210window_change_handler(int sig)-
211{-
212 received_window_change_signal = 1;-
213}
never executed: end of block
0
214-
215/*-
216 * Signal handler for signals that cause the program to terminate. These-
217 * signals must be trapped to restore terminal modes.-
218 */-
219/*ARGSUSED */-
220static void-
221signal_handler(int sig)-
222{-
223 received_signal = sig;-
224 quit_pending = 1;-
225}
never executed: end of block
0
226-
227/*-
228 * Sets control_persist_exit_time to the absolute time when the-
229 * backgrounded control master should exit due to expiry of the-
230 * ControlPersist timeout. Sets it to 0 if we are not a backgrounded-
231 * control master process, or if there is no ControlPersist timeout.-
232 */-
233static void-
234set_control_persist_exit_time(struct ssh *ssh)-
235{-
236 if (muxserver_sock == -1 || !options.control_persist
muxserver_sock == -1Description
TRUEnever evaluated
FALSEnever evaluated
!options.control_persistDescription
TRUEnever evaluated
FALSEnever evaluated
0
237 || options.control_persist_timeout == 0) {
options.contro...t_timeout == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
238 /* not using a ControlPersist timeout */-
239 control_persist_exit_time = 0;-
240 } else if (channel_still_open(ssh)) {
never executed: end of block
channel_still_open(ssh)Description
TRUEnever evaluated
FALSEnever evaluated
0
241 /* some client connections are still open */-
242 if (control_persist_exit_time > 0)
control_persist_exit_time > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
243 debug2("%s: cancel scheduled exit", __func__);
never executed: debug2("%s: cancel scheduled exit", __func__);
0
244 control_persist_exit_time = 0;-
245 } else if (control_persist_exit_time <= 0) {
never executed: end of block
control_persist_exit_time <= 0Description
TRUEnever evaluated
FALSEnever evaluated
0
246 /* a client connection has recently closed */-
247 control_persist_exit_time = monotime() +-
248 (time_t)options.control_persist_timeout;-
249 debug2("%s: schedule exit in %d seconds", __func__,-
250 options.control_persist_timeout);-
251 }
never executed: end of block
0
252 /* else we are already counting down to the timeout */-
253}
never executed: end of block
0
254-
255#define SSH_X11_VALID_DISPLAY_CHARS ":/.-_"-
256static int-
257client_x11_display_valid(const char *display)-
258{-
259 size_t i, dlen;-
260-
261 if (display == NULL)
display == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
262 return 0;
never executed: return 0;
0
263-
264 dlen = strlen(display);-
265 for (i = 0; i < dlen; i++) {
i < dlenDescription
TRUEnever evaluated
FALSEnever evaluated
0
266 if (!isalnum((u_char)display[i]) &&
! ((*__ctype_b...int) _ISalnum)Description
TRUEnever evaluated
FALSEnever evaluated
0
267 strchr(SSH_X11_VALID_DISPLAY_CHARS, display[i]) == NULL) {
(__extension__...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
__builtin_cons...( display[i] )Description
TRUEnever evaluated
FALSEnever evaluated
!__builtin_con..._p ( ":/.-_" )Description
TRUEnever evaluated
FALSEnever evaluated
( display[i] ) == '\0'Description
TRUEnever evaluated
FALSEnever evaluated
0
268 debug("Invalid character '%c' in DISPLAY", display[i]);-
269 return 0;
never executed: return 0;
0
270 }-
271 }
never executed: end of block
0
272 return 1;
never executed: return 1;
0
273}-
274-
275#define SSH_X11_PROTO "MIT-MAGIC-COOKIE-1"-
276#define X11_TIMEOUT_SLACK 60-
277int-
278client_x11_get_proto(struct ssh *ssh, const char *display,-
279 const char *xauth_path, u_int trusted, u_int timeout,-
280 char **_proto, char **_data)-
281{-
282 char *cmd, line[512], xdisplay[512];-
283 char xauthfile[PATH_MAX], xauthdir[PATH_MAX];-
284 static char proto[512], data[512];-
285 FILE *f;-
286 int got_data = 0, generated = 0, do_unlink = 0, r;-
287 struct stat st;-
288 u_int now, x11_timeout_real;-
289-
290 *_proto = proto;-
291 *_data = data;-
292 proto[0] = data[0] = xauthfile[0] = xauthdir[0] = '\0';-
293-
294 if (!client_x11_display_valid(display)) {
!client_x11_di...valid(display)Description
TRUEnever evaluated
FALSEnever evaluated
0
295 if (display != NULL)
display != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
296 logit("DISPLAY \"%s\" invalid; disabling X11 forwarding",
never executed: logit("DISPLAY \"%s\" invalid; disabling X11 forwarding", display);
0
297 display);
never executed: logit("DISPLAY \"%s\" invalid; disabling X11 forwarding", display);
0
298 return -1;
never executed: return -1;
0
299 }-
300 if (xauth_path != NULL && stat(xauth_path, &st) == -1) {
xauth_path != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
stat(xauth_path, &st) == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
301 debug("No xauth program.");-
302 xauth_path = NULL;-
303 }
never executed: end of block
0
304-
305 if (xauth_path != NULL) {
xauth_path != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
306 /*-
307 * Handle FamilyLocal case where $DISPLAY does-
308 * not match an authorization entry. For this we-
309 * just try "xauth list unix:displaynum.screennum".-
310 * XXX: "localhost" match to determine FamilyLocal-
311 * is not perfect.-
312 */-
313 if (strncmp(display, "localhost:", 10) == 0) {
never executed: __result = (((const unsigned char *) (const char *) ( display ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( "localhost:" ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
(__extension__... , 10 ))) == 0Description
TRUEnever evaluated
FALSEnever evaluated
__builtin_constant_p ( 10 )Description
TRUEnever evaluated
FALSEnever evaluated
__builtin_cons..._p ( display )Description
TRUEnever evaluated
FALSEnever evaluated
strlen ( displ...ize_t) ( 10 ))Description
TRUEnever evaluated
FALSEnever evaluated
__builtin_cons..."localhost:" )Description
TRUEnever evaluated
FALSEnever evaluated
strlen ( "loca...ize_t) ( 10 ))Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
314 if ((r = snprintf(xdisplay, sizeof(xdisplay), "unix:%s",
(r = snprintf(...lay + 10)) < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
315 display + 10)) < 0 ||
(r = snprintf(...lay + 10)) < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
316 (size_t)r >= sizeof(xdisplay)) {
(size_t)r >= sizeof(xdisplay)Description
TRUEnever evaluated
FALSEnever evaluated
0
317 error("%s: display name too long", __func__);-
318 return -1;
never executed: return -1;
0
319 }-
320 display = xdisplay;-
321 }
never executed: end of block
0
322 if (trusted == 0) {
trusted == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
323 /*-
324 * Generate an untrusted X11 auth cookie.-
325 *-
326 * The authentication cookie should briefly outlive-
327 * ssh's willingness to forward X11 connections to-
328 * avoid nasty fail-open behaviour in the X server.-
329 */-
330 mktemp_proto(xauthdir, sizeof(xauthdir));-
331 if (mkdtemp(xauthdir) == NULL) {
mkdtemp(xauthd...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
332 error("%s: mkdtemp: %s",-
333 __func__, strerror(errno));-
334 return -1;
never executed: return -1;
0
335 }-
336 do_unlink = 1;-
337 if ((r = snprintf(xauthfile, sizeof(xauthfile),
(r = snprintf(...xauthdir)) < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
338 "%s/xauthfile", xauthdir)) < 0 ||
(r = snprintf(...xauthdir)) < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
339 (size_t)r >= sizeof(xauthfile)) {
(size_t)r >= sizeof(xauthfile)Description
TRUEnever evaluated
FALSEnever evaluated
0
340 error("%s: xauthfile path too long", __func__);-
341 unlink(xauthfile);-
342 rmdir(xauthdir);-
343 return -1;
never executed: return -1;
0
344 }-
345-
346 if (timeout == 0) {
timeout == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
347 /* auth doesn't time out */-
348 xasprintf(&cmd, "%s -f %s generate %s %s "-
349 "untrusted 2>%s",-
350 xauth_path, xauthfile, display,-
351 SSH_X11_PROTO, _PATH_DEVNULL);-
352 } else {
never executed: end of block
0
353 /* Add some slack to requested expiry */-
354 if (timeout < UINT_MAX - X11_TIMEOUT_SLACK)
timeout < (0x7... 2U + 1U) - 60Description
TRUEnever evaluated
FALSEnever evaluated
0
355 x11_timeout_real = timeout +
never executed: x11_timeout_real = timeout + 60;
0
356 X11_TIMEOUT_SLACK;
never executed: x11_timeout_real = timeout + 60;
0
357 else {-
358 /* Don't overflow on long timeouts */-
359 x11_timeout_real = UINT_MAX;-
360 }
never executed: end of block
0
361 xasprintf(&cmd, "%s -f %s generate %s %s "-
362 "untrusted timeout %u 2>%s",-
363 xauth_path, xauthfile, display,-
364 SSH_X11_PROTO, x11_timeout_real,-
365 _PATH_DEVNULL);-
366 }
never executed: end of block
0
367 debug2("%s: %s", __func__, cmd);-
368-
369 if (timeout != 0 && x11_refuse_time == 0) {
timeout != 0Description
TRUEnever evaluated
FALSEnever evaluated
x11_refuse_time == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
370 now = monotime() + 1;-
371 if (UINT_MAX - timeout < now)
(0x7fffffff * ... timeout < nowDescription
TRUEnever evaluated
FALSEnever evaluated
0
372 x11_refuse_time = UINT_MAX;
never executed: x11_refuse_time = (0x7fffffff * 2U + 1U) ;
0
373 else-
374 x11_refuse_time = now + timeout;
never executed: x11_refuse_time = now + timeout;
0
375 channel_set_x11_refuse_time(ssh,-
376 x11_refuse_time);-
377 }
never executed: end of block
0
378 if (system(cmd) == 0)
system(cmd) == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
379 generated = 1;
never executed: generated = 1;
0
380 free(cmd);-
381 }
never executed: end of block
0
382-
383 /*-
384 * When in untrusted mode, we read the cookie only if it was-
385 * successfully generated as an untrusted one in the step-
386 * above.-
387 */-
388 if (trusted || generated) {
trustedDescription
TRUEnever evaluated
FALSEnever evaluated
generatedDescription
TRUEnever evaluated
FALSEnever evaluated
0
389 xasprintf(&cmd,-
390 "%s %s%s list %s 2>" _PATH_DEVNULL,-
391 xauth_path,-
392 generated ? "-f " : "" ,-
393 generated ? xauthfile : "",-
394 display);-
395 debug2("x11_get_proto: %s", cmd);-
396 f = popen(cmd, "r");-
397 if (f && fgets(line, sizeof(line), f) &&
fDescription
TRUEnever evaluated
FALSEnever evaluated
fgets(line, sizeof(line), f)Description
TRUEnever evaluated
FALSEnever evaluated
0
398 sscanf(line, "%*s %511s %511s", proto, data) == 2)
sscanf(line, "...to, data) == 2Description
TRUEnever evaluated
FALSEnever evaluated
0
399 got_data = 1;
never executed: got_data = 1;
0
400 if (f)
fDescription
TRUEnever evaluated
FALSEnever evaluated
0
401 pclose(f);
never executed: pclose(f);
0
402 free(cmd);-
403 }
never executed: end of block
0
404 }
never executed: end of block
0
405-
406 if (do_unlink) {
do_unlinkDescription
TRUEnever evaluated
FALSEnever evaluated
0
407 unlink(xauthfile);-
408 rmdir(xauthdir);-
409 }
never executed: end of block
0
410-
411 /* Don't fall back to fake X11 data for untrusted forwarding */-
412 if (!trusted && !got_data) {
!trustedDescription
TRUEnever evaluated
FALSEnever evaluated
!got_dataDescription
TRUEnever evaluated
FALSEnever evaluated
0
413 error("Warning: untrusted X11 forwarding setup failed: "-
414 "xauth key data not generated");-
415 return -1;
never executed: return -1;
0
416 }-
417-
418 /*-
419 * If we didn't get authentication data, just make up some-
420 * data. The forwarding code will check the validity of the-
421 * response anyway, and substitute this data. The X11-
422 * server, however, will ignore this fake data and use-
423 * whatever authentication mechanisms it was using otherwise-
424 * for the local connection.-
425 */-
426 if (!got_data) {
!got_dataDescription
TRUEnever evaluated
FALSEnever evaluated
0
427 u_int8_t rnd[16];-
428 u_int i;-
429-
430 logit("Warning: No xauth data; "-
431 "using fake authentication data for X11 forwarding.");-
432 strlcpy(proto, SSH_X11_PROTO, sizeof proto);-
433 arc4random_buf(rnd, sizeof(rnd));-
434 for (i = 0; i < sizeof(rnd); i++) {
i < sizeof(rnd)Description
TRUEnever evaluated
FALSEnever evaluated
0
435 snprintf(data + 2 * i, sizeof data - 2 * i, "%02x",-
436 rnd[i]);-
437 }
never executed: end of block
0
438 }
never executed: end of block
0
439-
440 return 0;
never executed: return 0;
0
441}-
442-
443/*-
444 * Checks if the client window has changed, and sends a packet about it to-
445 * the server if so. The actual change is detected elsewhere (by a software-
446 * interrupt on Unix); this just checks the flag and sends a message if-
447 * appropriate.-
448 */-
449-
450static void-
451client_check_window_change(struct ssh *ssh)-
452{-
453 if (!received_window_change_signal)
!received_window_change_signalDescription
TRUEnever evaluated
FALSEnever evaluated
0
454 return;
never executed: return;
0
455 /** XXX race */-
456 received_window_change_signal = 0;-
457-
458 debug2("%s: changed", __func__);-
459-
460 channel_send_window_changes(ssh);-
461}
never executed: end of block
0
462-
463static int-
464client_global_request_reply(int type, u_int32_t seq, struct ssh *ssh)-
465{-
466 struct global_confirm *gc;-
467-
468 if ((gc = TAILQ_FIRST(&global_confirms)) == NULL)
(gc = ((&globa...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
469 return 0;
never executed: return 0;
0
470 if (gc->cb != NULL)
gc->cb != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
471 gc->cb(ssh, type, seq, gc->ctx);
never executed: gc->cb(ssh, type, seq, gc->ctx);
0
472 if (--gc->ref_count <= 0) {
--gc->ref_count <= 0Description
TRUEnever evaluated
FALSEnever evaluated
0
473 TAILQ_REMOVE(&global_confirms, gc, entry);
never executed: (gc)->entry.tqe_next->entry.tqe_prev = (gc)->entry.tqe_prev;
never executed: (&global_confirms)->tqh_last = (gc)->entry.tqe_prev;
((gc)->entry.t...!= ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
474 explicit_bzero(gc, sizeof(*gc));-
475 free(gc);-
476 }
never executed: end of block
0
477-
478 packet_set_alive_timeouts(0);-
479 return 0;
never executed: return 0;
0
480}-
481-
482static void-
483server_alive_check(void)-
484{-
485 if (packet_inc_alive_timeouts() > options.server_alive_count_max) {
ssh_packet_inc...live_count_maxDescription
TRUEnever evaluated
FALSEnever evaluated
0
486 logit("Timeout, server %s not responding.", host);-
487 cleanup_exit(255);-
488 }
never executed: end of block
0
489 packet_start(SSH2_MSG_GLOBAL_REQUEST);-
490 packet_put_cstring("keepalive@openssh.com");-
491 packet_put_char(1); /* boolean: want reply */-
492 packet_send();-
493 /* Insert an empty placeholder to maintain ordering */-
494 client_register_global_confirm(NULL, NULL);-
495}
never executed: end of block
0
496-
497/*-
498 * Waits until the client can do something (some data becomes available on-
499 * one of the file descriptors).-
500 */-
501static void-
502client_wait_until_can_do_something(struct ssh *ssh,-
503 fd_set **readsetp, fd_set **writesetp,-
504 int *maxfdp, u_int *nallocp, int rekeying)-
505{-
506 struct timeval tv, *tvp;-
507 int timeout_secs;-
508 time_t minwait_secs = 0, server_alive_time = 0, now = monotime();-
509 int r, ret;-
510-
511 /* Add any selections by the channel mechanism. */-
512 channel_prepare_select(active_state, readsetp, writesetp, maxfdp,-
513 nallocp, &minwait_secs);-
514-
515 /* channel_prepare_select could have closed the last channel */-
516 if (session_closed && !channel_still_open(ssh) &&
session_closedDescription
TRUEnever evaluated
FALSEnever evaluated
!channel_still_open(ssh)Description
TRUEnever evaluated
FALSEnever evaluated
0
517 !packet_have_data_to_write()) {
!ssh_packet_ha...(active_state)Description
TRUEnever evaluated
FALSEnever evaluated
0
518 /* clear mask since we did not call select() */-
519 memset(*readsetp, 0, *nallocp);-
520 memset(*writesetp, 0, *nallocp);-
521 return;
never executed: return;
0
522 }-
523-
524 FD_SET(connection_in, *readsetp);-
525-
526 /* Select server connection if have data to write to the server. */-
527 if (packet_have_data_to_write())
ssh_packet_hav...(active_state)Description
TRUEnever evaluated
FALSEnever evaluated
0
528 FD_SET(connection_out, *writesetp);
never executed: kludge_FD_SET(connection_out, *writesetp);
0
529-
530 /*-
531 * Wait for something to happen. This will suspend the process until-
532 * some selected descriptor can be read, written, or has some other-
533 * event pending, or a timeout expires.-
534 */-
535-
536 timeout_secs = INT_MAX; /* we use INT_MAX to mean no timeout */-
537 if (options.server_alive_interval > 0) {
options.server...e_interval > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
538 timeout_secs = options.server_alive_interval;-
539 server_alive_time = now + options.server_alive_interval;-
540 }
never executed: end of block
0
541 if (options.rekey_interval > 0 && !rekeying)
options.rekey_interval > 0Description
TRUEnever evaluated
FALSEnever evaluated
!rekeyingDescription
TRUEnever evaluated
FALSEnever evaluated
0
542 timeout_secs = MINIMUM(timeout_secs, packet_get_rekey_timeout());
never executed: timeout_secs = (((timeout_secs) < (ssh_packet_get_rekey_timeout(active_state))) ? (timeout_secs) : (ssh_packet_get_rekey_timeout(active_state)));
((timeout_secs...ctive_state)))Description
TRUEnever evaluated
FALSEnever evaluated
0
543 set_control_persist_exit_time(ssh);-
544 if (control_persist_exit_time > 0) {
control_persist_exit_time > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
545 timeout_secs = MINIMUM(timeout_secs,
((timeout_secs...t_time - now))Description
TRUEnever evaluated
FALSEnever evaluated
0
546 control_persist_exit_time - now);-
547 if (timeout_secs < 0)
timeout_secs < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
548 timeout_secs = 0;
never executed: timeout_secs = 0;
0
549 }
never executed: end of block
0
550 if (minwait_secs != 0)
minwait_secs != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
551 timeout_secs = MINIMUM(timeout_secs, (int)minwait_secs);
never executed: timeout_secs = (((timeout_secs) < ((int)minwait_secs)) ? (timeout_secs) : ((int)minwait_secs));
((timeout_secs...minwait_secs))Description
TRUEnever evaluated
FALSEnever evaluated
0
552 if (timeout_secs == INT_MAX)
timeout_secs == 0x7fffffffDescription
TRUEnever evaluated
FALSEnever evaluated
0
553 tvp = NULL;
never executed: tvp = ((void *)0) ;
0
554 else {-
555 tv.tv_sec = timeout_secs;-
556 tv.tv_usec = 0;-
557 tvp = &tv;-
558 }
never executed: end of block
0
559-
560 ret = select((*maxfdp)+1, *readsetp, *writesetp, NULL, tvp);-
561 if (ret < 0) {
ret < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
562 /*-
563 * We have to clear the select masks, because we return.-
564 * We have to return, because the mainloop checks for the flags-
565 * set by the signal handlers.-
566 */-
567 memset(*readsetp, 0, *nallocp);-
568 memset(*writesetp, 0, *nallocp);-
569-
570 if (errno == EINTR)
(*__errno_location ()) == 4Description
TRUEnever evaluated
FALSEnever evaluated
0
571 return;
never executed: return;
0
572 /* Note: we might still have data in the buffers. */-
573 if ((r = sshbuf_putf(stderr_buffer,
(r = sshbuf_pu...n ()) ))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
574 "select: %s\r\n", strerror(errno))) != 0)
(r = sshbuf_pu...n ()) ))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
575 fatal("%s: buffer error: %s", __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
576 quit_pending = 1;-
577 } else if (ret == 0) {
never executed: end of block
ret == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
578 /*-
579 * Timeout. Could have been either keepalive or rekeying.-
580 * Keepalive we check here, rekeying is checked in clientloop.-
581 */-
582 if (server_alive_time != 0 && server_alive_time <= monotime())
server_alive_time != 0Description
TRUEnever evaluated
FALSEnever evaluated
server_alive_t... <= monotime()Description
TRUEnever evaluated
FALSEnever evaluated
0
583 server_alive_check();
never executed: server_alive_check();
0
584 }
never executed: end of block
0
585-
586}
never executed: end of block
0
587-
588static void-
589client_suspend_self(struct sshbuf *bin, struct sshbuf *bout, struct sshbuf *berr)-
590{-
591 /* Flush stdout and stderr buffers. */-
592 if (sshbuf_len(bout) > 0)
sshbuf_len(bout) > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
593 atomicio(vwrite, fileno(stdout), sshbuf_mutable_ptr(bout),
never executed: atomicio((ssize_t (*)(int, void *, size_t))write, fileno( stdout ), sshbuf_mutable_ptr(bout), sshbuf_len(bout));
0
594 sshbuf_len(bout));
never executed: atomicio((ssize_t (*)(int, void *, size_t))write, fileno( stdout ), sshbuf_mutable_ptr(bout), sshbuf_len(bout));
0
595 if (sshbuf_len(berr) > 0)
sshbuf_len(berr) > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
596 atomicio(vwrite, fileno(stderr), sshbuf_mutable_ptr(berr),
never executed: atomicio((ssize_t (*)(int, void *, size_t))write, fileno( stderr ), sshbuf_mutable_ptr(berr), sshbuf_len(berr));
0
597 sshbuf_len(berr));
never executed: atomicio((ssize_t (*)(int, void *, size_t))write, fileno( stderr ), sshbuf_mutable_ptr(berr), sshbuf_len(berr));
0
598-
599 leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);-
600-
601 sshbuf_reset(bin);-
602 sshbuf_reset(bout);-
603 sshbuf_reset(berr);-
604-
605 /* Send the suspend signal to the program itself. */-
606 kill(getpid(), SIGTSTP);-
607-
608 /* Reset window sizes in case they have changed */-
609 received_window_change_signal = 1;-
610-
611 enter_raw_mode(options.request_tty == REQUEST_TTY_FORCE);-
612}
never executed: end of block
0
613-
614static void-
615client_process_net_input(fd_set *readset)-
616{-
617 char buf[SSH_IOBUFSZ];-
618 int r, len;-
619-
620 /*-
621 * Read input from the server, and add any such data to the buffer of-
622 * the packet subsystem.-
623 */-
624 if (FD_ISSET(connection_in, readset)) {
kludge_FD_ISSE...n_in, readset)Description
TRUEnever evaluated
FALSEnever evaluated
0
625 /* Read as much as possible. */-
626 len = read(connection_in, buf, sizeof(buf));-
627 if (len == 0) {
len == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
628 /*-
629 * Received EOF. The remote host has closed the-
630 * connection.-
631 */-
632 if ((r = sshbuf_putf(stderr_buffer,
(r = sshbuf_pu...", host)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
633 "Connection to %.300s closed by remote host.\r\n",
(r = sshbuf_pu...", host)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
634 host)) != 0)
(r = sshbuf_pu...", host)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
635 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
636 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
637 quit_pending = 1;-
638 return;
never executed: return;
0
639 }-
640 /*-
641 * There is a kernel bug on Solaris that causes select to-
642 * sometimes wake up even though there is no data available.-
643 */-
644 if (len < 0 &&
len < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
645 (errno == EAGAIN || errno == EINTR || errno == EWOULDBLOCK))
(*__errno_location ()) == 11Description
TRUEnever evaluated
FALSEnever evaluated
(*__errno_location ()) == 4Description
TRUEnever evaluated
FALSEnever evaluated
(*__errno_location ()) == 11Description
TRUEnever evaluated
FALSEnever evaluated
0
646 len = 0;
never executed: len = 0;
0
647-
648 if (len < 0) {
len < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
649 /*-
650 * An error has encountered. Perhaps there is a-
651 * network problem.-
652 */-
653 if ((r = sshbuf_putf(stderr_buffer,
(r = sshbuf_pu...n ()) ))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
654 "Read from remote host %.300s: %.100s\r\n",
(r = sshbuf_pu...n ()) ))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
655 host, strerror(errno))) != 0)
(r = sshbuf_pu...n ()) ))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
656 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
657 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
658 quit_pending = 1;-
659 return;
never executed: return;
0
660 }-
661 packet_process_incoming(buf, len);-
662 }
never executed: end of block
0
663}
never executed: end of block
0
664-
665static void-
666client_status_confirm(struct ssh *ssh, int type, Channel *c, void *ctx)-
667{-
668 struct channel_reply_ctx *cr = (struct channel_reply_ctx *)ctx;-
669 char errmsg[256];-
670 int r, tochan;-
671-
672 /*-
673 * If a TTY was explicitly requested, then a failure to allocate-
674 * one is fatal.-
675 */-
676 if (cr->action == CONFIRM_TTY &&
cr->action == CONFIRM_TTYDescription
TRUEnever evaluated
FALSEnever evaluated
0
677 (options.request_tty == REQUEST_TTY_FORCE ||
options.request_tty == 3Description
TRUEnever evaluated
FALSEnever evaluated
0
678 options.request_tty == REQUEST_TTY_YES))
options.request_tty == 2Description
TRUEnever evaluated
FALSEnever evaluated
0
679 cr->action = CONFIRM_CLOSE;
never executed: cr->action = CONFIRM_CLOSE;
0
680-
681 /* XXX suppress on mux _client_ quietmode */-
682 tochan = options.log_level >= SYSLOG_LEVEL_ERROR &&
options.log_le...OG_LEVEL_ERRORDescription
TRUEnever evaluated
FALSEnever evaluated
0
683 c->ctl_chan != -1 && c->extended_usage == CHAN_EXTENDED_WRITE;
c->ctl_chan != -1Description
TRUEnever evaluated
FALSEnever evaluated
c->extended_usage == 2Description
TRUEnever evaluated
FALSEnever evaluated
0
684-
685 if (type == SSH2_MSG_CHANNEL_SUCCESS) {
type == 99Description
TRUEnever evaluated
FALSEnever evaluated
0
686 debug2("%s request accepted on channel %d",-
687 cr->request_type, c->self);-
688 } else if (type == SSH2_MSG_CHANNEL_FAILURE) {
never executed: end of block
type == 100Description
TRUEnever evaluated
FALSEnever evaluated
0
689 if (tochan) {
tochanDescription
TRUEnever evaluated
FALSEnever evaluated
0
690 snprintf(errmsg, sizeof(errmsg),-
691 "%s request failed\r\n", cr->request_type);-
692 } else {
never executed: end of block
0
693 snprintf(errmsg, sizeof(errmsg),-
694 "%s request failed on channel %d",-
695 cr->request_type, c->self);-
696 }
never executed: end of block
0
697 /* If error occurred on primary session channel, then exit */-
698 if (cr->action == CONFIRM_CLOSE && c->self == session_ident)
cr->action == CONFIRM_CLOSEDescription
TRUEnever evaluated
FALSEnever evaluated
c->self == session_identDescription
TRUEnever evaluated
FALSEnever evaluated
0
699 fatal("%s", errmsg);
never executed: fatal("%s", errmsg);
0
700 /*-
701 * If error occurred on mux client, append to-
702 * their stderr.-
703 */-
704 if (tochan) {
tochanDescription
TRUEnever evaluated
FALSEnever evaluated
0
705 if ((r = sshbuf_put(c->extended, errmsg,
(r = sshbuf_pu...errmsg))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
706 strlen(errmsg))) != 0)
(r = sshbuf_pu...errmsg))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
707 fatal("%s: buffer error %s", __func__,
never executed: fatal("%s: buffer error %s", __func__, ssh_err(r));
0
708 ssh_err(r));
never executed: fatal("%s: buffer error %s", __func__, ssh_err(r));
0
709 } else
never executed: end of block
0
710 error("%s", errmsg);
never executed: error("%s", errmsg);
0
711 if (cr->action == CONFIRM_TTY) {
cr->action == CONFIRM_TTYDescription
TRUEnever evaluated
FALSEnever evaluated
0
712 /*-
713 * If a TTY allocation error occurred, then arrange-
714 * for the correct TTY to leave raw mode.-
715 */-
716 if (c->self == session_ident)
c->self == session_identDescription
TRUEnever evaluated
FALSEnever evaluated
0
717 leave_raw_mode(0);
never executed: leave_raw_mode(0);
0
718 else-
719 mux_tty_alloc_failed(ssh, c);
never executed: mux_tty_alloc_failed(ssh, c);
0
720 } else if (cr->action == CONFIRM_CLOSE) {
cr->action == CONFIRM_CLOSEDescription
TRUEnever evaluated
FALSEnever evaluated
0
721 chan_read_failed(ssh, c);-
722 chan_write_failed(ssh, c);-
723 }
never executed: end of block
0
724 }
never executed: end of block
0
725 free(cr);-
726}
never executed: end of block
0
727-
728static void-
729client_abandon_status_confirm(struct ssh *ssh, Channel *c, void *ctx)-
730{-
731 free(ctx);-
732}
never executed: end of block
0
733-
734void-
735client_expect_confirm(struct ssh *ssh, int id, const char *request,-
736 enum confirm_action action)-
737{-
738 struct channel_reply_ctx *cr = xcalloc(1, sizeof(*cr));-
739-
740 cr->request_type = request;-
741 cr->action = action;-
742-
743 channel_register_status_confirm(ssh, id, client_status_confirm,-
744 client_abandon_status_confirm, cr);-
745}
never executed: end of block
0
746-
747void-
748client_register_global_confirm(global_confirm_cb *cb, void *ctx)-
749{-
750 struct global_confirm *gc, *last_gc;-
751-
752 /* Coalesce identical callbacks */-
753 last_gc = TAILQ_LAST(&global_confirms, global_confirms);-
754 if (last_gc && last_gc->cb == cb && last_gc->ctx == ctx) {
last_gcDescription
TRUEnever evaluated
FALSEnever evaluated
last_gc->cb == cbDescription
TRUEnever evaluated
FALSEnever evaluated
last_gc->ctx == ctxDescription
TRUEnever evaluated
FALSEnever evaluated
0
755 if (++last_gc->ref_count >= INT_MAX)
++last_gc->ref... >= 0x7fffffffDescription
TRUEnever evaluated
FALSEnever evaluated
0
756 fatal("%s: last_gc->ref_count = %d",
never executed: fatal("%s: last_gc->ref_count = %d", __func__, last_gc->ref_count);
0
757 __func__, last_gc->ref_count);
never executed: fatal("%s: last_gc->ref_count = %d", __func__, last_gc->ref_count);
0
758 return;
never executed: return;
0
759 }-
760-
761 gc = xcalloc(1, sizeof(*gc));-
762 gc->cb = cb;-
763 gc->ctx = ctx;-
764 gc->ref_count = 1;-
765 TAILQ_INSERT_TAIL(&global_confirms, gc, entry);-
766}
never executed: end of block
0
767-
768static void-
769process_cmdline(struct ssh *ssh)-
770{-
771 void (*handler)(int);-
772 char *s, *cmd;-
773 int ok, delete = 0, local = 0, remote = 0, dynamic = 0;-
774 struct Forward fwd;-
775-
776 memset(&fwd, 0, sizeof(fwd));-
777-
778 leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);-
779 handler = signal(SIGINT, SIG_IGN);-
780 cmd = s = read_passphrase("\r\nssh> ", RP_ECHO);-
781 if (s == NULL)
s == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
782 goto out;
never executed: goto out;
0
783 while (isspace((u_char)*s))
((*__ctype_b_l...int) _ISspace)Description
TRUEnever evaluated
FALSEnever evaluated
0
784 s++;
never executed: s++;
0
785 if (*s == '-')
*s == '-'Description
TRUEnever evaluated
FALSEnever evaluated
0
786 s++; /* Skip cmdline '-', if any */
never executed: s++;
0
787 if (*s == '\0')
*s == '\0'Description
TRUEnever evaluated
FALSEnever evaluated
0
788 goto out;
never executed: goto out;
0
789-
790 if (*s == 'h' || *s == 'H' || *s == '?') {
*s == 'h'Description
TRUEnever evaluated
FALSEnever evaluated
*s == 'H'Description
TRUEnever evaluated
FALSEnever evaluated
*s == '?'Description
TRUEnever evaluated
FALSEnever evaluated
0
791 logit("Commands:");-
792 logit(" -L[bind_address:]port:host:hostport "-
793 "Request local forward");-
794 logit(" -R[bind_address:]port:host:hostport "-
795 "Request remote forward");-
796 logit(" -D[bind_address:]port "-
797 "Request dynamic forward");-
798 logit(" -KL[bind_address:]port "-
799 "Cancel local forward");-
800 logit(" -KR[bind_address:]port "-
801 "Cancel remote forward");-
802 logit(" -KD[bind_address:]port "-
803 "Cancel dynamic forward");-
804 if (!options.permit_local_command)
!options.permit_local_commandDescription
TRUEnever evaluated
FALSEnever evaluated
0
805 goto out;
never executed: goto out;
0
806 logit(" !args "-
807 "Execute local command");-
808 goto out;
never executed: goto out;
0
809 }-
810-
811 if (*s == '!' && options.permit_local_command) {
*s == '!'Description
TRUEnever evaluated
FALSEnever evaluated
options.permit_local_commandDescription
TRUEnever evaluated
FALSEnever evaluated
0
812 s++;-
813 ssh_local_cmd(s);-
814 goto out;
never executed: goto out;
0
815 }-
816-
817 if (*s == 'K') {
*s == 'K'Description
TRUEnever evaluated
FALSEnever evaluated
0
818 delete = 1;-
819 s++;-
820 }
never executed: end of block
0
821 if (*s == 'L')
*s == 'L'Description
TRUEnever evaluated
FALSEnever evaluated
0
822 local = 1;
never executed: local = 1;
0
823 else if (*s == 'R')
*s == 'R'Description
TRUEnever evaluated
FALSEnever evaluated
0
824 remote = 1;
never executed: remote = 1;
0
825 else if (*s == 'D')
*s == 'D'Description
TRUEnever evaluated
FALSEnever evaluated
0
826 dynamic = 1;
never executed: dynamic = 1;
0
827 else {-
828 logit("Invalid command.");-
829 goto out;
never executed: goto out;
0
830 }-
831-
832 while (isspace((u_char)*++s))
((*__ctype_b_l...int) _ISspace)Description
TRUEnever evaluated
FALSEnever evaluated
0
833 ;
never executed: ;
0
834-
835 /* XXX update list of forwards in options */-
836 if (delete) {
deleteDescription
TRUEnever evaluated
FALSEnever evaluated
0
837 /* We pass 1 for dynamicfwd to restrict to 1 or 2 fields. */-
838 if (!parse_forward(&fwd, s, 1, 0)) {
!parse_forward(&fwd, s, 1, 0)Description
TRUEnever evaluated
FALSEnever evaluated
0
839 logit("Bad forwarding close specification.");-
840 goto out;
never executed: goto out;
0
841 }-
842 if (remote)
remoteDescription
TRUEnever evaluated
FALSEnever evaluated
0
843 ok = channel_request_rforward_cancel(ssh, &fwd) == 0;
never executed: ok = channel_request_rforward_cancel(ssh, &fwd) == 0;
0
844 else if (dynamic)
dynamicDescription
TRUEnever evaluated
FALSEnever evaluated
0
845 ok = channel_cancel_lport_listener(ssh, &fwd,
never executed: ok = channel_cancel_lport_listener(ssh, &fwd, 0, &options.fwd_opts) > 0;
0
846 0, &options.fwd_opts) > 0;
never executed: ok = channel_cancel_lport_listener(ssh, &fwd, 0, &options.fwd_opts) > 0;
0
847 else-
848 ok = channel_cancel_lport_listener(ssh, &fwd,
never executed: ok = channel_cancel_lport_listener(ssh, &fwd, -1, &options.fwd_opts) > 0;
0
849 CHANNEL_CANCEL_PORT_STATIC,
never executed: ok = channel_cancel_lport_listener(ssh, &fwd, -1, &options.fwd_opts) > 0;
0
850 &options.fwd_opts) > 0;
never executed: ok = channel_cancel_lport_listener(ssh, &fwd, -1, &options.fwd_opts) > 0;
0
851 if (!ok) {
!okDescription
TRUEnever evaluated
FALSEnever evaluated
0
852 logit("Unknown port forwarding.");-
853 goto out;
never executed: goto out;
0
854 }-
855 logit("Canceled forwarding.");-
856 } else {
never executed: end of block
0
857 if (!parse_forward(&fwd, s, dynamic, remote)) {
!parse_forward...namic, remote)Description
TRUEnever evaluated
FALSEnever evaluated
0
858 logit("Bad forwarding specification.");-
859 goto out;
never executed: goto out;
0
860 }-
861 if (local || dynamic) {
localDescription
TRUEnever evaluated
FALSEnever evaluated
dynamicDescription
TRUEnever evaluated
FALSEnever evaluated
0
862 if (!channel_setup_local_fwd_listener(ssh, &fwd,
!channel_setup...ions.fwd_opts)Description
TRUEnever evaluated
FALSEnever evaluated
0
863 &options.fwd_opts)) {
!channel_setup...ions.fwd_opts)Description
TRUEnever evaluated
FALSEnever evaluated
0
864 logit("Port forwarding failed.");-
865 goto out;
never executed: goto out;
0
866 }-
867 } else {
never executed: end of block
0
868 if (channel_request_remote_forwarding(ssh, &fwd) < 0) {
channel_reques...ssh, &fwd) < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
869 logit("Port forwarding failed.");-
870 goto out;
never executed: goto out;
0
871 }-
872 }
never executed: end of block
0
873 logit("Forwarding port.");-
874 }
never executed: end of block
0
875-
876out:
code before this statement never executed: out:
0
877 signal(SIGINT, handler);-
878 enter_raw_mode(options.request_tty == REQUEST_TTY_FORCE);-
879 free(cmd);-
880 free(fwd.listen_host);-
881 free(fwd.listen_path);-
882 free(fwd.connect_host);-
883 free(fwd.connect_path);-
884}
never executed: end of block
0
885-
886/* reasons to suppress output of an escape command in help output */-
887#define SUPPRESS_NEVER 0 /* never suppress, always show */-
888#define SUPPRESS_MUXCLIENT 1 /* don't show in mux client sessions */-
889#define SUPPRESS_MUXMASTER 2 /* don't show in mux master sessions */-
890#define SUPPRESS_SYSLOG 4 /* don't show when logging to syslog */-
891struct escape_help_text {-
892 const char *cmd;-
893 const char *text;-
894 unsigned int flags;-
895};-
896static struct escape_help_text esc_txt[] = {-
897 {".", "terminate session", SUPPRESS_MUXMASTER},-
898 {".", "terminate connection (and any multiplexed sessions)",-
899 SUPPRESS_MUXCLIENT},-
900 {"B", "send a BREAK to the remote system", SUPPRESS_NEVER},-
901 {"C", "open a command line", SUPPRESS_MUXCLIENT},-
902 {"R", "request rekey", SUPPRESS_NEVER},-
903 {"V/v", "decrease/increase verbosity (LogLevel)", SUPPRESS_MUXCLIENT},-
904 {"^Z", "suspend ssh", SUPPRESS_MUXCLIENT},-
905 {"#", "list forwarded connections", SUPPRESS_NEVER},-
906 {"&", "background ssh (when waiting for connections to terminate)",-
907 SUPPRESS_MUXCLIENT},-
908 {"?", "this message", SUPPRESS_NEVER},-
909};-
910-
911static void-
912print_escape_help(struct sshbuf *b, int escape_char, int mux_client,-
913 int using_stderr)-
914{-
915 unsigned int i, suppress_flags;-
916 int r;-
917-
918 if ((r = sshbuf_putf(b,
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
919 "%c?\r\nSupported escape sequences:\r\n", escape_char)) != 0)
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
920 fatal("%s: buffer error: %s", __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
921-
922 suppress_flags =-
923 (mux_client ? SUPPRESS_MUXCLIENT : 0) |
mux_clientDescription
TRUEnever evaluated
FALSEnever evaluated
0
924 (mux_client ? 0 : SUPPRESS_MUXMASTER) |-
925 (using_stderr ? 0 : SUPPRESS_SYSLOG);-
926-
927 for (i = 0; i < sizeof(esc_txt)/sizeof(esc_txt[0]); i++) {
i < sizeof(esc...of(esc_txt[0])Description
TRUEnever evaluated
FALSEnever evaluated
0
928 if (esc_txt[i].flags & suppress_flags)
esc_txt[i].fla...suppress_flagsDescription
TRUEnever evaluated
FALSEnever evaluated
0
929 continue;
never executed: continue;
0
930 if ((r = sshbuf_putf(b, " %c%-3s - %s\r\n",
(r = sshbuf_pu...i].text)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
931 escape_char, esc_txt[i].cmd, esc_txt[i].text)) != 0)
(r = sshbuf_pu...i].text)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
932 fatal("%s: buffer error: %s", __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
933 }
never executed: end of block
0
934-
935 if ((r = sshbuf_putf(b,
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
936 " %c%c - send the escape character by typing it twice\r\n"
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
937 "(Note that escapes are only recognized immediately after "
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
938 "newline.)\r\n", escape_char, escape_char)) != 0)
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
939 fatal("%s: buffer error: %s", __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
940}
never executed: end of block
0
941-
942/*-
943 * Process the characters one by one.-
944 */-
945static int-
946process_escapes(struct ssh *ssh, Channel *c,-
947 struct sshbuf *bin, struct sshbuf *bout, struct sshbuf *berr,-
948 char *buf, int len)-
949{-
950 pid_t pid;-
951 int r, bytes = 0;-
952 u_int i;-
953 u_char ch;-
954 char *s;-
955 struct escape_filter_ctx *efc = c->filter_ctx == NULL ?
c->filter_ctx == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
956 NULL : (struct escape_filter_ctx *)c->filter_ctx;-
957-
958 if (c->filter_ctx == NULL)
c->filter_ctx == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
959 return 0;
never executed: return 0;
0
960-
961 if (len <= 0)
len <= 0Description
TRUEnever evaluated
FALSEnever evaluated
0
962 return (0);
never executed: return (0);
0
963-
964 for (i = 0; i < (u_int)len; i++) {
i < (u_int)lenDescription
TRUEnever evaluated
FALSEnever evaluated
0
965 /* Get one character at a time. */-
966 ch = buf[i];-
967-
968 if (efc->escape_pending) {
efc->escape_pendingDescription
TRUEnever evaluated
FALSEnever evaluated
0
969 /* We have previously seen an escape character. */-
970 /* Clear the flag now. */-
971 efc->escape_pending = 0;-
972-
973 /* Process the escaped character. */-
974 switch (ch) {-
975 case '.':
never executed: case '.':
0
976 /* Terminate the connection. */-
977 if ((r = sshbuf_putf(berr, "%c.\r\n",
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
978 efc->escape_char)) != 0)
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
979 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
980 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
981 if (c && c->ctl_chan != -1) {
cDescription
TRUEnever evaluated
FALSEnever evaluated
c->ctl_chan != -1Description
TRUEnever evaluated
FALSEnever evaluated
0
982 chan_read_failed(ssh, c);-
983 chan_write_failed(ssh, c);-
984 if (c->detach_user) {
c->detach_userDescription
TRUEnever evaluated
FALSEnever evaluated
0
985 c->detach_user(ssh,-
986 c->self, NULL);-
987 }
never executed: end of block
0
988 c->type = SSH_CHANNEL_ABANDONED;-
989 sshbuf_reset(c->input);-
990 chan_ibuf_empty(ssh, c);-
991 return 0;
never executed: return 0;
0
992 } else-
993 quit_pending = 1;
never executed: quit_pending = 1;
0
994 return -1;
never executed: return -1;
0
995-
996 case 'Z' - 64:
never executed: case 'Z' - 64:
0
997 /* XXX support this for mux clients */-
998 if (c && c->ctl_chan != -1) {
cDescription
TRUEnever evaluated
FALSEnever evaluated
c->ctl_chan != -1Description
TRUEnever evaluated
FALSEnever evaluated
0
999 char b[16];-
1000 noescape:
code before this statement never executed: noescape:
0
1001 if (ch == 'Z' - 64)
ch == 'Z' - 64Description
TRUEnever evaluated
FALSEnever evaluated
0
1002 snprintf(b, sizeof b, "^Z");
never executed: snprintf(b, sizeof b, "^Z");
0
1003 else-
1004 snprintf(b, sizeof b, "%c", ch);
never executed: snprintf(b, sizeof b, "%c", ch);
0
1005 if ((r = sshbuf_putf(berr,
(r = sshbuf_pu...char, b)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1006 "%c%s escape not available to "
(r = sshbuf_pu...char, b)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1007 "multiplexed sessions\r\n",
(r = sshbuf_pu...char, b)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1008 efc->escape_char, b)) != 0)
(r = sshbuf_pu...char, b)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1009 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1010 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1011 continue;
never executed: continue;
0
1012 }-
1013 /* Suspend the program. Inform the user */-
1014 if ((r = sshbuf_putf(berr,
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1015 "%c^Z [suspend ssh]\r\n",
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1016 efc->escape_char)) != 0)
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1017 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1018 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1019-
1020 /* Restore terminal modes and suspend. */-
1021 client_suspend_self(bin, bout, berr);-
1022-
1023 /* We have been continued. */-
1024 continue;
never executed: continue;
0
1025-
1026 case 'B':
never executed: case 'B':
0
1027 if ((r = sshbuf_putf(berr,
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1028 "%cB\r\n", efc->escape_char)) != 0)
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1029 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1030 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1031 channel_request_start(ssh, c->self, "break", 0);-
1032 if ((r = sshpkt_put_u32(ssh, 1000)) != 0 ||
(r = sshpkt_pu...h, 1000)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1033 (r = sshpkt_send(ssh)) != 0)
(r = sshpkt_send(ssh)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1034 fatal("%s: %s", __func__,
never executed: fatal("%s: %s", __func__, ssh_err(r));
0
1035 ssh_err(r));
never executed: fatal("%s: %s", __func__, ssh_err(r));
0
1036 continue;
never executed: continue;
0
1037-
1038 case 'R':
never executed: case 'R':
0
1039 if (datafellows & SSH_BUG_NOREKEY)
datafellows & 0x00008000Description
TRUEnever evaluated
FALSEnever evaluated
0
1040 logit("Server does not "
never executed: logit("Server does not " "support re-keying");
0
1041 "support re-keying");
never executed: logit("Server does not " "support re-keying");
0
1042 else-
1043 need_rekeying = 1;
never executed: need_rekeying = 1;
0
1044 continue;
never executed: continue;
0
1045-
1046 case 'V':
never executed: case 'V':
0
1047 /* FALLTHROUGH */-
1048 case 'v':
never executed: case 'v':
0
1049 if (c && c->ctl_chan != -1)
cDescription
TRUEnever evaluated
FALSEnever evaluated
c->ctl_chan != -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1050 goto noescape;
never executed: goto noescape;
0
1051 if (!log_is_on_stderr()) {
!log_is_on_stderr()Description
TRUEnever evaluated
FALSEnever evaluated
0
1052 if ((r = sshbuf_putf(berr,
(r = sshbuf_pu...har, ch)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1053 "%c%c [Logging to syslog]\r\n",
(r = sshbuf_pu...har, ch)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1054 efc->escape_char, ch)) != 0)
(r = sshbuf_pu...har, ch)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1055 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1056 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1057 continue;
never executed: continue;
0
1058 }-
1059 if (ch == 'V' && options.log_level >
ch == 'V'Description
TRUEnever evaluated
FALSEnever evaluated
options.log_le...OG_LEVEL_QUIETDescription
TRUEnever evaluated
FALSEnever evaluated
0
1060 SYSLOG_LEVEL_QUIET)
options.log_le...OG_LEVEL_QUIETDescription
TRUEnever evaluated
FALSEnever evaluated
0
1061 log_change_level(--options.log_level);
never executed: log_change_level(--options.log_level);
0
1062 if (ch == 'v' && options.log_level <
ch == 'v'Description
TRUEnever evaluated
FALSEnever evaluated
options.log_le...G_LEVEL_DEBUG3Description
TRUEnever evaluated
FALSEnever evaluated
0
1063 SYSLOG_LEVEL_DEBUG3)
options.log_le...G_LEVEL_DEBUG3Description
TRUEnever evaluated
FALSEnever evaluated
0
1064 log_change_level(++options.log_level);
never executed: log_change_level(++options.log_level);
0
1065 if ((r = sshbuf_putf(berr,
(r = sshbuf_pu..._level))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1066 "%c%c [LogLevel %s]\r\n",
(r = sshbuf_pu..._level))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1067 efc->escape_char, ch,
(r = sshbuf_pu..._level))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1068 log_level_name(options.log_level))) != 0)
(r = sshbuf_pu..._level))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1069 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1070 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1071 continue;
never executed: continue;
0
1072-
1073 case '&':
never executed: case '&':
0
1074 if (c && c->ctl_chan != -1)
cDescription
TRUEnever evaluated
FALSEnever evaluated
c->ctl_chan != -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1075 goto noescape;
never executed: goto noescape;
0
1076 /*-
1077 * Detach the program (continue to serve-
1078 * connections, but put in background and no-
1079 * more new connections).-
1080 */-
1081 /* Restore tty modes. */-
1082 leave_raw_mode(-
1083 options.request_tty == REQUEST_TTY_FORCE);-
1084-
1085 /* Stop listening for new connections. */-
1086 channel_stop_listening(ssh);-
1087-
1088 if ((r = sshbuf_putf(berr,
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1089 "%c& [backgrounded]\n", efc->escape_char))
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1090 != 0)
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1091 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1092 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1093-
1094 /* Fork into background. */-
1095 pid = fork();-
1096 if (pid < 0) {
pid < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1097 error("fork: %.100s", strerror(errno));-
1098 continue;
never executed: continue;
0
1099 }-
1100 if (pid != 0) { /* This is the parent. */
pid != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1101 /* The parent just exits. */-
1102 exit(0);
never executed: exit(0);
0
1103 }-
1104 /* The child continues serving connections. */-
1105 /* fake EOF on stdin */-
1106 if ((r = sshbuf_put_u8(bin, 4)) != 0)
(r = sshbuf_pu...(bin, 4)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1107 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1108 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1109 return -1;
never executed: return -1;
0
1110 case '?':
never executed: case '?':
0
1111 print_escape_help(berr, efc->escape_char,-
1112 (c && c->ctl_chan != -1),-
1113 log_is_on_stderr());-
1114 continue;
never executed: continue;
0
1115-
1116 case '#':
never executed: case '#':
0
1117 if ((r = sshbuf_putf(berr, "%c#\r\n",
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1118 efc->escape_char)) != 0)
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1119 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1120 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1121 s = channel_open_message(ssh);-
1122 if ((r = sshbuf_put(berr, s, strlen(s))) != 0)
(r = sshbuf_pu...rlen(s))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1123 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1124 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1125 free(s);-
1126 continue;
never executed: continue;
0
1127-
1128 case 'C':
never executed: case 'C':
0
1129 if (c && c->ctl_chan != -1)
cDescription
TRUEnever evaluated
FALSEnever evaluated
c->ctl_chan != -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1130 goto noescape;
never executed: goto noescape;
0
1131 process_cmdline(ssh);-
1132 continue;
never executed: continue;
0
1133-
1134 default:
never executed: default:
0
1135 if (ch != efc->escape_char) {
ch != efc->escape_charDescription
TRUEnever evaluated
FALSEnever evaluated
0
1136 if ((r = sshbuf_put_u8(bin,
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1137 efc->escape_char)) != 0)
(r = sshbuf_pu...pe_char)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1138 fatal("%s: buffer error: %s",
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1139 __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1140 bytes++;-
1141 }
never executed: end of block
0
1142 /* Escaped characters fall through here */-
1143 break;
never executed: break;
0
1144 }-
1145 } else {-
1146 /*-
1147 * The previous character was not an escape char.-
1148 * Check if this is an escape.-
1149 */-
1150 if (last_was_cr && ch == efc->escape_char) {
last_was_crDescription
TRUEnever evaluated
FALSEnever evaluated
ch == efc->escape_charDescription
TRUEnever evaluated
FALSEnever evaluated
0
1151 /*-
1152 * It is. Set the flag and continue to-
1153 * next character.-
1154 */-
1155 efc->escape_pending = 1;-
1156 continue;
never executed: continue;
0
1157 }-
1158 }
never executed: end of block
0
1159-
1160 /*-
1161 * Normal character. Record whether it was a newline,-
1162 * and append it to the buffer.-
1163 */-
1164 last_was_cr = (ch == '\r' || ch == '\n');
ch == '\r'Description
TRUEnever evaluated
FALSEnever evaluated
ch == '\n'Description
TRUEnever evaluated
FALSEnever evaluated
0
1165 if ((r = sshbuf_put_u8(bin, ch)) != 0)
(r = sshbuf_pu...bin, ch)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1166 fatal("%s: buffer error: %s", __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1167 bytes++;-
1168 }
never executed: end of block
0
1169 return bytes;
never executed: return bytes;
0
1170}-
1171-
1172/*-
1173 * Get packets from the connection input buffer, and process them as long as-
1174 * there are packets available.-
1175 *-
1176 * Any unknown packets received during the actual-
1177 * session cause the session to terminate. This is-
1178 * intended to make debugging easier since no-
1179 * confirmations are sent. Any compatible protocol-
1180 * extensions must be negotiated during the-
1181 * preparatory phase.-
1182 */-
1183-
1184static void-
1185client_process_buffered_input_packets(void)-
1186{-
1187 ssh_dispatch_run_fatal(active_state, DISPATCH_NONBLOCK, &quit_pending);-
1188}
never executed: end of block
0
1189-
1190/* scan buf[] for '~' before sending data to the peer */-
1191-
1192/* Helper: allocate a new escape_filter_ctx and fill in its escape char */-
1193void *-
1194client_new_escape_filter_ctx(int escape_char)-
1195{-
1196 struct escape_filter_ctx *ret;-
1197-
1198 ret = xcalloc(1, sizeof(*ret));-
1199 ret->escape_pending = 0;-
1200 ret->escape_char = escape_char;-
1201 return (void *)ret;
never executed: return (void *)ret;
0
1202}-
1203-
1204/* Free the escape filter context on channel free */-
1205void-
1206client_filter_cleanup(struct ssh *ssh, int cid, void *ctx)-
1207{-
1208 free(ctx);-
1209}
never executed: end of block
0
1210-
1211int-
1212client_simple_escape_filter(struct ssh *ssh, Channel *c, char *buf, int len)-
1213{-
1214 if (c->extended_usage != CHAN_EXTENDED_WRITE)
c->extended_usage != 2Description
TRUEnever evaluated
FALSEnever evaluated
0
1215 return 0;
never executed: return 0;
0
1216-
1217 return process_escapes(ssh, c, c->input, c->output, c->extended,
never executed: return process_escapes(ssh, c, c->input, c->output, c->extended, buf, len);
0
1218 buf, len);
never executed: return process_escapes(ssh, c, c->input, c->output, c->extended, buf, len);
0
1219}-
1220-
1221static void-
1222client_channel_closed(struct ssh *ssh, int id, void *arg)-
1223{-
1224 channel_cancel_cleanup(ssh, id);-
1225 session_closed = 1;-
1226 leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);-
1227}
never executed: end of block
0
1228-
1229/*-
1230 * Implements the interactive session with the server. This is called after-
1231 * the user has been authenticated, and a command has been started on the-
1232 * remote host. If escape_char != SSH_ESCAPECHAR_NONE, it is the character-
1233 * used as an escape character for terminating or suspending the session.-
1234 */-
1235int-
1236client_loop(struct ssh *ssh, int have_pty, int escape_char_arg,-
1237 int ssh2_chan_id)-
1238{-
1239 fd_set *readset = NULL, *writeset = NULL;-
1240 double start_time, total_time;-
1241 int r, max_fd = 0, max_fd2 = 0, len;-
1242 u_int64_t ibytes, obytes;-
1243 u_int nalloc = 0;-
1244 char buf[100];-
1245-
1246 debug("Entering interactive session.");-
1247-
1248 if (options.control_master &&
options.control_masterDescription
TRUEnever evaluated
FALSEnever evaluated
0
1249 !option_clear_or_none(options.control_path)) {
!option_clear_....control_path)Description
TRUEnever evaluated
FALSEnever evaluated
0
1250 debug("pledge: id");-
1251 if (pledge("stdio rpath wpath cpath unix inet dns recvfd proc exec id tty",
pledge("stdio ...d *)0) ) == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1252 NULL) == -1)
pledge("stdio ...d *)0) ) == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1253 fatal("%s pledge(): %s", __func__, strerror(errno));
never executed: fatal("%s pledge(): %s", __func__, strerror( (*__errno_location ()) ));
0
1254-
1255 } else if (options.forward_x11 || options.permit_local_command) {
never executed: end of block
options.forward_x11Description
TRUEnever evaluated
FALSEnever evaluated
options.permit_local_commandDescription
TRUEnever evaluated
FALSEnever evaluated
0
1256 debug("pledge: exec");-
1257 if (pledge("stdio rpath wpath cpath unix inet dns proc exec tty",
pledge("stdio ...d *)0) ) == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1258 NULL) == -1)
pledge("stdio ...d *)0) ) == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1259 fatal("%s pledge(): %s", __func__, strerror(errno));
never executed: fatal("%s pledge(): %s", __func__, strerror( (*__errno_location ()) ));
0
1260-
1261 } else if (options.update_hostkeys) {
never executed: end of block
options.update_hostkeysDescription
TRUEnever evaluated
FALSEnever evaluated
0
1262 debug("pledge: filesystem full");-
1263 if (pledge("stdio rpath wpath cpath unix inet dns proc tty",
pledge("stdio ...d *)0) ) == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1264 NULL) == -1)
pledge("stdio ...d *)0) ) == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1265 fatal("%s pledge(): %s", __func__, strerror(errno));
never executed: fatal("%s pledge(): %s", __func__, strerror( (*__errno_location ()) ));
0
1266-
1267 } else if (!option_clear_or_none(options.proxy_command) ||
never executed: end of block
!option_clear_...proxy_command)Description
TRUEnever evaluated
FALSEnever evaluated
0
1268 fork_after_authentication_flag) {
fork_after_authentication_flagDescription
TRUEnever evaluated
FALSEnever evaluated
0
1269 debug("pledge: proc");-
1270 if (pledge("stdio cpath unix inet dns proc tty", NULL) == -1)
pledge("stdio ...d *)0) ) == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1271 fatal("%s pledge(): %s", __func__, strerror(errno));
never executed: fatal("%s pledge(): %s", __func__, strerror( (*__errno_location ()) ));
0
1272-
1273 } else {
never executed: end of block
0
1274 debug("pledge: network");-
1275 if (pledge("stdio unix inet dns proc tty", NULL) == -1)
pledge("stdio ...d *)0) ) == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1276 fatal("%s pledge(): %s", __func__, strerror(errno));
never executed: fatal("%s pledge(): %s", __func__, strerror( (*__errno_location ()) ));
0
1277 }
never executed: end of block
0
1278-
1279 start_time = monotime_double();-
1280-
1281 /* Initialize variables. */-
1282 last_was_cr = 1;-
1283 exit_status = -1;-
1284 connection_in = packet_get_connection_in();-
1285 connection_out = packet_get_connection_out();-
1286 max_fd = MAXIMUM(connection_in, connection_out);
((connection_i...nnection_out))Description
TRUEnever evaluated
FALSEnever evaluated
0
1287-
1288 quit_pending = 0;-
1289-
1290 /* Initialize buffer. */-
1291 if ((stderr_buffer = sshbuf_new()) == NULL)
(stderr_buffer...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1292 fatal("%s: sshbuf_new failed", __func__);
never executed: fatal("%s: sshbuf_new failed", __func__);
0
1293-
1294 client_init_dispatch();-
1295-
1296 /*-
1297 * Set signal handlers, (e.g. to restore non-blocking mode)-
1298 * but don't overwrite SIG_IGN, matches behaviour from rsh(1)-
1299 */-
1300 if (signal(SIGHUP, SIG_IGN) != SIG_IGN)
mysignal( 1 , ...ghandler_t) 1)Description
TRUEnever evaluated
FALSEnever evaluated
0
1301 signal(SIGHUP, signal_handler);
never executed: mysignal( 1 ,signal_handler);
0
1302 if (signal(SIGINT, SIG_IGN) != SIG_IGN)
mysignal( 2 , ...ghandler_t) 1)Description
TRUEnever evaluated
FALSEnever evaluated
0
1303 signal(SIGINT, signal_handler);
never executed: mysignal( 2 ,signal_handler);
0
1304 if (signal(SIGQUIT, SIG_IGN) != SIG_IGN)
mysignal( 3 , ...ghandler_t) 1)Description
TRUEnever evaluated
FALSEnever evaluated
0
1305 signal(SIGQUIT, signal_handler);
never executed: mysignal( 3 ,signal_handler);
0
1306 if (signal(SIGTERM, SIG_IGN) != SIG_IGN)
mysignal( 15 ,...ghandler_t) 1)Description
TRUEnever evaluated
FALSEnever evaluated
0
1307 signal(SIGTERM, signal_handler);
never executed: mysignal( 15 ,signal_handler);
0
1308 signal(SIGWINCH, window_change_handler);-
1309-
1310 if (have_pty)
have_ptyDescription
TRUEnever evaluated
FALSEnever evaluated
0
1311 enter_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
never executed: enter_raw_mode(options.request_tty == 3);
0
1312-
1313 session_ident = ssh2_chan_id;-
1314 if (session_ident != -1) {
session_ident != -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1315 if (escape_char_arg != SSH_ESCAPECHAR_NONE) {
escape_char_arg != -2Description
TRUEnever evaluated
FALSEnever evaluated
0
1316 channel_register_filter(ssh, session_ident,-
1317 client_simple_escape_filter, NULL,-
1318 client_filter_cleanup,-
1319 client_new_escape_filter_ctx(-
1320 escape_char_arg));-
1321 }
never executed: end of block
0
1322 channel_register_cleanup(ssh, session_ident,-
1323 client_channel_closed, 0);-
1324 }
never executed: end of block
0
1325-
1326 /* Main loop of the client for the interactive session mode. */-
1327 while (!quit_pending) {
!quit_pendingDescription
TRUEnever evaluated
FALSEnever evaluated
0
1328-
1329 /* Process buffered packets sent by the server. */-
1330 client_process_buffered_input_packets();-
1331-
1332 if (session_closed && !channel_still_open(ssh))
session_closedDescription
TRUEnever evaluated
FALSEnever evaluated
!channel_still_open(ssh)Description
TRUEnever evaluated
FALSEnever evaluated
0
1333 break;
never executed: break;
0
1334-
1335 if (ssh_packet_is_rekeying(ssh)) {
ssh_packet_is_rekeying(ssh)Description
TRUEnever evaluated
FALSEnever evaluated
0
1336 debug("rekeying in progress");-
1337 } else if (need_rekeying) {
never executed: end of block
need_rekeyingDescription
TRUEnever evaluated
FALSEnever evaluated
0
1338 /* manual rekey request */-
1339 debug("need rekeying");-
1340 if ((r = kex_start_rekex(ssh)) != 0)
(r = kex_start...kex(ssh)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1341 fatal("%s: kex_start_rekex: %s", __func__,
never executed: fatal("%s: kex_start_rekex: %s", __func__, ssh_err(r));
0
1342 ssh_err(r));
never executed: fatal("%s: kex_start_rekex: %s", __func__, ssh_err(r));
0
1343 need_rekeying = 0;-
1344 } else {
never executed: end of block
0
1345 /*-
1346 * Make packets from buffered channel data, and-
1347 * enqueue them for sending to the server.-
1348 */-
1349 if (packet_not_very_much_data_to_write())
ssh_packet_not...(active_state)Description
TRUEnever evaluated
FALSEnever evaluated
0
1350 channel_output_poll(ssh);
never executed: channel_output_poll(ssh);
0
1351-
1352 /*-
1353 * Check if the window size has changed, and buffer a-
1354 * message about it to the server if so.-
1355 */-
1356 client_check_window_change(ssh);-
1357-
1358 if (quit_pending)
quit_pendingDescription
TRUEnever evaluated
FALSEnever evaluated
0
1359 break;
never executed: break;
0
1360 }
never executed: end of block
0
1361 /*-
1362 * Wait until we have something to do (something becomes-
1363 * available on one of the descriptors).-
1364 */-
1365 max_fd2 = max_fd;-
1366 client_wait_until_can_do_something(ssh, &readset, &writeset,-
1367 &max_fd2, &nalloc, ssh_packet_is_rekeying(ssh));-
1368-
1369 if (quit_pending)
quit_pendingDescription
TRUEnever evaluated
FALSEnever evaluated
0
1370 break;
never executed: break;
0
1371-
1372 /* Do channel operations unless rekeying in progress. */-
1373 if (!ssh_packet_is_rekeying(ssh))
!ssh_packet_is_rekeying(ssh)Description
TRUEnever evaluated
FALSEnever evaluated
0
1374 channel_after_select(ssh, readset, writeset);
never executed: channel_after_select(ssh, readset, writeset);
0
1375-
1376 /* Buffer input from the connection. */-
1377 client_process_net_input(readset);-
1378-
1379 if (quit_pending)
quit_pendingDescription
TRUEnever evaluated
FALSEnever evaluated
0
1380 break;
never executed: break;
0
1381-
1382 /*-
1383 * Send as much buffered packet data as possible to the-
1384 * sender.-
1385 */-
1386 if (FD_ISSET(connection_out, writeset))
kludge_FD_ISSE...out, writeset)Description
TRUEnever evaluated
FALSEnever evaluated
0
1387 packet_write_poll();
never executed: packet_write_poll();
0
1388-
1389 /*-
1390 * If we are a backgrounded control master, and the-
1391 * timeout has expired without any active client-
1392 * connections, then quit.-
1393 */-
1394 if (control_persist_exit_time > 0) {
control_persist_exit_time > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1395 if (monotime() >= control_persist_exit_time) {
monotime() >= ...sist_exit_timeDescription
TRUEnever evaluated
FALSEnever evaluated
0
1396 debug("ControlPersist timeout expired");-
1397 break;
never executed: break;
0
1398 }-
1399 }
never executed: end of block
0
1400 }
never executed: end of block
0
1401 free(readset);-
1402 free(writeset);-
1403-
1404 /* Terminate the session. */-
1405-
1406 /* Stop watching for window change. */-
1407 signal(SIGWINCH, SIG_DFL);-
1408-
1409 packet_start(SSH2_MSG_DISCONNECT);-
1410 packet_put_int(SSH2_DISCONNECT_BY_APPLICATION);-
1411 packet_put_cstring("disconnected by user");-
1412 packet_put_cstring(""); /* language tag */-
1413 packet_send();-
1414 packet_write_wait();-
1415-
1416 channel_free_all(ssh);-
1417-
1418 if (have_pty)
have_ptyDescription
TRUEnever evaluated
FALSEnever evaluated
0
1419 leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);
never executed: leave_raw_mode(options.request_tty == 3);
0
1420-
1421 /* restore blocking io */-
1422 if (!isatty(fileno(stdin)))
!isatty(fileno( stdin ))Description
TRUEnever evaluated
FALSEnever evaluated
0
1423 unset_nonblock(fileno(stdin));
never executed: unset_nonblock(fileno( stdin ));
0
1424 if (!isatty(fileno(stdout)))
!isatty(fileno( stdout ))Description
TRUEnever evaluated
FALSEnever evaluated
0
1425 unset_nonblock(fileno(stdout));
never executed: unset_nonblock(fileno( stdout ));
0
1426 if (!isatty(fileno(stderr)))
!isatty(fileno( stderr ))Description
TRUEnever evaluated
FALSEnever evaluated
0
1427 unset_nonblock(fileno(stderr));
never executed: unset_nonblock(fileno( stderr ));
0
1428-
1429 /*-
1430 * If there was no shell or command requested, there will be no remote-
1431 * exit status to be returned. In that case, clear error code if the-
1432 * connection was deliberately terminated at this end.-
1433 */-
1434 if (no_shell_flag && received_signal == SIGTERM) {
no_shell_flagDescription
TRUEnever evaluated
FALSEnever evaluated
received_signal == 15Description
TRUEnever evaluated
FALSEnever evaluated
0
1435 received_signal = 0;-
1436 exit_status = 0;-
1437 }
never executed: end of block
0
1438-
1439 if (received_signal) {
received_signalDescription
TRUEnever evaluated
FALSEnever evaluated
0
1440 verbose("Killed by signal %d.", (int) received_signal);-
1441 cleanup_exit(0);-
1442 }
never executed: end of block
0
1443-
1444 /*-
1445 * In interactive mode (with pseudo tty) display a message indicating-
1446 * that the connection has been closed.-
1447 */-
1448 if (have_pty && options.log_level != SYSLOG_LEVEL_QUIET) {
have_ptyDescription
TRUEnever evaluated
FALSEnever evaluated
options.log_le...OG_LEVEL_QUIETDescription
TRUEnever evaluated
FALSEnever evaluated
0
1449 if ((r = sshbuf_putf(stderr_buffer,
(r = sshbuf_pu...", host)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1450 "Connection to %.64s closed.\r\n", host)) != 0)
(r = sshbuf_pu...", host)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1451 fatal("%s: buffer error: %s", __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1452 }
never executed: end of block
0
1453-
1454 /* Output any buffered data for stderr. */-
1455 if (sshbuf_len(stderr_buffer) > 0) {
sshbuf_len(stderr_buffer) > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1456 len = atomicio(vwrite, fileno(stderr),-
1457 (u_char *)sshbuf_ptr(stderr_buffer),-
1458 sshbuf_len(stderr_buffer));-
1459 if (len < 0 || (u_int)len != sshbuf_len(stderr_buffer))
len < 0Description
TRUEnever evaluated
FALSEnever evaluated
(u_int)len != ...stderr_buffer)Description
TRUEnever evaluated
FALSEnever evaluated
0
1460 error("Write failed flushing stderr buffer.");
never executed: error("Write failed flushing stderr buffer.");
0
1461 else if ((r = sshbuf_consume(stderr_buffer, len)) != 0)
(r = sshbuf_co...er, len)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1462 fatal("%s: buffer error: %s", __func__, ssh_err(r));
never executed: fatal("%s: buffer error: %s", __func__, ssh_err(r));
0
1463 }
never executed: end of block
0
1464-
1465 /* Clear and free any buffers. */-
1466 explicit_bzero(buf, sizeof(buf));-
1467 sshbuf_free(stderr_buffer);-
1468-
1469 /* Report bytes transferred, and transfer rates. */-
1470 total_time = monotime_double() - start_time;-
1471 packet_get_bytes(&ibytes, &obytes);-
1472 verbose("Transferred: sent %llu, received %llu bytes, in %.1f seconds",-
1473 (unsigned long long)obytes, (unsigned long long)ibytes, total_time);-
1474 if (total_time > 0)
total_time > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1475 verbose("Bytes per second: sent %.1f, received %.1f",
never executed: verbose("Bytes per second: sent %.1f, received %.1f", obytes / total_time, ibytes / total_time);
0
1476 obytes / total_time, ibytes / total_time);
never executed: verbose("Bytes per second: sent %.1f, received %.1f", obytes / total_time, ibytes / total_time);
0
1477 /* Return the exit status of the program. */-
1478 debug("Exit status %d", exit_status);-
1479 return exit_status;
never executed: return exit_status;
0
1480}-
1481-
1482/*********/-
1483-
1484static Channel *-
1485client_request_forwarded_tcpip(struct ssh *ssh, const char *request_type,-
1486 int rchan, u_int rwindow, u_int rmaxpack)-
1487{-
1488 Channel *c = NULL;-
1489 struct sshbuf *b = NULL;-
1490 char *listen_address, *originator_address;-
1491 u_short listen_port, originator_port;-
1492 int r;-
1493-
1494 /* Get rest of the packet */-
1495 listen_address = packet_get_string(NULL);-
1496 listen_port = packet_get_int();-
1497 originator_address = packet_get_string(NULL);-
1498 originator_port = packet_get_int();-
1499 packet_check_eom();
never executed: end of block
_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1500-
1501 debug("%s: listen %s port %d, originator %s port %d", __func__,-
1502 listen_address, listen_port, originator_address, originator_port);-
1503-
1504 c = channel_connect_by_listen_address(ssh, listen_address, listen_port,-
1505 "forwarded-tcpip", originator_address);-
1506-
1507 if (c != NULL && c->type == SSH_CHANNEL_MUX_CLIENT) {
c != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
c->type == 16Description
TRUEnever evaluated
FALSEnever evaluated
0
1508 if ((b = sshbuf_new()) == NULL) {
(b = sshbuf_ne...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1509 error("%s: alloc reply", __func__);-
1510 goto out;
never executed: goto out;
0
1511 }-
1512 /* reconstruct and send to muxclient */-
1513 if ((r = sshbuf_put_u8(b, 0)) != 0 || /* padlen */
(r = sshbuf_put_u8(b, 0)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1514 (r = sshbuf_put_u8(b, SSH2_MSG_CHANNEL_OPEN)) != 0 ||
(r = sshbuf_pu...8(b, 90)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1515 (r = sshbuf_put_cstring(b, request_type)) != 0 ||
(r = sshbuf_pu...st_type)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1516 (r = sshbuf_put_u32(b, rchan)) != 0 ||
(r = sshbuf_pu..., rchan)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1517 (r = sshbuf_put_u32(b, rwindow)) != 0 ||
(r = sshbuf_pu...rwindow)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1518 (r = sshbuf_put_u32(b, rmaxpack)) != 0 ||
(r = sshbuf_pu...maxpack)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1519 (r = sshbuf_put_cstring(b, listen_address)) != 0 ||
(r = sshbuf_pu...address)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1520 (r = sshbuf_put_u32(b, listen_port)) != 0 ||
(r = sshbuf_pu...en_port)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1521 (r = sshbuf_put_cstring(b, originator_address)) != 0 ||
(r = sshbuf_pu...address)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1522 (r = sshbuf_put_u32(b, originator_port)) != 0 ||
(r = sshbuf_pu...or_port)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1523 (r = sshbuf_put_stringb(c->output, b)) != 0) {
(r = sshbuf_pu...tput, b)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1524 error("%s: compose for muxclient %s", __func__,-
1525 ssh_err(r));-
1526 goto out;
never executed: goto out;
0
1527 }-
1528 }
never executed: end of block
0
1529-
1530 out:
code before this statement never executed: out:
0
1531 sshbuf_free(b);-
1532 free(originator_address);-
1533 free(listen_address);-
1534 return c;
never executed: return c;
0
1535}-
1536-
1537static Channel *-
1538client_request_forwarded_streamlocal(struct ssh *ssh,-
1539 const char *request_type, int rchan)-
1540{-
1541 Channel *c = NULL;-
1542 char *listen_path;-
1543-
1544 /* Get the remote path. */-
1545 listen_path = packet_get_string(NULL);-
1546 /* XXX: Skip reserved field for now. */-
1547 if (packet_get_string_ptr(NULL) == NULL)
ssh_packet_get...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1548 fatal("%s: packet_get_string_ptr failed", __func__);
never executed: fatal("%s: packet_get_string_ptr failed", __func__);
0
1549 packet_check_eom();
never executed: end of block
_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1550-
1551 debug("%s: %s", __func__, listen_path);-
1552-
1553 c = channel_connect_by_listen_path(ssh, listen_path,-
1554 "forwarded-streamlocal@openssh.com", "forwarded-streamlocal");-
1555 free(listen_path);-
1556 return c;
never executed: return c;
0
1557}-
1558-
1559static Channel *-
1560client_request_x11(struct ssh *ssh, const char *request_type, int rchan)-
1561{-
1562 Channel *c = NULL;-
1563 char *originator;-
1564 u_short originator_port;-
1565 int sock;-
1566-
1567 if (!options.forward_x11) {
!options.forward_x11Description
TRUEnever evaluated
FALSEnever evaluated
0
1568 error("Warning: ssh server tried X11 forwarding.");-
1569 error("Warning: this is probably a break-in attempt by a "-
1570 "malicious server.");-
1571 return NULL;
never executed: return ((void *)0) ;
0
1572 }-
1573 if (x11_refuse_time != 0 && (u_int)monotime() >= x11_refuse_time) {
x11_refuse_time != 0Description
TRUEnever evaluated
FALSEnever evaluated
(u_int)monotim...11_refuse_timeDescription
TRUEnever evaluated
FALSEnever evaluated
0
1574 verbose("Rejected X11 connection after ForwardX11Timeout "-
1575 "expired");-
1576 return NULL;
never executed: return ((void *)0) ;
0
1577 }-
1578 originator = packet_get_string(NULL);-
1579 originator_port = packet_get_int();-
1580 packet_check_eom();
never executed: end of block
_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1581 /* XXX check permission */-
1582 debug("client_request_x11: request from %s %d", originator,-
1583 originator_port);-
1584 free(originator);-
1585 sock = x11_connect_display(ssh);-
1586 if (sock < 0)
sock < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1587 return NULL;
never executed: return ((void *)0) ;
0
1588 c = channel_new(ssh, "x11",-
1589 SSH_CHANNEL_X11_OPEN, sock, sock, -1,-
1590 CHAN_TCP_WINDOW_DEFAULT, CHAN_X11_PACKET_DEFAULT, 0, "x11", 1);-
1591 c->force_drain = 1;-
1592 return c;
never executed: return c;
0
1593}-
1594-
1595static Channel *-
1596client_request_agent(struct ssh *ssh, const char *request_type, int rchan)-
1597{-
1598 Channel *c = NULL;-
1599 int r, sock;-
1600-
1601 if (!options.forward_agent) {
!options.forward_agentDescription
TRUEnever evaluated
FALSEnever evaluated
0
1602 error("Warning: ssh server tried agent forwarding.");-
1603 error("Warning: this is probably a break-in attempt by a "-
1604 "malicious server.");-
1605 return NULL;
never executed: return ((void *)0) ;
0
1606 }-
1607 if ((r = ssh_get_authentication_socket(&sock)) != 0) {
(r = ssh_get_a...t(&sock)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1608 if (r != SSH_ERR_AGENT_NOT_PRESENT)
r != -47Description
TRUEnever evaluated
FALSEnever evaluated
0
1609 debug("%s: ssh_get_authentication_socket: %s",
never executed: debug("%s: ssh_get_authentication_socket: %s", __func__, ssh_err(r));
0
1610 __func__, ssh_err(r));
never executed: debug("%s: ssh_get_authentication_socket: %s", __func__, ssh_err(r));
0
1611 return NULL;
never executed: return ((void *)0) ;
0
1612 }-
1613 c = channel_new(ssh, "authentication agent connection",-
1614 SSH_CHANNEL_OPEN, sock, sock, -1,-
1615 CHAN_X11_WINDOW_DEFAULT, CHAN_TCP_PACKET_DEFAULT, 0,-
1616 "authentication agent connection", 1);-
1617 c->force_drain = 1;-
1618 return c;
never executed: return c;
0
1619}-
1620-
1621char *-
1622client_request_tun_fwd(struct ssh *ssh, int tun_mode,-
1623 int local_tun, int remote_tun)-
1624{-
1625 Channel *c;-
1626 int fd;-
1627 char *ifname = NULL;-
1628-
1629 if (tun_mode == SSH_TUNMODE_NO)
tun_mode == 0x00Description
TRUEnever evaluated
FALSEnever evaluated
0
1630 return 0;
never executed: return 0;
0
1631-
1632 debug("Requesting tun unit %d in mode %d", local_tun, tun_mode);-
1633-
1634 /* Open local tunnel device */-
1635 if ((fd = tun_open(local_tun, tun_mode, &ifname)) == -1) {
(fd = tun_open...ifname)) == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1636 error("Tunnel device open failed.");-
1637 return NULL;
never executed: return ((void *)0) ;
0
1638 }-
1639 debug("Tunnel forwarding using interface %s", ifname);-
1640-
1641 c = channel_new(ssh, "tun", SSH_CHANNEL_OPENING, fd, fd, -1,-
1642 CHAN_TCP_WINDOW_DEFAULT, CHAN_TCP_PACKET_DEFAULT, 0, "tun", 1);-
1643 c->datagram = 1;-
1644-
1645#if defined(SSH_TUN_FILTER)-
1646 if (options.tun_open == SSH_TUNMODE_POINTOPOINT)
options.tun_open == 0x01Description
TRUEnever evaluated
FALSEnever evaluated
0
1647 channel_register_filter(ssh, c->self, sys_tun_infilter,
never executed: channel_register_filter(ssh, c->self, sys_tun_infilter, sys_tun_outfilter, ((void *)0) , ((void *)0) );
0
1648 sys_tun_outfilter, NULL, NULL);
never executed: channel_register_filter(ssh, c->self, sys_tun_infilter, sys_tun_outfilter, ((void *)0) , ((void *)0) );
0
1649#endif-
1650-
1651 packet_start(SSH2_MSG_CHANNEL_OPEN);-
1652 packet_put_cstring("tun@openssh.com");-
1653 packet_put_int(c->self);-
1654 packet_put_int(c->local_window_max);-
1655 packet_put_int(c->local_maxpacket);-
1656 packet_put_int(tun_mode);-
1657 packet_put_int(remote_tun);-
1658 packet_send();-
1659-
1660 return ifname;
never executed: return ifname;
0
1661}-
1662-
1663/* XXXX move to generic input handler */-
1664static int-
1665client_input_channel_open(int type, u_int32_t seq, struct ssh *ssh)-
1666{-
1667 Channel *c = NULL;-
1668 char *ctype;-
1669 int rchan;-
1670 u_int rmaxpack, rwindow, len;-
1671-
1672 ctype = packet_get_string(&len);-
1673 rchan = packet_get_int();-
1674 rwindow = packet_get_int();-
1675 rmaxpack = packet_get_int();-
1676-
1677 debug("client_input_channel_open: ctype %s rchan %d win %d max %d",-
1678 ctype, rchan, rwindow, rmaxpack);-
1679-
1680 if (strcmp(ctype, "forwarded-tcpip") == 0) {
never executed: __result = (((const unsigned char *) (const char *) ( ctype ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( "forwarded-tcpip" ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
__extension__ ... )))); }) == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1681 c = client_request_forwarded_tcpip(ssh, ctype, rchan, rwindow,-
1682 rmaxpack);-
1683 } else if (strcmp(ctype, "forwarded-streamlocal@openssh.com") == 0) {
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( ctype ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( "forwarded-streamlocal@openssh.com" ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
__extension__ ... )))); }) == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1684 c = client_request_forwarded_streamlocal(ssh, ctype, rchan);-
1685 } else if (strcmp(ctype, "x11") == 0) {
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( ctype ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( "x11" ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
__extension__ ... )))); }) == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1686 c = client_request_x11(ssh, ctype, rchan);-
1687 } else if (strcmp(ctype, "auth-agent@openssh.com") == 0) {
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( ctype ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( "auth-agent@openssh.com" ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
__extension__ ... )))); }) == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1688 c = client_request_agent(ssh, ctype, rchan);-
1689 }
never executed: end of block
0
1690 if (c != NULL && c->type == SSH_CHANNEL_MUX_CLIENT) {
c != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
c->type == 16Description
TRUEnever evaluated
FALSEnever evaluated
0
1691 debug3("proxied to downstream: %s", ctype);-
1692 } else if (c != NULL) {
never executed: end of block
c != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1693 debug("confirm %s", ctype);-
1694 c->remote_id = rchan;-
1695 c->have_remote_id = 1;-
1696 c->remote_window = rwindow;-
1697 c->remote_maxpacket = rmaxpack;-
1698 if (c->type != SSH_CHANNEL_CONNECTING) {
c->type != 12Description
TRUEnever evaluated
FALSEnever evaluated
0
1699 packet_start(SSH2_MSG_CHANNEL_OPEN_CONFIRMATION);-
1700 packet_put_int(c->remote_id);-
1701 packet_put_int(c->self);-
1702 packet_put_int(c->local_window);-
1703 packet_put_int(c->local_maxpacket);-
1704 packet_send();-
1705 }
never executed: end of block
0
1706 } else {
never executed: end of block
0
1707 debug("failure %s", ctype);-
1708 packet_start(SSH2_MSG_CHANNEL_OPEN_FAILURE);-
1709 packet_put_int(rchan);-
1710 packet_put_int(SSH2_OPEN_ADMINISTRATIVELY_PROHIBITED);-
1711 packet_put_cstring("open failed");-
1712 packet_put_cstring("");-
1713 packet_send();-
1714 }
never executed: end of block
0
1715 free(ctype);-
1716 return 0;
never executed: return 0;
0
1717}-
1718-
1719static int-
1720client_input_channel_req(int type, u_int32_t seq, struct ssh *ssh)-
1721{-
1722 Channel *c = NULL;-
1723 int exitval, id, reply, success = 0;-
1724 char *rtype;-
1725-
1726 id = packet_get_int();-
1727 c = channel_lookup(ssh, id);-
1728 if (channel_proxy_upstream(c, type, seq, ssh))
channel_proxy_...ype, seq, ssh)Description
TRUEnever evaluated
FALSEnever evaluated
0
1729 return 0;
never executed: return 0;
0
1730 rtype = packet_get_string(NULL);-
1731 reply = packet_get_char();-
1732-
1733 debug("client_input_channel_req: channel %d rtype %s reply %d",-
1734 id, rtype, reply);-
1735-
1736 if (id == -1) {
id == -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1737 error("client_input_channel_req: request for channel -1");-
1738 } else if (c == NULL) {
never executed: end of block
c == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1739 error("client_input_channel_req: channel %d: "-
1740 "unknown channel", id);-
1741 } else if (strcmp(rtype, "eow@openssh.com") == 0) {
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( rtype ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( "eow@openssh.com" ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
__extension__ ... )))); }) == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1742 packet_check_eom();
never executed: end of block
_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1743 chan_rcvd_eow(ssh, c);-
1744 } else if (strcmp(rtype, "exit-status") == 0) {
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( rtype ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( "exit-status" ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
__extension__ ... )))); }) == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1745 exitval = packet_get_int();-
1746 if (c->ctl_chan != -1) {
c->ctl_chan != -1Description
TRUEnever evaluated
FALSEnever evaluated
0
1747 mux_exit_message(ssh, c, exitval);-
1748 success = 1;-
1749 } else if (id == session_ident) {
never executed: end of block
id == session_identDescription
TRUEnever evaluated
FALSEnever evaluated
0
1750 /* Record exit value of local session */-
1751 success = 1;-
1752 exit_status = exitval;-
1753 } else {
never executed: end of block
0
1754 /* Probably for a mux channel that has already closed */-
1755 debug("%s: no sink for exit-status on channel %d",-
1756 __func__, id);-
1757 }
never executed: end of block
0
1758 packet_check_eom();
never executed: end of block
_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1759 }
never executed: end of block
0
1760 if (reply && c != NULL && !(c->flags & CHAN_CLOSE_SENT)) {
replyDescription
TRUEnever evaluated
FALSEnever evaluated
c != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
!(c->flags & 0x01)Description
TRUEnever evaluated
FALSEnever evaluated
0
1761 if (!c->have_remote_id)
!c->have_remote_idDescription
TRUEnever evaluated
FALSEnever evaluated
0
1762 fatal("%s: channel %d: no remote_id",
never executed: fatal("%s: channel %d: no remote_id", __func__, c->self);
0
1763 __func__, c->self);
never executed: fatal("%s: channel %d: no remote_id", __func__, c->self);
0
1764 packet_start(success ?-
1765 SSH2_MSG_CHANNEL_SUCCESS : SSH2_MSG_CHANNEL_FAILURE);-
1766 packet_put_int(c->remote_id);-
1767 packet_send();-
1768 }
never executed: end of block
0
1769 free(rtype);-
1770 return 0;
never executed: return 0;
0
1771}-
1772-
1773struct hostkeys_update_ctx {-
1774 /* The hostname and (optionally) IP address string for the server */-
1775 char *host_str, *ip_str;-
1776-
1777 /*-
1778 * Keys received from the server and a flag for each indicating-
1779 * whether they already exist in known_hosts.-
1780 * keys_seen is filled in by hostkeys_find() and later (for new-
1781 * keys) by client_global_hostkeys_private_confirm().-
1782 */-
1783 struct sshkey **keys;-
1784 int *keys_seen;-
1785 size_t nkeys, nnew;-
1786-
1787 /*-
1788 * Keys that are in known_hosts, but were not present in the update-
1789 * from the server (i.e. scheduled to be deleted).-
1790 * Filled in by hostkeys_find().-
1791 */-
1792 struct sshkey **old_keys;-
1793 size_t nold;-
1794};-
1795-
1796static void-
1797hostkeys_update_ctx_free(struct hostkeys_update_ctx *ctx)-
1798{-
1799 size_t i;-
1800-
1801 if (ctx == NULL)
ctx == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1802 return;
never executed: return;
0
1803 for (i = 0; i < ctx->nkeys; i++)
i < ctx->nkeysDescription
TRUEnever evaluated
FALSEnever evaluated
0
1804 sshkey_free(ctx->keys[i]);
never executed: sshkey_free(ctx->keys[i]);
0
1805 free(ctx->keys);-
1806 free(ctx->keys_seen);-
1807 for (i = 0; i < ctx->nold; i++)
i < ctx->noldDescription
TRUEnever evaluated
FALSEnever evaluated
0
1808 sshkey_free(ctx->old_keys[i]);
never executed: sshkey_free(ctx->old_keys[i]);
0
1809 free(ctx->old_keys);-
1810 free(ctx->host_str);-
1811 free(ctx->ip_str);-
1812 free(ctx);-
1813}
never executed: end of block
0
1814-
1815static int-
1816hostkeys_find(struct hostkey_foreach_line *l, void *_ctx)-
1817{-
1818 struct hostkeys_update_ctx *ctx = (struct hostkeys_update_ctx *)_ctx;-
1819 size_t i;-
1820 struct sshkey **tmp;-
1821-
1822 if (l->status != HKF_STATUS_MATCHED || l->key == NULL)
l->status != 3Description
TRUEnever evaluated
FALSEnever evaluated
l->key == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1823 return 0;
never executed: return 0;
0
1824-
1825 /* Mark off keys we've already seen for this host */-
1826 for (i = 0; i < ctx->nkeys; i++) {
i < ctx->nkeysDescription
TRUEnever evaluated
FALSEnever evaluated
0
1827 if (sshkey_equal(l->key, ctx->keys[i])) {
sshkey_equal(l... ctx->keys[i])Description
TRUEnever evaluated
FALSEnever evaluated
0
1828 debug3("%s: found %s key at %s:%ld", __func__,-
1829 sshkey_ssh_name(ctx->keys[i]), l->path, l->linenum);-
1830 ctx->keys_seen[i] = 1;-
1831 return 0;
never executed: return 0;
0
1832 }-
1833 }
never executed: end of block
0
1834 /* This line contained a key that not offered by the server */-
1835 debug3("%s: deprecated %s key at %s:%ld", __func__,-
1836 sshkey_ssh_name(l->key), l->path, l->linenum);-
1837 if ((tmp = recallocarray(ctx->old_keys, ctx->nold, ctx->nold + 1,
(tmp = recallo...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1838 sizeof(*ctx->old_keys))) == NULL)
(tmp = recallo...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1839 fatal("%s: recallocarray failed nold = %zu",
never executed: fatal("%s: recallocarray failed nold = %zu", __func__, ctx->nold);
0
1840 __func__, ctx->nold);
never executed: fatal("%s: recallocarray failed nold = %zu", __func__, ctx->nold);
0
1841 ctx->old_keys = tmp;-
1842 ctx->old_keys[ctx->nold++] = l->key;-
1843 l->key = NULL;-
1844-
1845 return 0;
never executed: return 0;
0
1846}-
1847-
1848static void-
1849update_known_hosts(struct hostkeys_update_ctx *ctx)-
1850{-
1851 int r, was_raw = 0;-
1852 int loglevel = options.update_hostkeys == SSH_UPDATE_HOSTKEYS_ASK ?
options.update_hostkeys == 2Description
TRUEnever evaluated
FALSEnever evaluated
0
1853 SYSLOG_LEVEL_INFO : SYSLOG_LEVEL_VERBOSE;-
1854 char *fp, *response;-
1855 size_t i;-
1856-
1857 for (i = 0; i < ctx->nkeys; i++) {
i < ctx->nkeysDescription
TRUEnever evaluated
FALSEnever evaluated
0
1858 if (ctx->keys_seen[i] != 2)
ctx->keys_seen[i] != 2Description
TRUEnever evaluated
FALSEnever evaluated
0
1859 continue;
never executed: continue;
0
1860 if ((fp = sshkey_fingerprint(ctx->keys[i],
(fp = sshkey_f...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1861 options.fingerprint_hash, SSH_FP_DEFAULT)) == NULL)
(fp = sshkey_f...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1862 fatal("%s: sshkey_fingerprint failed", __func__);
never executed: fatal("%s: sshkey_fingerprint failed", __func__);
0
1863 do_log2(loglevel, "Learned new hostkey: %s %s",-
1864 sshkey_type(ctx->keys[i]), fp);-
1865 free(fp);-
1866 }
never executed: end of block
0
1867 for (i = 0; i < ctx->nold; i++) {
i < ctx->noldDescription
TRUEnever evaluated
FALSEnever evaluated
0
1868 if ((fp = sshkey_fingerprint(ctx->old_keys[i],
(fp = sshkey_f...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1869 options.fingerprint_hash, SSH_FP_DEFAULT)) == NULL)
(fp = sshkey_f...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1870 fatal("%s: sshkey_fingerprint failed", __func__);
never executed: fatal("%s: sshkey_fingerprint failed", __func__);
0
1871 do_log2(loglevel, "Deprecating obsolete hostkey: %s %s",-
1872 sshkey_type(ctx->old_keys[i]), fp);-
1873 free(fp);-
1874 }
never executed: end of block
0
1875 if (options.update_hostkeys == SSH_UPDATE_HOSTKEYS_ASK) {
options.update_hostkeys == 2Description
TRUEnever evaluated
FALSEnever evaluated
0
1876 if (get_saved_tio() != NULL) {
get_saved_tio() != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1877 leave_raw_mode(1);-
1878 was_raw = 1;-
1879 }
never executed: end of block
0
1880 response = NULL;-
1881 for (i = 0; !quit_pending && i < 3; i++) {
!quit_pendingDescription
TRUEnever evaluated
FALSEnever evaluated
i < 3Description
TRUEnever evaluated
FALSEnever evaluated
0
1882 free(response);-
1883 response = read_passphrase("Accept updated hostkeys? "-
1884 "(yes/no): ", RP_ECHO);-
1885 if (strcasecmp(response, "yes") == 0)
strcasecmp(res...e, "yes") == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1886 break;
never executed: break;
0
1887 else if (quit_pending || response == NULL ||
quit_pendingDescription
TRUEnever evaluated
FALSEnever evaluated
response == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1888 strcasecmp(response, "no") == 0) {
strcasecmp(res...se, "no") == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1889 options.update_hostkeys = 0;-
1890 break;
never executed: break;
0
1891 } else {-
1892 do_log2(loglevel, "Please enter "-
1893 "\"yes\" or \"no\"");-
1894 }
never executed: end of block
0
1895 }-
1896 if (quit_pending || i >= 3 || response == NULL)
quit_pendingDescription
TRUEnever evaluated
FALSEnever evaluated
i >= 3Description
TRUEnever evaluated
FALSEnever evaluated
response == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1897 options.update_hostkeys = 0;
never executed: options.update_hostkeys = 0;
0
1898 free(response);-
1899 if (was_raw)
was_rawDescription
TRUEnever evaluated
FALSEnever evaluated
0
1900 enter_raw_mode(1);
never executed: enter_raw_mode(1);
0
1901 }
never executed: end of block
0
1902-
1903 /*-
1904 * Now that all the keys are verified, we can go ahead and replace-
1905 * them in known_hosts (assuming SSH_UPDATE_HOSTKEYS_ASK didn't-
1906 * cancel the operation).-
1907 */-
1908 if (options.update_hostkeys != 0 &&
options.update_hostkeys != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1909 (r = hostfile_replace_entries(options.user_hostfiles[0],
(r = hostfile_...nt_hash)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1910 ctx->host_str, ctx->ip_str, ctx->keys, ctx->nkeys,
(r = hostfile_...nt_hash)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1911 options.hash_known_hosts, 0,
(r = hostfile_...nt_hash)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1912 options.fingerprint_hash)) != 0)
(r = hostfile_...nt_hash)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1913 error("%s: hostfile_replace_entries failed: %s",
never executed: error("%s: hostfile_replace_entries failed: %s", __func__, ssh_err(r));
0
1914 __func__, ssh_err(r));
never executed: error("%s: hostfile_replace_entries failed: %s", __func__, ssh_err(r));
0
1915}
never executed: end of block
0
1916-
1917static void-
1918client_global_hostkeys_private_confirm(struct ssh *ssh, int type,-
1919 u_int32_t seq, void *_ctx)-
1920{-
1921 struct hostkeys_update_ctx *ctx = (struct hostkeys_update_ctx *)_ctx;-
1922 size_t i, ndone;-
1923 struct sshbuf *signdata;-
1924 int r, kexsigtype, use_kexsigtype;-
1925 const u_char *sig;-
1926 size_t siglen;-
1927-
1928 if (ctx->nnew == 0)
ctx->nnew == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1929 fatal("%s: ctx->nnew == 0", __func__); /* sanity */
never executed: fatal("%s: ctx->nnew == 0", __func__);
0
1930 if (type != SSH2_MSG_REQUEST_SUCCESS) {
type != 81Description
TRUEnever evaluated
FALSEnever evaluated
0
1931 error("Server failed to confirm ownership of "-
1932 "private host keys");-
1933 hostkeys_update_ctx_free(ctx);-
1934 return;
never executed: return;
0
1935 }-
1936 kexsigtype = sshkey_type_plain(-
1937 sshkey_type_from_name(ssh->kex->hostkey_alg));-
1938-
1939 if ((signdata = sshbuf_new()) == NULL)
(signdata = ss...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
1940 fatal("%s: sshbuf_new failed", __func__);
never executed: fatal("%s: sshbuf_new failed", __func__);
0
1941 /* Don't want to accidentally accept an unbound signature */-
1942 if (ssh->kex->session_id_len == 0)
ssh->kex->session_id_len == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1943 fatal("%s: ssh->kex->session_id_len == 0", __func__);
never executed: fatal("%s: ssh->kex->session_id_len == 0", __func__);
0
1944 /*-
1945 * Expect a signature for each of the ctx->nnew private keys we-
1946 * haven't seen before. They will be in the same order as the-
1947 * ctx->keys where the corresponding ctx->keys_seen[i] == 0.-
1948 */-
1949 for (ndone = i = 0; i < ctx->nkeys; i++) {
i < ctx->nkeysDescription
TRUEnever evaluated
FALSEnever evaluated
0
1950 if (ctx->keys_seen[i])
ctx->keys_seen[i]Description
TRUEnever evaluated
FALSEnever evaluated
0
1951 continue;
never executed: continue;
0
1952 /* Prepare data to be signed: session ID, unique string, key */-
1953 sshbuf_reset(signdata);-
1954 if ( (r = sshbuf_put_cstring(signdata,
(r = sshbuf_pu...sh.com")) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1955 "hostkeys-prove-00@openssh.com")) != 0 ||
(r = sshbuf_pu...sh.com")) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1956 (r = sshbuf_put_string(signdata, ssh->kex->session_id,
(r = sshbuf_pu..._id_len)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1957 ssh->kex->session_id_len)) != 0 ||
(r = sshbuf_pu..._id_len)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1958 (r = sshkey_puts(ctx->keys[i], signdata)) != 0)
(r = sshkey_pu...igndata)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1959 fatal("%s: failed to prepare signature: %s",
never executed: fatal("%s: failed to prepare signature: %s", __func__, ssh_err(r));
0
1960 __func__, ssh_err(r));
never executed: fatal("%s: failed to prepare signature: %s", __func__, ssh_err(r));
0
1961 /* Extract and verify signature */-
1962 if ((r = sshpkt_get_string_direct(ssh, &sig, &siglen)) != 0) {
(r = sshpkt_ge...&siglen)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1963 error("%s: couldn't parse message: %s",-
1964 __func__, ssh_err(r));-
1965 goto out;
never executed: goto out;
0
1966 }-
1967 /*-
1968 * For RSA keys, prefer to use the signature type negotiated-
1969 * during KEX to the default (SHA1).-
1970 */-
1971 use_kexsigtype = kexsigtype == KEY_RSA &&
kexsigtype == KEY_RSADescription
TRUEnever evaluated
FALSEnever evaluated
0
1972 sshkey_type_plain(ctx->keys[i]->type) == KEY_RSA;
sshkey_type_pl...pe) == KEY_RSADescription
TRUEnever evaluated
FALSEnever evaluated
0
1973 if ((r = sshkey_verify(ctx->keys[i], sig, siglen,
(r = sshkey_ve...)0) , 0)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1974 sshbuf_ptr(signdata), sshbuf_len(signdata),
(r = sshkey_ve...)0) , 0)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1975 use_kexsigtype ? ssh->kex->hostkey_alg : NULL, 0)) != 0) {
(r = sshkey_ve...)0) , 0)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1976 error("%s: server gave bad signature for %s key %zu",-
1977 __func__, sshkey_type(ctx->keys[i]), i);-
1978 goto out;
never executed: goto out;
0
1979 }-
1980 /* Key is good. Mark it as 'seen' */-
1981 ctx->keys_seen[i] = 2;-
1982 ndone++;-
1983 }
never executed: end of block
0
1984 if (ndone != ctx->nnew)
ndone != ctx->nnewDescription
TRUEnever evaluated
FALSEnever evaluated
0
1985 fatal("%s: ndone != ctx->nnew (%zu / %zu)", __func__,
never executed: fatal("%s: ndone != ctx->nnew (%zu / %zu)", __func__, ndone, ctx->nnew);
0
1986 ndone, ctx->nnew); /* Shouldn't happen */
never executed: fatal("%s: ndone != ctx->nnew (%zu / %zu)", __func__, ndone, ctx->nnew);
0
1987 ssh_packet_check_eom(ssh);
never executed: end of block
_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
1988-
1989 /* Make the edits to known_hosts */-
1990 update_known_hosts(ctx);-
1991 out:
code before this statement never executed: out:
0
1992 hostkeys_update_ctx_free(ctx);-
1993}
never executed: end of block
0
1994-
1995/*-
1996 * Returns non-zero if the key is accepted by HostkeyAlgorithms.-
1997 * Made slightly less trivial by the multiple RSA signature algorithm names.-
1998 */-
1999static int-
2000key_accepted_by_hostkeyalgs(const struct sshkey *key)-
2001{-
2002 const char *ktype = sshkey_ssh_name(key);-
2003 const char *hostkeyalgs = options.hostkeyalgorithms != NULL ?
options.hostke...!= ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
2004 options.hostkeyalgorithms : KEX_DEFAULT_PK_ALG;-
2005-
2006 if (key == NULL || key->type == KEY_UNSPEC)
key == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
key->type == KEY_UNSPECDescription
TRUEnever evaluated
FALSEnever evaluated
0
2007 return 0;
never executed: return 0;
0
2008 if (key->type == KEY_RSA &&
key->type == KEY_RSADescription
TRUEnever evaluated
FALSEnever evaluated
0
2009 (match_pattern_list("rsa-sha2-256", hostkeyalgs, 0) == 1 ||
match_pattern_...yalgs, 0) == 1Description
TRUEnever evaluated
FALSEnever evaluated
0
2010 match_pattern_list("rsa-sha2-512", hostkeyalgs, 0) == 1))
match_pattern_...yalgs, 0) == 1Description
TRUEnever evaluated
FALSEnever evaluated
0
2011 return 1;
never executed: return 1;
0
2012 return match_pattern_list(ktype, hostkeyalgs, 0) == 1;
never executed: return match_pattern_list(ktype, hostkeyalgs, 0) == 1;
0
2013}-
2014-
2015/*-
2016 * Handle hostkeys-00@openssh.com global request to inform the client of all-
2017 * the server's hostkeys. The keys are checked against the user's-
2018 * HostkeyAlgorithms preference before they are accepted.-
2019 */-
2020static int-
2021client_input_hostkeys(void)-
2022{-
2023 struct ssh *ssh = active_state; /* XXX */-
2024 const u_char *blob = NULL;-
2025 size_t i, len = 0;-
2026 struct sshbuf *buf = NULL;-
2027 struct sshkey *key = NULL, **tmp;-
2028 int r;-
2029 char *fp;-
2030 static int hostkeys_seen = 0; /* XXX use struct ssh */-
2031 extern struct sockaddr_storage hostaddr; /* XXX from ssh.c */-
2032 struct hostkeys_update_ctx *ctx = NULL;-
2033-
2034 if (hostkeys_seen)
hostkeys_seenDescription
TRUEnever evaluated
FALSEnever evaluated
0
2035 fatal("%s: server already sent hostkeys", __func__);
never executed: fatal("%s: server already sent hostkeys", __func__);
0
2036 if (options.update_hostkeys == SSH_UPDATE_HOSTKEYS_ASK &&
options.update_hostkeys == 2Description
TRUEnever evaluated
FALSEnever evaluated
0
2037 options.batch_mode)
options.batch_modeDescription
TRUEnever evaluated
FALSEnever evaluated
0
2038 return 1; /* won't ask in batchmode, so don't even try */
never executed: return 1;
0
2039 if (!options.update_hostkeys || options.num_user_hostfiles <= 0)
!options.update_hostkeysDescription
TRUEnever evaluated
FALSEnever evaluated
options.num_us...hostfiles <= 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2040 return 1;
never executed: return 1;
0
2041-
2042 ctx = xcalloc(1, sizeof(*ctx));-
2043 while (ssh_packet_remaining(ssh) > 0) {
ssh_packet_remaining(ssh) > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2044 sshkey_free(key);-
2045 key = NULL;-
2046 if ((r = sshpkt_get_string_direct(ssh, &blob, &len)) != 0) {
(r = sshpkt_ge...b, &len)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2047 error("%s: couldn't parse message: %s",-
2048 __func__, ssh_err(r));-
2049 goto out;
never executed: goto out;
0
2050 }-
2051 if ((r = sshkey_from_blob(blob, len, &key)) != 0) {
(r = sshkey_fr...n, &key)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2052 error("%s: parse key: %s", __func__, ssh_err(r));-
2053 goto out;
never executed: goto out;
0
2054 }-
2055 fp = sshkey_fingerprint(key, options.fingerprint_hash,-
2056 SSH_FP_DEFAULT);-
2057 debug3("%s: received %s key %s", __func__,-
2058 sshkey_type(key), fp);-
2059 free(fp);-
2060-
2061 if (!key_accepted_by_hostkeyalgs(key)) {
!key_accepted_...stkeyalgs(key)Description
TRUEnever evaluated
FALSEnever evaluated
0
2062 debug3("%s: %s key not permitted by HostkeyAlgorithms",-
2063 __func__, sshkey_ssh_name(key));-
2064 continue;
never executed: continue;
0
2065 }-
2066 /* Skip certs */-
2067 if (sshkey_is_cert(key)) {
sshkey_is_cert(key)Description
TRUEnever evaluated
FALSEnever evaluated
0
2068 debug3("%s: %s key is a certificate; skipping",-
2069 __func__, sshkey_ssh_name(key));-
2070 continue;
never executed: continue;
0
2071 }-
2072 /* Ensure keys are unique */-
2073 for (i = 0; i < ctx->nkeys; i++) {
i < ctx->nkeysDescription
TRUEnever evaluated
FALSEnever evaluated
0
2074 if (sshkey_equal(key, ctx->keys[i])) {
sshkey_equal(k... ctx->keys[i])Description
TRUEnever evaluated
FALSEnever evaluated
0
2075 error("%s: received duplicated %s host key",-
2076 __func__, sshkey_ssh_name(key));-
2077 goto out;
never executed: goto out;
0
2078 }-
2079 }
never executed: end of block
0
2080 /* Key is good, record it */-
2081 if ((tmp = recallocarray(ctx->keys, ctx->nkeys, ctx->nkeys + 1,
(tmp = recallo...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
2082 sizeof(*ctx->keys))) == NULL)
(tmp = recallo...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
2083 fatal("%s: recallocarray failed nkeys = %zu",
never executed: fatal("%s: recallocarray failed nkeys = %zu", __func__, ctx->nkeys);
0
2084 __func__, ctx->nkeys);
never executed: fatal("%s: recallocarray failed nkeys = %zu", __func__, ctx->nkeys);
0
2085 ctx->keys = tmp;-
2086 ctx->keys[ctx->nkeys++] = key;-
2087 key = NULL;-
2088 }
never executed: end of block
0
2089-
2090 if (ctx->nkeys == 0) {
ctx->nkeys == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2091 debug("%s: server sent no hostkeys", __func__);-
2092 goto out;
never executed: goto out;
0
2093 }-
2094-
2095 if ((ctx->keys_seen = calloc(ctx->nkeys,
(ctx->keys_see...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
2096 sizeof(*ctx->keys_seen))) == NULL)
(ctx->keys_see...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
2097 fatal("%s: calloc failed", __func__);
never executed: fatal("%s: calloc failed", __func__);
0
2098-
2099 get_hostfile_hostname_ipaddr(host,-
2100 options.check_host_ip ? (struct sockaddr *)&hostaddr : NULL,-
2101 options.port, &ctx->host_str,-
2102 options.check_host_ip ? &ctx->ip_str : NULL);-
2103-
2104 /* Find which keys we already know about. */-
2105 if ((r = hostkeys_foreach(options.user_hostfiles[0], hostkeys_find,
(r = hostkeys_...<1)|(1))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2106 ctx, ctx->host_str, ctx->ip_str,
(r = hostkeys_...<1)|(1))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2107 HKF_WANT_PARSE_KEY|HKF_WANT_MATCH)) != 0) {
(r = hostkeys_...<1)|(1))) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2108 error("%s: hostkeys_foreach failed: %s", __func__, ssh_err(r));-
2109 goto out;
never executed: goto out;
0
2110 }-
2111-
2112 /* Figure out if we have any new keys to add */-
2113 ctx->nnew = 0;-
2114 for (i = 0; i < ctx->nkeys; i++) {
i < ctx->nkeysDescription
TRUEnever evaluated
FALSEnever evaluated
0
2115 if (!ctx->keys_seen[i])
!ctx->keys_seen[i]Description
TRUEnever evaluated
FALSEnever evaluated
0
2116 ctx->nnew++;
never executed: ctx->nnew++;
0
2117 }
never executed: end of block
0
2118-
2119 debug3("%s: %zu keys from server: %zu new, %zu retained. %zu to remove",-
2120 __func__, ctx->nkeys, ctx->nnew, ctx->nkeys - ctx->nnew, ctx->nold);-
2121-
2122 if (ctx->nnew == 0 && ctx->nold != 0) {
ctx->nnew == 0Description
TRUEnever evaluated
FALSEnever evaluated
ctx->nold != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2123 /* We have some keys to remove. Just do it. */-
2124 update_known_hosts(ctx);-
2125 } else if (ctx->nnew != 0) {
never executed: end of block
ctx->nnew != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2126 /*-
2127 * We have received hitherto-unseen keys from the server.-
2128 * Ask the server to confirm ownership of the private halves.-
2129 */-
2130 debug3("%s: asking server to prove ownership for %zu keys",-
2131 __func__, ctx->nnew);-
2132 if ((r = sshpkt_start(ssh, SSH2_MSG_GLOBAL_REQUEST)) != 0 ||
(r = sshpkt_st...ssh, 80)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2133 (r = sshpkt_put_cstring(ssh,
(r = sshpkt_pu...sh.com")) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2134 "hostkeys-prove-00@openssh.com")) != 0 ||
(r = sshpkt_pu...sh.com")) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2135 (r = sshpkt_put_u8(ssh, 1)) != 0) /* bool: want reply */
(r = sshpkt_pu...(ssh, 1)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2136 fatal("%s: cannot prepare packet: %s",
never executed: fatal("%s: cannot prepare packet: %s", __func__, ssh_err(r));
0
2137 __func__, ssh_err(r));
never executed: fatal("%s: cannot prepare packet: %s", __func__, ssh_err(r));
0
2138 if ((buf = sshbuf_new()) == NULL)
(buf = sshbuf_...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
2139 fatal("%s: sshbuf_new", __func__);
never executed: fatal("%s: sshbuf_new", __func__);
0
2140 for (i = 0; i < ctx->nkeys; i++) {
i < ctx->nkeysDescription
TRUEnever evaluated
FALSEnever evaluated
0
2141 if (ctx->keys_seen[i])
ctx->keys_seen[i]Description
TRUEnever evaluated
FALSEnever evaluated
0
2142 continue;
never executed: continue;
0
2143 sshbuf_reset(buf);-
2144 if ((r = sshkey_putb(ctx->keys[i], buf)) != 0)
(r = sshkey_pu...i], buf)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2145 fatal("%s: sshkey_putb: %s",
never executed: fatal("%s: sshkey_putb: %s", __func__, ssh_err(r));
0
2146 __func__, ssh_err(r));
never executed: fatal("%s: sshkey_putb: %s", __func__, ssh_err(r));
0
2147 if ((r = sshpkt_put_stringb(ssh, buf)) != 0)
(r = sshpkt_pu...sh, buf)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2148 fatal("%s: sshpkt_put_string: %s",
never executed: fatal("%s: sshpkt_put_string: %s", __func__, ssh_err(r));
0
2149 __func__, ssh_err(r));
never executed: fatal("%s: sshpkt_put_string: %s", __func__, ssh_err(r));
0
2150 }
never executed: end of block
0
2151 if ((r = sshpkt_send(ssh)) != 0)
(r = sshpkt_send(ssh)) != 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2152 fatal("%s: sshpkt_send: %s", __func__, ssh_err(r));
never executed: fatal("%s: sshpkt_send: %s", __func__, ssh_err(r));
0
2153 client_register_global_confirm(-
2154 client_global_hostkeys_private_confirm, ctx);-
2155 ctx = NULL; /* will be freed in callback */-
2156 }
never executed: end of block
0
2157-
2158 /* Success */-
2159 out:
code before this statement never executed: out:
0
2160 hostkeys_update_ctx_free(ctx);-
2161 sshkey_free(key);-
2162 sshbuf_free(buf);-
2163 /*-
2164 * NB. Return success for all cases. The server doesn't need to know-
2165 * what the client does with its hosts file.-
2166 */-
2167 return 1;
never executed: return 1;
0
2168}-
2169-
2170static int-
2171client_input_global_request(int type, u_int32_t seq, struct ssh *ssh)-
2172{-
2173 char *rtype;-
2174 int want_reply;-
2175 int success = 0;-
2176-
2177 rtype = packet_get_cstring(NULL);-
2178 want_reply = packet_get_char();-
2179 debug("client_input_global_request: rtype %s want_reply %d",-
2180 rtype, want_reply);-
2181 if (strcmp(rtype, "hostkeys-00@openssh.com") == 0)
never executed: __result = (((const unsigned char *) (const char *) ( rtype ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
never executed: __result = (((const unsigned char *) (const char *) ( "hostkeys-00@openssh.com" ))[3] - __s2[3]);
never executed: end of block
never executed: end of block
__extension__ ... )))); }) == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s1_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 0Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 1Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
__s2_len > 2Description
TRUEnever evaluated
FALSEnever evaluated
__result == 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2182 success = client_input_hostkeys();
never executed: success = client_input_hostkeys();
0
2183 if (want_reply) {
want_replyDescription
TRUEnever evaluated
FALSEnever evaluated
0
2184 packet_start(success ?-
2185 SSH2_MSG_REQUEST_SUCCESS : SSH2_MSG_REQUEST_FAILURE);-
2186 packet_send();-
2187 packet_write_wait();-
2188 }
never executed: end of block
0
2189 free(rtype);-
2190 return 0;
never executed: return 0;
0
2191}-
2192-
2193void-
2194client_session2_setup(struct ssh *ssh, int id, int want_tty, int want_subsystem,-
2195 const char *term, struct termios *tiop, int in_fd, struct sshbuf *cmd,-
2196 char **env)-
2197{-
2198 int i, j, matched, len;-
2199 char *name, *val;-
2200 Channel *c = NULL;-
2201-
2202 debug2("%s: id %d", __func__, id);-
2203-
2204 if ((c = channel_lookup(ssh, id)) == NULL)
(c = channel_l...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
2205 fatal("%s: channel %d: unknown channel", __func__, id);
never executed: fatal("%s: channel %d: unknown channel", __func__, id);
0
2206-
2207 packet_set_interactive(want_tty,-
2208 options.ip_qos_interactive, options.ip_qos_bulk);-
2209-
2210 if (want_tty) {
want_ttyDescription
TRUEnever evaluated
FALSEnever evaluated
0
2211 struct winsize ws;-
2212-
2213 /* Store window size in the packet. */-
2214 if (ioctl(in_fd, TIOCGWINSZ, &ws) < 0)
ioctl(in_fd, 0x5413 , &ws) < 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2215 memset(&ws, 0, sizeof(ws));
never executed: memset(&ws, 0, sizeof(ws));
0
2216-
2217 channel_request_start(ssh, id, "pty-req", 1);-
2218 client_expect_confirm(ssh, id, "PTY allocation", CONFIRM_TTY);-
2219 packet_put_cstring(term != NULL ? term : "");-
2220 packet_put_int((u_int)ws.ws_col);-
2221 packet_put_int((u_int)ws.ws_row);-
2222 packet_put_int((u_int)ws.ws_xpixel);-
2223 packet_put_int((u_int)ws.ws_ypixel);-
2224 if (tiop == NULL)
tiop == ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
2225 tiop = get_saved_tio();
never executed: tiop = get_saved_tio();
0
2226 ssh_tty_make_modes(ssh, -1, tiop);-
2227 packet_send();-
2228 /* XXX wait for reply */-
2229 c->client_tty = 1;-
2230 }
never executed: end of block
0
2231-
2232 /* Transfer any environment variables from client to server */-
2233 if (options.num_send_env != 0 && env != NULL) {
options.num_send_env != 0Description
TRUEnever evaluated
FALSEnever evaluated
env != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
2234 debug("Sending environment.");-
2235 for (i = 0; env[i] != NULL; i++) {
env[i] != ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
0
2236 /* Split */-
2237 name = xstrdup(env[i]);-
2238 if ((val = strchr(name, '=')) == NULL) {
(val = (__exte...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
__builtin_constant_p ( '=' )Description
TRUEnever evaluated
FALSEnever evaluated
!__builtin_constant_p ( name )Description
TRUEnever evaluated
FALSEnever evaluated
( '=' ) == '\0'Description
TRUEnever evaluated
FALSEnever evaluated
0
2239 free(name);-
2240 continue;
never executed: continue;
0
2241 }-
2242 *val++ = '\0';-
2243-
2244 matched = 0;-
2245 for (j = 0; j < options.num_send_env; j++) {
j < options.num_send_envDescription
TRUEnever evaluated
FALSEnever evaluated
0
2246 if (match_pattern(name, options.send_env[j])) {
match_pattern(...s.send_env[j])Description
TRUEnever evaluated
FALSEnever evaluated
0
2247 matched = 1;-
2248 break;
never executed: break;
0
2249 }-
2250 }
never executed: end of block
0
2251 if (!matched) {
!matchedDescription
TRUEnever evaluated
FALSEnever evaluated
0
2252 debug3("Ignored env %s", name);-
2253 free(name);-
2254 continue;
never executed: continue;
0
2255 }-
2256-
2257 debug("Sending env %s = %s", name, val);-
2258 channel_request_start(ssh, id, "env", 0);-
2259 packet_put_cstring(name);-
2260 packet_put_cstring(val);-
2261 packet_send();-
2262 free(name);-
2263 }
never executed: end of block
0
2264 }
never executed: end of block
0
2265 for (i = 0; i < options.num_setenv; i++) {
i < options.num_setenvDescription
TRUEnever evaluated
FALSEnever evaluated
0
2266 /* Split */-
2267 name = xstrdup(options.setenv[i]);-
2268 if ((val = strchr(name, '=')) == NULL) {
(val = (__exte...== ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
__builtin_constant_p ( '=' )Description
TRUEnever evaluated
FALSEnever evaluated
!__builtin_constant_p ( name )Description
TRUEnever evaluated
FALSEnever evaluated
( '=' ) == '\0'Description
TRUEnever evaluated
FALSEnever evaluated
0
2269 free(name);-
2270 continue;
never executed: continue;
0
2271 }-
2272 *val++ = '\0';-
2273-
2274 debug("Setting env %s = %s", name, val);-
2275 channel_request_start(ssh, id, "env", 0);-
2276 packet_put_cstring(name);-
2277 packet_put_cstring(val);-
2278 packet_send();-
2279 free(name);-
2280 }
never executed: end of block
0
2281-
2282 len = sshbuf_len(cmd);-
2283 if (len > 0) {
len > 0Description
TRUEnever evaluated
FALSEnever evaluated
0
2284 if (len > 900)
len > 900Description
TRUEnever evaluated
FALSEnever evaluated
0
2285 len = 900;
never executed: len = 900;
0
2286 if (want_subsystem) {
want_subsystemDescription
TRUEnever evaluated
FALSEnever evaluated
0
2287 debug("Sending subsystem: %.*s",-
2288 len, (const u_char*)sshbuf_ptr(cmd));-
2289 channel_request_start(ssh, id, "subsystem", 1);-
2290 client_expect_confirm(ssh, id, "subsystem",-
2291 CONFIRM_CLOSE);-
2292 } else {
never executed: end of block
0
2293 debug("Sending command: %.*s",-
2294 len, (const u_char*)sshbuf_ptr(cmd));-
2295 channel_request_start(ssh, id, "exec", 1);-
2296 client_expect_confirm(ssh, id, "exec", CONFIRM_CLOSE);-
2297 }
never executed: end of block
0
2298 packet_put_string(sshbuf_ptr(cmd), sshbuf_len(cmd));-
2299 packet_send();-
2300 } else {
never executed: end of block
0
2301 channel_request_start(ssh, id, "shell", 1);-
2302 client_expect_confirm(ssh, id, "shell", CONFIRM_CLOSE);-
2303 packet_send();-
2304 }
never executed: end of block
0
2305}-
2306-
2307static void-
2308client_init_dispatch(void)-
2309{-
2310 dispatch_init(&dispatch_protocol_error);-
2311-
2312 dispatch_set(SSH2_MSG_CHANNEL_CLOSE, &channel_input_oclose);-
2313 dispatch_set(SSH2_MSG_CHANNEL_DATA, &channel_input_data);-
2314 dispatch_set(SSH2_MSG_CHANNEL_EOF, &channel_input_ieof);-
2315 dispatch_set(SSH2_MSG_CHANNEL_EXTENDED_DATA, &channel_input_extended_data);-
2316 dispatch_set(SSH2_MSG_CHANNEL_OPEN, &client_input_channel_open);-
2317 dispatch_set(SSH2_MSG_CHANNEL_OPEN_CONFIRMATION, &channel_input_open_confirmation);-
2318 dispatch_set(SSH2_MSG_CHANNEL_OPEN_FAILURE, &channel_input_open_failure);-
2319 dispatch_set(SSH2_MSG_CHANNEL_REQUEST, &client_input_channel_req);-
2320 dispatch_set(SSH2_MSG_CHANNEL_WINDOW_ADJUST, &channel_input_window_adjust);-
2321 dispatch_set(SSH2_MSG_CHANNEL_SUCCESS, &channel_input_status_confirm);-
2322 dispatch_set(SSH2_MSG_CHANNEL_FAILURE, &channel_input_status_confirm);-
2323 dispatch_set(SSH2_MSG_GLOBAL_REQUEST, &client_input_global_request);-
2324-
2325 /* rekeying */-
2326 dispatch_set(SSH2_MSG_KEXINIT, &kex_input_kexinit);-
2327-
2328 /* global request reply messages */-
2329 dispatch_set(SSH2_MSG_REQUEST_FAILURE, &client_global_request_reply);-
2330 dispatch_set(SSH2_MSG_REQUEST_SUCCESS, &client_global_request_reply);-
2331}
never executed: end of block
0
2332-
2333void-
2334client_stop_mux(void)-
2335{-
2336 if (options.control_path != NULL && muxserver_sock != -1)
options.contro...!= ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
muxserver_sock != -1Description
TRUEnever evaluated
FALSEnever evaluated
0
2337 unlink(options.control_path);
never executed: unlink(options.control_path);
0
2338 /*-
2339 * If we are in persist mode, or don't have a shell, signal that we-
2340 * should close when all active channels are closed.-
2341 */-
2342 if (options.control_persist || no_shell_flag) {
options.control_persistDescription
TRUEnever evaluated
FALSEnever evaluated
no_shell_flagDescription
TRUEnever evaluated
FALSEnever evaluated
0
2343 session_closed = 1;-
2344 setproctitle("[stopped mux]");-
2345 }
never executed: end of block
0
2346}
never executed: end of block
0
2347-
2348/* client specific fatal cleanup */-
2349void-
2350cleanup_exit(int i)-
2351{-
2352 leave_raw_mode(options.request_tty == REQUEST_TTY_FORCE);-
2353 leave_non_blocking();-
2354 if (options.control_path != NULL && muxserver_sock != -1)
options.contro...!= ((void *)0)Description
TRUEnever evaluated
FALSEnever evaluated
muxserver_sock != -1Description
TRUEnever evaluated
FALSEnever evaluated
0
2355 unlink(options.control_path);
never executed: unlink(options.control_path);
0
2356 ssh_kill_proxy_command();-
2357 _exit(i);-
2358}
never executed: end of block
0
Source codeSwitch to Preprocessed file

Generated by Squish Coco 4.2.2