Skip to content

Commit

Permalink
IRVerifier: Allow GlobalValue as llvm.threadlocal.address operand (#8…
Browse files Browse the repository at this point in the history
…8321)

Loosen `llvm.threadlocal.address` verifier checks to allow any
`GlobalValue` with `isThreadLocal()` set to true.
  • Loading branch information
MatzeB authored Apr 12, 2024
1 parent 0f82469 commit c6cd460
Show file tree
Hide file tree
Showing 4 changed files with 53 additions and 5 deletions.
3 changes: 2 additions & 1 deletion llvm/docs/LangRef.rst
Original file line number Diff line number Diff line change
Expand Up @@ -28130,7 +28130,8 @@ Syntax:
Arguments:
""""""""""

The first argument is a thread local :ref:`global variable <globalvars>`.
The `llvm.threadlocal.address` intrinsic requires a global value argument (a
:ref:`global variable <globalvars>` or alias) that is thread local.

Semantics:
""""""""""
Expand Down
8 changes: 4 additions & 4 deletions llvm/lib/IR/Verifier.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6226,10 +6226,10 @@ void Verifier::visitIntrinsicCall(Intrinsic::ID ID, CallBase &Call) {
}
case Intrinsic::threadlocal_address: {
const Value &Arg0 = *Call.getArgOperand(0);
Check(isa<GlobalVariable>(Arg0),
"llvm.threadlocal.address first argument must be a GlobalVariable");
Check(cast<GlobalVariable>(Arg0).isThreadLocal(),
"llvm.threadlocal.address operand isThreadLocal() must no be false");
Check(isa<GlobalValue>(Arg0),
"llvm.threadlocal.address first argument must be a GlobalValue");
Check(cast<GlobalValue>(Arg0).isThreadLocal(),
"llvm.threadlocal.address operand isThreadLocal() must be true");
break;
}
};
Expand Down
13 changes: 13 additions & 0 deletions llvm/test/Verifier/threadlocal-pass.ll
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
; RUN: opt -passes=verify -S < %s | FileCheck %s

@var = thread_local global i32 0
@alias = thread_local alias i32, ptr @var

; CHECK-LABEL: @should_pass
define void @should_pass() {
%p0 = call ptr @llvm.threadlocal.address(ptr @var)
store i32 42, ptr %p0, align 4
%p1 = call ptr @llvm.threadlocal.address(ptr @alias)
store i32 13, ptr %p1, align 4
ret void
}
34 changes: 34 additions & 0 deletions llvm/test/Verifier/threadlocal.ll
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
; RUN: not llvm-as %s -o /dev/null 2>&1 | FileCheck %s

@var = global i32 0
@tlsvar = thread_local addrspace(1) global i32 0

define void @fail0(ptr %arg) {
; CHECK: llvm.threadlocal.address first argument must be a GlobalValue
%p0 = call ptr @llvm.threadlocal.address(ptr %arg)
store i32 42, ptr %p0, align 4
ret void
}

define void @fail1() {
; CHECK: llvm.threadlocal.address first argument must be a GlobalValue
%p0 = call ptr @llvm.threadlocal.address.p0(ptr addrspacecast (ptr addrspace(1) @tlsvar to ptr addrspace(0)))
store i32 42, ptr %p0, align 4
ret void
}



define void @fail2() {
; CHECK: llvm.threadlocal.address operand isThreadLocal() must be true
%p0 = call ptr @llvm.threadlocal.address(ptr @var)
store i32 42, ptr %p0, align 4
ret void
}

define void @fail3() {
; CHECK: llvm.threadlocal.address operand isThreadLocal() must be true
%p0 = call ptr @llvm.threadlocal.address(ptr @fail2)
store i32 42, ptr %p0, align 4
ret void
}

0 comments on commit c6cd460

Please sign in to comment.