From b7e3d05ace895fce6be87592c9dfee3817436aae Mon Sep 17 00:00:00 2001 From: "S. Christoffer Eliesen" Date: Wed, 18 Nov 2015 15:03:20 +0100 Subject: [PATCH 1/2] stringop: Properly handle criteria strings. A criteria string (e.g. '[class="something" title="something"]') is now correctly treated as a single argument. --- sway/stringop.c | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/sway/stringop.c b/sway/stringop.c index fe5a97ca1..efa3a2073 100644 --- a/sway/stringop.c +++ b/sway/stringop.c @@ -117,6 +117,7 @@ char **split_args(const char *start, int *argc) { bool in_token = false; bool in_string = false; bool in_char = false; + bool in_brackets = false; // brackets are used for critera bool escaped = false; const char *end = start; if (start) { @@ -129,10 +130,14 @@ char **split_args(const char *start, int *argc) { in_string = !in_string; } else if (*end == '\'' && !in_string && !escaped) { in_char = !in_char; + } else if (*end == '[' && !in_string && !in_char && !in_brackets && !escaped) { + in_brackets = true; + } else if (*end == ']' && !in_string && !in_char && in_brackets && !escaped) { + in_brackets = false; } else if (*end == '\\') { escaped = !escaped; - } else if (*end == '\0' || (!in_string && !in_char && !escaped - && strchr(whitespace, *end))) { + } else if (*end == '\0' || (!in_string && !in_char && !in_brackets + && !escaped && strchr(whitespace, *end))) { goto add_token; } if (*end != '\\') { From db92920cf9bcdd0008ba446df4d7249e7902373a Mon Sep 17 00:00:00 2001 From: "S. Christoffer Eliesen" Date: Wed, 18 Nov 2015 19:03:24 +0100 Subject: [PATCH 2/2] handle_command: Skip commands that has a criteria string. We can't handle them currently (the criteria needs to e.g. be passed to each command handler which then needs to do the right thing), so it's better to just do nothing than to create unexpected results (because the command was executed on the wrong view). (Before this patch any command list with a criteria string would simply fail to parse, so this is at least a step in the right direction.) --- sway/commands.c | 21 +++++++++++++++++++-- 1 file changed, 19 insertions(+), 2 deletions(-) diff --git a/sway/commands.c b/sway/commands.c index f6d56bb4e..42105d5f4 100644 --- a/sway/commands.c +++ b/sway/commands.c @@ -1401,17 +1401,34 @@ struct cmd_results *handle_command(char *_exec) { head = exec; do { - // Handle criteria + // Extract criteria (valid for this command list only). + criteria = NULL; if (*head == '[') { + ++head; criteria = argsep(&head, "]"); if (head) { ++head; // TODO handle criteria } else { - results = cmd_results_new(CMD_INVALID, NULL, "Unmatched ["); + if (!results) { + results = cmd_results_new(CMD_INVALID, criteria, "Unmatched ["); + } + goto cleanup; } // Skip leading whitespace head += strspn(head, whitespace); + + // TODO: it will yield unexpected results to execute commands + // (on any view) that where meant for certain views only. + if (!results) { + int len = strlen(criteria) + strlen(head) + 4; + char *tmp = malloc(len); + snprintf(tmp, len, "[%s] %s", criteria, head); + results = cmd_results_new(CMD_INVALID, tmp, + "Can't handle criteria string: Refusing to execute command"); + free(tmp); + } + goto cleanup; } // Split command list cmdlist = argsep(&head, ";");