about summary refs log tree commit diff
path: root/compiler/rustc_codegen_llvm/src/asm.rs
diff options
context:
space:
mode:
authorGary Guo <gary@garyguo.net>2024-10-11 00:26:21 +0100
committerGary Guo <gary@garyguo.net>2024-11-24 14:18:10 +0000
commit73f8309300bce03e62c8a49e8a06b884175b5f88 (patch)
tree9c1feb6758ff77c142f728542c054c539cbcdc6e /compiler/rustc_codegen_llvm/src/asm.rs
parentb8df869ebb9219b98ca798aacb16c9be3f84496b (diff)
downloadrust-73f8309300bce03e62c8a49e8a06b884175b5f88.tar.gz
rust-73f8309300bce03e62c8a49e8a06b884175b5f88.zip
Support use of asm goto with outputs and `options(noreturn)`
When labels are present, the `noreturn` option really means that asm block
won't fallthrough -- if labels are present, then outputs can still be
meaningfully used.
Diffstat (limited to 'compiler/rustc_codegen_llvm/src/asm.rs')
-rw-r--r--compiler/rustc_codegen_llvm/src/asm.rs9
1 files changed, 8 insertions, 1 deletions
diff --git a/compiler/rustc_codegen_llvm/src/asm.rs b/compiler/rustc_codegen_llvm/src/asm.rs
index 2455d13df8d..07473190d6f 100644
--- a/compiler/rustc_codegen_llvm/src/asm.rs
+++ b/compiler/rustc_codegen_llvm/src/asm.rs
@@ -343,7 +343,14 @@ impl<'ll, 'tcx> AsmBuilderMethods<'tcx> for Builder<'_, 'll, 'tcx> {
         attributes::apply_to_callsite(result, llvm::AttributePlace::Function, &{ attrs });
 
         // Write results to outputs. We need to do this for all possible control flow.
-        for block in Some(dest).into_iter().chain(labels.iter().copied().map(Some)) {
+        //
+        // Note that `dest` maybe populated with unreachable_block when asm goto with outputs
+        // is used (because we need to codegen callbr which always needs a destination), so
+        // here we use the NORETURN option to determine if `dest` should be used.
+        for block in (if options.contains(InlineAsmOptions::NORETURN) { None } else { Some(dest) })
+            .into_iter()
+            .chain(labels.iter().copied().map(Some))
+        {
             if let Some(block) = block {
                 self.switch_to_block(block);
             }