Skip to content

Commit 9e80e06

Browse files
mshelegoigcbot
authored andcommitted
GenXStructSplitter opaque pointers fix
Handle the special opaque pointers case when a GEP user indexing into a non-structure type because leading zero indices are omitted.
1 parent 5e4a7b9 commit 9e80e06

File tree

2 files changed

+62
-8
lines changed

2 files changed

+62
-8
lines changed

IGC/VectorCompiler/lib/GenXCodeGen/GenXStructSplitter.cpp

Lines changed: 21 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
/*========================== begin_copyright_notice ============================
22
3-
Copyright (C) 2021-2024 Intel Corporation
3+
Copyright (C) 2021-2025 Intel Corporation
44
55
SPDX-License-Identifier: MIT
66
@@ -1582,6 +1582,16 @@ bool Substituter::processGEP(GetElementPtrInst &GEPI,
15821582
unsigned PlainTyIdx = FindIt - GottenTypeArr.begin();
15831583

15841584
if (PlainTyIdx == Size) {
1585+
Type *PrevType = IdxPath.getTyAt(Size - 1);
1586+
// In case of opaque pointers, GEP's leading zero indices can be omitted and
1587+
// in this case previous type is not a structure type
1588+
if (!isa<StructType>(PrevType)) {
1589+
Type *PlainType = getBaseTy(GottenTypeArr[Size - 1]);
1590+
Instruction *ToInsert =
1591+
generateNewGEPs(GEPI, *PlainType, IdxPath, NewInstr, Size - 1);
1592+
InstToInst.emplace_back(cast<Instruction>(&GEPI), ToInsert);
1593+
return true;
1594+
}
15851595
// Case of FE1
15861596
auto InstUses = getInstUses(GEPI);
15871597
if (!InstUses)
@@ -1590,7 +1600,6 @@ bool Substituter::processGEP(GetElementPtrInst &GEPI,
15901600

15911601
// That means that we are getting split struct so we need to create GEPs.
15921602
// STyToBeSplit is the result of the instruction.
1593-
Type *PrevType = IdxPath.getTyAt(Size - 1);
15941603
unsigned Idx = IdxPath.getIdxAt(Size - 1);
15951604
StructType *STyToBeSplit = cast<StructType>(PrevType);
15961605
const ListOfSplitElements &ListOfPossibleTypes =
@@ -1621,14 +1630,18 @@ bool Substituter::processGEP(GetElementPtrInst &GEPI,
16211630
return false;
16221631
} else {
16231632
Type *PrevType = IdxPath.getTyAt(PlainTyIdx);
1624-
unsigned Idx = IdxPath.getIdxAt(PlainTyIdx);
1625-
StructType *STyToBeSplit = cast<StructType>(PrevType);
1626-
IGC_ASSERT_MESSAGE(
1627-
Graph.getElementsListOfSTyAtIdx(*STyToBeSplit, Idx).size() == 1,
1628-
"Access to element of Struct does not get unsplit type.");
16291633
Type *PlainType = getBaseTy(GottenTypeArr[PlainTyIdx]);
1634+
// In case of opaque pointers, GEP's leading zero indices can be omitted and
1635+
// in this case previous type is not a structure type
1636+
if (auto *STyToBeSplit = dyn_cast<StructType>(PrevType)) {
1637+
unsigned Idx = IdxPath.getIdxAt(PlainTyIdx);
1638+
IGC_ASSERT_MESSAGE(
1639+
Graph.getElementsListOfSTyAtIdx(*STyToBeSplit, Idx).size() == 1,
1640+
"Access to element of Struct does not get unsplit type.");
1641+
PlainTyIdx += 1;
1642+
}
16301643
Instruction *ToInsert =
1631-
generateNewGEPs(GEPI, *PlainType, IdxPath, NewInstr, PlainTyIdx + 1);
1644+
generateNewGEPs(GEPI, *PlainType, IdxPath, NewInstr, PlainTyIdx);
16321645
InstToInst.emplace_back(cast<Instruction>(&GEPI), ToInsert);
16331646
}
16341647
return true;
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
;=========================== begin_copyright_notice ============================
2+
;
3+
; Copyright (C) 2025 Intel Corporation
4+
;
5+
; SPDX-License-Identifier: MIT
6+
;
7+
;============================ end_copyright_notice =============================
8+
9+
; RUN: %opt_opaque_ptrs %use_old_pass_manager% -GenXStructSplitter -dce -vc-struct-splitting=1 -march=genx64 -mcpu=XeLP -S < %s | FileCheck %s --check-prefixes=CHECK
10+
11+
%struct1 = type { [6 x %struct2] }
12+
%struct2 = type { [129 x float] }
13+
14+
; CHECK-LABEL: @test1
15+
define dllexport spir_kernel void @test1(float %val, i64 %idx1, i64 %idx2) {
16+
entry:
17+
; CHECK: [[ALLOCA_F:%.*]] = alloca [6 x %struct2]
18+
%alloca = alloca %struct1
19+
; CHECK-NEXT: [[GEP1_SPLIT:%.*]] = getelementptr [6 x %struct2], ptr [[ALLOCA_F]], i64 0, i64 %idx1
20+
%gep1 = getelementptr [6 x %struct2], ptr %alloca, i64 0, i64 %idx1
21+
; CHECK-NEXT: [[GEP2:%.*]] = getelementptr [129 x float], ptr [[GEP1_SPLIT]], i64 0, i64 %idx2
22+
%gep2 = getelementptr [129 x float], ptr %gep1, i64 0, i64 %idx2
23+
; CHECK-NEXT: store float %val, ptr [[GEP2]]
24+
store float %val, ptr %gep2
25+
; CHECK-NEXT: ret void
26+
ret void
27+
}
28+
29+
; CHECK-LABEL: @test2
30+
define dllexport spir_kernel void @test2(float %val, i64 %idx) {
31+
entry:
32+
; CHECK: [[ALLOCA_F:%.*]] = alloca [6 x %struct2]
33+
%alloca = alloca %struct1
34+
; CHECK-NEXT: [[GEP_SPLIT:%.*]] = getelementptr [129 x float], ptr [[ALLOCA_F]], i64 0, i64 %idx
35+
%gep = getelementptr [129 x float], ptr %alloca, i64 0, i64 %idx
36+
; CHECK-NEXT: store float %val, ptr [[GEP_SPLIT]]
37+
store float %val, ptr %gep
38+
; CHECK-NEXT: ret void
39+
ret void
40+
}
41+

0 commit comments

Comments
 (0)