diff options
author | Mattias Andrée <maandree@operamail.com> | 2014-11-11 04:28:17 +0100 |
---|---|---|
committer | Mattias Andrée <maandree@operamail.com> | 2014-11-11 04:28:17 +0100 |
commit | 897bc5e18e06931add00582fc09edead23959bef (patch) | |
tree | fc3a83dbbfa8fc0edd1ad838028f9b300ff32fae /src/mds-kbdc | |
parent | CHARS_END => END (diff) | |
download | mds-897bc5e18e06931add00582fc09edead23959bef.tar.gz mds-897bc5e18e06931add00582fc09edead23959bef.tar.bz2 mds-897bc5e18e06931add00582fc09edead23959bef.tar.xz |
mds-kbdc: have + memory leak on destruction of have
Signed-off-by: Mattias Andrée <maandree@operamail.com>
Diffstat (limited to '')
-rw-r--r-- | src/mds-kbdc/make-tree.c | 73 | ||||
-rw-r--r-- | src/mds-kbdc/tree.c | 2 |
2 files changed, 73 insertions, 2 deletions
diff --git a/src/mds-kbdc/make-tree.c b/src/mds-kbdc/make-tree.c index cd4a8fb..6822261 100644 --- a/src/mds-kbdc/make-tree.c +++ b/src/mds-kbdc/make-tree.c @@ -352,6 +352,70 @@ while (0) +/** + * Take next parameter, which should be a key combination or strings, + * and store it in the current node + * + * @param var:identifier The name of the member variable, for the current + * node, where the parameter should be stored + */ +#define KEYS(var) \ + do \ + { \ + if (too_few) \ + break; \ + line += strlen(line); \ + *end = prev_end_char, prev_end_char = '\0'; \ + while (*line && (*line == ' ')) \ + line++; \ + if (*line == '\0') \ + { \ + line = original, end = line + strlen(line); \ + NEW_ERROR(1, ERROR, "too few parameters"); \ + line = end, too_few = 1; \ + } \ + else \ + { \ + char* arg_end = line; \ + char* call_end = arg_end; \ + int escape = 0, quote = 0, triangle = (*arg_end == '<'); \ + while (*arg_end) \ + { \ + char c = *arg_end++ ; \ + if (escape) escape = 0; \ + else if (arg_end <= call_end) ; \ + else if (c == '\\') \ + { \ + escape = 0; \ + call_end = arg_end + get_end_of_call(arg_end, 0, strlen(arg_end)); \ + } \ + else if (quote) quote = (c != '"'); \ + else if (c == '\"') quote = 1; \ + else if (c == '>') triangle = 0; \ + else if ((c == ' ') && !triangle) break; \ + } \ + prev_end_char = *arg_end, *arg_end = '\0'; \ + if (*line == '<') \ + { \ + mds_kbdc_tree_keys_t* subnode; \ + fail_if (xcalloc(subnode, 1, mds_kbdc_tree_keys_t)); \ + subnode->type = MDS_KBDC_TREE_TYPE_KEYS; \ + node->var = (mds_kbdc_tree_t*)subnode; \ + fail_if ((subnode->keys = strdup(line)) == NULL); \ + } \ + else \ + { \ + mds_kbdc_tree_string_t* subnode; \ + fail_if (xcalloc(subnode, 1, mds_kbdc_tree_string_t)); \ + subnode->type = MDS_KBDC_TREE_TYPE_STRING; \ + node->var = (mds_kbdc_tree_t*)subnode; \ + fail_if ((subnode->string = strdup(line)) == NULL); \ + } \ + end = line = arg_end; \ + } \ + } \ + while (0) + /** @@ -559,7 +623,13 @@ int parse_to_tree(const char* restrict filename, mds_kbdc_tree_t** restrict resu BRANCH("for"); } else if (!strcmp(line, "let")) ; /* TODO */ - else if (!strcmp(line, "have")) ; /* TODO */ + else if (!strcmp(line, "have")) + { + NEW_NODE(assumption_have, ASSUMPTION_HAVE); + KEYS(data); + END; + LEAF; + } else if (!strcmp(line, "have_chars")) { NEW_NODE(assumption_have_chars, ASSUMPTION_HAVE_CHARS); @@ -628,6 +698,7 @@ int parse_to_tree(const char* restrict filename, mds_kbdc_tree_t** restrict resu +#undef KEYS #undef TEST_FOR_KEYWORD #undef QUOTES_1 #undef QUOTES diff --git a/src/mds-kbdc/tree.c b/src/mds-kbdc/tree.c index 99fa223..4f0fec0 100644 --- a/src/mds-kbdc/tree.c +++ b/src/mds-kbdc/tree.c @@ -96,7 +96,7 @@ static void mds_kbdc_tree_destroy_(mds_kbdc_tree_t* restrict this, int recursive break; case MDS_KBDC_TREE_TYPE_ASSUMPTION_HAVE: - xfree(mds_kbdc_tree_assumption_have_t*, data); + xdestroy(mds_kbdc_tree_assumption_have_t*, data); break; case MDS_KBDC_TREE_TYPE_ASSUMPTION_HAVE_CHARS: |