use of org.graalvm.compiler.lir.LIRInstruction.OperandFlag 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);
}
});
}
}
use of org.graalvm.compiler.lir.LIRInstruction.OperandFlag in project graal by oracle.
the class RegisterVerifier method processOperations.
void processOperations(AbstractBlockBase<?> block, final Interval[] inputState) {
ArrayList<LIRInstruction> ops = allocator.getLIR().getLIRforBlock(block);
DebugContext debug = allocator.getDebug();
InstructionValueConsumer useConsumer = new InstructionValueConsumer() {
@Override
public void visitValue(LIRInstruction op, Value operand, OperandMode mode, EnumSet<OperandFlag> flags) {
// we skip spill moves inserted by the spill position optimization
if (LinearScan.isVariableOrRegister(operand) && allocator.isProcessed(operand) && op.id() != LinearScan.DOMINATOR_SPILL_MOVE_ID) {
Interval interval = intervalAt(operand);
if (op.id() != -1) {
interval = interval.getSplitChildAtOpId(op.id(), mode, allocator);
}
assert checkState(block, op, inputState, interval.operand, interval.location(), interval.splitParent());
}
}
};
InstructionValueConsumer defConsumer = (op, operand, mode, flags) -> {
if (LinearScan.isVariableOrRegister(operand) && allocator.isProcessed(operand)) {
Interval interval = intervalAt(operand);
if (op.id() != -1) {
interval = interval.getSplitChildAtOpId(op.id(), mode, allocator);
}
statePut(debug, inputState, interval.location(), interval.splitParent());
}
};
// visit all instructions of the block
for (int i = 0; i < ops.size(); i++) {
final LIRInstruction op = ops.get(i);
if (debug.isLogEnabled()) {
debug.log("%s", op.toStringWithIdPrefix());
}
// check if input operands are correct
op.visitEachInput(useConsumer);
// invalidate all caller save registers at calls
if (op.destroysCallerSavedRegisters()) {
for (Register r : allocator.getRegisterAllocationConfig().getRegisterConfig().getCallerSaveRegisters()) {
statePut(debug, inputState, r.asValue(), null);
}
}
op.visitEachAlive(useConsumer);
// set temp operands (some operations use temp operands also as output operands, so
// can't set them null)
op.visitEachTemp(defConsumer);
// set output operands
op.visitEachOutput(defConsumer);
}
}
use of org.graalvm.compiler.lir.LIRInstruction.OperandFlag in project graal by oracle.
the class RegisterVerifier method processOperations.
void processOperations(AbstractBlockBase<?> block, final TraceInterval[] inputState) {
ArrayList<LIRInstruction> ops = allocator.getLIR().getLIRforBlock(block);
DebugContext debug = allocator.getDebug();
InstructionValueConsumer useConsumer = new InstructionValueConsumer() {
@Override
public void visitValue(LIRInstruction op, Value operand, OperandMode mode, EnumSet<OperandFlag> flags) {
// we skip spill moves inserted by the spill position optimization
if (isVariableOrRegister(operand) && allocator.isProcessed(operand) && op.id() != TraceLinearScanPhase.DOMINATOR_SPILL_MOVE_ID) {
TraceInterval interval = intervalAt(asVariable(operand));
if (op.id() != -1) {
interval = interval.getSplitChildAtOpId(op.id(), mode);
}
assert checkState(block, op, inputState, allocator.getOperand(interval), interval.location(), interval.splitParent());
}
}
};
InstructionValueConsumer defConsumer = (op, operand, mode, flags) -> {
if (isVariableOrRegister(operand) && allocator.isProcessed(operand)) {
TraceInterval interval = intervalAt(asVariable(operand));
if (op.id() != -1) {
interval = interval.getSplitChildAtOpId(op.id(), mode);
}
statePut(debug, inputState, interval.location(), interval.splitParent());
}
};
// visit all instructions of the block
for (int i = 0; i < ops.size(); i++) {
final LIRInstruction op = ops.get(i);
if (debug.isLogEnabled()) {
debug.log("%s", op.toStringWithIdPrefix());
}
// check if input operands are correct
op.visitEachInput(useConsumer);
// invalidate all caller save registers at calls
if (op.destroysCallerSavedRegisters()) {
for (Register r : allocator.getRegisterAllocationConfig().getRegisterConfig().getCallerSaveRegisters()) {
statePut(debug, inputState, r.asValue(), null);
}
}
op.visitEachAlive(useConsumer);
// set temp operands (some operations use temp operands also as output operands, so
// can't set them null)
op.visitEachTemp(defConsumer);
// set output operands
op.visitEachOutput(defConsumer);
}
}
use of org.graalvm.compiler.lir.LIRInstruction.OperandFlag in project graal by oracle.
the class FrameMapBuilderImpl method verifyStackSlotAllocation.
private static void verifyStackSlotAllocation(LIRGenerationResult res) {
LIR lir = res.getLIR();
InstructionValueConsumer verifySlots = (LIRInstruction op, Value value, OperandMode mode, EnumSet<OperandFlag> flags) -> {
assert !isVirtualStackSlot(value) : String.format("Instruction %s contains a virtual stack slot %s", op, value);
};
for (AbstractBlockBase<?> block : lir.getControlFlowGraph().getBlocks()) {
lir.getLIRforBlock(block).forEach(op -> {
op.visitEachInput(verifySlots);
op.visitEachAlive(verifySlots);
op.visitEachState(verifySlots);
op.visitEachTemp(verifySlots);
op.visitEachOutput(verifySlots);
});
}
}
Aggregations