Mercurial > dropbear
diff cli-runopts.c @ 47:4b53a43f0082
- client pubkey auth works
- rearrange the runopts code for client and server (hostkey reading is needed
by both (if the client is doing pubkey auth. otherwise....))
author | Matt Johnston <matt@ucc.asn.au> |
---|---|
date | Fri, 06 Aug 2004 16:18:01 +0000 |
parents | 3bea78e1b175 |
children | 6f091656c100 |
line wrap: on
line diff
--- a/cli-runopts.c Fri Aug 06 02:51:17 2004 +0000 +++ b/cli-runopts.c Fri Aug 06 16:18:01 2004 +0000 @@ -31,17 +31,24 @@ cli_runopts cli_opts; /* GLOBAL */ -static void printhelp(const char * progname); +static void printhelp(); +static void parsehostname(char* userhostarg); +#ifdef DROPBEAR_PUBKEY_AUTH +static void loadidentityfile(const char* filename); +#endif -static void printhelp(const char * progname) { +static void printhelp() { fprintf(stderr, "Dropbear client v%s\n" - "Usage: %s [options] user@host[:port]\n" + "Usage: %s [options] user@host\n" "Options are:\n" - "user Remote username\n" - "host Remote host\n" - "port Remote port\n" - ,DROPBEAR_VERSION, progname); + "-p <remoteport>\n" + "-t Allocate a pty" + "-T Don't allocate a pty" +#ifdef DROPBEAR_PUBKEY_AUTH + "-i <identityfile> (multiple allowed)" +#endif + ,DROPBEAR_VERSION, cli_opts.progname); } void cli_getopts(int argc, char ** argv) { @@ -49,12 +56,11 @@ unsigned int i, j; char ** next = 0; unsigned int cmdlen; +#ifdef DROPBEAR_PUBKEY_AUTH int nextiskey = 0; /* A flag if the next argument is a keyfile */ +#endif - uid_t uid; - struct passwd *pw = NULL; - char* userhostarg = NULL; /* see printhelp() for options */ cli_opts.progname = argv[0]; @@ -62,7 +68,10 @@ cli_opts.remoteport = NULL; cli_opts.username = NULL; cli_opts.cmd = NULL; - cli_opts.wantpty = 1; + cli_opts.wantpty = 9; /* 9 means "it hasn't been touched", gets set later */ +#ifdef DROPBEAR_PUBKEY_AUTH + cli_opts.pubkeys = NULL; +#endif opts.nolocaltcp = 0; opts.noremotetcp = 0; /* not yet @@ -70,17 +79,18 @@ opts.ipv6 = 1; */ - if (argc != 2) { - printhelp(argv[0]); - exit(EXIT_FAILURE); - } - + /* Iterate all the arguments */ for (i = 1; i < (unsigned int)argc; i++) { +#ifdef DROPBEAR_PUBKEY_AUTH if (nextiskey) { - /* XXX do stuff */ - break; + /* Load a hostkey since the previous argument was "-i" */ + loadidentityfile(argv[i]); + nextiskey = 0; + continue; } +#endif if (next) { + /* The previous flag set a value to assign */ *next = argv[i]; if (*next == NULL) { dropbear_exit("Invalid null argument"); @@ -90,59 +100,43 @@ } if (argv[i][0] == '-') { + /* A flag *waves* */ - /* A flag *waves* */ switch (argv[i][1]) { - case 'p': + case 'p': /* remoteport */ next = &cli_opts.remoteport; break; #ifdef DROPBEAR_PUBKEY_AUTH - case 'i': + case 'i': /* an identityfile */ nextiskey = 1; break; #endif + case 't': /* we want a pty */ + cli_opts.wantpty = 1; + break; + case 'T': /* don't want a pty */ + cli_opts.wantpty = 0; + break; default: - fprintf(stderr, "Unknown argument %s\n", argv[i]); - printhelp(argv[0]); + fprintf(stderr, "Unknown argument '%s'\n", argv[i]); + printhelp(); exit(EXIT_FAILURE); break; } /* Switch */ + continue; /* next argument */ + } else { + TRACE(("non-flag arg")); /* Either the hostname or commands */ - /* Hostname is first up, must be set before we get the cmds */ if (cli_opts.remotehost == NULL) { - /* We'll be editing it, should probably make a copy */ - userhostarg = m_strdup(argv[1]); - cli_opts.remotehost = strchr(userhostarg, '@'); - if (cli_opts.remotehost == NULL) { - /* no username portion, the cli-auth.c code can figure the - * local user's name */ - cli_opts.remotehost = userhostarg; - } else { - cli_opts.remotehost[0] = '\0'; /* Split the user/host */ - cli_opts.remotehost++; - cli_opts.username = userhostarg; - } + parsehostname(argv[i]); - if (cli_opts.username == NULL) { - uid = getuid(); - - pw = getpwuid(uid); - if (pw == NULL || pw->pw_name == NULL) { - dropbear_exit("I don't know my own [user]name"); - } + } else { - cli_opts.username = m_strdup(pw->pw_name); - } - - if (cli_opts.remotehost[0] == '\0') { - dropbear_exit("Bad hostname"); - } - } else { /* this is part of the commands to send - after this we * don't parse any more options, and flags are sent as the * command */ @@ -166,4 +160,82 @@ } } } + + if (cli_opts.remotehost == NULL) { + dropbear_exit("Bad syntax"); + } + + if (cli_opts.remoteport == NULL) { + cli_opts.remoteport = "22"; + } + + /* If not explicitly specified with -t or -T, we don't want a pty if + * there's a command, but we do otherwise */ + if (cli_opts.wantpty == 9) { + if (cli_opts.cmd == NULL) { + cli_opts.wantpty = 1; + } else { + cli_opts.wantpty = 0; + } + } } + +#ifdef DROPBEAR_PUBKEY_AUTH +static void loadidentityfile(const char* filename) { + + struct PubkeyList * nextkey; + sign_key *key; + int keytype; + + 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 PubkeyList*)m_malloc(sizeof(struct PubkeyList)); + nextkey->key = key; + nextkey->next = cli_opts.pubkeys; + nextkey->type = keytype; + cli_opts.pubkeys = nextkey; + } +} +#endif + + +/* Parses a [user@]hostname argument. userhostarg is the argv[i] corresponding + * - note that it will be modified */ +static void parsehostname(char* userhostarg) { + + uid_t uid; + struct passwd *pw = NULL; + + cli_opts.remotehost = strchr(userhostarg, '@'); + if (cli_opts.remotehost == NULL) { + /* no username portion, the cli-auth.c code can figure the + * local user's name */ + cli_opts.remotehost = userhostarg; + } else { + cli_opts.remotehost[0] = '\0'; /* Split the user/host */ + cli_opts.remotehost++; + cli_opts.username = userhostarg; + } + + if (cli_opts.username == NULL) { + uid = getuid(); + + pw = getpwuid(uid); + if (pw == NULL || pw->pw_name == NULL) { + dropbear_exit("Unknown own user"); + } + + cli_opts.username = m_strdup(pw->pw_name); + } + + if (cli_opts.remotehost[0] == '\0') { + dropbear_exit("Bad hostname"); + } +}