[llvm] [llvm] Let RelLookupTableConverter act on globals with many uses (PR #188163)
Paul Kirth via llvm-commits
llvm-commits at lists.llvm.org
Fri Apr 3 12:27:33 PDT 2026
================
@@ -0,0 +1,104 @@
+; RUN: opt < %s -passes=rel-lookup-table-converter -relocation-model=pic -S | FileCheck %s
+
+target triple = "x86_64-unknown-linux-gnu"
+
+ at .str = private unnamed_addr constant [5 x i8] c"zero\00", align 1
+ at .str.1 = private unnamed_addr constant [4 x i8] c"one\00", align 1
+ at .str.2 = private unnamed_addr constant [4 x i8] c"two\00", align 1
+
+ at switch.table.multiple_uses = private unnamed_addr constant [3 x ptr]
+ [
+ ptr @.str,
+ ptr @.str.1,
+ ptr @.str.2
+ ], align 8
+
+ at switch.table.mixed_uses = private unnamed_addr constant [3 x ptr]
+ [
+ ptr @.str,
+ ptr @.str.1,
+ ptr @.str.2
+ ], align 8
+
+ at switch.table.bitcast = private unnamed_addr constant [3 x ptr]
+ [
+ ptr @.str,
+ ptr @.str.1,
+ ptr @.str.2
+ ], align 8
+
+; CHECK: @switch.table.multiple_uses.rel = private unnamed_addr constant [3 x i32] [
+; CHECK-SAME: i32 trunc (i64 sub (i64 ptrtoint (ptr @.str to i64), i64 ptrtoint (ptr @switch.table.multiple_uses.rel to i64)) to i32),
+; CHECK-SAME: i32 trunc (i64 sub (i64 ptrtoint (ptr @.str.1 to i64), i64 ptrtoint (ptr @switch.table.multiple_uses.rel to i64)) to i32),
+; CHECK-SAME: i32 trunc (i64 sub (i64 ptrtoint (ptr @.str.2 to i64), i64 ptrtoint (ptr @switch.table.multiple_uses.rel to i64)) to i32)
+; CHECK-SAME: ], align 4
+
+; CHECK: @switch.table.mixed_uses = private unnamed_addr constant [3 x ptr]
+; CHECK: @switch.table.bitcast = private unnamed_addr constant [3 x ptr]
+
+;; Here to allow loads to be used.
+declare void @escape(ptr %p)
+
+define void @test(i32 %idx) {
+; CHECK-LABEL: @test(
+; CHECK-NEXT: entry:
+; CHECK-NEXT: [[SHIFT:%.*]] = shl i32 %idx, 2
+; CHECK-NEXT: [[RES:%.*]] = call ptr @llvm.load.relative.i32(ptr @switch.table.multiple_uses.rel, i32 [[SHIFT]])
+; CHECK-NEXT: [[SHIFT2:%.*]] = shl i32 %idx, 2
+; CHECK-NEXT: [[RES2:%.*]] = call ptr @llvm.load.relative.i32(ptr @switch.table.multiple_uses.rel, i32 [[SHIFT2]])
+;
+entry:
+ %gep1 = getelementptr inbounds [3 x ptr], ptr @switch.table.multiple_uses, i32 0, i32 %idx
+ %load1 = load ptr, ptr %gep1, align 8
+ %gep2 = getelementptr inbounds [3 x ptr], ptr @switch.table.multiple_uses, i32 0, i32 %idx
+ %load2 = load ptr, ptr %gep2, align 8
+ call void @escape(ptr %load1)
+ call void @escape(ptr %load2)
+ ret void
+}
+
+define void @accross_functions(i32 %idx) {
+; CHECK-LABEL: @accross_functions(
+; CHECK-NEXT: entry:
+; CHECK-NEXT: [[SHIFT:%.*]] = shl i32 %idx, 2
+; CHECK-NEXT: [[RES:%.*]] = call ptr @llvm.load.relative.i32(ptr @switch.table.multiple_uses.rel, i32 [[SHIFT]])
+;
----------------
ilovepi wrote:
```suggestion
```
or add this below for consistency...
https://github.com/llvm/llvm-project/pull/188163
More information about the llvm-commits
mailing list