1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2024-11-26 04:32:44 +01:00
llvm-mirror/test/Transforms/InstCombine/gep-vector-indices.ll
Caroline Concatto 7714042905 [InstSimplify] Add constant fold for extractelement + splat for scalable vectors
This patch allows that scalable vector can fold extractelement and constant splat
only when the lane index is lower than the minimum number of elements of the vector.

Differential Revision: https://reviews.llvm.org/D103180
2021-06-10 12:41:40 +01:00

148 lines
6.2 KiB
LLVM

; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
; RUN: opt -instcombine %s -S | FileCheck %s
define i32* @vector_splat_indices_v2i64_ext0(i32* %a) {
; CHECK-LABEL: @vector_splat_indices_v2i64_ext0(
; CHECK-NEXT: [[RES:%.*]] = getelementptr i32, i32* [[A:%.*]], i64 4
; CHECK-NEXT: ret i32* [[RES]]
;
%gep = getelementptr i32, i32* %a, <2 x i64> <i64 4, i64 4>
%res = extractelement <2 x i32*> %gep, i32 0
ret i32* %res
}
define i32* @vector_splat_indices_nxv2i64_ext0(i32* %a) {
; CHECK-LABEL: @vector_splat_indices_nxv2i64_ext0(
; CHECK-NEXT: [[RES:%.*]] = getelementptr inbounds i32, i32* [[A:%.*]], i64 4
; CHECK-NEXT: ret i32* [[RES]]
;
%tmp = insertelement <vscale x 2 x i64> poison, i64 4, i32 0
%splatof4 = shufflevector <vscale x 2 x i64> %tmp, <vscale x 2 x i64> poison, <vscale x 2 x i32> zeroinitializer
%gep = getelementptr inbounds i32, i32* %a, <vscale x 2 x i64> %splatof4
%res = extractelement <vscale x 2 x i32*> %gep, i32 0
ret i32* %res
}
define i32* @vector_indices_v2i64_ext0(i32* %a, <2 x i64> %indices) {
; CHECK-LABEL: @vector_indices_v2i64_ext0(
; CHECK-NEXT: [[TMP0:%.*]] = extractelement <2 x i64> [[INDICES:%.*]], i32 0
; CHECK-NEXT: [[RES:%.*]] = getelementptr i32, i32* [[A:%.*]], i64 [[TMP0]]
; CHECK-NEXT: ret i32* [[RES]]
;
%gep = getelementptr i32, i32* %a, <2 x i64> %indices
%res = extractelement <2 x i32*> %gep, i32 0
ret i32* %res
}
define i32* @vector_indices_nxv1i64_ext0(i32* %a, <vscale x 1 x i64> %indices) {
; CHECK-LABEL: @vector_indices_nxv1i64_ext0(
; CHECK-NEXT: [[TMP0:%.*]] = extractelement <vscale x 1 x i64> [[INDICES:%.*]], i32 0
; CHECK-NEXT: [[RES:%.*]] = getelementptr i32, i32* [[A:%.*]], i64 [[TMP0]]
; CHECK-NEXT: ret i32* [[RES]]
;
%gep = getelementptr i32, i32* %a, <vscale x 1 x i64> %indices
%res = extractelement <vscale x 1 x i32*> %gep, i32 0
ret i32* %res
}
define i32* @vector_splat_ptrs_v2i64_ext0(i32* %a, i64 %index) {
; CHECK-LABEL: @vector_splat_ptrs_v2i64_ext0(
; CHECK-NEXT: [[RES:%.*]] = getelementptr i32, i32* [[A:%.*]], i64 [[INDEX:%.*]]
; CHECK-NEXT: ret i32* [[RES]]
;
%tmp = insertelement <2 x i32*> poison, i32* %a, i32 0
%splatofa = shufflevector <2 x i32*> %tmp, <2 x i32*> poison, <2 x i32> zeroinitializer
%gep = getelementptr i32, <2 x i32*> %splatofa, i64 %index
%res = extractelement <2 x i32*> %gep, i32 0
ret i32* %res
}
define i32* @vector_splat_ptrs_nxv2i64_ext0(i32* %a, i64 %index) {
; CHECK-LABEL: @vector_splat_ptrs_nxv2i64_ext0(
; CHECK-NEXT: [[RES:%.*]] = getelementptr i32, i32* [[A:%.*]], i64 [[INDEX:%.*]]
; CHECK-NEXT: ret i32* [[RES]]
;
%tmp = insertelement <vscale x 2 x i32*> poison, i32* %a, i32 0
%splatofa = shufflevector <vscale x 2 x i32*> %tmp, <vscale x 2 x i32*> poison, <vscale x 2 x i32> zeroinitializer
%gep = getelementptr i32, <vscale x 2 x i32*> %splatofa, i64 %index
%res = extractelement <vscale x 2 x i32*> %gep, i32 0
ret i32* %res
}
define float* @vector_struct1_splat_indices_v4i64_ext1({float, float}* %a) {
; CHECK-LABEL: @vector_struct1_splat_indices_v4i64_ext1(
; CHECK-NEXT: [[RES:%.*]] = getelementptr { float, float }, { float, float }* [[A:%.*]], i64 4, i32 0
; CHECK-NEXT: ret float* [[RES]]
;
%gep = getelementptr {float, float}, {float, float}* %a, <4 x i32> <i32 4, i32 4, i32 4, i32 4>, i32 0
%res = extractelement <4 x float*> %gep, i32 1
ret float* %res
}
define float* @vector_struct2_splat_indices_v4i64_ext1({float, [8 x float]}* %a) {
; CHECK-LABEL: @vector_struct2_splat_indices_v4i64_ext1(
; CHECK-NEXT: [[RES:%.*]] = getelementptr { float, [8 x float] }, { float, [8 x float] }* [[A:%.*]], i64 2, i32 1, i64 4
; CHECK-NEXT: ret float* [[RES]]
;
%gep = getelementptr {float, [8 x float]}, {float, [8 x float]}* %a, i32 2, i32 1, <4 x i32> <i32 4, i32 4, i32 4, i32 4>
%res = extractelement <4 x float*> %gep, i32 1
ret float* %res
}
; Negative tests
define i32* @vector_indices_nxv2i64_ext3(i32* %a, <vscale x 2 x i64> %indices) {
; CHECK-LABEL: @vector_indices_nxv2i64_ext3(
; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, i32* [[A:%.*]], <vscale x 2 x i64> [[INDICES:%.*]]
; CHECK-NEXT: [[RES:%.*]] = extractelement <vscale x 2 x i32*> [[GEP]], i32 3
; CHECK-NEXT: ret i32* [[RES]]
;
%gep = getelementptr i32, i32* %a, <vscale x 2 x i64> %indices
%res = extractelement <vscale x 2 x i32*> %gep, i32 3
ret i32* %res
}
define i32* @vector_indices_nxv2i64_extN(i32* %a, <vscale x 2 x i64> %indices, i32 %N) {
; CHECK-LABEL: @vector_indices_nxv2i64_extN(
; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, i32* [[A:%.*]], <vscale x 2 x i64> [[INDICES:%.*]]
; CHECK-NEXT: [[RES:%.*]] = extractelement <vscale x 2 x i32*> [[GEP]], i32 [[N:%.*]]
; CHECK-NEXT: ret i32* [[RES]]
;
%gep = getelementptr i32, i32* %a, <vscale x 2 x i64> %indices
%res = extractelement <vscale x 2 x i32*> %gep, i32 %N
ret i32* %res
}
define void @vector_indices_nxv2i64_mulitple_use(i32* %a, <vscale x 2 x i64> %indices, i32** %b, i32** %c) {
; CHECK-LABEL: @vector_indices_nxv2i64_mulitple_use(
; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, i32* [[A:%.*]], <vscale x 2 x i64> [[INDICES:%.*]]
; CHECK-NEXT: [[LANE0:%.*]] = extractelement <vscale x 2 x i32*> [[GEP]], i32 0
; CHECK-NEXT: [[LANE1:%.*]] = extractelement <vscale x 2 x i32*> [[GEP]], i32 1
; CHECK-NEXT: store i32* [[LANE0]], i32** [[B:%.*]], align 8
; CHECK-NEXT: store i32* [[LANE1]], i32** [[C:%.*]], align 8
; CHECK-NEXT: ret void
;
%gep = getelementptr i32, i32* %a, <vscale x 2 x i64> %indices
%lane0 = extractelement <vscale x 2 x i32*> %gep, i32 0
%lane1 = extractelement <vscale x 2 x i32*> %gep, i32 1
store i32* %lane0, i32** %b, align 8
store i32* %lane1, i32** %c, align 8
ret void
}
define i32* @vector_ptrs_and_indices_ext0(<vscale x 4 x i32*> %a, <vscale x 4 x i64> %indices) {
; CHECK-LABEL: @vector_ptrs_and_indices_ext0(
; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, <vscale x 4 x i32*> [[A:%.*]], <vscale x 4 x i64> [[INDICES:%.*]]
; CHECK-NEXT: [[RES:%.*]] = extractelement <vscale x 4 x i32*> [[GEP]], i32 0
; CHECK-NEXT: ret i32* [[RES]]
;
%gep = getelementptr i32, <vscale x 4 x i32*> %a, <vscale x 4 x i64> %indices
%res = extractelement <vscale x 4 x i32*> %gep, i32 0
ret i32* %res
}