Beispiel #1
0
        public override Node visitFunctionDeclaration(JuliarParser.FunctionDeclarationContext ctx)
        {
            string           funcName         = ctx.funcName().Text;
            FunctionDeclNode functionDeclNode = new FunctionDeclNode(funcName, new List <Node>());

            callStack.Push(funcName);
            symbolTable.addLevel(funcName + "_" + functionDeclCount++);

            new IterateOverContext(this, ctx, this, functionDeclNode);

            callStack.Pop();
            popScope(functionDeclNode.Type);

            functionNodeMap[funcName] = functionDeclNode;

            return(functionDeclNode);
        }
Beispiel #2
0
        public override Node visitSubtract(JuliarParser.SubtractContext ctx)
        {
            string text = ctx.subtraction().Text;

            if ("subtract".Equals(text) || "-".Equals(text))
            {
                if (ctx.types().size() == 2)
                {
                    BinaryNode node = new BinaryNode();
                    try
                    {
                        /*
                         *                  Node n = node.makeNode(
                         *                              Operation.subtract,
                         *                              ctx.types(0).accept(this),
                         *                              ctx.types(1).accept(this));
                         *                  n.addInst( funcContextStack, n);
                         */
                    }
                    catch (Exception ex)
                    {
                        JuliarLogger.log(ex.Message, ex);
                    }
                }

                if (ctx.types().size() > 2)
                {
                    IList <IntegralTypeNode> data = new List <IntegralTypeNode>();

                    for (int i = 0; i < ctx.types().size(); i++)
                    {
                        data.Add((IntegralTypeNode)ctx.types(i).accept(this));
                    }
                    AggregateNode aggregateNode = new AggregateNode(Operation.subtract, data);

                    FunctionDeclNode functionDeclNode = (FunctionDeclNode)funcContextStack.Peek();
                    functionDeclNode.addInst(aggregateNode);
                }
            }
            return(null);
        }
        public static IList <Node> evalFunctionCall(Node node, ActivationFrameStack activationFrame, string mainFunctionName, IDictionary <string, Node> functionNodeMap, Interpreter callback)
        {
            FunctionCallNode functionCallNode = (FunctionCallNode)node;
            string           functionToCall   = functionCallNode.functionName();

            //ActivationFrame evalFrame = activationFrameStack.pop();
            bool isPrimitive = EvaluatePrimitives.evalIfPrimitive(node, activationFrame.peek(), callback);

            //activationFrameStack.push( evalFrame );
            if (isPrimitive)
            {
                return(new List <>());
            }

            // main should only be called from the compliationUnit
            if (functionCallNode.Equals(mainFunctionName))
            {
                return(new List <>());
            }

            FunctionDeclNode functionDeclNode = (FunctionDeclNode)functionNodeMap[functionToCall];

            if (functionDeclNode != null)
            {
                ActivationFrame frame = new ActivationFrame();
                frame.frameName = functionToCall;

                IList <VariableNode>            sourceVariables = new List <VariableNode>();
                IList <VariableDeclarationNode> targetVariables = new List <VariableDeclarationNode>();

                foreach (Node v in node.Instructions)
                {
                    if (v is VariableNode)
                    {
                        sourceVariables.Add((VariableNode)v);
                    }
                }

                foreach (Node v in functionDeclNode.Instructions)
                {
                    if (v is VariableDeclarationNode)
                    {
                        targetVariables.Add((VariableDeclarationNode)v);
                    }
                }

                if (sourceVariables.Count != targetVariables.Count)
                {
                    throw new Exception("Source and target variable count do not match");
                }

                // since the function that is getting called can reference the variable using the
                // formal parameters of the function this code will match the calling functions data
                // with the target calling functions variable name.
                for (int i = 0; i < sourceVariables.Count; i++)
                {
                    VariableNode variableNode = (VariableNode)targetVariables[0].Instructions[1];
                    if (variableNode.integralTypeNode == sourceVariables[i].integralTypeNode)
                    {
                        frame.variableSet[variableNode.variableName] = activationFrame.peek().variableSet[sourceVariables[i].variableName];
                    }
                    else
                    {
                        throw new Exception("data types are not the same");
                    }
                }

                activationFrame.push(frame);


                IList <Node> statements = getFunctionStatements(functionDeclNode.Instructions);
                callback.execute(statements);
                activationFrame.pop();

                //activationFrame.push(frame);
                //execute(functionDeclNode.getInstructions());

                return(new List <Node>());
            }
            else
            {
                FinalNode primitiveArg = new FinalNode();
                primitiveArg.DataString = functionToCall;
                PrimitiveNode primitiveNode = new PrimitiveNode();
                primitiveNode.addInst(primitiveArg);

                foreach (Node primArgs in node.Instructions)
                {
                    if (primArgs is VariableNode || primArgs is IntegralTypeNode)
                    {
                        primitiveNode.addInst(primArgs);
                    }
                }

                return(EvaluatePrimitives.evalPrimitives(primitiveNode, activationFrame.peek(), callback));
            }
        }