Esempio n. 1
0
        /// <summary cref="IBackendCodeGenerator.GenerateCode(UnconditionalBranch)"/>
        public void GenerateCode(UnconditionalBranch branch)
        {
            using var command = BeginCommand(PTXInstructions.BranchOperation);
            var targetLabel = blockLookup[branch.Target];

            command.AppendLabel(targetLabel);
        }
Esempio n. 2
0
        // 10: brfalse    14
        // 11: ldstr      "pos"
        // 12: call       System.Void System.Console::WriteLine(System.String)
        // 13: br         16
        //
        // 14: ldstr      "pos"
        // 15: call       System.Void System.Console::WriteLine(System.String)
        // 16: ret
        public void VisitBranch(ConditionalBranch conditional)
        {
            if (m_offset < 0)
            {
                // If it's a forward conditional branch,
                if (conditional.Target.Index > conditional.Index)
                {
                    // and the not-taken case ends with a forward unconditional branch,
                    UnconditionalBranch unconditional = m_info.Instructions[conditional.Target.Index - 1] as UnconditionalBranch;
                    if (unconditional != null && unconditional.Target.Index > unconditional.Index)
                    {
                        // then we have a contruct that resembles an if statement so we'll
                        // compare the code in the two branches.
                        int num1 = unconditional.Index - conditional.Index - 1;
                        int num2 = unconditional.Target.Index - conditional.Target.Index;
                        Log.DebugLine(this, "not taken at {0:X2} has {1} instructions, taken has {2} instructions", conditional.Untyped.Offset, num1, num2);

                        if (num1 == num2 && conditional.Target.Index + num2 <= m_info.Instructions.Length)
                        {
                            if (DoMatches(conditional.Index + 1, conditional.Target.Index, num1))
                            {
                                Log.DebugLine(this, "matches");
                                m_offset = conditional.Untyped.Offset;
                            }
                        }
                    }
                }
            }
        }
 /// <summary cref="IValueVisitor.Visit(UnconditionalBranch)"/>
 public void Visit(UnconditionalBranch branch)
 {
     using (var command = BeginCommand(PTXInstructions.BranchOperation))
     {
         var targetLabel = blockLookup[branch.Target];
         command.AppendLabel(targetLabel);
     }
 }
Esempio n. 4
0
        ////////////////////////////////////////////////////////////////////////////
        public override Statement visit(ConditionalBranch s)
        {
            ControlStatement result = s;

//            var ne = si.fae.visit(this);
            ProgramVariable oc = s.condition;
            ProgramVariable nc = s.condition;

            EqualityDatabase.Representative rep = database.tryGetRepresentative(s.condition);

            if (rep != null)
            {
                Expression ne = rep.expression;

                if (ne is LiteralExpression)
                {
                    if (((ne as LiteralExpression).value as BooleanValue).value)
                    {
                        result = new UnconditionalBranch(s.trueBranch.source, s.trueBranch.target);
                    }
                    else
                    {
                        result = new UnconditionalBranch(s.falseBranch.source, s.falseBranch.target);
                    }
                    nc = null;
                }
                else
                {
                    if (ne is ProgramVariableExpression)
                    {
                        s.condition = (ne as ProgramVariableExpression).programVariable;
                        nc          = s.condition;
                    }
                    else
                    {
                        nc =
                            (EqualityDatabase.getCompactNegationIfBoolean(ne) as ProgramVariableExpression).
                            programVariable;

                        result = new ConditionalBranch(
                            database.statementId.basicBlock,
                            nc,
                            s.falseBranch.target,
                            s.trueBranch.target
                            );
                    }
                }
            }

            if (nc != null && !database.conditionVariableIndices.ContainsKey(nc.name))
            {
                database.addConditionVariable(nc);
            }

            return(result);
        }
Esempio n. 5
0
        /// <summary cref="IBackendCodeGenerator.GenerateCode(UnconditionalBranch)"/>
        public void GenerateCode(UnconditionalBranch branch)
        {
            if (Schedule.IsImplicitSuccessor(branch.BasicBlock, branch.Target))
            {
                return;
            }

            using var command = BeginCommand(PTXInstructions.BranchOperation);
            var targetLabel = blockLookup[branch.Target];

            command.AppendLabel(targetLabel);
        }
Esempio n. 6
0
        private List <BasicBlock> DoGetDeadBlocks(TypedInstructionCollection instructions, Dictionary <int, BasicBlock> blocks, List <BasicBlock> reachable)
        {
            List <BasicBlock> deadBlocks = new List <BasicBlock>();

            // If the block isn't the target of a branch and it's preceded by an end
            // instruction it's dead code. This can happen if a catch block throws.
            foreach (KeyValuePair <int, BasicBlock> entry in blocks)
            {
                BasicBlock b = entry.Value;
                int        i = b.First.Index;

                if (m_branchTargets.IndexOf(i) < 0)
                {
                    if (instructions.TryCatchCollection.HandlerStartsAt(i) == null)
                    {
                        if (i > 0 && (instructions[i - 1] is End || instructions[i - 1] is UnconditionalBranch))
                        {
                            deadBlocks.Add(b);
                        }
                    }
                }
            }

            // If a leave is dead code then its target is dead as well.
            List <BasicBlock> deaderBlocks = new List <BasicBlock>();

            foreach (BasicBlock b in deadBlocks)
            {
                if (b.Length > 0)
                {
                    for (int i = b.First.Index; i <= b.Last.Index; ++i)
                    {
                        if (instructions[i].Untyped.OpCode.Code == Code.Leave || instructions[i].Untyped.OpCode.Code == Code.Leave_S)
                        {
                            UnconditionalBranch branch = (UnconditionalBranch)instructions[i];
                            if (reachable.IndexOf(blocks[branch.Target.Index]) < 0 && deaderBlocks.IndexOf(blocks[branch.Target.Index]) < 0)
                            {
                                deaderBlocks.Add(blocks[branch.Target.Index]);
                            }
                        }
                    }
                }
            }
            deadBlocks.AddRange(deaderBlocks);

            return(deadBlocks);
        }
Esempio n. 7
0
        // 08: switch     26 35 53 44 44 44
        // 21: br         53
        // 26: ldstr      "zero"
        // 2B: call       System.Void System.Console::WriteLine(System.String)
        // 30: br         53
        // 35: ldstr      "zero"
        // 3A: call       System.Void System.Console::WriteLine(System.String)
        // 3F: br         53
        // 44: ldstr      "zero"
        // 49: call       System.Void System.Console::WriteLine(System.String)
        // 4E: br         53
        // 53: ret
        public void VisitSwitch(Switch swtch)
        {
            if (m_offset < 0)
            {
                UnconditionalBranch unconditional = m_info.Instructions[swtch.Index + 1] as UnconditionalBranch;
                if (unconditional != null && unconditional.Target.Index > unconditional.Index)
                {
                    TypedInstruction last = unconditional.Target;

                    List <TypedInstruction> cases = new List <TypedInstruction>();
                    foreach (TypedInstruction ti in swtch.Targets)
                    {
                        if (ti.Index != last.Index)
                        {
                            if (cases.IndexOf(ti) < 0)
                            {
                                cases.Add(ti);
                            }
                        }
                    }
                    cases.Add(last);

                    cases.Sort((lhs, rhs) => lhs.Index.CompareTo(rhs.Index));

                    for (int i = 0; i < cases.Count - 1 && m_offset < 0; ++i)
                    {
                        TypedInstruction ti1 = cases[i];
                        int len1             = cases[i + 1].Index - ti1.Index - 1;

                        for (int j = i + 1; j < cases.Count - 1 && m_offset < 0; ++j)
                        {
                            TypedInstruction ti2 = cases[j];
                            int len2             = cases[j + 1].Index - ti2.Index - 1;
                            if (len1 == len2)
                            {
                                if (DoMatches(ti1.Index, ti2.Index, len1))
                                {
                                    Log.DebugLine(this, "{0:X2} matches {1:X2}", ti1.Untyped.Offset, ti2.Untyped.Offset);
                                    m_offset = swtch.Untyped.Offset;
                                }
                            }
                        }
                    }
                }
            }
        }
        /// <summary cref="IBackendCodeGenerator.GenerateCode(UnconditionalBranch)"/>
        public void GenerateCode(UnconditionalBranch branch)
        {
            if (Schedule.IsImplicitSuccessor(branch.BasicBlock, branch.Target))
            {
                return;
            }

            // Determine the branch operation to be used
            var branchOperation = Uniforms.IsUniform(branch)
                ? PTXInstructions.UniformBranchOperation
                : PTXInstructions.BranchOperation;

            using var command = BeginCommand(branchOperation);
            var targetLabel = blockLookup[branch.Target];

            command.AppendLabel(targetLabel);
        }
Esempio n. 9
0
        private int DoFindBranch(int index, int target)
        {
            while (index < m_info.Instructions.Length)
            {
                UnconditionalBranch ub = m_info.Instructions[index] as UnconditionalBranch;
                if (ub != null)
                {
                    return(-1);
                }

                Branch branch = m_info.Instructions[index++] as Branch;
                if (branch != null && branch.Target.Index == target)
                {
                    Log.DebugLine(this, "   found backward branch at {0:X2}", branch.Untyped.Offset);
                    return(branch.Index);
                }
            }

            return(-1);
        }
Esempio n. 10
0
 public virtual Statement visit(UnconditionalBranch s)
 {
     return(s);
 }
Esempio n. 11
0
 /// <summary cref="IValueVisitor.Visit(UnconditionalBranch)"/>
 public void Visit(UnconditionalBranch branch) =>
 CodeGenerator.GenerateCode(branch);
Esempio n. 12
0
 /// <summary cref="IValueVisitor.Visit(UnconditionalBranch)"/>
 public void Visit(UnconditionalBranch branch)
 {
     // TODO: implement
     throw new NotImplementedException();
 }
Esempio n. 13
0
 /// <summary cref="IBackendCodeGenerator.GenerateCode(UnconditionalBranch)"/>
 public void GenerateCode(UnconditionalBranch branch) =>
 GotoStatement(branch.Target);
Esempio n. 14
0
        private void DoWireBlock(TypedInstructionCollection instructions, Dictionary <int, BasicBlock> blocks, BasicBlock block)
        {
            var nextBlocks = new List <BasicBlock>();

            if (block.First.Index == 0)
            {
                DoWireCatches(instructions, nextBlocks, blocks, 0);
            }

            do
            {
                ConditionalBranch conditional = block.Last as ConditionalBranch;
                if (conditional != null)
                {
                    nextBlocks.Add(blocks[conditional.Index + 1]);
                    nextBlocks.Add(blocks[conditional.Target.Index]);

                    DoWireCatches(instructions, nextBlocks, blocks, conditional.Index + 1);
                    DoWireCatches(instructions, nextBlocks, blocks, conditional.Target.Index);
                    break;
                }

                UnconditionalBranch unconditional = block.Last as UnconditionalBranch;
                if (unconditional != null)
                {
                    nextBlocks.Add(blocks[unconditional.Target.Index]);
                    DoWireCatches(instructions, nextBlocks, blocks, unconditional.Target.Index);

                    if (block.Last.Untyped.OpCode.Code == Code.Leave || block.Last.Untyped.OpCode.Code == Code.Leave_S)
                    {
                        DoAddFinally(instructions, nextBlocks, blocks, block);
                    }
                    break;
                }

                Switch swtch = block.Last as Switch;
                if (swtch != null)
                {
                    foreach (TypedInstruction t in swtch.Targets)
                    {
                        nextBlocks.Add(blocks[t.Index]);
                        DoWireCatches(instructions, nextBlocks, blocks, t.Index);
                    }
                    nextBlocks.Add(blocks[swtch.Index + 1]);
                    DoWireCatches(instructions, nextBlocks, blocks, swtch.Index + 1);
                    break;
                }

                End end = block.Last as End;
                if (end != null)
                {
                    DoAddFinally(instructions, nextBlocks, blocks, block);
                    break;
                }

                DoWireCatches(instructions, nextBlocks, blocks, block.Last.Index + 1);
                nextBlocks.Add(blocks[block.Last.Index + 1]);
            }while (false);

            block.Next = nextBlocks.ToArray();
            Log.DebugLine(this, "Wired block: {0}", block);
        }
 /// <summary cref="IValueVisitor.Visit(UnconditionalBranch)"/>
 public void Visit(UnconditionalBranch branch)
 {
     GotoStatement(branch.Target);
 }