Mercurial > dropbear
diff cli-runopts.c @ 546:568638be7203 agent-client
propagate from branch 'au.asn.ucc.matt.dropbear' (head 899a8851a5edf840b2f7925bcc26ffe99dcac54d)
to branch 'au.asn.ucc.matt.dropbear.cli-agent' (head 6bbab8364de17bd9ecb1dee5ffb796e48c0380d2)
author | Matt Johnston <matt@ucc.asn.au> |
---|---|
date | Wed, 01 Jul 2009 04:16:32 +0000 |
parents | d588e3ea557a 9e51707cd6f2 |
children | c3f2ec71e3d4 |
line wrap: on
line diff
--- a/cli-runopts.c Tue Sep 23 16:05:04 2008 +0000 +++ b/cli-runopts.c Wed Jul 01 04:16:32 2009 +0000 @@ -49,7 +49,11 @@ static void printhelp() { fprintf(stderr, "Dropbear client v%s\n" +#ifdef ENABLE_CLI_MULTIHOP + "Usage: %s [options] [user@]host[/port][,[user@]host/port],...] [command]\n" +#else "Usage: %s [options] [user@]host[/port] [command]\n" +#endif "Options are:\n" "-p <remoteport>\n" "-l <username>\n" @@ -74,22 +78,22 @@ #endif "-W <receive_window_buffer> (default %d, larger may be faster, max 1MB)\n" "-K <keepalive> (0 is never, default %d)\n" + "-I <idle_timeout> (0 is never, default %d)\n" #ifdef ENABLE_CLI_NETCAT - "-B <endhost:endport> Netcat-alike bouncing\n" + "-B <endhost:endport> Netcat-alike forwarding\n" #endif #ifdef ENABLE_CLI_PROXYCMD - "-J <proxy_program> Use program rather than tcp connection\n" + "-J <proxy_program> Use program pipe rather than TCP connection\n" #endif #ifdef DEBUG_TRACE - "-v verbose\n" + "-v verbose (compiled with DEBUG_TRACE)\n" #endif ,DROPBEAR_VERSION, cli_opts.progname, - DEFAULT_RECV_WINDOW, DEFAULT_KEEPALIVE); + DEFAULT_RECV_WINDOW, DEFAULT_KEEPALIVE, DEFAULT_IDLE_TIMEOUT); } void cli_getopts(int argc, char ** argv) { - unsigned int i, j; char ** next = 0; unsigned int cmdlen; @@ -109,6 +113,8 @@ char* recv_window_arg = NULL; char* keepalive_arg = NULL; + char* idle_timeout_arg = NULL; + char *host_arg = NULL; /* see printhelp() for options */ cli_opts.progname = argv[0]; @@ -264,6 +270,9 @@ case 'K': next = &keepalive_arg; break; + case 'I': + next = &idle_timeout_arg; + break; #ifdef ENABLE_CLI_AGENTFWD case 'A': cli_opts.agent_fwd = 1; @@ -307,12 +316,8 @@ /* Either the hostname or commands */ - if (cli_opts.remotehost == NULL) { -#ifdef ENABLE_CLI_MULTIHOP - parse_multihop_hostname(argv[i], argv[0]); -#else - parse_hostname(argv[i]); -#endif + if (host_arg == NULL) { + host_arg = argv[i]; } else { /* this is part of the commands to send - after this we @@ -341,7 +346,7 @@ /* And now a few sanity checks and setup */ - if (cli_opts.remotehost == NULL) { + if (host_arg == NULL) { printhelp(); exit(EXIT_FAILURE); } @@ -377,12 +382,26 @@ } } + if (idle_timeout_arg) { + if (m_str_to_uint(idle_timeout_arg, &opts.idle_timeout_secs) == DROPBEAR_FAILURE) { + dropbear_exit("Bad idle_timeout '%s'", idle_timeout_arg); + } + } + #ifdef ENABLE_CLI_NETCAT if (cli_opts.cmd && cli_opts.netcat_host) { dropbear_log(LOG_INFO, "Ignoring command '%s' in netcat mode", cli_opts.cmd); } #endif - + + /* The hostname gets set up last, since + * in multi-hop mode it will require knowledge + * of other flags such as -i */ +#ifdef ENABLE_CLI_MULTIHOP + parse_multihop_hostname(host_arg, argv[0]); +#else + parse_hostname(host_arg); +#endif } #ifdef ENABLE_CLI_PUBKEY_AUTH @@ -395,14 +414,12 @@ key = new_sign_key(); keytype = DROPBEAR_SIGNKEY_ANY; if ( readhostkey(filename, key, &keytype) != DROPBEAR_SUCCESS ) { - fprintf(stderr, "Failed loading keyfile '%s'\n", filename); sign_key_free(key); - } else { - nextkey = (struct SignKeyList*)m_malloc(sizeof(struct SignKeyList)); nextkey->key = key; + nextkey->filename = m_strdup(filename); nextkey->next = cli_opts.privkeys; nextkey->type = keytype; nextkey->source = SIGNKEY_SOURCE_RAW_FILE; @@ -413,6 +430,39 @@ #ifdef ENABLE_CLI_MULTIHOP +static char* +multihop_passthrough_args() { + char *ret; + int total; + unsigned int len = 0; + struct SignKeyList *nextkey; + /* Fill out -i and -W options that make sense for all + * the intermediate processes */ + for (nextkey = cli_opts.privkeys; nextkey; nextkey = nextkey->next) + { + len += 3 + strlen(nextkey->filename); + } + len += 20; // space for -W <size>, terminator. + ret = m_malloc(len); + total = 0; + + if (opts.recv_window != DEFAULT_RECV_WINDOW) + { + int written = snprintf(ret+total, len-total, "-W %d", opts.recv_window); + total += written; + } + + for (nextkey = cli_opts.privkeys; nextkey; nextkey = nextkey->next) + { + const size_t size = len - total; + int written = snprintf(ret+total, size, "-i %s", nextkey->filename); + dropbear_assert(written < size); + total += written; + } + + return ret; +} + /* Sets up 'onion-forwarding' connections. This will spawn * a separate dbclient process for each hop. * As an example, if the cmdline is @@ -427,6 +477,7 @@ */ static void parse_multihop_hostname(const char* orighostarg, const char* argv0) { char *userhostarg = NULL; + char *hostbuf = NULL; char *last_hop = NULL;; char *remainder = NULL; @@ -439,11 +490,12 @@ && strchr(cli_opts.username, ',') && strchr(cli_opts.username, '@')) { unsigned int len = strlen(orighostarg) + strlen(cli_opts.username) + 2; - userhostarg = m_malloc(len); - snprintf(userhostarg, len, "%s@%s", cli_opts.username, orighostarg); + hostbuf = m_malloc(len); + snprintf(hostbuf, len, "%s@%s", cli_opts.username, orighostarg); } else { - userhostarg = m_strdup(orighostarg); + hostbuf = m_strdup(orighostarg); } + userhostarg = hostbuf; last_hop = strrchr(userhostarg, ','); if (last_hop) { @@ -461,19 +513,24 @@ if (last_hop) { /* Set up the proxycmd */ unsigned int cmd_len = 0; + char *passthrough_args = multihop_passthrough_args(); if (cli_opts.proxycmd) { dropbear_exit("-J can't be used with multihop mode"); } if (cli_opts.remoteport == NULL) { cli_opts.remoteport = "22"; } - cmd_len = strlen(remainder) + cmd_len = strlen(argv0) + strlen(remainder) + strlen(cli_opts.remotehost) + strlen(cli_opts.remoteport) - + strlen(argv0) + 30; + + strlen(passthrough_args) + + 30; cli_opts.proxycmd = m_malloc(cmd_len); - snprintf(cli_opts.proxycmd, cmd_len, "%s -B %s:%s %s", - argv0, cli_opts.remotehost, cli_opts.remoteport, remainder); + snprintf(cli_opts.proxycmd, cmd_len, "%s -B %s:%s %s %s", + argv0, cli_opts.remotehost, cli_opts.remoteport, + passthrough_args, remainder); + m_free(passthrough_args); } + m_free(hostbuf); } #endif /* !ENABLE_CLI_MULTIHOP */ @@ -622,6 +679,7 @@ goto badport; } + newfwd->have_reply = 0; newfwd->next = *fwdlist; *fwdlist = newfwd;