diff --git a/tools/qfcc/include/symtab.h b/tools/qfcc/include/symtab.h index 125f77203..6dc2b2fa0 100644 --- a/tools/qfcc/include/symtab.h +++ b/tools/qfcc/include/symtab.h @@ -84,10 +84,13 @@ typedef struct symbol_s { typedef enum { stab_global, ///< global (many symbols) + stab_param, ///< local (few symbols: func) stab_local, ///< local (few symbols: func) + stab_ivars, stab_struct, stab_union, stab_enum, + stab_label, } stab_type_e; typedef struct symtab_s { @@ -131,7 +134,7 @@ symbol_t *new_symbol_type (const char *name, struct type_s *type); supports both code block scoping and ivar inheritance. \param parent Pointer to parent scope symbol table. - \param type The type of symbol table. Currently governs expected size. + \param type The type of symbol table. \return The new, empty symbol table. */ symtab_t *new_symtab (symtab_t *parent, stab_type_e type); @@ -194,6 +197,7 @@ symbol_t *copy_symbol (symbol_t *symbol); \param symtab The symbol table chain to be copied. \param parent The parent symbol table of the new symbol table, or null. + \param type The type of symbol table. \return The new symbol table. \dot @@ -221,7 +225,8 @@ symbol_t *copy_symbol (symbol_t *symbol); } \enddot */ -symtab_t *symtab_flat_copy (symtab_t *symtab, symtab_t *parent); +symtab_t *symtab_flat_copy (symtab_t *symtab, symtab_t *parent, + stab_type_e type); /** Create a global symbol and allocate space for a variable. diff --git a/tools/qfcc/source/class.c b/tools/qfcc/source/class.c index 5be3015d9..deb17d471 100644 --- a/tools/qfcc/source/class.c +++ b/tools/qfcc/source/class.c @@ -1320,7 +1320,7 @@ class_new_ivars (class_t *class) if (class->super_class) super_ivars = class->super_class->ivars; - ivars = new_symtab (super_ivars, stab_local); + ivars = new_symtab (super_ivars, stab_ivars); ivars->class = class; return ivars; } @@ -1903,7 +1903,7 @@ class_to_struct (class_t *class, symtab_t *symtab) // connect the ivars symbol table chain to the struct symbol table ancestor->parent = symtab; // create a new struct symbol table from the ivars symbol table chain - symtab = symtab_flat_copy (ivars, 0); + symtab = symtab_flat_copy (ivars, 0, stab_struct); // disconnect the ivars symbol table chain ancestor->parent = 0; // connect the new struct symbol table to the scope @@ -1917,7 +1917,7 @@ class_ivar_scope (class_type_t *class_type, symtab_t *parent) class_t *class = extract_class (class_type); if (!class->ivars) return 0; - return symtab_flat_copy (class->ivars, parent); + return symtab_flat_copy (class->ivars, parent, stab_ivars); } static expr_t * diff --git a/tools/qfcc/source/function.c b/tools/qfcc/source/function.c index 7e89d8fd4..6ed067765 100644 --- a/tools/qfcc/source/function.c +++ b/tools/qfcc/source/function.c @@ -598,9 +598,9 @@ build_scope (symbol_t *fsym, symtab_t *parent) check_function (fsym); - fsym->s.func->label_scope = new_symtab (0, stab_local); + fsym->s.func->label_scope = new_symtab (0, stab_label); - parameters = new_symtab (parent, stab_local); + parameters = new_symtab (parent, stab_param); parameters->space = defspace_new (ds_virtual); fsym->s.func->parameters = parameters; diff --git a/tools/qfcc/source/struct.c b/tools/qfcc/source/struct.c index fbfcb02c5..8f4dc6b70 100644 --- a/tools/qfcc/source/struct.c +++ b/tools/qfcc/source/struct.c @@ -220,7 +220,7 @@ start_enum (symbol_t *sym) error (0, "%s defined as wrong kind of tag", sym->name); sym = find_enum (0); } - sym->type->t.symtab = new_symtab (current_symtab, stab_local); + sym->type->t.symtab = new_symtab (current_symtab, stab_enum); sym->type->alignment = 1; sym->type->width = 1; return sym->type->t.symtab; diff --git a/tools/qfcc/source/symtab.c b/tools/qfcc/source/symtab.c index ca6fe4bc4..6470d2682 100644 --- a/tools/qfcc/source/symtab.c +++ b/tools/qfcc/source/symtab.c @@ -178,13 +178,13 @@ copy_symbol (symbol_t *symbol) } symtab_t * -symtab_flat_copy (symtab_t *symtab, symtab_t *parent) +symtab_flat_copy (symtab_t *symtab, symtab_t *parent, stab_type_e type) { symtab_t *newtab; symbol_t *newsym; symbol_t *symbol; - newtab = new_symtab (parent, stab_local); + newtab = new_symtab (parent, type); do { for (symbol = symtab->symbols; symbol; symbol = symbol->next) { if (symbol->visibility == vis_anonymous