internal sealed override MSA.Expression /*!*/ TransformRead(AstGenerator /*!*/ gen) { string debugString = (IsSingletonDeclaration) ? "SINGLETON" : ((this is ClassDefinition) ? "CLASS" : "MODULE") + " " + QualifiedName.Name; ScopeBuilder outerLocals = gen.CurrentScope; // definition needs to take place outside the defined lexical scope: var definition = MakeDefinitionExpression(gen); var selfVariable = outerLocals.DefineHiddenVariable("#module", typeof(RubyModule)); var parentScope = gen.CurrentScopeVariable; // inner locals: ScopeBuilder scope = DefineLocals(); var scopeVariable = scope.DefineHiddenVariable("#scope", typeof(RubyScope)); gen.EnterModuleDefinition( scope, selfVariable, scopeVariable, IsSingletonDeclaration ); // transform body: MSA.Expression transformedBody = Body.TransformRead(gen); // outer local: MSA.Expression resultVariable = outerLocals.DefineHiddenVariable("#result", transformedBody.Type); // begin with new scope // self = DefineModule/Class(... parent scope here ...) // <body> // end MSA.Expression result = new AstBlock { gen.DebugMarker(debugString), Ast.Assign(selfVariable, definition), scope.CreateScope( scopeVariable, Methods.CreateModuleScope.OpCall( scope.MakeLocalsStorage(), scope.GetVariableNamesExpression(), parentScope, selfVariable ), Ast.Block( Ast.Assign(resultVariable, transformedBody), AstUtils.Empty() ) ), gen.DebugMarker("END OF " + debugString), resultVariable }; gen.LeaveModuleDefinition(); return(result); }