Dominance.cs 3.0 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. using Ryujinx.Graphics.Shader.IntermediateRepresentation;
  2. using System.Collections.Generic;
  3. namespace Ryujinx.Graphics.Shader.Translation
  4. {
  5. static class Dominance
  6. {
  7. // Those methods are an implementation of the algorithms on "A Simple, Fast Dominance Algorithm".
  8. // https://www.cs.rice.edu/~keith/EMBED/dom.pdf
  9. public static void FindDominators(ControlFlowGraph cfg)
  10. {
  11. BasicBlock Intersect(BasicBlock block1, BasicBlock block2)
  12. {
  13. while (block1 != block2)
  14. {
  15. while (cfg.PostOrderMap[block1.Index] < cfg.PostOrderMap[block2.Index])
  16. {
  17. block1 = block1.ImmediateDominator;
  18. }
  19. while (cfg.PostOrderMap[block2.Index] < cfg.PostOrderMap[block1.Index])
  20. {
  21. block2 = block2.ImmediateDominator;
  22. }
  23. }
  24. return block1;
  25. }
  26. cfg.Blocks[0].ImmediateDominator = cfg.Blocks[0];
  27. bool modified;
  28. do
  29. {
  30. modified = false;
  31. for (int blkIndex = cfg.PostOrderBlocks.Length - 2; blkIndex >= 0; blkIndex--)
  32. {
  33. BasicBlock block = cfg.PostOrderBlocks[blkIndex];
  34. BasicBlock newIDom = null;
  35. foreach (BasicBlock predecessor in block.Predecessors)
  36. {
  37. if (predecessor.ImmediateDominator != null)
  38. {
  39. if (newIDom != null)
  40. {
  41. newIDom = Intersect(predecessor, newIDom);
  42. }
  43. else
  44. {
  45. newIDom = predecessor;
  46. }
  47. }
  48. }
  49. if (block.ImmediateDominator != newIDom)
  50. {
  51. block.ImmediateDominator = newIDom;
  52. modified = true;
  53. }
  54. }
  55. }
  56. while (modified);
  57. }
  58. public static void FindDominanceFrontiers(BasicBlock[] blocks)
  59. {
  60. for (int blkIndex = 0; blkIndex < blocks.Length; blkIndex++)
  61. {
  62. BasicBlock block = blocks[blkIndex];
  63. if (block.Predecessors.Count < 2)
  64. {
  65. continue;
  66. }
  67. for (int pBlkIndex = 0; pBlkIndex < block.Predecessors.Count; pBlkIndex++)
  68. {
  69. BasicBlock current = block.Predecessors[pBlkIndex];
  70. while (current != block.ImmediateDominator)
  71. {
  72. current.DominanceFrontiers.Add(block);
  73. current = current.ImmediateDominator;
  74. }
  75. }
  76. }
  77. }
  78. }
  79. }