=================================================================== RCS file: /cvsrepo/anoncvs/cvs/src/usr.bin/tmux/Attic/cmd-string.c,v retrieving revision 1.25 retrieving revision 1.26 diff -u -r1.25 -r1.26 --- src/usr.bin/tmux/Attic/cmd-string.c 2017/01/15 22:00:56 1.25 +++ src/usr.bin/tmux/Attic/cmd-string.c 2017/01/16 14:49:14 1.26 @@ -1,4 +1,4 @@ -/* $OpenBSD: cmd-string.c,v 1.25 2017/01/15 22:00:56 nicm Exp $ */ +/* $OpenBSD: cmd-string.c,v 1.26 2017/01/16 14:49:14 nicm Exp $ */ /* * Copyright (c) 2008 Nicholas Marriott @@ -54,17 +54,15 @@ (*p)--; } -struct cmd_list * -cmd_string_parse(const char *s, const char *file, u_int line, char **cause) +int +cmd_string_split(const char *s, int *rargc, char ***rargv) { - size_t p = 0; - int ch, i, argc = 0; - char **argv = NULL, *buf = NULL, *t; - const char *whitespace, *equals; - size_t len = 0; - struct cmd_list *cmdlist = NULL; + size_t p = 0; + int ch, argc = 0, append = 0; + char **argv = NULL, *buf = NULL, *t; + const char *whitespace, *equals; + size_t len = 0; - *cause = NULL; for (;;) { ch = cmd_string_getc(s, &p); switch (ch) { @@ -115,43 +113,67 @@ argc--; memmove(argv, argv + 1, argc * (sizeof *argv)); } - if (argc == 0) - goto out; - - cmdlist = cmd_list_parse(argc, argv, file, line, cause); - goto out; + goto done; case '~': - if (buf == NULL) { - t = cmd_string_expand_tilde(s, &p); - if (t == NULL) - goto error; - cmd_string_copy(&buf, t, &len); + if (buf != NULL) { + append = 1; break; } - /* FALLTHROUGH */ + t = cmd_string_expand_tilde(s, &p); + if (t == NULL) + goto error; + cmd_string_copy(&buf, t, &len); + break; default: + append = 1; + break; + } + if (append) { if (len >= SIZE_MAX - 2) goto error; - buf = xrealloc(buf, len + 1); buf[len++] = ch; - break; } + append = 0; } -error: - xasprintf(cause, "invalid or unknown command: %s", s); +done: + *rargc = argc; + *rargv = argv; -out: free(buf); + return (0); - if (argv != NULL) { - for (i = 0; i < argc; i++) - free(argv[i]); - free(argv); - } +error: + if (argv != NULL) + cmd_free_argv(argc, argv); + free(buf); + return (-1); +} +struct cmd_list * +cmd_string_parse(const char *s, const char *file, u_int line, char **cause) +{ + struct cmd_list *cmdlist = NULL; + int argc; + char **argv; + + *cause = NULL; + if (cmd_string_split(s, &argc, &argv) != 0) + goto error; + if (argc != 0) { + cmdlist = cmd_list_parse(argc, argv, file, line, cause); + if (cmdlist == NULL) { + cmd_free_argv(argc, argv); + goto error; + } + } + cmd_free_argv(argc, argv); return (cmdlist); + +error: + xasprintf(cause, "invalid or unknown command: %s", s); + return (NULL); } static void