about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--tests/run-make/avr-rjmp-offset/avr-rjmp-offsets.rs (renamed from tests/assembly/avr-rjmp-offsets.rs)35
-rw-r--r--tests/run-make/avr-rjmp-offset/rmake.rs28
2 files changed, 40 insertions, 23 deletions
diff --git a/tests/assembly/avr-rjmp-offsets.rs b/tests/run-make/avr-rjmp-offset/avr-rjmp-offsets.rs
index 0acf54fada4..d0e5ef19973 100644
--- a/tests/assembly/avr-rjmp-offsets.rs
+++ b/tests/run-make/avr-rjmp-offset/avr-rjmp-offsets.rs
@@ -1,17 +1,11 @@
-//@ compile-flags: -Copt-level=s --target=avr-unknown-gnu-atmega328 -C panic=abort
-//@ needs-llvm-components: avr
-//@ assembly-output: emit-asm
-
-#![feature(
-    no_core,
-    lang_items,
-    intrinsics,
-    rustc_attrs,
-    arbitrary_self_types,
-    asm_experimental_arch
-)]
-#![crate_type = "rlib"]
+//! This test case is a `#![no_core]`-version of the MVCE presented in #129301.
+//!
+//! The function [`delay()`] is minimized and does not actually contain a loop
+//! in order to remove the need for additional lang items.
+#![feature(no_core, lang_items, intrinsics, rustc_attrs, asm_experimental_arch)]
 #![no_core]
+#![no_main]
+#![allow(internal_features)]
 
 #[rustc_builtin_macro]
 macro_rules! asm {
@@ -20,18 +14,13 @@ macro_rules! asm {
 
 use minicore::ptr;
 
-// CHECK-LABEL: pin_toggling
-// CHECK: ldi [[REG_1:r[0-9]+]], 1
-// CHECK: ldi [[REG_2:r[0-9]+]], 2
-// CHECK: .LBB0_1:
-// CHECK-NEXT: out 5, [[REG_1]]
-// CHECK-NEXT: call delay
-// CHECK-NEXT: out 5, [[REG_2]]
-// CHECK-NEXT: call delay
-// CHECK-NEXT: rjmp .LBB0_1
 #[no_mangle]
-pub fn pin_toggling() {
+pub fn main() -> ! {
     let port_b = 0x25 as *mut u8; // the I/O-address of PORTB
+
+    // a simple loop with some trivial instructions within. This loop label has
+    // to be placed correctly before the `ptr::write_volatile()` (some LLVM ver-
+    // sions did place it after the first loop instruction, causing unsoundness)
     loop {
         unsafe { ptr::write_volatile(port_b, 1) };
         delay(500_0000);
diff --git a/tests/run-make/avr-rjmp-offset/rmake.rs b/tests/run-make/avr-rjmp-offset/rmake.rs
new file mode 100644
index 00000000000..666aa41ef41
--- /dev/null
+++ b/tests/run-make/avr-rjmp-offset/rmake.rs
@@ -0,0 +1,28 @@
+//@ needs-llvm-components: avr
+//! Regression test for #129301/llvm-project#106722 within `rustc`.
+//!
+//! Some LLVM-versions had wrong offsets in the local labels, causing the first
+//! loop instruction to be missed. This test therefore contains a simple loop
+//! with trivial instructions in it, to see, where the label is placed.
+//!
+//! This must be a `rmake`-test and cannot be a `tests/assembly`-test, since the
+//! wrong output is only produced with direct assembly generation, but not when
+//! "emit-asm" is used, as described in the issue description of #129301:
+//! https://github.com/rust-lang/rust/issues/129301#issue-2475070770
+use run_make_support::{llvm_objdump, rustc};
+
+fn main() {
+    rustc()
+        .input("avr-rjmp-offsets.rs")
+        .opt_level("s")
+        .panic("abort")
+        .target("avr-unknown-gnu-atmega328")
+        .output("compiled")
+        .run();
+
+    llvm_objdump()
+        .disassemble()
+        .input("compiled")
+        .run()
+        .assert_stdout_contains_regex(r"rjmp.*\.-14");
+}