diff --git a/llvm/lib/Transforms/Scalar/SeparateConstOffsetFromGEP.cpp b/llvm/lib/Transforms/Scalar/SeparateConstOffsetFromGEP.cpp --- a/llvm/lib/Transforms/Scalar/SeparateConstOffsetFromGEP.cpp +++ b/llvm/lib/Transforms/Scalar/SeparateConstOffsetFromGEP.cpp @@ -1003,6 +1003,15 @@ // one. If LowerGEP is enabled, a structure index is accumulated in the // constant offset. LowerToSingleIndexGEPs or lowerToArithmetics will later // handle the constant offset and won't need a new structure index. + + // If GEP only has one index and it is used by non-gep instructions, + // it is not benificial to do the split. + if (GEP->getNumOperands() == 2) { + Value *Idx = GEP->getOperand(1); + if (!llvm::all_of(Idx->users(), + [](const User *U) { return isa(U); })) + return false; + } gep_type_iterator GTI = gep_type_begin(*GEP); for (unsigned I = 1, E = GEP->getNumOperands(); I != E; ++I, ++GTI) { if (GTI.isSequential()) { diff --git a/llvm/test/CodeGen/AArch64/aarch64-loop-gep-opt.ll b/llvm/test/CodeGen/AArch64/aarch64-loop-gep-opt.ll --- a/llvm/test/CodeGen/AArch64/aarch64-loop-gep-opt.ll +++ b/llvm/test/CodeGen/AArch64/aarch64-loop-gep-opt.ll @@ -48,3 +48,29 @@ br label %do.body.i.backedge } + +define i64 @test_loop2(i64* %arg, i64* %save, i64 %tmp1) { +bb: +; CHECK-LABEL: bb: +; CHECK %tmp1 = load i64, i64* null, align 8 +; CHECK %tmp22 = add nsw i64 %tmp1, -1 +; CHECK-NOT %uglygep = getelementptr i8, i8* %0, i64 %1 +; CHECK-NOT %uglygep2 = getelementptr i8, i8* %uglygep, i64 -8 + + %tmp22 = add nsw i64 %tmp1, -1 + %tmp23 = getelementptr inbounds i64, i64* %arg, i64 %tmp22 + %tmp24 = load i64, i64* %tmp23, align 2 + br label %bb25 + +bb25: ; preds = %bb25, %bb18 + %tmp26 = phi i64 [ 1, %bb ], [ 0, %bb25 ] + %tmp29 = icmp eq i64 0, %tmp24 + %tmp30 = select i1 %tmp29, i64 0, i64 %tmp26 + store i64 %tmp30, i64* %save + %tmp31 = icmp eq i64 0, %tmp22 + br i1 %tmp31, label %bb32, label %bb25 + +bb32: ; preds = %bb25 + ret i64 0 + +} \ No newline at end of file diff --git a/llvm/test/Transforms/SeparateConstOffsetFromGEP/RISCV/split-gep.ll b/llvm/test/Transforms/SeparateConstOffsetFromGEP/RISCV/split-gep.ll --- a/llvm/test/Transforms/SeparateConstOffsetFromGEP/RISCV/split-gep.ll +++ b/llvm/test/Transforms/SeparateConstOffsetFromGEP/RISCV/split-gep.ll @@ -11,13 +11,13 @@ ; CHECK-LABEL: @test1( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[ADD:%.*]] = add nsw i64 [[I:%.*]], 5 -; CHECK-NEXT: [[TMP0:%.*]] = getelementptr i64, i64* [[ARRAY:%.*]], i64 [[I]] -; CHECK-NEXT: [[GEP4:%.*]] = getelementptr inbounds i64, i64* [[TMP0]], i64 5 -; CHECK-NEXT: store i64 [[J:%.*]], i64* [[GEP4]], align 4 -; CHECK-NEXT: [[GEP26:%.*]] = getelementptr inbounds i64, i64* [[TMP0]], i64 6 -; CHECK-NEXT: store i64 [[J]], i64* [[GEP26]], align 4 -; CHECK-NEXT: [[GEP38:%.*]] = getelementptr inbounds i64, i64* [[TMP0]], i64 35 -; CHECK-NEXT: store i64 [[ADD]], i64* [[GEP38]], align 4 +; CHECK-NEXT: [[GEP:%.*]] = getelementptr inbounds i64, i64* [[ARRAY:%.*]], i64 [[ADD]] +; CHECK-NEXT: store i64 [[J:%.*]], i64* [[GEP]], align 4 +; CHECK-NEXT: [[TMP0:%.*]] = getelementptr i64, i64* [[ARRAY]], i64 [[I]] +; CHECK-NEXT: [[GEP22:%.*]] = getelementptr inbounds i64, i64* [[TMP0]], i64 6 +; CHECK-NEXT: store i64 [[J]], i64* [[GEP22]], align 4 +; CHECK-NEXT: [[GEP34:%.*]] = getelementptr inbounds i64, i64* [[TMP0]], i64 35 +; CHECK-NEXT: store i64 [[ADD]], i64* [[GEP34]], align 4 ; CHECK-NEXT: ret i64 undef ; entry: