Skip to content

[llvm][StackProtector] Add noreturn to __stack_chk_fail call #143976

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Jun 16, 2025

Conversation

PiJoules
Copy link
Contributor

@PiJoules PiJoules commented Jun 12, 2025

It's possible for __stack_chk_fail to be an alias when using CrossDSOCFI since it will make a jump table entry for this function and replace it with an alias. StackProtector can crash since it always expects this to be a regular function. Instead add the noreturn attribute to the call.

@llvmbot
Copy link
Member

llvmbot commented Jun 12, 2025

@llvm/pr-subscribers-llvm-transforms

Author: None (PiJoules)

Changes

It's possible for __stack_chk_fail to be an alias when using CrossDSOCFI since it will make a jump table entry for this function and replace it with an alias. StackProtector can crash since it always expects this to be a regular function. I think it should be safe to continue treating this as an alias since we only call into it, and we can apply the noreturn attr to the underlying function if it is an alias.


Full diff: https://github.com/llvm/llvm-project/pull/143976.diff

2 Files Affected:

  • (modified) llvm/lib/CodeGen/StackProtector.cpp (+3-1)
  • (added) llvm/test/Transforms/StackProtector/stack-chk-fail-alias.ll (+17)
diff --git a/llvm/lib/CodeGen/StackProtector.cpp b/llvm/lib/CodeGen/StackProtector.cpp
index 5f866eea7d4e7..0e5c421d2fa5e 100644
--- a/llvm/lib/CodeGen/StackProtector.cpp
+++ b/llvm/lib/CodeGen/StackProtector.cpp
@@ -725,7 +725,9 @@ BasicBlock *CreateFailBB(Function *F, const Triple &Trip) {
     StackChkFail =
         M->getOrInsertFunction("__stack_chk_fail", Type::getVoidTy(Context));
   }
-  cast<Function>(StackChkFail.getCallee())->addFnAttr(Attribute::NoReturn);
+  cast<Function>(
+      cast<GlobalValue>(StackChkFail.getCallee())->getAliaseeObject())
+      ->addFnAttr(Attribute::NoReturn);
   B.CreateCall(StackChkFail, Args);
   B.CreateUnreachable();
   return FailBB;
diff --git a/llvm/test/Transforms/StackProtector/stack-chk-fail-alias.ll b/llvm/test/Transforms/StackProtector/stack-chk-fail-alias.ll
new file mode 100644
index 0000000000000..9314800cf0441
--- /dev/null
+++ b/llvm/test/Transforms/StackProtector/stack-chk-fail-alias.ll
@@ -0,0 +1,17 @@
+;; __stack_chk_fail should have the noreturn attr even if it is an alias
+; RUN: opt -triple=x86_64-pc-linux-gnu %s -passes=stack-protector -S | FileCheck %s
+
+define hidden void @__stack_chk_fail_impl() {
+  unreachable
+}
+
+@__stack_chk_fail = hidden alias void (), ptr @__stack_chk_fail_impl
+
+; CHECK-LABEL: @store_captures(
+define void @store_captures() sspstrong {
+entry:
+  %a = alloca i32, align 4
+  %j = alloca ptr, align 8
+  store ptr %a, ptr %j, align 8
+  ret void
+}

@PiJoules PiJoules force-pushed the stack-chk-fail-alias branch from 704e60f to f27ab2d Compare June 13, 2025 22:20
@PiJoules PiJoules changed the title [llvm][StackProtector] Add noreturn to __stack_chk_fail aliassee [llvm][StackProtector] Add noreturn to __stack_chk_fail call Jun 13, 2025
@PiJoules PiJoules requested a review from efriedma-quic June 13, 2025 22:21
@ilovepi
Copy link
Contributor

ilovepi commented Jun 14, 2025

Shouldn’t we have a test for crossdsocfi if that’s the bug you’re fixing gets exercised? Certainly the simple test you’ve added is good, but I’d think we want to test the actual failure case as well.

@PiJoules PiJoules force-pushed the stack-chk-fail-alias branch from f27ab2d to 11b9450 Compare June 16, 2025 21:41
@PiJoules
Copy link
Contributor Author

Shouldn’t we have a test for crossdsocfi if that’s the bug you’re fixing gets exercised? Certainly the simple test you’ve added is good, but I’d think we want to test the actual failure case as well.

Done

It's possible for __stack_chk_fail to be an alias when using CrossDSOCFI
since it will make a jump table entry for this function and replace it
with an alias. StackProtector can crash since it always expects this to
be a regular function. I think it should be safe to continue treating
this as an alias since we only call into it, and we can apply the
noreturn attr to the underlying function if it is an alias.
@PiJoules PiJoules force-pushed the stack-chk-fail-alias branch from 11b9450 to 8907144 Compare June 16, 2025 21:42
Copy link
Collaborator

@efriedma-quic efriedma-quic left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

Copy link
Contributor

@ilovepi ilovepi left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM. Thanks for adding the regression test.

@PiJoules PiJoules merged commit 99e53cb into llvm:main Jun 16, 2025
6 of 7 checks passed
@PiJoules PiJoules deleted the stack-chk-fail-alias branch June 16, 2025 22:47
@llvm-ci
Copy link
Collaborator

llvm-ci commented Jun 16, 2025

LLVM Buildbot has detected a new failure on builder llvm-clang-aarch64-darwin running on doug-worker-4 while building llvm at step 6 "test-build-unified-tree-check-all".

Full details are available at: https://lab.llvm.org/buildbot/#/builders/190/builds/21563

Here is the relevant piece of the build log for the reference
Step 6 (test-build-unified-tree-check-all) failure: test (failure)
******************** TEST 'LLVM :: Transforms/StackProtector/cross-dso-cfi-stack-chk-fail.ll' FAILED ********************
Exit Code: 139

Command Output (stderr):
--
/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt -mtriple=x86_64-pc-linux-gnu /Users/buildbot/buildbot-root/aarch64-darwin/llvm-project/llvm/test/Transforms/StackProtector/cross-dso-cfi-stack-chk-fail.ll -passes=lowertypetests,cross-dso-cfi,stack-protector # RUN: at line 3
+ /Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt -mtriple=x86_64-pc-linux-gnu /Users/buildbot/buildbot-root/aarch64-darwin/llvm-project/llvm/test/Transforms/StackProtector/cross-dso-cfi-stack-chk-fail.ll -passes=lowertypetests,cross-dso-cfi,stack-protector
/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt: warning: failed to infer data layout: unable to get target for 'x86_64-pc-linux-gnu', see --version and --triple.
/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt: WARNING: failed to create target machine for 'x86_64-pc-linux-gnu': unable to get target for 'x86_64-pc-linux-gnu', see --version and --triple.
PLEASE submit a bug report to https://github.com/llvm/llvm-project/issues/ and include the crash backtrace.
Stack dump:
0.	Program arguments: /Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt -mtriple=x86_64-pc-linux-gnu /Users/buildbot/buildbot-root/aarch64-darwin/llvm-project/llvm/test/Transforms/StackProtector/cross-dso-cfi-stack-chk-fail.ll -passes=lowertypetests,cross-dso-cfi,stack-protector
1.	Running pass "function(stack-protector)" on module "/Users/buildbot/buildbot-root/aarch64-darwin/llvm-project/llvm/test/Transforms/StackProtector/cross-dso-cfi-stack-chk-fail.ll"
 #0 0x00000001040ac6f4 llvm::sys::PrintStackTrace(llvm::raw_ostream&, int) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt+0x1017c06f4)
 #1 0x00000001040aa7b4 llvm::sys::RunSignalHandlers() (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt+0x1017be7b4)
 #2 0x00000001040acf30 SignalHandler(int, __siginfo*, void*) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt+0x1017c0f30)
 #3 0x000000019d937584 (/usr/lib/system/libsystem_platform.dylib+0x18047b584)
 #4 0x00000001034be434 llvm::StackProtectorPass::run(llvm::Function&, llvm::AnalysisManager<llvm::Function>&) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt+0x100bd2434)
 #5 0x00000001034be434 llvm::StackProtectorPass::run(llvm::Function&, llvm::AnalysisManager<llvm::Function>&) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt+0x100bd2434)
 #6 0x000000010377295c llvm::ModuleToFunctionPassAdaptor::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt+0x100e8695c)
 #7 0x000000010376d844 llvm::PassManager<llvm::Module, llvm::AnalysisManager<llvm::Module>>::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt+0x100e81844)
 #8 0x000000010454d830 llvm::runPassPipeline(llvm::StringRef, llvm::Module&, llvm::TargetMachine*, llvm::TargetLibraryInfoImpl*, llvm::ToolOutputFile*, llvm::ToolOutputFile*, llvm::ToolOutputFile*, llvm::StringRef, llvm::ArrayRef<llvm::PassPlugin>, llvm::ArrayRef<std::__1::function<void (llvm::PassBuilder&)>>, llvm::opt_tool::OutputKind, llvm::opt_tool::VerifierKind, bool, bool, bool, bool, bool, bool, bool) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt+0x101c61830)
 #9 0x000000010455880c optMain (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt+0x101c6c80c)
#10 0x000000019d57b154 
/Users/buildbot/buildbot-root/aarch64-darwin/build/test/Transforms/StackProtector/Output/cross-dso-cfi-stack-chk-fail.ll.script: line 1:  4426 Segmentation fault: 11  /Users/buildbot/buildbot-root/aarch64-darwin/build/bin/opt -mtriple=x86_64-pc-linux-gnu /Users/buildbot/buildbot-root/aarch64-darwin/llvm-project/llvm/test/Transforms/StackProtector/cross-dso-cfi-stack-chk-fail.ll -passes=lowertypetests,cross-dso-cfi,stack-protector

--

********************


Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants