WebAssemblyFrameLowering::getOpcConst(MF) &&
MRI.hasOneNonDBGUse(Def->getOperand(0).getReg())) {
MachineOperand &ImmMO = Def->getOperand(1);
- ImmMO.setImm(ImmMO.getImm() + uint32_t(FrameOffset));
- MI.getOperand(FIOperandNum)
- .ChangeToRegister(FrameRegister, /*isDef=*/false);
- return;
+ if (ImmMO.isImm()) {
+ ImmMO.setImm(ImmMO.getImm() + uint32_t(FrameOffset));
+ MI.getOperand(FIOperandNum)
+ .ChangeToRegister(FrameRegister, /*isDef=*/false);
+ return;
+ }
}
}
}
ret void
}
+; We optimize the format of "frame offset + operand" by folding it, but this is
+; only possible when that operand is an immediate. In this example it is a
+; global address, so we should not fold it.
+; CHECK-LABEL: frame_offset_with_global_address
+; CHECK: i[[PTR]].const ${{.*}}=, str
+@str = local_unnamed_addr global [3 x i8] c"abc", align 16
+define i8 @frame_offset_with_global_address() {
+ %1 = alloca i8, align 4
+ %2 = ptrtoint i8* %1 to i32
+ ;; Here @str is a global address and not an immediate, so cannot be folded
+ %3 = getelementptr [3 x i8], [3 x i8]* @str, i32 0, i32 %2
+ %4 = load i8, i8* %3, align 8
+ %5 = and i8 %4, 67
+ ret i8 %5
+}
+
; CHECK: .globaltype __stack_pointer, i[[PTR]]{{$}}
; TODO: test over-aligned alloca