use of jdk.vm.ci.meta.AllocatableValue in project graal by oracle.
the class LIRFrameState method processValues.
protected void processValues(LIRInstruction inst, JavaValue[] values, InstructionValueProcedure proc) {
for (int i = 0; i < values.length; i++) {
JavaValue value = values[i];
if (isIllegalJavaValue(value)) {
continue;
}
if (value instanceof AllocatableValue) {
AllocatableValue allocatable = (AllocatableValue) value;
Value result = proc.doValue(inst, allocatable, OperandMode.ALIVE, STATE_FLAGS);
if (!allocatable.identityEquals(result)) {
values[i] = (JavaValue) result;
}
} else if (value instanceof StackLockValue) {
StackLockValue monitor = (StackLockValue) value;
JavaValue owner = monitor.getOwner();
if (owner instanceof AllocatableValue) {
monitor.setOwner((JavaValue) proc.doValue(inst, (AllocatableValue) owner, OperandMode.ALIVE, STATE_FLAGS));
}
Value slot = monitor.getSlot();
if (isVirtualStackSlot(slot)) {
monitor.setSlot(asAllocatableValue(proc.doValue(inst, slot, OperandMode.ALIVE, STATE_FLAGS)));
}
} else {
assert unprocessed(value);
}
}
}
use of jdk.vm.ci.meta.AllocatableValue in project graal by oracle.
the class TraceLinearScanPhase method printFixedInterval.
private static void printFixedInterval(FixedInterval interval, IntervalVisitor visitor) {
Value hint = null;
AllocatableValue operand = interval.operand;
String type = "fixed";
visitor.visitIntervalStart(operand, operand, operand, hint, type);
// print ranges
for (FixedRange range = interval.first(); range != FixedRange.EndMarker; range = range.next) {
visitor.visitRange(range.from, range.to);
}
// no use positions
visitor.visitIntervalEnd("NOT_SUPPORTED");
}
use of jdk.vm.ci.meta.AllocatableValue in project graal by oracle.
the class TraceLocalMoveResolver method resolveMappings.
@SuppressWarnings("try")
private void resolveMappings() {
try (Indent indent = debug.logAndIndent("resolveMapping")) {
assert verifyBeforeResolve();
if (debug.isLogEnabled()) {
printMapping();
}
// Block all registers that are used as input operands of a move.
// When a register is blocked, no move to this register is emitted.
// This is necessary for detecting cycles in moves.
int i;
for (i = mappingFrom.size() - 1; i >= 0; i--) {
TraceInterval fromInterval = mappingFrom.get(i);
if (fromInterval != null) {
blockRegisters(fromInterval);
}
}
ArrayList<AllocatableValue> busySpillSlots = null;
while (mappingFrom.size() > 0) {
boolean processedInterval = false;
int spillCandidate = -1;
for (i = mappingFrom.size() - 1; i >= 0; i--) {
TraceInterval fromInterval = mappingFrom.get(i);
TraceInterval toInterval = mappingTo.get(i);
if (safeToProcessMove(fromInterval, toInterval)) {
// this interval can be processed because target is free
if (fromInterval != null) {
insertMove(fromInterval, toInterval);
unblockRegisters(fromInterval);
} else {
insertMove(mappingFromOpr.get(i), toInterval);
}
if (isStackSlotValue(toInterval.location())) {
if (busySpillSlots == null) {
busySpillSlots = new ArrayList<>(2);
}
busySpillSlots.add(toInterval.location());
}
mappingFrom.remove(i);
mappingFromOpr.remove(i);
mappingTo.remove(i);
processedInterval = true;
} else if (fromInterval != null && isRegister(fromInterval.location()) && (busySpillSlots == null || !busySpillSlots.contains(fromInterval.spillSlot()))) {
// this interval cannot be processed now because target is not free
// it starts in a register, so it is a possible candidate for spilling
spillCandidate = i;
}
}
if (!processedInterval) {
breakCycle(spillCandidate);
}
}
}
// check that all intervals have been processed
assert checkEmpty();
}
use of jdk.vm.ci.meta.AllocatableValue in project graal by oracle.
the class MoveResolver method resolveMappings.
@SuppressWarnings("try")
private void resolveMappings() {
DebugContext debug = allocator.getDebug();
try (Indent indent = debug.logAndIndent("resolveMapping")) {
assert verifyBeforeResolve();
if (debug.isLogEnabled()) {
printMapping();
}
// Block all registers that are used as input operands of a move.
// When a register is blocked, no move to this register is emitted.
// This is necessary for detecting cycles in moves.
int i;
for (i = mappingFrom.size() - 1; i >= 0; i--) {
Interval fromInterval = mappingFrom.get(i);
if (fromInterval != null) {
blockRegisters(fromInterval);
}
}
ArrayList<AllocatableValue> busySpillSlots = null;
while (mappingFrom.size() > 0) {
boolean processedInterval = false;
int spillCandidate = -1;
for (i = mappingFrom.size() - 1; i >= 0; i--) {
Interval fromInterval = mappingFrom.get(i);
Interval toInterval = mappingTo.get(i);
if (safeToProcessMove(fromInterval, toInterval)) {
// this interval can be processed because target is free
final LIRInstruction move;
if (fromInterval != null) {
move = insertMove(fromInterval, toInterval);
unblockRegisters(fromInterval);
} else {
move = insertMove(mappingFromOpr.get(i), toInterval);
}
move.setComment(res, "MoveResolver resolve mapping");
if (LIRValueUtil.isStackSlotValue(toInterval.location())) {
if (busySpillSlots == null) {
busySpillSlots = new ArrayList<>(2);
}
busySpillSlots.add(toInterval.location());
}
mappingFrom.remove(i);
mappingFromOpr.remove(i);
mappingTo.remove(i);
processedInterval = true;
} else if (fromInterval != null && isRegister(fromInterval.location()) && (busySpillSlots == null || !busySpillSlots.contains(fromInterval.spillSlot()))) {
// this interval cannot be processed now because target is not free
// it starts in a register, so it is a possible candidate for spilling
spillCandidate = i;
}
}
if (!processedInterval) {
breakCycle(spillCandidate);
}
}
}
// reset to default value
multipleReadsAllowed = false;
// check that all intervals have been processed
assert checkEmpty();
}
use of jdk.vm.ci.meta.AllocatableValue in project graal by oracle.
the class SSALinearScanLifetimeAnalysisPhase method addRegisterHint.
@Override
protected void addRegisterHint(final LIRInstruction op, final Value targetValue, OperandMode mode, EnumSet<OperandFlag> flags, final boolean hintAtDef) {
super.addRegisterHint(op, targetValue, mode, flags, hintAtDef);
if (hintAtDef && op instanceof LabelOp) {
LabelOp label = (LabelOp) op;
Interval to = allocator.getOrCreateInterval((AllocatableValue) targetValue);
SSAUtil.forEachPhiRegisterHint(allocator.getLIR(), allocator.blockForId(label.id()), label, targetValue, mode, (ValueConsumer) (registerHint, valueMode, valueFlags) -> {
if (LinearScan.isVariableOrRegister(registerHint)) {
Interval from = allocator.getOrCreateInterval((AllocatableValue) registerHint);
setHint(debug, op, to, from);
setHint(debug, op, from, to);
}
});
}
}
Aggregations