Skip to content

Commit

Permalink
issue #35 fixes and updated test results
Browse files Browse the repository at this point in the history
  • Loading branch information
dibyendumajumdar committed Oct 2, 2020
1 parent 6f1b448 commit 7b2af91
Show file tree
Hide file tree
Showing 3 changed files with 154 additions and 24 deletions.
8 changes: 7 additions & 1 deletion src/linearizer.c
Original file line number Diff line number Diff line change
Expand Up @@ -2266,9 +2266,15 @@ static void output_pseudo(struct pseudo *pseudo, buffer_t *mb)
break;
}
case SYM_UPVALUE: {
raviX_buffer_add_fstring(mb, "Upval(%u, Proc%%%d, %s)", pseudo->regnum,
if (pseudo->symbol->upvalue.target_variable->symbol_type == SYM_LOCAL) {
raviX_buffer_add_fstring(mb, "Upval(%u, Proc%%%d, %s)", pseudo->regnum,
pseudo->symbol->upvalue.target_variable->variable.block->function->function_expr.proc_id,
pseudo->symbol->upvalue.target_variable->variable.var_name->str);
}
else if (pseudo->symbol->upvalue.target_variable->symbol_type == SYM_ENV) {
raviX_buffer_add_fstring(mb, "Upval(%s)",
pseudo->symbol->upvalue.target_variable->variable.var_name->str);
}
break;
}
case SYM_GLOBAL: {
Expand Down
46 changes: 27 additions & 19 deletions src/parser.c
Original file line number Diff line number Diff line change
Expand Up @@ -311,6 +311,32 @@ static void add_upvalue_in_levels_upto(struct parser_state *parser, struct ast_n
}
}

/**
* Adds an upvalue for _ENV.
*/
static void add_upvalue_for_ENV(struct parser_state *parser)
{
// We have to check whether we need to add upvalue for _ENV
bool is_local = false;
struct lua_symbol *env = search_for_variable(parser, parser->container->_ENV, &is_local);
if (env == NULL) {
// Create special upvalue symbol _ENV - so that upvalues can reference it
struct lua_symbol *env = raviX_allocator_allocate(&parser->container->symbol_allocator, 0);
env->symbol_type = SYM_ENV;
env->variable.var_name = parser->container->_ENV;
env->variable.block = NULL;
set_type(&env->variable.value_type, RAVI_TTABLE); // _ENV is by default a table
// First time we encounter the global _ENV we add as upvalue
add_upvalue_in_levels_upto(parser, parser->current_function, NULL, env);
} else if (env->symbol_type == SYM_UPVALUE && env->upvalue.target_function != parser->current_function) {
// We found an upvalue but it is not at the same level
// Ensure all levels have the upvalue
// Note that if the upvalue refers to special _ENV symbol then target function will be NULL
add_upvalue_in_levels_upto(parser, parser->current_function, env->upvalue.target_function,
env->upvalue.target_variable);
}
}

/* Creates a symbol reference to the name; the returned symbol reference
* may be local, upvalue or global.
*/
Expand Down Expand Up @@ -350,25 +376,7 @@ static struct ast_node *new_symbol_reference(struct parser_state *parser, const
// We don't add globals to any scope so that they are
// always looked up
symbol = global;
// We have to check whether we need to add upvalue for _ENV
bool is_local = false;
struct lua_symbol *env = search_for_variable(parser, parser->container->_ENV, &is_local);
if (env == NULL) {
struct lua_symbol *env = raviX_allocator_allocate(&parser->container->symbol_allocator, 0);
env->symbol_type = SYM_ENV;
env->variable.var_name = varname;
env->variable.block = NULL;
set_type(&env->variable.value_type, RAVI_TTABLE); // _ENV is by default a table
// First time we encounter the global _ENV we add as upvalue
add_upvalue_in_levels_upto(parser, parser->current_function, NULL, env);
}
else if (env->symbol_type == SYM_UPVALUE && symbol->upvalue.target_function != parser->current_function) {
// We found an upvalue but it is not at the same level
// Ensure all levels have the upvalue
// Note that if the upvalue refers to special _ENV symbol then target function will be NULL
add_upvalue_in_levels_upto(parser, parser->current_function, symbol->upvalue.target_function,
symbol->upvalue.target_variable);
}
add_upvalue_for_ENV(parser); // Since we have a global reference we need to add upvalue for _ENV
}
struct ast_node *symbol_expr = allocate_expr_ast_node(parser, EXPR_SYMBOL);
symbol_expr->symbol_expr.type = symbol->variable.value_type;
Expand Down
Loading

0 comments on commit 7b2af91

Please sign in to comment.