Skip to content

Commit 56beac9

Browse files
authored
[SPIRV] Fix assertion violation caused by unexpected ConstantExpr. (#170524)
`SPIRVEmitIntrinsics::simplifyZeroLengthArrayGepInst` asserted that it always expected a `GetElementPtrInst` from `IRBuilder::CreateGEP` (which returns a `Value`). `IRBuilder` can fold and return a `ConstantExpr` instead, thus violating the assertion. The patch fixes this by using `GetElementPtrInst::Create` to always return a `GetElementPtrInst`. This LLVM defect was identified via the AMD Fuzzing project.
1 parent e52cddc commit 56beac9

File tree

2 files changed

+22
-5
lines changed

2 files changed

+22
-5
lines changed

llvm/lib/Target/SPIRV/SPIRVEmitIntrinsics.cpp

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2834,13 +2834,11 @@ SPIRVEmitIntrinsics::simplifyZeroLengthArrayGepInst(GetElementPtrInst *GEP) {
28342834
ArrayType *ArrTy = dyn_cast<ArrayType>(SrcTy);
28352835
if (ArrTy && ArrTy->getNumElements() == 0 &&
28362836
PatternMatch::match(Indices[0], PatternMatch::m_Zero())) {
2837-
IRBuilder<> Builder(GEP);
28382837
Indices.erase(Indices.begin());
28392838
SrcTy = ArrTy->getElementType();
2840-
Value *NewGEP = Builder.CreateGEP(SrcTy, GEP->getPointerOperand(), Indices,
2841-
"", GEP->getNoWrapFlags());
2842-
assert(llvm::isa<GetElementPtrInst>(NewGEP) && "NewGEP should be a GEP");
2843-
return cast<GetElementPtrInst>(NewGEP);
2839+
return GetElementPtrInst::Create(SrcTy, GEP->getPointerOperand(), Indices,
2840+
GEP->getNoWrapFlags(), "",
2841+
GEP->getIterator());
28442842
}
28452843
return nullptr;
28462844
}
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 6
2+
; RUN: llc -O0 -mtriple=spirv64-unknown-unknown < %s | FileCheck %s
3+
; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown < %s -filetype=obj | spirv-val %}
4+
5+
define spir_kernel void @_Z6kernelPi() addrspace(4) {
6+
; CHECK-LABEL: _Z6kernelPi
7+
; CHECK: %12 = OpFunction %3 None %4 ; -- Begin function _Z6kernelPi
8+
; CHECK-NEXT: %2 = OpLabel
9+
; CHECK-NEXT: %13 = OpBitcast %6 %11
10+
; CHECK-NEXT: %14 = OpInBoundsPtrAccessChain %6 %13 %10
11+
; CHECK-NEXT: %15 = OpConvertPtrToU %5 %14
12+
; CHECK-NEXT: %16 = OpBitcast %6 %11
13+
; CHECK-NEXT: OpStore %16 %15 Aligned 4
14+
; CHECK-NEXT: OpReturn
15+
; CHECK-NEXT: OpFunctionEnd
16+
entry:
17+
store i32 ptrtoint (ptr addrspace(4) getelementptr inbounds ([0 x i32], ptr addrspace(4) null, i64 0, i64 1) to i32), ptr addrspace(4) null, align 4
18+
ret void
19+
}

0 commit comments

Comments
 (0)