예제 #1
0
        public void Visit(AST.LocalFunctionStatement statement)
        {
            int funcStackPos = State.stackPosition;
            State.bytecodes.Add(VirtualMachine.OpCodes.MakeLOADK(State.AddConstant(null)));
            State.bytecodes.Add(VirtualMachine.OpCodes.MakeCLOSEVAR(1));
            State.stackVars[statement.Name] = State.stackPosition; State.stackPosition++;
            State.newClosedVars[statement.Name] = State.closureStackPosition; State.closureStackPosition++;

            FunctionCompiler funcCompiler = new FunctionCompiler(State, statement.Body, false);

            VirtualMachine.Function function = new VirtualMachine.Function(funcCompiler.State.bytecodes.ToArray(), funcCompiler.State.constants.ToArray(), Guid.NewGuid().ToString(),
                                                                           funcCompiler.State.childFunctions, funcCompiler.State.positions, statement.Name);
            State.childFunctions.Add(function);

            State.bytecodes.Add(VirtualMachine.OpCodes.MakeCLOSURE(State.AddConstant(function.Id)));
            State.stackPosition++;

            State.bytecodes.Add(VirtualMachine.OpCodes.MakePUTSTACK(State.stackPosition - funcStackPos));
            State.stackPosition--;
        }
예제 #2
0
        public void Visit(AST.FunctionStatement statement)
        {
            bool isSelfFunction = statement.SelfName != null;
            bool isGlobal = !isSelfFunction && statement.FieldNames.Count == 0;

            if (!isGlobal)
            {
                // Get the table
                AST.Expression expr = new AST.NameExpression(statement.MainName);

                if (statement.FieldNames.Count > 0)
                {
                    foreach (String field in statement.FieldNames.GetRange(0, statement.FieldNames.Count - 1))
                    {
                        expr = new AST.LookupExpression(expr, field);
                    }

                    if (isSelfFunction)
                    {
                        expr = new AST.LookupExpression(expr, statement.FieldNames.Last());
                    }
                }

                expr.Visit(new ExpressionCompiler(State, 1));

                // Get the key
                if (isSelfFunction)
                {
                    State.bytecodes.Add(VirtualMachine.OpCodes.MakeLOADK(State.AddConstant(statement.SelfName))); State.stackPosition++;
                }
                else
                {
                    State.bytecodes.Add(VirtualMachine.OpCodes.MakeLOADK(State.AddConstant(statement.FieldNames.Last()))); State.stackPosition++;
                }
            }

            FunctionCompiler funcCompiler = new FunctionCompiler(State, statement.Body, isSelfFunction);

            VirtualMachine.Function function = new VirtualMachine.Function(funcCompiler.State.bytecodes.ToArray(), funcCompiler.State.constants.ToArray(), Guid.NewGuid().ToString(),
                                                                           funcCompiler.State.childFunctions, funcCompiler.State.positions, statement.MainName);
            State.childFunctions.Add(function);

            State.bytecodes.Add(VirtualMachine.OpCodes.MakeCLOSURE(State.AddConstant(function.Id))); State.stackPosition++;

            if (!isGlobal)
            {
                State.bytecodes.Add(VirtualMachine.OpCodes.PUTTABLE); State.stackPosition -= 3;
            }
            else
            {
                if (State.stackVars.ContainsKey(statement.MainName))
                {
                    State.bytecodes.Add(VirtualMachine.OpCodes.MakePUTSTACK(State.stackPosition - State.stackVars[statement.MainName])); State.stackPosition--;
                }
                else
                {
                    State.bytecodes.Add(VirtualMachine.OpCodes.MakePUTGLOBAL(State.AddConstant(statement.MainName))); State.stackPosition--;
                }
            }
        }
예제 #3
0
        public void Visit(AST.FunctionExpression expression)
        {
            FunctionCompiler funcCompiler = new FunctionCompiler(State, expression.Body, false);

            VirtualMachine.Function function = new VirtualMachine.Function(funcCompiler.State.bytecodes.ToArray(), funcCompiler.State.constants.ToArray(), Guid.NewGuid().ToString(),
                                                                           funcCompiler.State.childFunctions, funcCompiler.State.positions, "anon");
            State.childFunctions.Add(function);

            State.bytecodes.Add(VirtualMachine.OpCodes.MakeCLOSURE(State.AddConstant(function.Id)));

            State.stackPosition++;
        }