void PatternCompiler::visit(VariablePattern& pattern, int value) { // Assign to the variable if it isn't a throwaway. if (*pattern.name() != "_") { compiler_.compileAssignment(pattern.pos(), pattern.resolved(), value, true); } // Compile the inner pattern. if (!pattern.pattern().isNull()) { pattern.pattern()->accept(*this, value); } }
void ExprCompiler::compileParamField(PatternCompiler& compiler, gc<Pattern> param, int slot) { VariablePattern* variable = param->asVariablePattern(); if (variable != NULL) { // It's a variable, so compile its inner pattern. We don't worry about // the variable itself because the calling convention ensures its value // is already in the right slot. compiler.compile(variable->pattern(), slot); // If we closed over the parameter, then we don't want in a local slot, // we want it in the upvar, so create it and copy the value up. if (*variable->name() != "_" && variable->resolved()->scope() == NAME_CLOSURE) { write(variable->pos(), OP_SET_UPVAR, variable->resolved()->index(), slot, 1); } } else { // Not a variable, so just compile it normally. compiler.compile(param, slot); } }
void Resolver::resolveParam(gc<Pattern> param) { VariablePattern* variable = param->asVariablePattern(); if (variable != NULL) { // It's a variable, so resolve its inner pattern. if (!variable->pattern().isNull()) { scope_->resolve(*variable->pattern()); } } else { // Not a variable, so just resolve it normally. scope_->resolve(*param); } }
void Compiler::declareVariables(gc<Pattern> pattern, Module* module) { RecordPattern* record = pattern->asRecordPattern(); if (record != NULL) { for (int i = 0; i < record->fields().count(); i++) { declareVariables(record->fields()[i].value, module); } return; } VariablePattern* variable = pattern->asVariablePattern(); if (variable != NULL) { declareVariable(variable->pos(), variable->name(), module); if (!variable->pattern().isNull()) { declareVariables(variable->pattern(), module); } } }
void Scope::visit(VariablePattern& pattern, int dummy) { if (*pattern.name() != "_") { if (isTopLevel()) { // It's a top-level module variable. Since these are forward declared, // they should already exist. Just look up the existing one. int module = resolver_.compiler_.getModuleIndex(resolver_.module_); int index = resolver_.module_.findVariable(pattern.name()); if (index == -1) { resolver_.compiler_.reporter().error(pattern.pos(), "Variable '%s' is not defined.", pattern.name()->cString()); // Put a fake index in so we can continue and report more errors. index = 0; } pattern.setResolved(new ResolvedName(module, index)); } else { // Declaring a local variable, so create a slot for it. gc<ResolvedName> resolved = resolver_.makeLocal(pattern.pos(), pattern.name()); pattern.setResolved(resolved); } } if (!pattern.pattern().isNull()) { pattern.pattern()->accept(*this, dummy); } }