diff options
author | Sergey Poznyakoff <gray@gnu.org.ua> | 2011-05-13 10:27:58 +0300 |
---|---|---|
committer | Sergey Poznyakoff <gray@gnu.org.ua> | 2011-05-13 10:27:58 +0300 |
commit | 4c1056b45580fcb687cac656834f42dd9fba4ae8 (patch) | |
tree | d4bc6aaa3749fd0dbcb86f4d3e86d3b44d036b51 /src | |
parent | 967d4d82ef9d10ecd6b32a29f2b3f2743175a268 (diff) | |
download | grecs-4c1056b45580fcb687cac656834f42dd9fba4ae8.tar.gz grecs-4c1056b45580fcb687cac656834f42dd9fba4ae8.tar.bz2 |
Fix memory leaks.
* src/grecs-gram.y (slist production): Free ep->data after appending.
* src/grecs-lex.l (string_list): Remove. All uses updated.
* src/tree.c (grecs_node_free): Free ident.
(grecs_tree_process): Fill config_keywords with zeros.
* src/grecs.h (grecs_getline): New proto.
* src/preproc.c (pp_getline): Rename to grecs_getline,
drop static qualifier. Improve initial allocation.
Diffstat (limited to 'src')
-rw-r--r-- | src/grecs-gram.y | 5 | ||||
-rw-r--r-- | src/grecs-lex.l | 7 | ||||
-rw-r--r-- | src/grecs.h | 2 | ||||
-rw-r--r-- | src/preproc.c | 31 | ||||
-rw-r--r-- | src/tree.c | 2 |
5 files changed, 23 insertions, 24 deletions
diff --git a/src/grecs-gram.y b/src/grecs-gram.y index 8d0adbf..960567e 100644 --- a/src/grecs-gram.y +++ b/src/grecs-gram.y @@ -166,14 +166,17 @@ string : STRING slist : slist0 { struct grecs_list_entry *ep; grecs_line_begin(); - for (ep = $1->head; ep; ep = ep->next) + for (ep = $1->head; ep; ep = ep->next) { grecs_line_add(ep->data, strlen(ep->data)); + free(ep->data); + ep->data = NULL; + } $$ = grecs_line_finish(); grecs_list_free($1); } ; slist0 : QSTRING diff --git a/src/grecs-lex.l b/src/grecs-lex.l index faf6c4c..a3cc7d8 100644 --- a/src/grecs-lex.l +++ b/src/grecs-lex.l @@ -46,13 +46,12 @@ grecs_locus_t grecs_current_locus; /* Input file location */ Uff, running two preprocessors is confusing... */ static size_t xlines; static struct grecs_list *line_acc; -static struct grecs_list *string_list; static void multiline_begin(char *); static void multiline_add(char *); static char *multiline_strip_tabs(char *text); static void line_add_unescape_last(char *text, size_t len); static int ident(void); @@ -182,13 +181,12 @@ grecs_lex_begin(const char *name) { if (yy_flex_debug > 0) yy_flex_debug = 0; line_acc = grecs_list_create(); line_acc->free_entry = line_acc_free_entry; - string_list = grecs_list_create(); if (grecs_preprocessor) { int fd; fd = open(name, O_RDONLY); if (fd == -1) { @@ -210,15 +208,12 @@ grecs_lex_begin(const char *name) return 0; } void grecs_lex_end(int err) { - if (!err) - string_list->free_entry = NULL; - grecs_list_free(string_list); grecs_list_clear(line_acc); } static int isemptystr(int off) { @@ -389,13 +384,12 @@ grecs_line_finish() for (ep = line_acc->head; ep; ep = ep->next) { struct line_acc_entry *ent = ep->data; size += ent->size; } str = grecs_malloc(size + 1); - grecs_list_append(string_list, str); for (ep = line_acc->head, p = str; ep; ep = ep->next) { struct line_acc_entry *ent = ep->data; char *str = line_acc_ptr(ent); memcpy(p, str, ent->size); p += ent->size; } @@ -414,13 +408,12 @@ ident() for (p = yytext; *p && isspace(*p); p++) ; len = strlen(p); str = grecs_malloc(len + 1); strcpy(str, p); - grecs_list_append(string_list, str); yylval.string = str; return IDENT; } void grecs_lex_trace(int n) diff --git a/src/grecs.h b/src/grecs.h index b2ef734..05eeff2 100644 --- a/src/grecs.h +++ b/src/grecs.h @@ -247,12 +247,14 @@ char *grecs_install_text(const char *str); void grecs_destroy_text(void); struct grecs_symtab *grecs_text_table(void); void grecs_include_path_setup(const char *dir, ...); void grecs_include_path_setup_v(char **dirs); +ssize_t grecs_getline(char **pbuf, size_t *psize, FILE *fp); + const char *grecs_data_type_string(enum grecs_data_type type); void grecs_format_docstring(const char *docstring, unsigned level, FILE *stream); void grecs_format_simple_statement(struct grecs_keyword *kwp, unsigned level, FILE *stream); void grecs_format_block_statement(struct grecs_keyword *kwp, diff --git a/src/preproc.c b/src/preproc.c index cd83e2f..ea77506 100644 --- a/src/preproc.c +++ b/src/preproc.c @@ -63,40 +63,39 @@ static size_t putback_size; static size_t putback_max; static int push_source (const char *name, int once); static int pop_source (void); static int parse_include (const char *text, int once); -static ssize_t -pp_getline(char **pbuf, size_t *psize, FILE *fp) +ssize_t +grecs_getline(char **pbuf, size_t *psize, FILE *fp) { char *buf = *pbuf; size_t size = *psize; ssize_t off = 0; + if (!buf) { + size = 1; + buf = grecs_malloc(size); + } + do { if (off == size - 1) { - if (!buf) { - size = 1; - buf = grecs_malloc(size); - } else { - size_t nsize = 2 * size; - if (nsize < size) - grecs_alloc_die(); - buf = grecs_realloc(buf, nsize); - size = nsize; - } + size_t nsize = 2 * size; + if (nsize < size) + grecs_alloc_die(); + buf = grecs_realloc(buf, nsize); + size = nsize; } if (!fgets(buf + off, size - off, fp)) { if (off == 0) off = -1; break; } off += strlen(buf + off); - } - while (buf[off - 1] != '\n'); + } while (buf[off - 1] != '\n'); *pbuf = buf; *psize = size; return off; } @@ -160,13 +159,13 @@ next_line() rc = putback_size; putback_size = 0; } else if (!context_stack) return 0; else - rc = pp_getline(&linebuf, &bufsize, INFILE); + rc = grecs_getline(&linebuf, &bufsize, INFILE); } while (rc == -1 && pop_source() == 0); return rc; } size_t grecs_preproc_fill_buffer(char *buf, size_t size) @@ -661,13 +660,13 @@ grecs_preproc_extrn_start(const char *file_name, pid_t *ppid) default: /* Sub-master */ close (p[1]); fp = fdopen(p[0], "r"); if (grecs_log_setup_hook) grecs_log_setup_hook(); - while (pp_getline(&buf, &size, fp) > 0) + while (grecs_getline(&buf, &size, fp) > 0) grecs_error(NULL, 0, "%s", buf); } } else { grecs_preproc_run(file_name, grecs_preprocessor); } exit (0); @@ -191,12 +191,13 @@ grecs_node_free(struct grecs_node *node) case grecs_node_root: grecs_symtab_free(node->v.texttab); break; default: grecs_value_free(node->v.value); } + grecs_free(node->ident); grecs_free(node); } static enum grecs_tree_recurse_res freeproc(enum grecs_tree_recurse_op op, struct grecs_node *node, void *data) { @@ -859,12 +860,13 @@ int grecs_tree_process(struct grecs_node *node, struct grecs_keyword *kwd) { int rc; struct nodeproc_closure clos; struct grecs_keyword config_keywords; + memset(&config_keywords, 0, sizeof(config_keywords)); config_keywords.kwd = kwd; clos.cursect = &config_keywords; clos.sections = grecs_list_create(); if (node->type == grecs_node_root) node = node->down; rc = grecs_tree_recurse(node, nodeproc, &clos); |