示例#1
0
        public void CreatesMultipleBasicBlocksWhenBranchingInstructionsArePresent()
        {
            // Arrange.
            var instructions = new InstructionBase[]
            {
                new NormalInstruction(),
                new NormalInstruction(),
                new BranchingInstruction {
                    BranchType = BranchType.Conditional
                },
                new NormalInstruction()
            };

            // Act.
            var controlFlowGraph = ControlFlowGraph.FromInstructions(instructions);

            // Assert.
            Assert.That(controlFlowGraph.BasicBlocks, Is.Not.Null);
            Assert.That(controlFlowGraph.BasicBlocks, Has.Count.EqualTo(2));
            Assert.That(controlFlowGraph.BasicBlocks[0].Position, Is.EqualTo(0));
            Assert.That(controlFlowGraph.BasicBlocks[0].Instructions, Has.Count.EqualTo(3));
            Assert.That(controlFlowGraph.BasicBlocks[0].Successors, Has.Count.EqualTo(1));
            Assert.That(controlFlowGraph.BasicBlocks[0].Successors[0], Is.EqualTo(controlFlowGraph.BasicBlocks[1]));
            Assert.That(controlFlowGraph.BasicBlocks[1].Position, Is.EqualTo(1));
            Assert.That(controlFlowGraph.BasicBlocks[1].Instructions, Has.Count.EqualTo(1));
            Assert.That(controlFlowGraph.BasicBlocks[1].Successors, Is.Empty);
        }
        public void SetsNextProgramCounterForEveryInstruction()
        {
            // Arrange.
            var instructions = new List <InstructionBase>
            {
                CreateInstruction <NormalInstruction>(),                   // 0
                CreateInstruction <BranchingInstruction>(),                // 1 Unconditional branch to [3]
                CreateInstruction <NormalInstruction>(),                   // 2 Skipped
                CreateInstruction <BranchingInstruction>(),                // 3 Conditional branch to [5]
                CreateInstruction <NormalInstruction>(),                   // 4
                CreateInstruction <NormalInstruction>()                    // 5
            };

            ((BranchingInstruction)instructions[1]).BranchType   = BranchType.Unconditional;
            ((BranchingInstruction)instructions[1]).BranchTarget = instructions[3];
            ((BranchingInstruction)instructions[3]).BranchType   = BranchType.Conditional;
            ((BranchingInstruction)instructions[3]).BranchTarget = instructions[5];
            var controlFlowGraph = ControlFlowGraph.FromInstructions(instructions);

            // Act.
            var executableInstructions = ExecutableInstructionRewriter.Rewrite(controlFlowGraph).ToList();

            // Assert.
            Assert.That(executableInstructions, Has.Count.EqualTo(6));
            Assert.That(((NonDivergentExecutableInstruction)executableInstructions[0]).NextPC, Is.EqualTo(1));
            Assert.That(((NonDivergentExecutableInstruction)executableInstructions[1]).NextPC, Is.EqualTo(3));
            Assert.That(((NonDivergentExecutableInstruction)executableInstructions[2]).NextPC, Is.EqualTo(3));
            Assert.That(((DivergentExecutableInstruction)executableInstructions[3]).NextPCs, Is.EquivalentTo(new[] { 4, 5 }));
            Assert.That(((DivergentExecutableInstruction)executableInstructions[3]).ReconvergencePC, Is.EqualTo(5));
            Assert.That(((NonDivergentExecutableInstruction)executableInstructions[4]).NextPC, Is.EqualTo(5));
            Assert.That(((NonDivergentExecutableInstruction)executableInstructions[5]).NextPC, Is.EqualTo(6));
        }
        public ControlFlowViewerViewModel(IExtendedShell extendedShell)
        {
            _graph = new CfgGraph();

            extendedShell.ActiveDocumentChanged += (sender, e) =>
            {
                Graph.RemoveVertexIf(x => true);
                Graph.Clear();

                var rewrittenInstructions = ExplicitBranchingRewriter.Rewrite(e.Editor.BytecodeContainer.Shader.InstructionTokens);
                var cfg = ControlFlowGraph.FromInstructions(rewrittenInstructions);

                var basicBlockLookup = cfg.BasicBlocks.ToDictionary(x => x, x => new BasicBlockViewModel(x));

                Graph.AddVertexRange(basicBlockLookup.Values);

                foreach (var basicBlock in cfg.BasicBlocks)
                {
                    foreach (var successor in basicBlock.Successors)
                    {
                        Graph.AddEdge(new CfgEdge(basicBlockLookup[basicBlock], basicBlockLookup[successor]));
                    }
                    if (basicBlock.ImmediatePostDominator != null)
                    {
                        Graph.AddEdge(new CfgEdge(basicBlockLookup[basicBlock],
                                                  basicBlockLookup[basicBlock.ImmediatePostDominator])
                        {
                            IsImmediatePostDominatorEdge = true
                        });
                    }
                }

                NotifyOfPropertyChange(() => LayoutAlgorithmType);
            };
        }
示例#4
0
        public void CreatesSingleBasicBlockWhenNoBranchingInstructions()
        {
            // Arrange.
            var instructions = new[]
            {
                new NormalInstruction(),
                new NormalInstruction(),
                new NormalInstruction()
            };

            // Act.
            var controlFlowGraph = ControlFlowGraph.FromInstructions(instructions);

            // Assert.
            Assert.That(controlFlowGraph.BasicBlocks, Is.Not.Null);
            Assert.That(controlFlowGraph.BasicBlocks, Has.Count.EqualTo(1));
            Assert.That(controlFlowGraph.BasicBlocks[0].Position, Is.EqualTo(0));
            Assert.That(controlFlowGraph.BasicBlocks[0].Instructions, Has.Count.EqualTo(3));
            Assert.That(controlFlowGraph.BasicBlocks[0].Successors, Is.Empty);
        }
示例#5
0
        public VirtualMachine(BytecodeContainer bytecode, int numContexts)
        {
            if (bytecode.Shader.Version.ProgramType == ProgramType.PixelShader && numContexts % 4 != 0)
            {
                throw new ArgumentOutOfRangeException("numContexts", "numContexts must be a multiple of 4 for pixel shaders.");
            }

            _bytecode = bytecode;

            var instructionTokens     = bytecode.Shader.Tokens.OfType <InstructionToken>().ToArray();
            var branchingInstructions = ExplicitBranchingRewriter.Rewrite(instructionTokens);
            var controlFlowGraph      = ControlFlowGraph.FromInstructions(branchingInstructions);

            _executableInstructions = ExecutableInstructionRewriter.Rewrite(controlFlowGraph).ToArray();

            _requiredRegisters = RequiredRegisters.FromShader(bytecode.Shader);

            _executionContexts = new ExecutionContext[numContexts];
            for (int i = 0; i < _executionContexts.Length; i++)
            {
                _executionContexts[i] = new ExecutionContext(this, i, _requiredRegisters);
            }

            ConstantBuffers = new Number4[_requiredRegisters.ConstantBuffers.Count][];
            for (int i = 0; i < _requiredRegisters.ConstantBuffers.Count; i++)
            {
                ConstantBuffers[i] = new Number4[_requiredRegisters.ConstantBuffers[i]];
            }

            TextureSamplers = new TextureSampler[_requiredRegisters.Resources.Count];
            for (int i = 0; i < _requiredRegisters.Resources.Count; i++)
            {
                TextureSamplers[i] = TextureSamplerFactory.Create(_requiredRegisters.Resources[i]);
            }

            Textures = new ITexture[_requiredRegisters.Resources.Count];
            Samplers = new SamplerState[_requiredRegisters.Samplers];
        }