summaryrefslogtreecommitdiff
path: root/symbol.c
diff options
context:
space:
mode:
Diffstat (limited to 'symbol.c')
-rw-r--r--symbol.c37
1 files changed, 18 insertions, 19 deletions
diff --git a/symbol.c b/symbol.c
index 3cb8a9b..ad06203 100644
--- a/symbol.c
+++ b/symbol.c
@@ -23,17 +23,14 @@ getsym(Rune *name, int fresh)
Symtab *tab;
for(tab = getcurrentsymtab(); tab; tab = tab->chain){
for(int i = 0; i < tab->nsyms; i++){
- if(runestrcmp(tab->syms[i]->name, name) == 0){
- freesymtab(tab);
+ if(runestrcmp(tab->syms[i]->name, name) == 0)
return tab->syms[i];
- }
}
if(fresh)
break;
}
/* make sure to allocate in the most local scope if the symbol is not found */
- freesymtab(tab);
tab = getcurrentsymtab();
tab->nsyms++;
@@ -44,7 +41,6 @@ getsym(Rune *name, int fresh)
tab->syms[tab->nsyms-1]->setfn = nil;
tab->syms[tab->nsyms-1]->value = nil;
- freesymtab(tab);
return tab->syms[tab->nsyms-1];
}
@@ -56,10 +52,7 @@ newsymtab(Symtab *chain)
tab->syms = nil;
tab->io = globalIO();
tab->div = globalDIV();
- tab->refs = 1;
tab->chain = chain;
- if(chain)
- chain->refs++;
return tab;
}
@@ -80,7 +73,6 @@ dupsymtab(Symtab *tab)
{
Symtab *new = newsymtab(tab->chain);
memcpy(new, tab, sizeof(Symtab));
- new->refs = 1;
new->syms = emalloc(sizeof(Symbol*) * new->nsyms);
for(int i = 0; i < tab->nsyms; i++)
new->syms[i] = dupsymbol(tab->syms[i]);
@@ -92,10 +84,8 @@ freesymtab(Symtab *tab)
{
if(tab == nil)
return;
- if(tab->refs-- > 1)
- return;
- if(tab == globalsymtab)
+ if(tab == globalsymtab) /* Never free the global symtab */
return;
int i;
@@ -104,7 +94,6 @@ freesymtab(Symtab *tab)
freedatum(s->value);
free(s->name);
}
- freesymtab(tab->chain);
free(tab->syms);
free(tab);
}
@@ -162,6 +151,7 @@ pushdfnframe(Rune *code, Symtab *scope, Datum *lefto, Datum *righto, Array *left
incarrayref(right);
new->prev = td->currentdfn;
new->errorguards = nil;
+
td->currentdfn = new;
return new;
}
@@ -345,7 +335,19 @@ dupscope(Symtab *old)
if(!found){
new->nsyms++;
new->syms = erealloc(new->syms, sizeof(Symbol *) * new->nsyms);
- new->syms[new->nsyms-1] = dupsymbol(sym);
+ Symbol *s = dupsymbol(sym);
+ new->syms[new->nsyms-1] = s;
+ if(s->value){
+ switch(s->value->tag){
+ case FunctionTag:
+ s->value->func.scope = new;
+ break;
+ case MonadicOpTag:
+ case DyadicOpTag:
+ s->value->operator.scope = new;
+ break;
+ }
+ }
}
}
}
@@ -356,11 +358,8 @@ Symtab *
getcurrentsymtab(void)
{
DfnFrame *dfn = getcurrentdfn();
- if(dfn == nil){
- globalsymtab->refs++;
+ if(dfn == nil)
return globalsymtab;
- }else{
- dfn->symtab->refs++;
+ else
return dfn->symtab;
- }
} \ No newline at end of file