mirror of
https://github.com/capstone-engine/llvm-capstone.git
synced 2024-11-27 07:31:28 +00:00
[RISCV] Prevent RISCVMergeBaseOffsetOpt from calling getVRegDef on a physical register. (#78762)
Fixes #78679.
This commit is contained in:
parent
924701311a
commit
9ae28fb9d3
@ -181,7 +181,7 @@ bool RISCVMergeBaseOffsetOpt::foldLargeOffset(MachineInstr &Hi,
|
||||
Register Reg = Rs == GAReg ? Rt : Rs;
|
||||
|
||||
// Can't fold if the register has more than one use.
|
||||
if (!MRI->hasOneUse(Reg))
|
||||
if (!Reg.isVirtual() || !MRI->hasOneUse(Reg))
|
||||
return false;
|
||||
// This can point to an ADDI(W) or a LUI:
|
||||
MachineInstr &OffsetTail = *MRI->getVRegDef(Reg);
|
||||
@ -192,9 +192,11 @@ bool RISCVMergeBaseOffsetOpt::foldLargeOffset(MachineInstr &Hi,
|
||||
MachineOperand &AddiImmOp = OffsetTail.getOperand(2);
|
||||
if (AddiImmOp.getTargetFlags() != RISCVII::MO_None)
|
||||
return false;
|
||||
Register AddiReg = OffsetTail.getOperand(1).getReg();
|
||||
if (!AddiReg.isVirtual())
|
||||
return false;
|
||||
int64_t OffLo = AddiImmOp.getImm();
|
||||
MachineInstr &OffsetLui =
|
||||
*MRI->getVRegDef(OffsetTail.getOperand(1).getReg());
|
||||
MachineInstr &OffsetLui = *MRI->getVRegDef(AddiReg);
|
||||
MachineOperand &LuiImmOp = OffsetLui.getOperand(1);
|
||||
if (OffsetLui.getOpcode() != RISCV::LUI ||
|
||||
LuiImmOp.getTargetFlags() != RISCVII::MO_None ||
|
||||
@ -246,14 +248,14 @@ bool RISCVMergeBaseOffsetOpt::foldShiftedOffset(MachineInstr &Hi,
|
||||
TailShXAdd.getOpcode() == RISCV::SH3ADD) &&
|
||||
"Expected SHXADD instruction!");
|
||||
|
||||
// The first source is the shifted operand.
|
||||
Register Rs1 = TailShXAdd.getOperand(1).getReg();
|
||||
|
||||
if (GAReg != TailShXAdd.getOperand(2).getReg())
|
||||
return false;
|
||||
|
||||
// The first source is the shifted operand.
|
||||
Register Rs1 = TailShXAdd.getOperand(1).getReg();
|
||||
|
||||
// Can't fold if the register has more than one use.
|
||||
if (!MRI->hasOneUse(Rs1))
|
||||
if (!Rs1.isVirtual() || !MRI->hasOneUse(Rs1))
|
||||
return false;
|
||||
// This can point to an ADDI X0, C.
|
||||
MachineInstr &OffsetTail = *MRI->getVRegDef(Rs1);
|
||||
|
@ -964,3 +964,69 @@ for.body: ; preds = %for.body.lr.ph, %fo
|
||||
}
|
||||
|
||||
declare void @f(ptr)
|
||||
|
||||
@g = external dso_local global [100 x [100 x i8]]
|
||||
|
||||
; This test used to crash due to calling getVRegDef on X0.
|
||||
define i32 @crash() {
|
||||
; RV32I-LABEL: crash:
|
||||
; RV32I: # %bb.0: # %entry
|
||||
; RV32I-NEXT: li a0, 1
|
||||
; RV32I-NEXT: lui a1, %hi(g)
|
||||
; RV32I-NEXT: addi a1, a1, %lo(g)
|
||||
; RV32I-NEXT: add a0, a1, a0
|
||||
; RV32I-NEXT: lbu a0, 400(a0)
|
||||
; RV32I-NEXT: seqz a0, a0
|
||||
; RV32I-NEXT: sw a0, 0(zero)
|
||||
; RV32I-NEXT: li a0, 0
|
||||
; RV32I-NEXT: ret
|
||||
;
|
||||
; RV32I-MEDIUM-LABEL: crash:
|
||||
; RV32I-MEDIUM: # %bb.0: # %entry
|
||||
; RV32I-MEDIUM-NEXT: li a0, 1
|
||||
; RV32I-MEDIUM-NEXT: .Lpcrel_hi14:
|
||||
; RV32I-MEDIUM-NEXT: auipc a1, %pcrel_hi(g)
|
||||
; RV32I-MEDIUM-NEXT: addi a1, a1, %pcrel_lo(.Lpcrel_hi14)
|
||||
; RV32I-MEDIUM-NEXT: add a0, a1, a0
|
||||
; RV32I-MEDIUM-NEXT: lbu a0, 400(a0)
|
||||
; RV32I-MEDIUM-NEXT: seqz a0, a0
|
||||
; RV32I-MEDIUM-NEXT: sw a0, 0(zero)
|
||||
; RV32I-MEDIUM-NEXT: li a0, 0
|
||||
; RV32I-MEDIUM-NEXT: ret
|
||||
;
|
||||
; RV64I-LABEL: crash:
|
||||
; RV64I: # %bb.0: # %entry
|
||||
; RV64I-NEXT: li a0, 1
|
||||
; RV64I-NEXT: lui a1, %hi(g)
|
||||
; RV64I-NEXT: addi a1, a1, %lo(g)
|
||||
; RV64I-NEXT: add a0, a1, a0
|
||||
; RV64I-NEXT: lbu a0, 400(a0)
|
||||
; RV64I-NEXT: seqz a0, a0
|
||||
; RV64I-NEXT: sw a0, 0(zero)
|
||||
; RV64I-NEXT: li a0, 0
|
||||
; RV64I-NEXT: ret
|
||||
;
|
||||
; RV64I-MEDIUM-LABEL: crash:
|
||||
; RV64I-MEDIUM: # %bb.0: # %entry
|
||||
; RV64I-MEDIUM-NEXT: li a0, 1
|
||||
; RV64I-MEDIUM-NEXT: .Lpcrel_hi14:
|
||||
; RV64I-MEDIUM-NEXT: auipc a1, %pcrel_hi(g)
|
||||
; RV64I-MEDIUM-NEXT: addi a1, a1, %pcrel_lo(.Lpcrel_hi14)
|
||||
; RV64I-MEDIUM-NEXT: add a0, a1, a0
|
||||
; RV64I-MEDIUM-NEXT: lbu a0, 400(a0)
|
||||
; RV64I-MEDIUM-NEXT: seqz a0, a0
|
||||
; RV64I-MEDIUM-NEXT: sw a0, 0(zero)
|
||||
; RV64I-MEDIUM-NEXT: li a0, 0
|
||||
; RV64I-MEDIUM-NEXT: ret
|
||||
entry:
|
||||
%idxprom7.peel = sext i32 1 to i64
|
||||
br label %for.inc.peel
|
||||
|
||||
for.inc.peel: ; preds = %entry
|
||||
%arrayidx8.3.peel = getelementptr [100 x [100 x i8]], ptr @g, i64 0, i64 4, i64 %idxprom7.peel
|
||||
%0 = load i8, ptr %arrayidx8.3.peel, align 1
|
||||
%tobool.not.3.peel = icmp eq i8 %0, 0
|
||||
%spec.select = select i1 %tobool.not.3.peel, i32 1, i32 0
|
||||
store i32 %spec.select, ptr null, align 4
|
||||
ret i32 0
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user