src/jdk.internal.vm.compiler/share/classes/org.graalvm.compiler.lir/src/org/graalvm/compiler/lir/alloc/lsra/OptimizingLinearScanWalker.java
Index
Unified diffs
Context diffs
Sdiffs
Patch
New
Old
Previous File
Next File
hotspot Cdiff src/jdk.internal.vm.compiler/share/classes/org.graalvm.compiler.lir/src/org/graalvm/compiler/lir/alloc/lsra/OptimizingLinearScanWalker.java
src/jdk.internal.vm.compiler/share/classes/org.graalvm.compiler.lir/src/org/graalvm/compiler/lir/alloc/lsra/OptimizingLinearScanWalker.java
Print this page
*** 20,44 ****
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package org.graalvm.compiler.lir.alloc.lsra;
- import static org.graalvm.compiler.lir.LIRValueUtil.isStackSlotValue;
import static jdk.vm.ci.code.ValueUtil.asRegister;
import static jdk.vm.ci.code.ValueUtil.isRegister;
import org.graalvm.compiler.core.common.cfg.AbstractBlockBase;
! import org.graalvm.compiler.debug.Debug;
! import org.graalvm.compiler.debug.Debug.Scope;
import org.graalvm.compiler.debug.Indent;
import org.graalvm.compiler.lir.alloc.lsra.Interval.RegisterBinding;
import org.graalvm.compiler.lir.alloc.lsra.Interval.RegisterBindingLists;
import org.graalvm.compiler.lir.alloc.lsra.Interval.RegisterPriority;
import org.graalvm.compiler.lir.alloc.lsra.Interval.State;
import org.graalvm.compiler.options.Option;
- import org.graalvm.compiler.options.OptionType;
import org.graalvm.compiler.options.OptionKey;
import jdk.vm.ci.code.Register;
import jdk.vm.ci.meta.AllocatableValue;
public class OptimizingLinearScanWalker extends LinearScanWalker {
--- 20,43 ----
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package org.graalvm.compiler.lir.alloc.lsra;
import static jdk.vm.ci.code.ValueUtil.asRegister;
import static jdk.vm.ci.code.ValueUtil.isRegister;
+ import static org.graalvm.compiler.lir.LIRValueUtil.isStackSlotValue;
import org.graalvm.compiler.core.common.cfg.AbstractBlockBase;
! import org.graalvm.compiler.debug.DebugContext;
import org.graalvm.compiler.debug.Indent;
import org.graalvm.compiler.lir.alloc.lsra.Interval.RegisterBinding;
import org.graalvm.compiler.lir.alloc.lsra.Interval.RegisterBindingLists;
import org.graalvm.compiler.lir.alloc.lsra.Interval.RegisterPriority;
import org.graalvm.compiler.lir.alloc.lsra.Interval.State;
import org.graalvm.compiler.options.Option;
import org.graalvm.compiler.options.OptionKey;
+ import org.graalvm.compiler.options.OptionType;
import jdk.vm.ci.code.Register;
import jdk.vm.ci.meta.AllocatableValue;
public class OptimizingLinearScanWalker extends LinearScanWalker {
*** 63,89 ****
if (interval.canMaterialize()) {
assert !isStackSlotValue(interval.location()) : "interval can materialize but assigned to a stack slot " + interval;
return;
}
assert isStackSlotValue(interval.location()) : "interval not assigned to a stack slot " + interval;
! try (Scope s1 = Debug.scope("LSRAOptimization")) {
! Debug.log("adding stack to unhandled list %s", interval);
unhandledLists.addToListSortedByStartAndUsePositions(RegisterBinding.Stack, interval);
}
}
@SuppressWarnings("unused")
! private static void printRegisterBindingList(RegisterBindingLists list, RegisterBinding binding) {
for (Interval interval = list.get(binding); !interval.isEndMarker(); interval = interval.next) {
! Debug.log("%s", interval);
}
}
@SuppressWarnings("try")
@Override
void walk() {
! try (Scope s = Debug.scope("OptimizingLinearScanWalker")) {
for (AbstractBlockBase<?> block : allocator.sortedBlocks()) {
optimizeBlock(block);
}
}
super.walk();
--- 62,89 ----
if (interval.canMaterialize()) {
assert !isStackSlotValue(interval.location()) : "interval can materialize but assigned to a stack slot " + interval;
return;
}
assert isStackSlotValue(interval.location()) : "interval not assigned to a stack slot " + interval;
! DebugContext debug = allocator.getDebug();
! try (DebugContext.Scope s1 = debug.scope("LSRAOptimization")) {
! debug.log("adding stack to unhandled list %s", interval);
unhandledLists.addToListSortedByStartAndUsePositions(RegisterBinding.Stack, interval);
}
}
@SuppressWarnings("unused")
! private static void printRegisterBindingList(DebugContext debug, RegisterBindingLists list, RegisterBinding binding) {
for (Interval interval = list.get(binding); !interval.isEndMarker(); interval = interval.next) {
! debug.log("%s", interval);
}
}
@SuppressWarnings("try")
@Override
void walk() {
! try (DebugContext.Scope s = allocator.getDebug().scope("OptimizingLinearScanWalker")) {
for (AbstractBlockBase<?> block : allocator.sortedBlocks()) {
optimizeBlock(block);
}
}
super.walk();
*** 91,121 ****
@SuppressWarnings("try")
private void optimizeBlock(AbstractBlockBase<?> block) {
if (block.getPredecessorCount() == 1) {
int nextBlock = allocator.getFirstLirInstructionId(block);
! try (Scope s1 = Debug.scope("LSRAOptimization")) {
! Debug.log("next block: %s (%d)", block, nextBlock);
}
! try (Indent indent0 = Debug.indent()) {
walkTo(nextBlock);
! try (Scope s1 = Debug.scope("LSRAOptimization")) {
boolean changed = true;
// we need to do this because the active lists might change
loop: while (changed) {
changed = false;
! try (Indent indent1 = Debug.logAndIndent("Active intervals: (block %s [%d])", block, nextBlock)) {
for (Interval active = activeLists.get(RegisterBinding.Any); !active.isEndMarker(); active = active.next) {
! Debug.log("active (any): %s", active);
if (optimize(nextBlock, block, active, RegisterBinding.Any)) {
changed = true;
break loop;
}
}
for (Interval active = activeLists.get(RegisterBinding.Stack); !active.isEndMarker(); active = active.next) {
! Debug.log("active (stack): %s", active);
if (optimize(nextBlock, block, active, RegisterBinding.Stack)) {
changed = true;
break loop;
}
}
--- 91,122 ----
@SuppressWarnings("try")
private void optimizeBlock(AbstractBlockBase<?> block) {
if (block.getPredecessorCount() == 1) {
int nextBlock = allocator.getFirstLirInstructionId(block);
! DebugContext debug = allocator.getDebug();
! try (DebugContext.Scope s1 = debug.scope("LSRAOptimization")) {
! debug.log("next block: %s (%d)", block, nextBlock);
}
! try (Indent indent0 = debug.indent()) {
walkTo(nextBlock);
! try (DebugContext.Scope s1 = debug.scope("LSRAOptimization")) {
boolean changed = true;
// we need to do this because the active lists might change
loop: while (changed) {
changed = false;
! try (Indent indent1 = debug.logAndIndent("Active intervals: (block %s [%d])", block, nextBlock)) {
for (Interval active = activeLists.get(RegisterBinding.Any); !active.isEndMarker(); active = active.next) {
! debug.log("active (any): %s", active);
if (optimize(nextBlock, block, active, RegisterBinding.Any)) {
changed = true;
break loop;
}
}
for (Interval active = activeLists.get(RegisterBinding.Stack); !active.isEndMarker(); active = active.next) {
! debug.log("active (stack): %s", active);
if (optimize(nextBlock, block, active, RegisterBinding.Stack)) {
changed = true;
break loop;
}
}
*** 169,181 ****
return false;
}
assert isStackSlotValue(currentLocation) || isRegister(currentLocation) : "current location not a register or stack slot " + currentLocation;
! try (Indent indent = Debug.logAndIndent("location differs: %s vs. %s", predecessorLocation, currentLocation)) {
// split current interval at current position
! Debug.log("splitting at position %d", currentPos);
assert allocator.isBlockBegin(currentPos) && ((currentPos & 1) == 0) : "split pos must be even when on block boundary";
Interval splitPart = currentInterval.split(currentPos, allocator);
activeLists.remove(binding, currentInterval);
--- 170,183 ----
return false;
}
assert isStackSlotValue(currentLocation) || isRegister(currentLocation) : "current location not a register or stack slot " + currentLocation;
! DebugContext debug = allocator.getDebug();
! try (Indent indent = debug.logAndIndent("location differs: %s vs. %s", predecessorLocation, currentLocation)) {
// split current interval at current position
! debug.log("splitting at position %d", currentPos);
assert allocator.isBlockBegin(currentPos) && ((currentPos & 1) == 0) : "split pos must be even when on block boundary";
Interval splitPart = currentInterval.split(currentPos, allocator);
activeLists.remove(binding, currentInterval);
*** 184,207 ****
// the currentSplitChild is needed later when moves are inserted for reloading
assert splitPart.currentSplitChild() == currentInterval : "overwriting wrong currentSplitChild";
splitPart.makeCurrentSplitChild();
! if (Debug.isLogEnabled()) {
! Debug.log("left interval : %s", currentInterval.logString(allocator));
! Debug.log("right interval : %s", splitPart.logString(allocator));
}
if (Options.LSRAOptSplitOnly.getValue(allocator.getOptions())) {
// just add the split interval to the unhandled list
unhandledLists.addToListSortedByStartAndUsePositions(RegisterBinding.Any, splitPart);
} else {
if (isRegister(predecessorLocation)) {
splitRegisterInterval(splitPart, asRegister(predecessorLocation));
} else {
assert isStackSlotValue(predecessorLocation);
! Debug.log("assigning interval %s to %s", splitPart, predecessorLocation);
splitPart.assignLocation(predecessorLocation);
// activate interval
activeLists.addToListSortedByCurrentFromPositions(RegisterBinding.Stack, splitPart);
splitPart.state = State.Active;
--- 186,209 ----
// the currentSplitChild is needed later when moves are inserted for reloading
assert splitPart.currentSplitChild() == currentInterval : "overwriting wrong currentSplitChild";
splitPart.makeCurrentSplitChild();
! if (debug.isLogEnabled()) {
! debug.log("left interval : %s", currentInterval.logString(allocator));
! debug.log("right interval : %s", splitPart.logString(allocator));
}
if (Options.LSRAOptSplitOnly.getValue(allocator.getOptions())) {
// just add the split interval to the unhandled list
unhandledLists.addToListSortedByStartAndUsePositions(RegisterBinding.Any, splitPart);
} else {
if (isRegister(predecessorLocation)) {
splitRegisterInterval(splitPart, asRegister(predecessorLocation));
} else {
assert isStackSlotValue(predecessorLocation);
! debug.log("assigning interval %s to %s", splitPart, predecessorLocation);
splitPart.assignLocation(predecessorLocation);
// activate interval
activeLists.addToListSortedByCurrentFromPositions(RegisterBinding.Stack, splitPart);
splitPart.state = State.Active;
*** 222,238 ****
assert unhandledLists.get(RegisterBinding.Fixed).isEndMarker() : "must not have unhandled fixed intervals because all fixed intervals have a use at position 0";
spillBlockInactiveFixed(interval);
spillCollectActiveAny(RegisterPriority.LiveAtLoopEnd);
spillCollectInactiveAny(interval);
! if (Debug.isLogEnabled()) {
! try (Indent indent2 = Debug.logAndIndent("state of registers:")) {
for (Register register : availableRegs) {
int i = register.number;
! try (Indent indent3 = Debug.logAndIndent("reg %d: usePos: %d, blockPos: %d, intervals: ", i, usePos[i], blockPos[i])) {
for (int j = 0; j < spillIntervals[i].size(); j++) {
! Debug.log("%d ", spillIntervals[i].get(j).operandNumber);
}
}
}
}
}
--- 224,241 ----
assert unhandledLists.get(RegisterBinding.Fixed).isEndMarker() : "must not have unhandled fixed intervals because all fixed intervals have a use at position 0";
spillBlockInactiveFixed(interval);
spillCollectActiveAny(RegisterPriority.LiveAtLoopEnd);
spillCollectInactiveAny(interval);
! DebugContext debug = allocator.getDebug();
! if (debug.isLogEnabled()) {
! try (Indent indent2 = debug.logAndIndent("state of registers:")) {
for (Register register : availableRegs) {
int i = register.number;
! try (Indent indent3 = debug.logAndIndent("reg %d: usePos: %d, blockPos: %d, intervals: ", i, usePos[i], blockPos[i])) {
for (int j = 0; j < spillIntervals[i].size(); j++) {
! debug.log("%d ", spillIntervals[i].get(j).operandNumber);
}
}
}
}
}
*** 243,253 ****
int splitPos = blockPos[reg.number];
assert splitPos > 0 : "invalid splitPos";
assert needSplit || splitPos > interval.from() : "splitting interval at from";
! Debug.log("assigning interval %s to %s", interval, reg);
interval.assignLocation(reg.asValue(interval.kind()));
if (needSplit) {
// register not available for full interval : so split it
splitWhenPartialRegisterAvailable(interval, splitPos);
}
--- 246,256 ----
int splitPos = blockPos[reg.number];
assert splitPos > 0 : "invalid splitPos";
assert needSplit || splitPos > interval.from() : "splitting interval at from";
! debug.log("assigning interval %s to %s", interval, reg);
interval.assignLocation(reg.asValue(interval.kind()));
if (needSplit) {
// register not available for full interval : so split it
splitWhenPartialRegisterAvailable(interval, splitPos);
}
src/jdk.internal.vm.compiler/share/classes/org.graalvm.compiler.lir/src/org/graalvm/compiler/lir/alloc/lsra/OptimizingLinearScanWalker.java
Index
Unified diffs
Context diffs
Sdiffs
Patch
New
Old
Previous File
Next File