void declare_as_global(char *label, char *special) { union label *lptr; if (islocal(label)) { nasm_error(ERR_NONFATAL, "attempt to declare local symbol `%s' as" " global", label); return; } lptr = find_label(label, 1); if (!lptr) return; switch (lptr->defn.is_global & TYPE_MASK) { case NOT_DEFINED_YET: lptr->defn.is_global = GLOBAL_PLACEHOLDER; lptr->defn.special = special ? perm_copy(special) : NULL; break; case GLOBAL_PLACEHOLDER: /* already done: silently ignore */ case GLOBAL_SYMBOL: break; case LOCAL_SYMBOL: if (!(lptr->defn.is_global & EXTERN_BIT)) { nasm_error(ERR_WARNING, "symbol `%s': GLOBAL directive " "after symbol definition is an experimental feature", label); lptr->defn.is_global = GLOBAL_SYMBOL; } break; } }
PRIVATE void reopen_input(char *name) { char *p; FILE *fp; static char name_buf[128]; strcpy(name_buf, name); fp = freopen(name_buf, "r", yyin); if (fp == NULL) { p = name_buf + strlen(name_buf); while (p > name_buf && p[-1] != DIRSEP) p--; if (strchr(p, '.') == NULL) { strcat(name_buf, ".tex"); fp = freopen(name_buf, "r", yyin); } } if (fp == NULL) { fprintf(errout, "fuzz: can't read %s\n", name_buf); exit(2); } file_name = perm_copy(name_buf); }
void declare_as_global (char *label, char *special, efunc error) { union label *lptr; if (islocal(label)) { error(ERR_NONFATAL, "attempt to declare local symbol `%s' as" " global", label); return; } lptr = find_label (label, 1); switch (lptr->defn.is_global & TYPE_MASK) { case NOT_DEFINED_YET: lptr->defn.is_global = GLOBAL_PLACEHOLDER; lptr->defn.special = special ? perm_copy(special, "") : NULL; break; case GLOBAL_PLACEHOLDER: /* already done: silently ignore */ case GLOBAL_SYMBOL: break; case LOCAL_SYMBOL: if (!lptr->defn.is_global & EXTERN_BIT) error(ERR_NONFATAL, "symbol `%s': GLOBAL directive must" " appear before symbol definition", label); break; } }
/* * Set a prefix or suffix */ void set_label_mangle(enum mangle_index which, const char *what) { if (mangle_string_set[which]) return; /* Once set, do not change */ mangle_strings[which] = perm_copy(what); mangle_string_set[which] = true; }
static bool declare_label_lptr(union label *lptr, enum label_type type, const char *special) { if (special && !special[0]) special = NULL; if (lptr->defn.type == type || (pass0 == 0 && lptr->defn.type == LBL_LOCAL)) { lptr->defn.type = type; if (special) { if (!lptr->defn.special) lptr->defn.special = perm_copy(special); else if (nasm_stricmp(lptr->defn.special, special)) nasm_error(ERR_NONFATAL, "symbol `%s' has inconsistent attributes `%s' and `%s'", lptr->defn.label, lptr->defn.special, special); } return true; } /* EXTERN can be replaced with GLOBAL or COMMON */ if (lptr->defn.type == LBL_EXTERN && (type == LBL_GLOBAL || type == LBL_COMMON)) { lptr->defn.type = type; /* Override special unconditionally */ if (special) lptr->defn.special = perm_copy(special); return true; } /* GLOBAL or COMMON ignore subsequent EXTERN */ if ((lptr->defn.type == LBL_GLOBAL || lptr->defn.type == LBL_COMMON) && type == LBL_EXTERN) { if (!lptr->defn.special) lptr->defn.special = perm_copy(special); return false; /* Don't call define_label() after this! */ } nasm_error(ERR_NONFATAL, "symbol `%s' declared both as %s and %s", lptr->defn.label, types[lptr->defn.type], types[type]); return false; }
/* * Internal routine: finds the `union label' corresponding to the * given label name. Creates a new one, if it isn't found, and if * `create' is TRUE. */ static union label *find_label(char *label, int create) { int hash = 0; char *p, *prev; int prevlen; union label *lptr; if (islocal(label)) prev = prevlabel; else prev = ""; prevlen = strlen(prev); p = prev; while (*p) hash += *p++; p = label; while (*p) hash += *p++; hash %= LABEL_HASHES; lptr = ltab[hash]; while (lptr->admin.movingon != END_LIST) { if (lptr->admin.movingon == END_BLOCK) { lptr = lptr->admin.next; if (!lptr) break; } if (!strncmp(lptr->defn.label, prev, prevlen) && !strcmp(lptr->defn.label + prevlen, label)) return lptr; lptr++; } if (create) { if (lfree[hash]->admin.movingon == END_BLOCK) { /* * must allocate a new block */ lfree[hash]->admin.next = (union label *)nasm_malloc(LBLK_SIZE); lfree[hash] = lfree[hash]->admin.next; init_block(lfree[hash]); } lfree[hash]->admin.movingon = BOGUS_VALUE; lfree[hash]->defn.label = perm_copy(prev, label); lfree[hash]->defn.special = NULL; lfree[hash]->defn.is_global = NOT_DEFINED_YET; return lfree[hash]++; } else return NULL; }
/* * Internal routine: finds the `union label' corresponding to the * given label name. Creates a new one, if it isn't found, and if * `create' is true. */ static union label *find_label(char *label, int create) { char *prev; int prevlen, len; union label *lptr, **lpp; char label_str[IDLEN_MAX]; struct hash_insert ip; if (islocal(label)) { prev = prevlabel; prevlen = strlen(prev); len = strlen(label); if (prevlen + len >= IDLEN_MAX) { nasm_error(ERR_NONFATAL, "identifier length exceed %i bytes", IDLEN_MAX); return NULL; } memcpy(label_str, prev, prevlen); memcpy(label_str+prevlen, label, len+1); label = label_str; } else { prev = ""; prevlen = 0; } lpp = (union label **) hash_find(<ab, label, &ip); lptr = lpp ? *lpp : NULL; if (lptr || !create) return lptr; /* Create a new label... */ if (lfree->admin.movingon == END_BLOCK) { /* * must allocate a new block */ lfree->admin.next = (union label *)nasm_malloc(LBLK_SIZE); lfree = lfree->admin.next; init_block(lfree); } lfree->admin.movingon = BOGUS_VALUE; lfree->defn.label = perm_copy(label); lfree->defn.special = NULL; lfree->defn.is_global = NOT_DEFINED_YET; hash_add(&ip, lfree->defn.label, lfree); return lfree++; }
/* * Internal routine: finds the `union label' corresponding to the * given label name. Creates a new one, if it isn't found, and if * `create' is true. */ static union label *find_label(const char *label, bool create, bool *created) { union label *lptr, **lpp; char *label_str = NULL; struct hash_insert ip; nasm_assert(label != NULL); if (islocal(label)) label = label_str = nasm_strcat(prevlabel, label); lpp = (union label **) hash_find(<ab, label, &ip); lptr = lpp ? *lpp : NULL; if (lptr || !create) { if (created) *created = false; return lptr; } /* Create a new label... */ if (lfree->admin.movingon == END_BLOCK) { /* * must allocate a new block */ lfree->admin.next = nasm_malloc(LBLK_SIZE); lfree = lfree->admin.next; init_block(lfree); } if (created) *created = true; nasm_zero(*lfree); lfree->defn.label = perm_copy(label); lfree->defn.subsection = NO_SEG; if (label_str) nasm_free(label_str); hash_add(&ip, lfree->defn.label, lfree); return lfree++; }
/* open_prelude -- find and open the prelude file as yyin */ PRIVATE void open_prelude(void) { char *fn; extern char *envname; extern char *getenv(); if (pflag) fn = prelude; else { fn = getenv(envname); if (fn == NULL) { fn = prelude; } } if (fn == NULL || (yyin = fopen(fn, "r")) == NULL) { (void) fprintf(errout, "fuzz: can't read prelude file %s\n", fn); exit(2); } file_name = perm_copy(fn); }