From a62a4646621b03ab6dee626d5fd4d2d048c43e1e Mon Sep 17 00:00:00 2001 From: Camille GILLOT Date: Sun, 26 Dec 2021 21:00:15 +0100 Subject: [PATCH 1/3] Sort MonoItems by span instead of definition index. --- compiler/rustc_middle/src/mir/mono.rs | 49 +++++++++++++-------------- 1 file changed, 23 insertions(+), 26 deletions(-) diff --git a/compiler/rustc_middle/src/mir/mono.rs b/compiler/rustc_middle/src/mir/mono.rs index 21ae121e1ce69..eab7944979c07 100644 --- a/compiler/rustc_middle/src/mir/mono.rs +++ b/compiler/rustc_middle/src/mir/mono.rs @@ -7,7 +7,6 @@ use rustc_data_structures::fx::FxHashMap; use rustc_data_structures::stable_hasher::{HashStable, StableHasher}; use rustc_hir::def_id::{CrateNum, DefId, LOCAL_CRATE}; use rustc_hir::ItemId; -use rustc_index::vec::Idx; use rustc_query_system::ich::StableHashingContext; use rustc_session::config::OptLevel; use rustc_span::source_map::Span; @@ -348,35 +347,33 @@ impl<'tcx> CodegenUnit<'tcx> { tcx: TyCtxt<'tcx>, ) -> Vec<(MonoItem<'tcx>, (Linkage, Visibility))> { // The codegen tests rely on items being process in the same order as - // they appear in the file, so for local items, we sort by node_id first + // they appear in the file, so for local items, we sort by span first #[derive(PartialEq, Eq, PartialOrd, Ord)] - pub struct ItemSortKey<'tcx>(Option, SymbolName<'tcx>); + pub struct ItemSortKey<'tcx>(Option, SymbolName<'tcx>); fn item_sort_key<'tcx>(tcx: TyCtxt<'tcx>, item: MonoItem<'tcx>) -> ItemSortKey<'tcx> { - ItemSortKey( - match item { - MonoItem::Fn(ref instance) => { - match instance.def { - // We only want to take HirIds of user-defined - // instances into account. The others don't matter for - // the codegen tests and can even make item order - // unstable. - InstanceDef::Item(def) => def.did.as_local().map(Idx::index), - InstanceDef::VTableShim(..) - | InstanceDef::ReifyShim(..) - | InstanceDef::Intrinsic(..) - | InstanceDef::FnPtrShim(..) - | InstanceDef::Virtual(..) - | InstanceDef::ClosureOnceShim { .. } - | InstanceDef::DropGlue(..) - | InstanceDef::CloneShim(..) => None, - } + let span = match item { + MonoItem::Fn(ref instance) => { + match instance.def { + // We only want to take HirIds of user-defined + // instances into account. The others don't matter for + // the codegen tests and can even make item order + // unstable. + InstanceDef::Item(def) => tcx.hir().span_if_local(def.did), + InstanceDef::VTableShim(..) + | InstanceDef::ReifyShim(..) + | InstanceDef::Intrinsic(..) + | InstanceDef::FnPtrShim(..) + | InstanceDef::Virtual(..) + | InstanceDef::ClosureOnceShim { .. } + | InstanceDef::DropGlue(..) + | InstanceDef::CloneShim(..) => None, } - MonoItem::Static(def_id) => def_id.as_local().map(Idx::index), - MonoItem::GlobalAsm(item_id) => Some(item_id.def_id.index()), - }, - item.symbol_name(tcx), - ) + } + MonoItem::Static(def_id) => tcx.hir().span_if_local(def_id), + MonoItem::GlobalAsm(item_id) => Some(tcx.def_span(item_id.def_id)), + }; + ItemSortKey(span, item.symbol_name(tcx)) } let mut items: Vec<_> = self.items().iter().map(|(&i, &l)| (i, l)).collect(); From 6b725d21650ed178c24448f3797b9a2e392a5c35 Mon Sep 17 00:00:00 2001 From: Camille GILLOT Date: Sun, 16 Jan 2022 14:39:08 +0100 Subject: [PATCH 2/3] Directly cache the SpanData. --- compiler/rustc_middle/src/mir/mono.rs | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/compiler/rustc_middle/src/mir/mono.rs b/compiler/rustc_middle/src/mir/mono.rs index eab7944979c07..09879f6c073a9 100644 --- a/compiler/rustc_middle/src/mir/mono.rs +++ b/compiler/rustc_middle/src/mir/mono.rs @@ -9,8 +9,8 @@ use rustc_hir::def_id::{CrateNum, DefId, LOCAL_CRATE}; use rustc_hir::ItemId; use rustc_query_system::ich::StableHashingContext; use rustc_session::config::OptLevel; -use rustc_span::source_map::Span; use rustc_span::symbol::Symbol; +use rustc_span::{Span, SpanData}; use std::fmt; use std::hash::Hash; @@ -348,8 +348,10 @@ impl<'tcx> CodegenUnit<'tcx> { ) -> Vec<(MonoItem<'tcx>, (Linkage, Visibility))> { // The codegen tests rely on items being process in the same order as // they appear in the file, so for local items, we sort by span first + // + // We directly cache a SpanData to avoid having to query the interner for each comparison. #[derive(PartialEq, Eq, PartialOrd, Ord)] - pub struct ItemSortKey<'tcx>(Option, SymbolName<'tcx>); + pub struct ItemSortKey<'tcx>(Option, SymbolName<'tcx>); fn item_sort_key<'tcx>(tcx: TyCtxt<'tcx>, item: MonoItem<'tcx>) -> ItemSortKey<'tcx> { let span = match item { @@ -373,6 +375,7 @@ impl<'tcx> CodegenUnit<'tcx> { MonoItem::Static(def_id) => tcx.hir().span_if_local(def_id), MonoItem::GlobalAsm(item_id) => Some(tcx.def_span(item_id.def_id)), }; + let span = span.map(Span::data); ItemSortKey(span, item.symbol_name(tcx)) } From e64ba94e7d9696f70e0ac27cc535bcee762fc8f6 Mon Sep 17 00:00:00 2001 From: Camille GILLOT Date: Mon, 27 Dec 2021 19:42:34 +0100 Subject: [PATCH 3/3] Adjust assembly tests. --- src/test/assembly/asm/avr-types.rs | 88 +++++++++++++------------- src/test/assembly/asm/bpf-types.rs | 44 ++++++------- src/test/assembly/asm/hexagon-types.rs | 68 ++++++++++---------- src/test/assembly/asm/mips-types.rs | 84 ++++++++++++------------ src/test/assembly/asm/msp430-types.rs | 88 +++++++++++++------------- src/test/assembly/asm/s390x-types.rs | 44 ++++++------- 6 files changed, 206 insertions(+), 210 deletions(-) diff --git a/src/test/assembly/asm/avr-types.rs b/src/test/assembly/asm/avr-types.rs index 53a601e51c8bf..744588d024839 100644 --- a/src/test/assembly/asm/avr-types.rs +++ b/src/test/assembly/asm/avr-types.rs @@ -30,50 +30,6 @@ impl Copy for i32 {} impl Copy for i64 {} impl Copy for ptr {} -macro_rules! check { - ($func:ident $ty:ident $class:ident) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - let y; - asm!("mov {}, {}", lateout($class) y, in($class) x); - y - } - }; -} - -macro_rules! checkw { - ($func:ident $ty:ident $class:ident) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - let y; - asm!("movw {}, {}", lateout($class) y, in($class) x); - y - } - }; -} - -macro_rules! check_reg { - ($func:ident $ty:ident $reg:tt) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - let y; - asm!(concat!("mov ", $reg, ", ", $reg), lateout($reg) y, in($reg) x); - y - } - }; -} - -macro_rules! check_regw { - ($func:ident $ty:ident $reg:tt $reg_lit:tt) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - let y; - asm!(concat!("movw ", $reg_lit, ", ", $reg_lit), lateout($reg) y, in($reg) x); - y - } - }; -} - extern "C" { fn extern_func(); static extern_static: i8; @@ -161,6 +117,17 @@ pub unsafe fn muls_clobber(x: i8, y: i8) -> i16 { z } +macro_rules! check { + ($func:ident $ty:ident $class:ident) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + let y; + asm!("mov {}, {}", lateout($class) y, in($class) x); + y + } + }; +} + // CHECK-LABEL: reg_i8: // CHECK: ;APP // CHECK: mov r{{[0-9]+}}, r{{[0-9]+}} @@ -173,6 +140,17 @@ check!(reg_i8 i8 reg); // CHECK: ;NO_APP check!(reg_upper_i8 i8 reg_upper); +macro_rules! checkw { + ($func:ident $ty:ident $class:ident) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + let y; + asm!("movw {}, {}", lateout($class) y, in($class) x); + y + } + }; +} + // CHECK-LABEL: reg_pair_i16: // CHECK: ;APP // CHECK: movw r{{[0-9]+}}, r{{[0-9]+}} @@ -191,6 +169,17 @@ checkw!(reg_iw_i16 i16 reg_iw); // CHECK: ;NO_APP checkw!(reg_ptr_i16 i16 reg_ptr); +macro_rules! check_reg { + ($func:ident $ty:ident $reg:tt) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + let y; + asm!(concat!("mov ", $reg, ", ", $reg), lateout($reg) y, in($reg) x); + y + } + }; +} + // CHECK-LABEL: r2_i8: // CHECK: ;APP // CHECK: mov r2, r2 @@ -209,6 +198,17 @@ check_reg!(xl_i8 i8 "XL"); // CHECK: ;NO_APP check_reg!(xh_i8 i8 "XH"); +macro_rules! check_regw { + ($func:ident $ty:ident $reg:tt $reg_lit:tt) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + let y; + asm!(concat!("movw ", $reg_lit, ", ", $reg_lit), lateout($reg) y, in($reg) x); + y + } + }; +} + // CHECK-LABEL: x_i16: // CHECK: ;APP // CHECK: movw r26, r26 diff --git a/src/test/assembly/asm/bpf-types.rs b/src/test/assembly/asm/bpf-types.rs index 3428d93fb1205..9c5269ea898ac 100644 --- a/src/test/assembly/asm/bpf-types.rs +++ b/src/test/assembly/asm/bpf-types.rs @@ -34,28 +34,6 @@ impl Copy for i32 {} impl Copy for i64 {} impl Copy for ptr {} -macro_rules! check { - ($func:ident $ty:ident $class:ident) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - let y; - asm!("{} = {}", out($class) y, in($class) x); - y - } - }; -} - -macro_rules! check_reg { - ($func:ident $ty:ident $reg:tt) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - let y; - asm!(concat!($reg, " = ", $reg), lateout($reg) y, in($reg) x); - y - } - }; -} - extern "C" { fn extern_func(); } @@ -69,6 +47,17 @@ pub unsafe fn sym_fn() { asm!("call {}", sym extern_func); } +macro_rules! check { + ($func:ident $ty:ident $class:ident) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + let y; + asm!("{} = {}", out($class) y, in($class) x); + y + } + }; +} + // CHECK-LABEL: reg_i8: // CHECK: #APP // CHECK: r{{[0-9]+}} = r{{[0-9]+}} @@ -111,6 +100,17 @@ check!(wreg_i16 i16 wreg); // CHECK: #NO_APP check!(wreg_i32 i32 wreg); +macro_rules! check_reg { + ($func:ident $ty:ident $reg:tt) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + let y; + asm!(concat!($reg, " = ", $reg), lateout($reg) y, in($reg) x); + y + } + }; +} + // CHECK-LABEL: r0_i8: // CHECK: #APP // CHECK: r0 = r0 diff --git a/src/test/assembly/asm/hexagon-types.rs b/src/test/assembly/asm/hexagon-types.rs index eff9a0bb431d4..f5c2459d2e8c7 100644 --- a/src/test/assembly/asm/hexagon-types.rs +++ b/src/test/assembly/asm/hexagon-types.rs @@ -37,40 +37,6 @@ extern "C" { static extern_static: u8; } -macro_rules! check { - ($func:ident $ty:ident $class:ident) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - // Hack to avoid function merging - extern "Rust" { - fn dont_merge(s: &str); - } - dont_merge(stringify!($func)); - - let y; - asm!("{} = {}", out($class) y, in($class) x); - y - } - }; -} - -macro_rules! check_reg { - ($func:ident $ty:ident $reg:tt) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - // Hack to avoid function merging - extern "Rust" { - fn dont_merge(s: &str); - } - dont_merge(stringify!($func)); - - let y; - asm!(concat!($reg, " = ", $reg), lateout($reg) y, in($reg) x); - y - } - }; -} - // CHECK-LABEL: sym_static: // CHECK: InlineAsm Start // CHECK: r0 = {{#+}}extern_static @@ -120,6 +86,23 @@ pub unsafe fn packet() { }}", out(reg) _, in(reg) &val); } +macro_rules! check { + ($func:ident $ty:ident $class:ident) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + // Hack to avoid function merging + extern "Rust" { + fn dont_merge(s: &str); + } + dont_merge(stringify!($func)); + + let y; + asm!("{} = {}", out($class) y, in($class) x); + y + } + }; +} + // CHECK-LABEL: reg_ptr: // CHECK: InlineAsm Start // CHECK: r{{[0-9]+}} = r{{[0-9]+}} @@ -150,6 +133,23 @@ check!(reg_i8 i8 reg); // CHECK: InlineAsm End check!(reg_i16 i16 reg); +macro_rules! check_reg { + ($func:ident $ty:ident $reg:tt) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + // Hack to avoid function merging + extern "Rust" { + fn dont_merge(s: &str); + } + dont_merge(stringify!($func)); + + let y; + asm!(concat!($reg, " = ", $reg), lateout($reg) y, in($reg) x); + y + } + }; +} + // CHECK-LABEL: r0_ptr: // CHECK: InlineAsm Start // CHECK: r0 = r0 diff --git a/src/test/assembly/asm/mips-types.rs b/src/test/assembly/asm/mips-types.rs index 04bf49a40efbc..d79daff17a1a2 100644 --- a/src/test/assembly/asm/mips-types.rs +++ b/src/test/assembly/asm/mips-types.rs @@ -48,28 +48,6 @@ extern "Rust" { fn dont_merge(s: &str); } -macro_rules! check { ($func:ident, $ty:ty, $class:ident, $mov:literal) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - dont_merge(stringify!($func)); - - let y; - asm!(concat!($mov," {}, {}"), out($class) y, in($class) x); - y - } -};} - -macro_rules! check_reg { ($func:ident, $ty:ty, $reg:tt, $mov:literal) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - dont_merge(stringify!($func)); - - let y; - asm!(concat!($mov, " ", $reg, ", ", $reg), lateout($reg) y, in($reg) x); - y - } -};} - // mips32-LABEL: sym_static_32: // mips32: #APP // mips32: lw $3, %got(extern_static) @@ -110,46 +88,35 @@ pub unsafe fn sym_fn_64() { asm!("ld $v1, {}", sym extern_func); } +macro_rules! check { ($func:ident, $ty:ty, $class:ident, $mov:literal) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + dont_merge(stringify!($func)); + + let y; + asm!(concat!($mov," {}, {}"), out($class) y, in($class) x); + y + } +};} + // CHECK-LABEL: reg_f32: // CHECK: #APP // CHECK: mov.s $f{{[0-9]+}}, $f{{[0-9]+}} // CHECK: #NO_APP check!(reg_f32, f32, freg, "mov.s"); -// CHECK-LABEL: f0_f32: -// CHECK: #APP -// CHECK: mov.s $f0, $f0 -// CHECK: #NO_APP -#[no_mangle] -check_reg!(f0_f32, f32, "$f0", "mov.s"); - // CHECK-LABEL: reg_f32_64: // CHECK: #APP // CHECK: mov.d $f{{[0-9]+}}, $f{{[0-9]+}} // CHECK: #NO_APP check!(reg_f32_64, f32, freg, "mov.d"); -// CHECK-LABEL: f0_f32_64: -// CHECK: #APP -// CHECK: mov.d $f0, $f0 -// CHECK: #NO_APP -#[no_mangle] -check_reg!(f0_f32_64, f32, "$f0", "mov.d"); - // CHECK-LABEL: reg_f64: // CHECK: #APP // CHECK: mov.d $f{{[0-9]+}}, $f{{[0-9]+}} // CHECK: #NO_APP -#[no_mangle] check!(reg_f64, f64, freg, "mov.d"); -// CHECK-LABEL: f0_f64: -// CHECK: #APP -// CHECK: mov.d $f0, $f0 -// CHECK: #NO_APP -#[no_mangle] -check_reg!(f0_f64, f64, "$f0", "mov.d"); - // CHECK-LABEL: reg_ptr: // CHECK: #APP // CHECK: move ${{[0-9]+}}, ${{[0-9]+}} @@ -200,6 +167,35 @@ check!(reg_i16, i16, reg, "move"); #[cfg(mips64)] check!(reg_i64, i64, reg, "move"); +macro_rules! check_reg { ($func:ident, $ty:ty, $reg:tt, $mov:literal) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + dont_merge(stringify!($func)); + + let y; + asm!(concat!($mov, " ", $reg, ", ", $reg), lateout($reg) y, in($reg) x); + y + } +};} + +// CHECK-LABEL: f0_f32: +// CHECK: #APP +// CHECK: mov.s $f0, $f0 +// CHECK: #NO_APP +check_reg!(f0_f32, f32, "$f0", "mov.s"); + +// CHECK-LABEL: f0_f32_64: +// CHECK: #APP +// CHECK: mov.d $f0, $f0 +// CHECK: #NO_APP +check_reg!(f0_f32_64, f32, "$f0", "mov.d"); + +// CHECK-LABEL: f0_f64: +// CHECK: #APP +// CHECK: mov.d $f0, $f0 +// CHECK: #NO_APP +check_reg!(f0_f64, f64, "$f0", "mov.d"); + // CHECK-LABEL: r8_ptr: // CHECK: #APP // CHECK: move $8, $8 diff --git a/src/test/assembly/asm/msp430-types.rs b/src/test/assembly/asm/msp430-types.rs index 6cfb86e276e23..086b608a924b3 100644 --- a/src/test/assembly/asm/msp430-types.rs +++ b/src/test/assembly/asm/msp430-types.rs @@ -30,50 +30,6 @@ impl Copy for i32 {} impl Copy for i64 {} impl Copy for ptr {} -macro_rules! check { - ($func:ident $ty:ident $class:ident) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - let y; - asm!("mov {}, {}", lateout($class) y, in($class) x); - y - } - }; -} - -macro_rules! checkb { - ($func:ident $ty:ident $class:ident) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - let y; - asm!("mov.b {}, {}", lateout($class) y, in($class) x); - y - } - }; -} - -macro_rules! check_reg { - ($func:ident $ty:ident $reg:tt) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - let y; - asm!(concat!("mov ", $reg, ", ", $reg), lateout($reg) y, in($reg) x); - y - } - }; -} - -macro_rules! check_regb { - ($func:ident $ty:ident $reg:tt) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - let y; - asm!(concat!("mov.b ", $reg, ", ", $reg), lateout($reg) y, in($reg) x); - y - } - }; -} - extern "C" { fn extern_func(); static extern_static: i8; @@ -121,6 +77,17 @@ pub unsafe fn mov_postincrement(mut x: *const i16) -> (i16, *const i16) { (y, x) } +macro_rules! check { + ($func:ident $ty:ident $class:ident) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + let y; + asm!("mov {}, {}", lateout($class) y, in($class) x); + y + } + }; +} + // CHECK-LABEL: reg_i8: // CHECK: ;APP // CHECK: mov r{{[0-9]+}}, r{{[0-9]+}} @@ -133,12 +100,34 @@ check!(reg_i8 i8 reg); // CHECK: ;NO_APP check!(reg_i16 i16 reg); +macro_rules! checkb { + ($func:ident $ty:ident $class:ident) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + let y; + asm!("mov.b {}, {}", lateout($class) y, in($class) x); + y + } + }; +} + // CHECK-LABEL: reg_i8b: // CHECK: ;APP // CHECK: mov.b r{{[0-9]+}}, r{{[0-9]+}} // CHECK: ;NO_APP checkb!(reg_i8b i8 reg); +macro_rules! check_reg { + ($func:ident $ty:ident $reg:tt) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + let y; + asm!(concat!("mov ", $reg, ", ", $reg), lateout($reg) y, in($reg) x); + y + } + }; +} + // CHECK-LABEL: r5_i8: // CHECK: ;APP // CHECK: mov r5, r5 @@ -151,6 +140,17 @@ check_reg!(r5_i8 i8 "r5"); // CHECK: ;NO_APP check_reg!(r5_i16 i16 "r5"); +macro_rules! check_regb { + ($func:ident $ty:ident $reg:tt) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + let y; + asm!(concat!("mov.b ", $reg, ", ", $reg), lateout($reg) y, in($reg) x); + y + } + }; +} + // CHECK-LABEL: r5_i8b: // CHECK: ;APP // CHECK: mov.b r5, r5 diff --git a/src/test/assembly/asm/s390x-types.rs b/src/test/assembly/asm/s390x-types.rs index 6a12902a0461f..0e2adb295ca41 100644 --- a/src/test/assembly/asm/s390x-types.rs +++ b/src/test/assembly/asm/s390x-types.rs @@ -47,28 +47,6 @@ extern "Rust" { fn dont_merge(s: &str); } -macro_rules! check { ($func:ident, $ty:ty, $class:ident, $mov:literal) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - dont_merge(stringify!($func)); - - let y; - asm!(concat!($mov," {}, {}"), out($class) y, in($class) x); - y - } -};} - -macro_rules! check_reg { ($func:ident, $ty:ty, $reg:tt, $mov:literal) => { - #[no_mangle] - pub unsafe fn $func(x: $ty) -> $ty { - dont_merge(stringify!($func)); - - let y; - asm!(concat!($mov, " %", $reg, ", %", $reg), lateout($reg) y, in($reg) x); - y - } -};} - // CHECK-LABEL: sym_fn_32: // CHECK: #APP // CHECK: brasl %r14, extern_func @@ -88,6 +66,17 @@ pub unsafe fn sym_static() { asm!("brasl %r14, {}", sym extern_static); } +macro_rules! check { ($func:ident, $ty:ty, $class:ident, $mov:literal) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + dont_merge(stringify!($func)); + + let y; + asm!(concat!($mov," {}, {}"), out($class) y, in($class) x); + y + } +};} + // CHECK-LABEL: reg_i8: // CHECK: #APP // CHECK: lgr %r{{[0-9]+}}, %r{{[0-9]+}} @@ -130,6 +119,17 @@ check!(reg_f64, f64, freg, "ldr"); // CHECK: #NO_APP check!(reg_ptr, ptr, reg, "lgr"); +macro_rules! check_reg { ($func:ident, $ty:ty, $reg:tt, $mov:literal) => { + #[no_mangle] + pub unsafe fn $func(x: $ty) -> $ty { + dont_merge(stringify!($func)); + + let y; + asm!(concat!($mov, " %", $reg, ", %", $reg), lateout($reg) y, in($reg) x); + y + } +};} + // CHECK-LABEL: r0_i8: // CHECK: #APP // CHECK: lr %r0, %r0