Example #1
0
        public override void VisitFor(ForStatement forStatement)
        {
            Visit(forStatement.From);
            Program.Add(new Assignment(forStatement.ForVariable.Name, ExpressionStack.Pop()));
            var forBegin    = NewLabel;
            var forEnd      = NewLabel;
            var forVariable = new Identifier(forStatement.ForVariable.Name);

            Visit(forStatement.To);
            var forTo = ExpressionStack.Pop();
            var check = new ConditionalGoto(
                forEnd,
                new BinaryOperation(forVariable, Operation.Greater, forTo))
            {
                Label = forBegin
            };

            Program.Add(check);
            Visit(forStatement.Body);
            Program.Add(Assignment.Increment(forVariable.Name));
            Program.Add(new Goto(forBegin));
            Program.Add(new NoOperation(forEnd));
        }
 protected bool Equals(ConditionalGoto other)
 {
     return(base.Equals(other) && Equals(Condition, other.Condition));
 }
Example #3
0
        public List <ThreeAddressCommand> transformToThreeAddressCode()
        {
            var res = new List <ThreeAddressCommand>();

            var done  = new HashSet <BasicBlock>();
            var stack = new Stack <BasicBlock>();

            stack.Push(getBlockById(GetMinBlockId()));

            BasicBlock cur = null;

            while (done.Count < this.GetCount())
            {
                cur = stack.Pop();
                done.Add(cur);

                foreach (var c in cur.Commands)
                {
                    res.Add(c);
                }

                switch (cur.OutputBlocks.Count)
                {
                case 0:
                    continue;

                case 1:
                    BasicBlock outBlock = getBlockById(cur.OutputBlocks[0]);
                    if (!done.Contains(outBlock) && !stack.Contains(outBlock))
                    {
                        stack.Push(outBlock);
                    }
                    break;

                case 2:
                    int             lastStatementIndex = cur.Commands.Count - 1;
                    ConditionalGoto lastStatement      = (ConditionalGoto)cur.Commands[lastStatementIndex];

                    BasicBlock outFirst  = getBlockById(cur.OutputBlocks[0]);
                    BasicBlock outSecond = getBlockById(cur.OutputBlocks[1]);

                    string labelFirst  = outFirst.Commands[0].Label;
                    string labelSecond = outSecond.Commands[0].Label;
                    string gotoLabel   = lastStatement.GotoLabel;

                    if (gotoLabel == labelFirst)
                    {
                        BasicBlock t = outFirst;
                        outFirst  = outSecond;
                        outSecond = t;
                    }

                    int firstLastIndex             = outFirst.Commands.Count - 1;
                    ThreeAddressCommand secondLast = outFirst.Commands[firstLastIndex];
                    if ((secondLast is Goto) && !(secondLast is ConditionalGoto))
                    {
                        BasicBlock afterIfStatement = getBlockById(outFirst.OutputBlocks[0]);
                        if (!stack.Contains(afterIfStatement) && !done.Contains(afterIfStatement))
                        {
                            stack.Push(afterIfStatement);
                        }
                    }

                    if (!done.Contains(outSecond) && !stack.Contains(outSecond))
                    {
                        stack.Push(outSecond);
                    }

                    if (!done.Contains(outFirst) && !stack.Contains(outFirst))
                    {
                        stack.Push(outFirst);
                    }
                    break;

                default:
                    throw new Exception("There cannot be more than two output blocks!");
                }
            }

            return(res);
        }