forked from github/server
Merge pull request #559 from ennorehling/develop
fix syntaxtree memory leak
This commit is contained in:
commit
149d1a43a6
4 changed files with 25 additions and 26 deletions
|
@ -288,14 +288,12 @@ static void perform_join(void)
|
||||||
static syntaxtree * build_syntax(void) {
|
static syntaxtree * build_syntax(void) {
|
||||||
syntaxtree *slang, *stree = stree_create();
|
syntaxtree *slang, *stree = stree_create();
|
||||||
for (slang = stree; slang; slang = slang->next) {
|
for (slang = stree; slang; slang = slang->next) {
|
||||||
struct tnode *leaf = 0;
|
stree_add(slang, LOC(slang->lang, alliance_kwd[ALLIANCE_KICK]), &cmd_kick);
|
||||||
add_command(&leaf, NULL, LOC(slang->lang, alliance_kwd[ALLIANCE_KICK]), &cmd_kick);
|
stree_add(slang, LOC(slang->lang, alliance_kwd[ALLIANCE_LEAVE]), &cmd_leave);
|
||||||
add_command(&leaf, NULL, LOC(slang->lang, alliance_kwd[ALLIANCE_LEAVE]), &cmd_leave);
|
stree_add(slang, LOC(slang->lang, alliance_kwd[ALLIANCE_TRANSFER]), &cmd_transfer);
|
||||||
add_command(&leaf, NULL, LOC(slang->lang, alliance_kwd[ALLIANCE_TRANSFER]), &cmd_transfer);
|
stree_add(slang, LOC(slang->lang, alliance_kwd[ALLIANCE_NEW]), &cmd_new);
|
||||||
add_command(&leaf, NULL, LOC(slang->lang, alliance_kwd[ALLIANCE_NEW]), &cmd_new);
|
stree_add(slang, LOC(slang->lang, alliance_kwd[ALLIANCE_INVITE]), &cmd_invite);
|
||||||
add_command(&leaf, NULL, LOC(slang->lang, alliance_kwd[ALLIANCE_INVITE]), &cmd_invite);
|
stree_add(slang, LOC(slang->lang, alliance_kwd[ALLIANCE_JOIN]), &cmd_join);
|
||||||
add_command(&leaf, NULL, LOC(slang->lang, alliance_kwd[ALLIANCE_JOIN]), &cmd_join);
|
|
||||||
slang->root = leaf;
|
|
||||||
}
|
}
|
||||||
return stree;
|
return stree;
|
||||||
}
|
}
|
||||||
|
|
|
@ -30,7 +30,7 @@
|
||||||
|
|
||||||
typedef struct command {
|
typedef struct command {
|
||||||
parser fun;
|
parser fun;
|
||||||
void *nodes;
|
struct command *next;
|
||||||
} command;
|
} command;
|
||||||
|
|
||||||
void *stree_find(const syntaxtree * stree, const struct locale *lang)
|
void *stree_find(const syntaxtree * stree, const struct locale *lang)
|
||||||
|
@ -44,6 +44,11 @@ void *stree_find(const syntaxtree * stree, const struct locale *lang)
|
||||||
}
|
}
|
||||||
|
|
||||||
void stree_free(syntaxtree *stree) {
|
void stree_free(syntaxtree *stree) {
|
||||||
|
while (stree->cmds) {
|
||||||
|
command *next = stree->cmds->next;
|
||||||
|
free(stree->cmds);
|
||||||
|
stree->cmds = next;
|
||||||
|
}
|
||||||
while (stree) {
|
while (stree) {
|
||||||
syntaxtree *snext = stree->next;
|
syntaxtree *snext = stree->next;
|
||||||
freetokens(stree->root);
|
freetokens(stree->root);
|
||||||
|
@ -61,24 +66,23 @@ syntaxtree *stree_create(void)
|
||||||
stree->lang = lang;
|
stree->lang = lang;
|
||||||
stree->next = sroot;
|
stree->next = sroot;
|
||||||
stree->root = 0;
|
stree->root = 0;
|
||||||
|
stree->cmds = 0;
|
||||||
sroot = stree;
|
sroot = stree;
|
||||||
lang = nextlocale(lang);
|
lang = nextlocale(lang);
|
||||||
}
|
}
|
||||||
return sroot;
|
return sroot;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void stree_add(struct syntaxtree *stree, const char *str, parser fun) {
|
||||||
add_command(struct tnode **keys, void *tnext,
|
|
||||||
const char *str, parser fun)
|
|
||||||
{
|
|
||||||
command *cmd = (command *)malloc(sizeof(command));
|
command *cmd = (command *)malloc(sizeof(command));
|
||||||
variant var;
|
variant var;
|
||||||
|
|
||||||
assert(str);
|
assert(str);
|
||||||
cmd->fun = fun;
|
cmd->fun = fun;
|
||||||
cmd->nodes = tnext;
|
|
||||||
var.v = cmd;
|
var.v = cmd;
|
||||||
addtoken(keys, str, var);
|
cmd->next = stree->cmds;
|
||||||
|
stree->cmds = cmd;
|
||||||
|
addtoken(&stree->root, str, var);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int do_command_i(const struct tnode *keys, struct unit *u, struct order *ord)
|
static int do_command_i(const struct tnode *keys, struct unit *u, struct order *ord)
|
||||||
|
@ -90,12 +94,8 @@ static int do_command_i(const struct tnode *keys, struct unit *u, struct order *
|
||||||
c = gettoken(token, sizeof(token));
|
c = gettoken(token, sizeof(token));
|
||||||
if (findtoken(keys, c, &var) == E_TOK_SUCCESS) {
|
if (findtoken(keys, c, &var) == E_TOK_SUCCESS) {
|
||||||
command *cmd = (command *)var.v;
|
command *cmd = (command *)var.v;
|
||||||
if (cmd->nodes && *c) {
|
if (cmd->fun) {
|
||||||
assert(!cmd->fun);
|
cmd->fun(0, u, ord);
|
||||||
return do_command_i(cmd->nodes, u, ord);
|
|
||||||
}
|
|
||||||
else if (cmd->fun) {
|
|
||||||
cmd->fun(cmd->nodes, u, ord);
|
|
||||||
return E_TOK_SUCCESS;
|
return E_TOK_SUCCESS;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,19 +20,20 @@ extern "C" {
|
||||||
struct order;
|
struct order;
|
||||||
struct unit;
|
struct unit;
|
||||||
struct tnode;
|
struct tnode;
|
||||||
|
struct command;
|
||||||
|
|
||||||
typedef struct syntaxtree {
|
typedef struct syntaxtree {
|
||||||
const struct locale *lang;
|
const struct locale *lang;
|
||||||
struct tnode *root;
|
struct tnode *root;
|
||||||
struct syntaxtree *next;
|
struct syntaxtree *next;
|
||||||
|
struct command *cmds;
|
||||||
} syntaxtree;
|
} syntaxtree;
|
||||||
|
|
||||||
typedef void(*parser) (const void *nodes, struct unit * u, struct order *);
|
typedef void(*parser) (const void *nodes, struct unit * u, struct order *);
|
||||||
void add_command(struct tnode **troot, void *tnext,
|
|
||||||
const char *str, parser fun);
|
|
||||||
void do_command(const struct tnode *troot, struct unit *u, struct order *);
|
void do_command(const struct tnode *troot, struct unit *u, struct order *);
|
||||||
|
|
||||||
struct syntaxtree *stree_create(void);
|
struct syntaxtree *stree_create(void);
|
||||||
|
void stree_add(struct syntaxtree *, const char *str, parser fun);
|
||||||
void stree_free(struct syntaxtree *);
|
void stree_free(struct syntaxtree *);
|
||||||
void *stree_find(const struct syntaxtree *stree,
|
void *stree_find(const struct syntaxtree *stree,
|
||||||
const struct locale *lang);
|
const struct locale *lang);
|
||||||
|
|
|
@ -37,8 +37,8 @@ static void test_command(CuTest * tc) {
|
||||||
CuAssertPtrEquals(tc, loc, (struct locale *)st->lang);
|
CuAssertPtrEquals(tc, loc, (struct locale *)st->lang);
|
||||||
CuAssertPtrEquals(tc, 0, st->root);
|
CuAssertPtrEquals(tc, 0, st->root);
|
||||||
CuAssertPtrEquals(tc, 0, st->next);
|
CuAssertPtrEquals(tc, 0, st->next);
|
||||||
add_command(&st->root, 0, "two", parser_two);
|
stree_add(st, "two", parser_two);
|
||||||
add_command(&st->root, 0, "six", parser_six);
|
stree_add(st, "six", parser_six);
|
||||||
CuAssertPtrNotNull(tc, st->root);
|
CuAssertPtrNotNull(tc, st->root);
|
||||||
CuAssertPtrEquals(tc, st->root, stree_find(st, loc));
|
CuAssertPtrEquals(tc, st->root, stree_find(st, loc));
|
||||||
u = test_create_unit(test_create_faction(0), test_create_region(0, 0, 0));
|
u = test_create_unit(test_create_faction(0), test_create_region(0, 0, 0));
|
||||||
|
@ -54,4 +54,4 @@ CuSuite *get_command_suite(void)
|
||||||
CuSuite *suite = CuSuiteNew();
|
CuSuite *suite = CuSuiteNew();
|
||||||
SUITE_ADD_TEST(suite, test_command);
|
SUITE_ADD_TEST(suite, test_command);
|
||||||
return suite;
|
return suite;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue