Mercurial > hg-old > index.cgi
diff src/pseudo.c @ 90:6097cb1486f8
Added EXPORT pseudo op
author | lost |
---|---|
date | Sat, 17 Jan 2009 05:07:45 +0000 |
parents | 033a328a10ae |
children | 83ba34ed11b3 |
line wrap: on
line diff
--- a/src/pseudo.c Sat Jan 17 04:38:32 2009 +0000 +++ b/src/pseudo.c Sat Jan 17 05:07:45 2009 +0000 @@ -721,6 +721,7 @@ s -> oblen = 0; s -> obsize = 0; s -> rl = NULL; + s -> exports = NULL; // parse options; only one "bss" if (opts && as -> passnum == 1) { @@ -784,3 +785,65 @@ lwasm_register_symbol(as, l, l -> sym, 0, SYMBOL_EXTERN); } + +OPFUNC(pseudo_export) +{ + lwasm_symbol_ent_t *se; + export_list_t *ex; + + if (as -> outformat != OUTPUT_OBJ) + { + register_error(as, l, 1, "Symbol exports only supported for obj target"); + return; + } + + if (as -> passnum == 1) + return; + + // the symbol better be defined at this point (pass 2) + // local symbols cannot be exported nor can "global" symbols + se = lwasm_find_symbol(as, l -> sym, -1); + if (!se) + { + register_error(as, l, 2, "Exported symbols must be fully defined within a section"); + return; + } + if (se -> sect == NULL) + { + register_error(as, l, 2, "Only non-local symbols within a section can be exported"); + return; + } + + if (se -> flags & SYMBOL_SET) + { + register_error(as, l, 2, "You cannot export symbols defined with SET"); + return; + } + + // if the symbol is not already a simple value, re-evaluate it + // and see if it becomes simple + + + if (se -> flags & SYMBOL_COMPLEX) + { + register_error(as, l, 2, "Exported symbols must be fully resolved on pass 2"); + return; + } + + // search for existing export + for (ex = se -> sect -> exports; ex; ex = ex -> next) + if (!strcmp(l -> sym, ex -> sym)) + break; + if (ex) + { + register_error(as, l, 2, "Symbol %s already exported", l -> sym); + return; + } + + // add an external reference + ex = lwasm_alloc(sizeof(export_list_t)); + ex -> next = se -> sect -> exports; + se -> sect -> exports = ex; + ex -> offset = se -> value; + ex -> sym = lwasm_strdup(se -> sym); +}