awk: free unused parsing structures after parse is done
function old new delta hash_clear - 90 +90 awk_main 827 849 +22 clear_array 90 - -90 ------------------------------------------------------------------------------ (add/remove: 1/1 grow/shrink: 1/0 up/down: 112/-90) Total: 22 bytes Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
This commit is contained in:
parent
21fbee2e87
commit
b3c91a127f
@ -530,7 +530,8 @@ struct globals {
|
||||
xhash *ahash; /* argument names, used only while parsing function bodies */
|
||||
xhash *fnhash; /* function names, used only in parsing stage */
|
||||
xhash *vhash; /* variables and arrays */
|
||||
xhash *fdhash; /* file objects, used only in execution stage */
|
||||
//xhash *fdhash; /* file objects, used only in execution stage */
|
||||
//we are reusing ahash as fdhash, via define (see later)
|
||||
const char *g_progname;
|
||||
int g_lineno;
|
||||
int nfields;
|
||||
@ -592,10 +593,13 @@ struct globals2 {
|
||||
#define break_ptr (G1.break_ptr )
|
||||
#define continue_ptr (G1.continue_ptr)
|
||||
#define iF (G1.iF )
|
||||
#define vhash (G1.vhash )
|
||||
#define ahash (G1.ahash )
|
||||
#define fdhash (G1.fdhash )
|
||||
#define fnhash (G1.fnhash )
|
||||
#define vhash (G1.vhash )
|
||||
#define fdhash ahash
|
||||
//^^^^^^^^^^^^^^^^^^ ahash is cleared after every function parsing,
|
||||
// and ends up empty after parsing phase. Thus, we can simply reuse it
|
||||
// for fdhash in execution stage.
|
||||
#define g_progname (G1.g_progname )
|
||||
#define g_lineno (G1.g_lineno )
|
||||
#define nfields (G1.nfields )
|
||||
@ -682,6 +686,33 @@ static xhash *hash_init(void)
|
||||
return newhash;
|
||||
}
|
||||
|
||||
static void hash_clear(xhash *hash)
|
||||
{
|
||||
unsigned i;
|
||||
hash_item *hi, *thi;
|
||||
|
||||
for (i = 0; i < hash->csize; i++) {
|
||||
hi = hash->items[i];
|
||||
while (hi) {
|
||||
thi = hi;
|
||||
hi = hi->next;
|
||||
free(thi->data.v.string);
|
||||
free(thi);
|
||||
}
|
||||
hash->items[i] = NULL;
|
||||
}
|
||||
hash->glen = hash->nel = 0;
|
||||
}
|
||||
|
||||
#if 0 //UNUSED
|
||||
static void hash_free(xhash *hash)
|
||||
{
|
||||
hash_clear(hash);
|
||||
free(hash->items);
|
||||
free(hash);
|
||||
}
|
||||
#endif
|
||||
|
||||
/* find item in hash, return ptr to data, NULL if not found */
|
||||
static void *hash_search(xhash *hash, const char *name)
|
||||
{
|
||||
@ -869,23 +900,7 @@ static xhash *iamarray(var *v)
|
||||
return a->x.array;
|
||||
}
|
||||
|
||||
static void clear_array(xhash *array)
|
||||
{
|
||||
unsigned i;
|
||||
hash_item *hi, *thi;
|
||||
|
||||
for (i = 0; i < array->csize; i++) {
|
||||
hi = array->items[i];
|
||||
while (hi) {
|
||||
thi = hi;
|
||||
hi = hi->next;
|
||||
free(thi->data.v.string);
|
||||
free(thi);
|
||||
}
|
||||
array->items[i] = NULL;
|
||||
}
|
||||
array->glen = array->nel = 0;
|
||||
}
|
||||
#define clear_array(array) hash_clear(array)
|
||||
|
||||
/* clear a variable */
|
||||
static var *clrvar(var *v)
|
||||
@ -1742,7 +1757,7 @@ static void parse_program(char *p)
|
||||
}
|
||||
seq = &f->body;
|
||||
chain_group();
|
||||
clear_array(ahash);
|
||||
hash_clear(ahash);
|
||||
} else if (tclass & TS_OPSEQ) {
|
||||
debug_printf_parse("%s: TS_OPSEQ\n", __func__);
|
||||
rollback_token();
|
||||
@ -3471,11 +3486,16 @@ int awk_main(int argc UNUSED_PARAM, char **argv)
|
||||
bb_show_usage();
|
||||
parse_program(*argv++);
|
||||
}
|
||||
//free_hash(ahash) // ~250 bytes, arg names, used only during parse of function bodies
|
||||
//ahash = NULL; // debug
|
||||
//free_hash(fnhash) // ~250 bytes, used only for function names
|
||||
//fnhash = NULL; // debug
|
||||
/* parsing done, on to executing */
|
||||
/* Free unused parse structures */
|
||||
//hash_free(fnhash); // ~250 bytes when empty, used only for function names
|
||||
//^^^^^^^^^^^^^^^^^ does not work, hash_clear() inside SEGVs
|
||||
// (IOW: hash_clear() assumes it's a hash of variables. fnhash is not).
|
||||
free(fnhash->items);
|
||||
free(fnhash);
|
||||
fnhash = NULL; // debug
|
||||
//hash_free(ahash); // empty after parsing, will reuse as fdhash instead of freeing
|
||||
|
||||
/* Parsing done, on to executing */
|
||||
|
||||
/* fill in ARGV array */
|
||||
setari_u(intvar[ARGV], 0, "awk");
|
||||
@ -3484,7 +3504,7 @@ int awk_main(int argc UNUSED_PARAM, char **argv)
|
||||
setari_u(intvar[ARGV], ++i, *argv++);
|
||||
setvar_i(intvar[ARGC], i + 1);
|
||||
|
||||
fdhash = hash_init();
|
||||
//fdhash = ahash - done via define
|
||||
newfile("/dev/stdin")->F = stdin;
|
||||
newfile("/dev/stdout")->F = stdout;
|
||||
newfile("/dev/stderr")->F = stderr;
|
||||
|
Loading…
Reference in New Issue
Block a user