imcc symbol handling

XXX: SymReg stuff has become overused. SymReg should be for symbolic registers, reg allocation, etc. but we are now using it for extensive symbol table management. Need to convert much of this over the use Symbol and SymbolTable (see symbol.h and symbol.c)

Functions ^

void push_namespace

Begins a new namespace in PASM/PIR, named after the given name.

void pop_namespace

Ends the current namespace, popping back to the previous. If the namespace stack is empty, throws a syntax error.

static SymReg *_get_sym_typed

Gets a symbol from the hash, with the given name of the specific type t.

static SymReg *_mk_symreg

Makes a new SymReg in the given SymHash from a varname and type.

SymReg *mk_symreg

Makes a new SymReg in the current unit, given a varname and type.

char *symreg_to_str

Dumps a SymReg to a printable format.

SymReg *mk_temp_reg

Makes a new unique and temporary SymReg of the specified type t.

SymReg *mk_pcc_sub

Makes a SymReg representing a PCC sub of the given name with the specified type.

void add_namespace

Add the current namespace to a sub declaration.

void add_pcc_arg

Adds a register or constant to the function arg list.

void add_pcc_result

Adds a register or constant to the function's return list.

void add_pcc_multi

Adds a :multi signature to the sub.

void add_pcc_sub

Sets the current sub in the given SymReg to the second SymReg.

void add_pcc_cc

Adds a continuation (?) to the current sub.

SymReg *mk_pasm_reg

Makes a SymReg representing a PASM register.

static char *_mk_fullname

Combines the namespace and name together, separated by a ::. If there's no namespace, the name is returned on its own.

The returned string must be free()d.

SymReg *mk_ident

Makes a new identifier.

SymReg *mk_ident_ur

Creates and returns a SymReg representing a unique (non-volatile) register.

static SymReg *mk_pmc_const_2

Makes a constant PMC and inserts instructions to access it.

SymReg *mk_const_ident

Makes a new identifier constant with value val.

SymReg *_mk_const

Makes a new constant (internal use only).

SymReg *mk_const

Makes a new constant (and populates the cache of global symbols).

static char *add_ns

Adds a namespace to the current sub.

SymReg *_mk_address

Makes a new address (internal use only).

SymReg *mk_sub_label

Makes and stores a new address label for a sub. The label gets a fixup entry.

SymReg *mk_sub_address

Makes a symbol for a label. The symbol gets a fixup entry.

SymReg *mk_local_label

Makes a local symbol, giving it no fixup entry.

SymReg *mk_label_address

Makes a new label address.

SymReg *dup_sym

Links keys to a keys structure = SymReg

we might have

what op type pbc.c:build_key() -------------------------------------------------- int const _kic VTCONST no int reg _ki VTREG no str const _kc VTCONST yes str reg _kc VTREG yes

 "key" ';' "key" _kc           -> (list of above)   yes
 "key" ';' $I0   _kc  VTREGKEY -> (list of above)   yes

 The information about which reg should be passed to build_key() is
 in the instruction.

 A key containing a variable has a special flag VTREGKEY
 because this key must be considered for life analysis for
 all the chain members, that are variables.

 An instruction with a keychain looks like this

 e.h. set I0, P["abc";0;I1]

 ins->r[2]  = keychain  'K'
 keychain->nextkey = SymReg(VTCONST) "abc"
             ->nextkey = SymReg(VTCONST) 0
                ->nextkey = SymReg(VTREG), ...->reg = VTVAR I1
                   ->nextkey = 0

 We can't use the consts or keys in the chain directly,
 because a different usage would destroy the ->nextkey pointers
 so these are all copies.
 XXX and currently not freed
SymReg *link_keys

Links keys together in a keychain.

void free_sym

Frees all memory of the specified SymReg. If it has a pcc_sub_t entry, frees all memory of that structure as well.

void create_symhash

Creates a symbol hash table with space for 16 entries.

static void resize_symhash

Resizes a symbol hash table.

void _store_symreg

Stores a symbol in the hash (internal use only).

void store_symreg

Stores a symbol in the hash.

SymReg *_get_sym

Fetches a symbol from the hash (internal use only).

SymReg *get_sym

Gets a symbol from the current unit's symbol table.

SymReg *_find_sym

Find a symbol hash or ghash (internal use only);

SymReg *find_sym

Finds a symbol hash or ghash in the current unit, if it exists. Otherwise returns NULL.

void clear_sym_hash

Frees all memory of the symbols in the specified hash table.

void debug_dump_sym_hash

Prints all identifiers in the specified hash table to stderr.

void clear_locals

Deletes all local symbols and clears life info from the given IMC_Unit.

void clear_globals

Clears global symbols.

unsigned int hash_str

Computes the hash value for the string argument.