Mercurial > hg > truffle
comparison graal/com.oracle.graal.phases/src/com/oracle/graal/phases/schedule/SchedulePhase.java @ 18941:c943ba97b2a7
Remove class ScheduledNode from the node class hierarchy.
author | Thomas Wuerthinger <thomas.wuerthinger@oracle.com> |
---|---|
date | Sat, 24 Jan 2015 00:45:12 +0100 |
parents | 498a56d8bb9b |
children | bef8b6316627 |
comparison
equal
deleted
inserted
replaced
18940:2ad82c6147f1 | 18941:c943ba97b2a7 |
---|---|
267 private NodeMap<Block> earliestCache; | 267 private NodeMap<Block> earliestCache; |
268 | 268 |
269 /** | 269 /** |
270 * Map from blocks to the nodes in each block. | 270 * Map from blocks to the nodes in each block. |
271 */ | 271 */ |
272 private BlockMap<List<ScheduledNode>> blockToNodesMap; | 272 private BlockMap<List<ValueNode>> blockToNodesMap; |
273 private BlockMap<KillSet> blockToKillSet; | 273 private BlockMap<KillSet> blockToKillSet; |
274 private final SchedulingStrategy selectedStrategy; | 274 private final SchedulingStrategy selectedStrategy; |
275 private final MemoryScheduling memsched; | 275 private final MemoryScheduling memsched; |
276 | 276 |
277 public SchedulePhase() { | 277 public SchedulePhase() { |
381 } | 381 } |
382 | 382 |
383 /** | 383 /** |
384 * Gets the map from each block to the nodes in the block. | 384 * Gets the map from each block to the nodes in the block. |
385 */ | 385 */ |
386 public BlockMap<List<ScheduledNode>> getBlockToNodesMap() { | 386 public BlockMap<List<ValueNode>> getBlockToNodesMap() { |
387 return blockToNodesMap; | 387 return blockToNodesMap; |
388 } | 388 } |
389 | 389 |
390 /** | 390 /** |
391 * Gets the nodes in a given block. | 391 * Gets the nodes in a given block. |
392 */ | 392 */ |
393 public List<ScheduledNode> nodesFor(Block block) { | 393 public List<ValueNode> nodesFor(Block block) { |
394 return blockToNodesMap.get(block); | 394 return blockToNodesMap.get(block); |
395 } | 395 } |
396 | 396 |
397 private void assignBlockToNodes(StructuredGraph graph, SchedulingStrategy strategy) { | 397 private void assignBlockToNodes(StructuredGraph graph, SchedulingStrategy strategy) { |
398 for (Block block : cfg.getBlocks()) { | 398 for (Block block : cfg.getBlocks()) { |
399 List<ScheduledNode> nodes = new ArrayList<>(); | 399 List<ValueNode> nodes = new ArrayList<>(); |
400 if (blockToNodesMap.get(block) != null) { | 400 if (blockToNodesMap.get(block) != null) { |
401 throw new SchedulingError(); | 401 throw new SchedulingError(); |
402 } | 402 } |
403 blockToNodesMap.put(block, nodes); | 403 blockToNodesMap.put(block, nodes); |
404 for (FixedNode node : block.getNodes()) { | 404 for (FixedNode node : block.getNodes()) { |
405 nodes.add(node); | 405 nodes.add(node); |
406 } | 406 } |
407 } | 407 } |
408 | 408 |
409 for (Node n : graph.getNodes()) { | 409 for (Node n : graph.getNodes()) { |
410 if (n instanceof ScheduledNode) { | 410 if (n instanceof ValueNode) { |
411 assignBlockToNode((ScheduledNode) n, strategy); | 411 assignBlockToNode((ValueNode) n, strategy); |
412 } | 412 } |
413 } | 413 } |
414 } | 414 } |
415 | 415 |
416 /** | 416 /** |
417 * Assigns a block to the given node. This method expects that PhiNodes and FixedNodes are | 417 * Assigns a block to the given node. This method expects that PhiNodes and FixedNodes are |
418 * already assigned to a block. | 418 * already assigned to a block. |
419 */ | 419 */ |
420 private void assignBlockToNode(ScheduledNode node, SchedulingStrategy strategy) { | 420 private void assignBlockToNode(ValueNode node, SchedulingStrategy strategy) { |
421 assert !node.isDeleted(); | 421 assert !node.isDeleted(); |
422 | 422 |
423 if (cfg.getNodeToBlock().containsKey(node)) { | 423 if (cfg.getNodeToBlock().containsKey(node)) { |
424 return; | 424 return; |
425 } | 425 } |
615 * Calculates the last block that the given node could be scheduled in, i.e., the common | 615 * Calculates the last block that the given node could be scheduled in, i.e., the common |
616 * dominator of all usages. To do so all usages are also assigned to blocks. | 616 * dominator of all usages. To do so all usages are also assigned to blocks. |
617 * | 617 * |
618 * @param strategy | 618 * @param strategy |
619 */ | 619 */ |
620 private Block latestBlock(ScheduledNode node, SchedulingStrategy strategy) { | 620 private Block latestBlock(ValueNode node, SchedulingStrategy strategy) { |
621 CommonDominatorBlockClosure cdbc = new CommonDominatorBlockClosure(null); | 621 CommonDominatorBlockClosure cdbc = new CommonDominatorBlockClosure(null); |
622 for (Node succ : node.successors().nonNull()) { | 622 for (Node succ : node.successors().nonNull()) { |
623 if (cfg.getNodeToBlock().get(succ) == null) { | 623 if (cfg.getNodeToBlock().get(succ) == null) { |
624 throw new SchedulingError(); | 624 throw new SchedulingError(); |
625 } | 625 } |
745 * | 745 * |
746 * @param node the node that needs to be scheduled | 746 * @param node the node that needs to be scheduled |
747 * @param usage the usage whose blocks need to be considered | 747 * @param usage the usage whose blocks need to be considered |
748 * @param closure the closure that will be called for each block | 748 * @param closure the closure that will be called for each block |
749 */ | 749 */ |
750 private void blocksForUsage(ScheduledNode node, Node usage, BlockClosure closure, SchedulingStrategy strategy) { | 750 private void blocksForUsage(ValueNode node, Node usage, BlockClosure closure, SchedulingStrategy strategy) { |
751 if (node instanceof PhiNode) { | 751 if (node instanceof PhiNode) { |
752 throw new SchedulingError(node.toString()); | 752 throw new SchedulingError(node.toString()); |
753 } | 753 } |
754 | 754 |
755 if (usage instanceof PhiNode) { | 755 if (usage instanceof PhiNode) { |
805 } | 805 } |
806 if (!(unscheduledUsage instanceof NodeWithState)) { | 806 if (!(unscheduledUsage instanceof NodeWithState)) { |
807 throw new SchedulingError(unscheduledUsage.toString()); | 807 throw new SchedulingError(unscheduledUsage.toString()); |
808 } | 808 } |
809 // Otherwise: Put the input into the same block as the usage. | 809 // Otherwise: Put the input into the same block as the usage. |
810 assignBlockToNode((ScheduledNode) unscheduledUsage, strategy); | 810 assignBlockToNode((ValueNode) unscheduledUsage, strategy); |
811 closure.apply(cfg.getNodeToBlock().get(unscheduledUsage)); | 811 closure.apply(cfg.getNodeToBlock().get(unscheduledUsage)); |
812 } | 812 } |
813 } | 813 } |
814 } else { | 814 } else { |
815 // All other types of usages: Put the input into the same block as the usage. | 815 // All other types of usages: Put the input into the same block as the usage. |
816 assignBlockToNode((ScheduledNode) usage, strategy); | 816 assignBlockToNode((ValueNode) usage, strategy); |
817 closure.apply(cfg.getNodeToBlock().get(usage)); | 817 closure.apply(cfg.getNodeToBlock().get(usage)); |
818 } | 818 } |
819 } | 819 } |
820 | 820 |
821 private void ensureScheduledUsages(Node node, SchedulingStrategy strategy) { | 821 private void ensureScheduledUsages(Node node, SchedulingStrategy strategy) { |
822 for (Node usage : node.usages().filter(ScheduledNode.class)) { | 822 for (Node usage : node.usages().filter(ValueNode.class)) { |
823 assignBlockToNode((ScheduledNode) usage, strategy); | 823 assignBlockToNode((ValueNode) usage, strategy); |
824 } | 824 } |
825 // now true usages are ready | 825 // now true usages are ready |
826 } | 826 } |
827 | 827 |
828 private void sortNodesWithinBlocks(StructuredGraph graph, SchedulingStrategy strategy) { | 828 private void sortNodesWithinBlocks(StructuredGraph graph, SchedulingStrategy strategy) { |
833 assert noDuplicatedNodesInBlock(b) : "duplicated nodes in " + b; | 833 assert noDuplicatedNodesInBlock(b) : "duplicated nodes in " + b; |
834 } | 834 } |
835 } | 835 } |
836 | 836 |
837 private boolean noDuplicatedNodesInBlock(Block b) { | 837 private boolean noDuplicatedNodesInBlock(Block b) { |
838 List<ScheduledNode> list = blockToNodesMap.get(b); | 838 List<ValueNode> list = blockToNodesMap.get(b); |
839 Set<ScheduledNode> hashset = Node.newSet(list); | 839 Set<ValueNode> hashset = Node.newSet(list); |
840 return list.size() == hashset.size(); | 840 return list.size() == hashset.size(); |
841 } | 841 } |
842 | 842 |
843 private void sortNodesWithinBlock(Block b, NodeBitMap visited, NodeBitMap beforeLastLocation, SchedulingStrategy strategy) { | 843 private void sortNodesWithinBlock(Block b, NodeBitMap visited, NodeBitMap beforeLastLocation, SchedulingStrategy strategy) { |
844 if (visited.isMarked(b.getBeginNode()) || cfg.blockFor(b.getBeginNode()) != b) { | 844 if (visited.isMarked(b.getBeginNode()) || cfg.blockFor(b.getBeginNode()) != b) { |
846 } | 846 } |
847 if (visited.isMarked(b.getEndNode()) || cfg.blockFor(b.getEndNode()) != b) { | 847 if (visited.isMarked(b.getEndNode()) || cfg.blockFor(b.getEndNode()) != b) { |
848 throw new SchedulingError(); | 848 throw new SchedulingError(); |
849 } | 849 } |
850 | 850 |
851 List<ScheduledNode> sortedInstructions; | 851 List<ValueNode> sortedInstructions; |
852 switch (strategy) { | 852 switch (strategy) { |
853 case EARLIEST: | 853 case EARLIEST: |
854 sortedInstructions = sortNodesWithinBlockEarliest(b, visited); | 854 sortedInstructions = sortNodesWithinBlockEarliest(b, visited); |
855 break; | 855 break; |
856 case LATEST: | 856 case LATEST: |
864 filterSchedulableNodes(blockToNodesMap.get(b)) + " vs. " + removeProxies(sortedInstructions); | 864 filterSchedulableNodes(blockToNodesMap.get(b)) + " vs. " + removeProxies(sortedInstructions); |
865 assert sameOrderForFixedNodes(blockToNodesMap.get(b), sortedInstructions) : "fixed nodes in sorted block are not in the same order"; | 865 assert sameOrderForFixedNodes(blockToNodesMap.get(b), sortedInstructions) : "fixed nodes in sorted block are not in the same order"; |
866 blockToNodesMap.put(b, sortedInstructions); | 866 blockToNodesMap.put(b, sortedInstructions); |
867 } | 867 } |
868 | 868 |
869 private static List<ScheduledNode> removeProxies(List<ScheduledNode> list) { | 869 private static List<ValueNode> removeProxies(List<ValueNode> list) { |
870 List<ScheduledNode> result = new ArrayList<>(); | 870 List<ValueNode> result = new ArrayList<>(); |
871 for (ScheduledNode n : list) { | 871 for (ValueNode n : list) { |
872 if (!(n instanceof ProxyNode)) { | 872 if (!(n instanceof ProxyNode)) { |
873 result.add(n); | 873 result.add(n); |
874 } | 874 } |
875 } | 875 } |
876 return result; | 876 return result; |
877 } | 877 } |
878 | 878 |
879 private static List<ScheduledNode> filterSchedulableNodes(List<ScheduledNode> list) { | 879 private static List<ValueNode> filterSchedulableNodes(List<ValueNode> list) { |
880 List<ScheduledNode> result = new ArrayList<>(); | 880 List<ValueNode> result = new ArrayList<>(); |
881 for (ScheduledNode n : list) { | 881 for (ValueNode n : list) { |
882 if (!(n instanceof PhiNode)) { | 882 if (!(n instanceof PhiNode)) { |
883 result.add(n); | 883 result.add(n); |
884 } | 884 } |
885 } | 885 } |
886 return result; | 886 return result; |
887 } | 887 } |
888 | 888 |
889 private static boolean sameOrderForFixedNodes(List<ScheduledNode> fixed, List<ScheduledNode> sorted) { | 889 private static boolean sameOrderForFixedNodes(List<ValueNode> fixed, List<ValueNode> sorted) { |
890 Iterator<ScheduledNode> fixedIterator = fixed.iterator(); | 890 Iterator<ValueNode> fixedIterator = fixed.iterator(); |
891 Iterator<ScheduledNode> sortedIterator = sorted.iterator(); | 891 Iterator<ValueNode> sortedIterator = sorted.iterator(); |
892 | 892 |
893 while (sortedIterator.hasNext()) { | 893 while (sortedIterator.hasNext()) { |
894 ScheduledNode sortedCurrent = sortedIterator.next(); | 894 ValueNode sortedCurrent = sortedIterator.next(); |
895 if (sortedCurrent instanceof FixedNode) { | 895 if (sortedCurrent instanceof FixedNode) { |
896 if (!(fixedIterator.hasNext() && fixedIterator.next() == sortedCurrent)) { | 896 if (!(fixedIterator.hasNext() && fixedIterator.next() == sortedCurrent)) { |
897 return false; | 897 return false; |
898 } | 898 } |
899 } | 899 } |
910 | 910 |
911 private static class SortState { | 911 private static class SortState { |
912 private Block block; | 912 private Block block; |
913 private NodeBitMap visited; | 913 private NodeBitMap visited; |
914 private NodeBitMap beforeLastLocation; | 914 private NodeBitMap beforeLastLocation; |
915 private List<ScheduledNode> sortedInstructions; | 915 private List<ValueNode> sortedInstructions; |
916 private List<FloatingReadNode> reads; | 916 private List<FloatingReadNode> reads; |
917 | 917 |
918 SortState(Block block, NodeBitMap visited, NodeBitMap beforeLastLocation, List<ScheduledNode> sortedInstructions) { | 918 SortState(Block block, NodeBitMap visited, NodeBitMap beforeLastLocation, List<ValueNode> sortedInstructions) { |
919 this.block = block; | 919 this.block = block; |
920 this.visited = visited; | 920 this.visited = visited; |
921 this.beforeLastLocation = beforeLastLocation; | 921 this.beforeLastLocation = beforeLastLocation; |
922 this.sortedInstructions = sortedInstructions; | 922 this.sortedInstructions = sortedInstructions; |
923 this.reads = null; | 923 this.reads = null; |
959 return 0; | 959 return 0; |
960 } | 960 } |
961 return reads.size(); | 961 return reads.size(); |
962 } | 962 } |
963 | 963 |
964 void removeRead(ScheduledNode i) { | 964 void removeRead(ValueNode i) { |
965 assert reads != null; | 965 assert reads != null; |
966 reads.remove(i); | 966 reads.remove(i); |
967 } | 967 } |
968 | 968 |
969 List<FloatingReadNode> readsSnapshot() { | 969 List<FloatingReadNode> readsSnapshot() { |
970 assert reads != null; | 970 assert reads != null; |
971 return new ArrayList<>(reads); | 971 return new ArrayList<>(reads); |
972 } | 972 } |
973 | 973 |
974 List<ScheduledNode> getSortedInstructions() { | 974 List<ValueNode> getSortedInstructions() { |
975 return sortedInstructions; | 975 return sortedInstructions; |
976 } | 976 } |
977 | 977 |
978 boolean containsInstruction(ScheduledNode i) { | 978 boolean containsInstruction(ValueNode i) { |
979 return sortedInstructions.contains(i); | 979 return sortedInstructions.contains(i); |
980 } | 980 } |
981 | 981 |
982 void addInstruction(ScheduledNode i) { | 982 void addInstruction(ValueNode i) { |
983 sortedInstructions.add(i); | 983 sortedInstructions.add(i); |
984 } | 984 } |
985 } | 985 } |
986 | 986 |
987 /** | 987 /** |
988 * Sorts the nodes within a block by adding the nodes to a list in a post-order iteration over | 988 * Sorts the nodes within a block by adding the nodes to a list in a post-order iteration over |
989 * all inputs. This means that a node is added to the list after all its inputs have been | 989 * all inputs. This means that a node is added to the list after all its inputs have been |
990 * processed. | 990 * processed. |
991 */ | 991 */ |
992 private List<ScheduledNode> sortNodesWithinBlockLatest(Block b, NodeBitMap visited, NodeBitMap beforeLastLocation) { | 992 private List<ValueNode> sortNodesWithinBlockLatest(Block b, NodeBitMap visited, NodeBitMap beforeLastLocation) { |
993 SortState state = new SortState(b, visited, beforeLastLocation, new ArrayList<>(blockToNodesMap.get(b).size() + 2)); | 993 SortState state = new SortState(b, visited, beforeLastLocation, new ArrayList<>(blockToNodesMap.get(b).size() + 2)); |
994 List<ScheduledNode> instructions = blockToNodesMap.get(b); | 994 List<ValueNode> instructions = blockToNodesMap.get(b); |
995 | 995 |
996 if (memsched == MemoryScheduling.OPTIMAL) { | 996 if (memsched == MemoryScheduling.OPTIMAL) { |
997 for (ScheduledNode i : instructions) { | 997 for (ValueNode i : instructions) { |
998 if (i instanceof FloatingReadNode) { | 998 if (i instanceof FloatingReadNode) { |
999 FloatingReadNode frn = (FloatingReadNode) i; | 999 FloatingReadNode frn = (FloatingReadNode) i; |
1000 if (!frn.location().getLocationIdentity().isImmutable()) { | 1000 if (!frn.location().getLocationIdentity().isImmutable()) { |
1001 state.addRead(frn); | 1001 state.addRead(frn); |
1002 if (nodesFor(b).contains(frn.getLastLocationAccess())) { | 1002 if (nodesFor(b).contains(frn.getLastLocationAccess())) { |
1006 } | 1006 } |
1007 } | 1007 } |
1008 } | 1008 } |
1009 } | 1009 } |
1010 | 1010 |
1011 for (ScheduledNode i : instructions) { | 1011 for (ValueNode i : instructions) { |
1012 addToLatestSorting(i, state); | 1012 addToLatestSorting(i, state); |
1013 } | 1013 } |
1014 assert state.readsSize() == 0 : "not all reads are scheduled"; | 1014 assert state.readsSize() == 0 : "not all reads are scheduled"; |
1015 | 1015 |
1016 // Make sure that last node gets really last (i.e. when a frame state successor hangs off | 1016 // Make sure that last node gets really last (i.e. when a frame state successor hangs off |
1017 // it). | 1017 // it). |
1018 List<ScheduledNode> sortedInstructions = state.getSortedInstructions(); | 1018 List<ValueNode> sortedInstructions = state.getSortedInstructions(); |
1019 Node lastSorted = sortedInstructions.get(sortedInstructions.size() - 1); | 1019 Node lastSorted = sortedInstructions.get(sortedInstructions.size() - 1); |
1020 if (lastSorted != b.getEndNode()) { | 1020 if (lastSorted != b.getEndNode()) { |
1021 int idx = sortedInstructions.indexOf(b.getEndNode()); | 1021 int idx = sortedInstructions.indexOf(b.getEndNode()); |
1022 boolean canNotMove = false; | 1022 boolean canNotMove = false; |
1023 for (int i = idx + 1; i < sortedInstructions.size(); i++) { | 1023 for (int i = idx + 1; i < sortedInstructions.size(); i++) { |
1064 | 1064 |
1065 for (Node input : state.inputs()) { | 1065 for (Node input : state.inputs()) { |
1066 if (input instanceof VirtualState) { | 1066 if (input instanceof VirtualState) { |
1067 addUnscheduledToLatestSorting((VirtualState) input, sortState); | 1067 addUnscheduledToLatestSorting((VirtualState) input, sortState); |
1068 } else { | 1068 } else { |
1069 addToLatestSorting((ScheduledNode) input, sortState); | 1069 addToLatestSorting((ValueNode) input, sortState); |
1070 } | 1070 } |
1071 } | 1071 } |
1072 } | 1072 } |
1073 } | 1073 } |
1074 | 1074 |
1075 private void addToLatestSorting(ScheduledNode i, SortState state) { | 1075 private void addToLatestSorting(ValueNode i, SortState state) { |
1076 if (i == null || state.isVisited(i) || cfg.getNodeToBlock().get(i) != state.currentBlock() || i instanceof PhiNode) { | 1076 if (i == null || state.isVisited(i) || cfg.getNodeToBlock().get(i) != state.currentBlock() || i instanceof PhiNode) { |
1077 return; | 1077 return; |
1078 } | 1078 } |
1079 | 1079 |
1080 FrameState stateAfter = null; | 1080 FrameState stateAfter = null; |
1093 if (input != stateAfter) { | 1093 if (input != stateAfter) { |
1094 addUnscheduledToLatestSorting((FrameState) input, state); | 1094 addUnscheduledToLatestSorting((FrameState) input, state); |
1095 } | 1095 } |
1096 } else { | 1096 } else { |
1097 if (!(i instanceof ProxyNode && input instanceof LoopExitNode)) { | 1097 if (!(i instanceof ProxyNode && input instanceof LoopExitNode)) { |
1098 addToLatestSorting((ScheduledNode) input, state); | 1098 addToLatestSorting((ValueNode) input, state); |
1099 } | 1099 } |
1100 } | 1100 } |
1101 } | 1101 } |
1102 | 1102 |
1103 if (memsched == MemoryScheduling.OPTIMAL && state.readsSize() != 0) { | 1103 if (memsched == MemoryScheduling.OPTIMAL && state.readsSize() != 0) { |
1110 } | 1110 } |
1111 } | 1111 } |
1112 assert MemoryCheckpoint.TypeAssertion.correctType(i); | 1112 assert MemoryCheckpoint.TypeAssertion.correctType(i); |
1113 } | 1113 } |
1114 | 1114 |
1115 addToLatestSorting((ScheduledNode) i.predecessor(), state); | 1115 addToLatestSorting((ValueNode) i.predecessor(), state); |
1116 state.markVisited(i); | 1116 state.markVisited(i); |
1117 addUnscheduledToLatestSorting(stateAfter, state); | 1117 addUnscheduledToLatestSorting(stateAfter, state); |
1118 | 1118 |
1119 // Now predecessors and inputs are scheduled => we can add this node. | 1119 // Now predecessors and inputs are scheduled => we can add this node. |
1120 if (!state.containsInstruction(i)) { | 1120 if (!state.containsInstruction(i)) { |
1129 /** | 1129 /** |
1130 * Sorts the nodes within a block by adding the nodes to a list in a post-order iteration over | 1130 * Sorts the nodes within a block by adding the nodes to a list in a post-order iteration over |
1131 * all usages. The resulting list is reversed to create an earliest-possible scheduling of | 1131 * all usages. The resulting list is reversed to create an earliest-possible scheduling of |
1132 * nodes. | 1132 * nodes. |
1133 */ | 1133 */ |
1134 private List<ScheduledNode> sortNodesWithinBlockEarliest(Block b, NodeBitMap visited) { | 1134 private List<ValueNode> sortNodesWithinBlockEarliest(Block b, NodeBitMap visited) { |
1135 List<ScheduledNode> sortedInstructions = new ArrayList<>(blockToNodesMap.get(b).size() + 2); | 1135 List<ValueNode> sortedInstructions = new ArrayList<>(blockToNodesMap.get(b).size() + 2); |
1136 addToEarliestSorting(b, b.getEndNode(), sortedInstructions, visited); | 1136 addToEarliestSorting(b, b.getEndNode(), sortedInstructions, visited); |
1137 Collections.reverse(sortedInstructions); | 1137 Collections.reverse(sortedInstructions); |
1138 return sortedInstructions; | 1138 return sortedInstructions; |
1139 } | 1139 } |
1140 | 1140 |
1141 private void addToEarliestSorting(Block b, ScheduledNode i, List<ScheduledNode> sortedInstructions, NodeBitMap visited) { | 1141 private void addToEarliestSorting(Block b, ValueNode i, List<ValueNode> sortedInstructions, NodeBitMap visited) { |
1142 ScheduledNode instruction = i; | 1142 ValueNode instruction = i; |
1143 while (true) { | 1143 while (true) { |
1144 if (instruction == null || visited.isMarked(instruction) || cfg.getNodeToBlock().get(instruction) != b || instruction instanceof PhiNode) { | 1144 if (instruction == null || visited.isMarked(instruction) || cfg.getNodeToBlock().get(instruction) != b || instruction instanceof PhiNode) { |
1145 return; | 1145 return; |
1146 } | 1146 } |
1147 | 1147 |
1151 // only fixed nodes can have VirtualState -> no need to schedule them | 1151 // only fixed nodes can have VirtualState -> no need to schedule them |
1152 } else { | 1152 } else { |
1153 if (instruction instanceof LoopExitNode && usage instanceof ProxyNode) { | 1153 if (instruction instanceof LoopExitNode && usage instanceof ProxyNode) { |
1154 // value proxies should be scheduled before the loopexit, not after | 1154 // value proxies should be scheduled before the loopexit, not after |
1155 } else { | 1155 } else { |
1156 addToEarliestSorting(b, (ScheduledNode) usage, sortedInstructions, visited); | 1156 addToEarliestSorting(b, (ValueNode) usage, sortedInstructions, visited); |
1157 } | 1157 } |
1158 } | 1158 } |
1159 } | 1159 } |
1160 | 1160 |
1161 if (instruction instanceof BeginNode) { | 1161 if (instruction instanceof BeginNode) { |
1162 ArrayList<ProxyNode> proxies = (instruction instanceof LoopExitNode) ? new ArrayList<>() : null; | 1162 ArrayList<ProxyNode> proxies = (instruction instanceof LoopExitNode) ? new ArrayList<>() : null; |
1163 for (ScheduledNode inBlock : blockToNodesMap.get(b)) { | 1163 for (ValueNode inBlock : blockToNodesMap.get(b)) { |
1164 if (!visited.isMarked(inBlock)) { | 1164 if (!visited.isMarked(inBlock)) { |
1165 if (inBlock instanceof ProxyNode) { | 1165 if (inBlock instanceof ProxyNode) { |
1166 proxies.add((ProxyNode) inBlock); | 1166 proxies.add((ProxyNode) inBlock); |
1167 } else { | 1167 } else { |
1168 addToEarliestSorting(b, inBlock, sortedInstructions, visited); | 1168 addToEarliestSorting(b, inBlock, sortedInstructions, visited); |
1174 sortedInstructions.addAll(proxies); | 1174 sortedInstructions.addAll(proxies); |
1175 } | 1175 } |
1176 break; | 1176 break; |
1177 } else { | 1177 } else { |
1178 sortedInstructions.add(instruction); | 1178 sortedInstructions.add(instruction); |
1179 instruction = (ScheduledNode) instruction.predecessor(); | 1179 instruction = (ValueNode) instruction.predecessor(); |
1180 } | 1180 } |
1181 } | 1181 } |
1182 } | 1182 } |
1183 } | 1183 } |