From 0296d4968eb28dad447a9b0e0f00925236be1ee7 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Tue, 10 Mar 2020 21:53:22 +0100 Subject: [PATCH 1/5] fix layout_test visitor name --- src/librustc_passes/layout_test.rs | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/librustc_passes/layout_test.rs b/src/librustc_passes/layout_test.rs index 9f6598a0ec1fe..b0edbb46e2929 100644 --- a/src/librustc_passes/layout_test.rs +++ b/src/librustc_passes/layout_test.rs @@ -17,15 +17,15 @@ use rustc_span::symbol::sym; pub fn test_layout(tcx: TyCtxt<'_>) { if tcx.features().rustc_attrs { // if the `rustc_attrs` feature is not enabled, don't bother testing layout - tcx.hir().krate().visit_all_item_likes(&mut VarianceTest { tcx }); + tcx.hir().krate().visit_all_item_likes(&mut LayoutTest { tcx }); } } -struct VarianceTest<'tcx> { +struct LayoutTest<'tcx> { tcx: TyCtxt<'tcx>, } -impl ItemLikeVisitor<'tcx> for VarianceTest<'tcx> { +impl ItemLikeVisitor<'tcx> for LayoutTest<'tcx> { fn visit_item(&mut self, item: &'tcx hir::Item<'tcx>) { let item_def_id = self.tcx.hir().local_def_id(item.hir_id); @@ -42,7 +42,7 @@ impl ItemLikeVisitor<'tcx> for VarianceTest<'tcx> { fn visit_impl_item(&mut self, _: &'tcx hir::ImplItem<'tcx>) {} } -impl VarianceTest<'tcx> { +impl LayoutTest<'tcx> { fn dump_layout_of(&self, item_def_id: DefId, item: &hir::Item<'tcx>, attr: &Attribute) { let tcx = self.tcx; let param_env = self.tcx.param_env(item_def_id); From 55c2cf2a3214cc3be11d9e27da5aa419653cac0c Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Tue, 10 Mar 2020 22:25:53 +0100 Subject: [PATCH 2/5] add debug option to #[rustc_layout] --- src/librustc_passes/layout_test.rs | 7 +++++++ src/librustc_span/symbol.rs | 1 + 2 files changed, 8 insertions(+) diff --git a/src/librustc_passes/layout_test.rs b/src/librustc_passes/layout_test.rs index b0edbb46e2929..66297eb972736 100644 --- a/src/librustc_passes/layout_test.rs +++ b/src/librustc_passes/layout_test.rs @@ -81,6 +81,13 @@ impl LayoutTest<'tcx> { ); } + sym::debug => { + self.tcx.sess.span_err( + item.span, + &format!("layout debugging: {:#?}", *ty_layout), + ); + } + name => { self.tcx.sess.span_err( meta_item.span(), diff --git a/src/librustc_span/symbol.rs b/src/librustc_span/symbol.rs index 5685505f6948d..771de54707e9e 100644 --- a/src/librustc_span/symbol.rs +++ b/src/librustc_span/symbol.rs @@ -253,6 +253,7 @@ symbols! { debug_trait, declare_lint_pass, decl_macro, + debug, Debug, Decodable, Default, From d9f60bcf67ea175ab3298608d8a94563e1ac0f6d Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Tue, 10 Mar 2020 22:31:27 +0100 Subject: [PATCH 3/5] add a test for rustc_layout(debug) --- src/test/ui/layout/debug.rs | 7 ++ src/test/ui/layout/debug.stderr | 120 ++++++++++++++++++++++++++++++++ 2 files changed, 127 insertions(+) create mode 100644 src/test/ui/layout/debug.rs create mode 100644 src/test/ui/layout/debug.stderr diff --git a/src/test/ui/layout/debug.rs b/src/test/ui/layout/debug.rs new file mode 100644 index 0000000000000..64a02ee5a22c8 --- /dev/null +++ b/src/test/ui/layout/debug.rs @@ -0,0 +1,7 @@ +#![feature(never_type, rustc_attrs)] +#![crate_type = "lib"] + +enum E { Foo, Bar(!, i32, i32) } + +#[rustc_layout(debug)] +type Test = E; //~ ERROR: layout debugging diff --git a/src/test/ui/layout/debug.stderr b/src/test/ui/layout/debug.stderr new file mode 100644 index 0000000000000..df8b70f307074 --- /dev/null +++ b/src/test/ui/layout/debug.stderr @@ -0,0 +1,120 @@ +error: layout debugging: LayoutDetails { + fields: Arbitrary { + offsets: [ + Size { + raw: 0, + }, + ], + memory_index: [ + 0, + ], + }, + variants: Multiple { + discr: Scalar { + value: Int( + I32, + false, + ), + valid_range: 0..=0, + }, + discr_kind: Tag, + discr_index: 0, + variants: [ + LayoutDetails { + fields: Arbitrary { + offsets: [], + memory_index: [], + }, + variants: Single { + index: 0, + }, + abi: Aggregate { + sized: true, + }, + largest_niche: None, + align: AbiAndPrefAlign { + abi: Align { + pow2: 0, + }, + pref: Align { + pow2: 3, + }, + }, + size: Size { + raw: 4, + }, + }, + LayoutDetails { + fields: Arbitrary { + offsets: [ + Size { + raw: 4, + }, + Size { + raw: 4, + }, + Size { + raw: 8, + }, + ], + memory_index: [ + 0, + 1, + 2, + ], + }, + variants: Single { + index: 1, + }, + abi: Uninhabited, + largest_niche: None, + align: AbiAndPrefAlign { + abi: Align { + pow2: 2, + }, + pref: Align { + pow2: 3, + }, + }, + size: Size { + raw: 12, + }, + }, + ], + }, + abi: Aggregate { + sized: true, + }, + largest_niche: Some( + Niche { + offset: Size { + raw: 0, + }, + scalar: Scalar { + value: Int( + I32, + false, + ), + valid_range: 0..=0, + }, + }, + ), + align: AbiAndPrefAlign { + abi: Align { + pow2: 2, + }, + pref: Align { + pow2: 3, + }, + }, + size: Size { + raw: 12, + }, +} + --> $DIR/debug.rs:7:1 + | +LL | type Test = E; + | ^^^^^^^^^^^^^^ + +error: aborting due to previous error + From c62e36bf4c6f7a128f1af4dadd2abd5ecce397f0 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Fri, 20 Mar 2020 17:48:03 +0100 Subject: [PATCH 4/5] make rustc_layout also work for type definitions --- src/librustc_passes/layout_test.rs | 14 +- src/test/ui/layout/debug.rs | 11 +- src/test/ui/layout/debug.stderr | 223 ++++++++++++++++++++++++++++- 3 files changed, 238 insertions(+), 10 deletions(-) diff --git a/src/librustc_passes/layout_test.rs b/src/librustc_passes/layout_test.rs index 66297eb972736..32561c6bd87e7 100644 --- a/src/librustc_passes/layout_test.rs +++ b/src/librustc_passes/layout_test.rs @@ -29,12 +29,18 @@ impl ItemLikeVisitor<'tcx> for LayoutTest<'tcx> { fn visit_item(&mut self, item: &'tcx hir::Item<'tcx>) { let item_def_id = self.tcx.hir().local_def_id(item.hir_id); - if let ItemKind::TyAlias(..) = item.kind { - for attr in self.tcx.get_attrs(item_def_id).iter() { - if attr.check_name(sym::rustc_layout) { - self.dump_layout_of(item_def_id, item, attr); + match item.kind { + ItemKind::TyAlias(..) | + ItemKind::Enum(..) | + ItemKind::Struct(..) | + ItemKind::Union(..) => { + for attr in self.tcx.get_attrs(item_def_id).iter() { + if attr.check_name(sym::rustc_layout) { + self.dump_layout_of(item_def_id, item, attr); + } } } + _ => {} } } diff --git a/src/test/ui/layout/debug.rs b/src/test/ui/layout/debug.rs index 64a02ee5a22c8..047002c9c99e2 100644 --- a/src/test/ui/layout/debug.rs +++ b/src/test/ui/layout/debug.rs @@ -1,7 +1,14 @@ #![feature(never_type, rustc_attrs)] #![crate_type = "lib"] -enum E { Foo, Bar(!, i32, i32) } +#[rustc_layout(debug)] +enum E { Foo, Bar(!, i32, i32) } //~ ERROR: layout debugging + +#[rustc_layout(debug)] +struct S { f1: i32, f2: (), f3: i32 } //~ ERROR: layout debugging + +#[rustc_layout(debug)] +union U { f1: (i32, i32), f3: i32 } //~ ERROR: layout debugging #[rustc_layout(debug)] -type Test = E; //~ ERROR: layout debugging +type Test = Result; //~ ERROR: layout debugging diff --git a/src/test/ui/layout/debug.stderr b/src/test/ui/layout/debug.stderr index df8b70f307074..6e704528c4130 100644 --- a/src/test/ui/layout/debug.stderr +++ b/src/test/ui/layout/debug.stderr @@ -111,10 +111,225 @@ error: layout debugging: LayoutDetails { raw: 12, }, } - --> $DIR/debug.rs:7:1 + --> $DIR/debug.rs:5:1 | -LL | type Test = E; - | ^^^^^^^^^^^^^^ +LL | enum E { Foo, Bar(!, i32, i32) } + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -error: aborting due to previous error +error: layout debugging: LayoutDetails { + fields: Arbitrary { + offsets: [ + Size { + raw: 0, + }, + Size { + raw: 0, + }, + Size { + raw: 4, + }, + ], + memory_index: [ + 1, + 0, + 2, + ], + }, + variants: Single { + index: 0, + }, + abi: ScalarPair( + Scalar { + value: Int( + I32, + true, + ), + valid_range: 0..=4294967295, + }, + Scalar { + value: Int( + I32, + true, + ), + valid_range: 0..=4294967295, + }, + ), + largest_niche: None, + align: AbiAndPrefAlign { + abi: Align { + pow2: 2, + }, + pref: Align { + pow2: 3, + }, + }, + size: Size { + raw: 8, + }, +} + --> $DIR/debug.rs:8:1 + | +LL | struct S { f1: i32, f2: (), f3: i32 } + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: layout debugging: LayoutDetails { + fields: Union( + 2, + ), + variants: Single { + index: 0, + }, + abi: Aggregate { + sized: true, + }, + largest_niche: None, + align: AbiAndPrefAlign { + abi: Align { + pow2: 2, + }, + pref: Align { + pow2: 3, + }, + }, + size: Size { + raw: 8, + }, +} + --> $DIR/debug.rs:11:1 + | +LL | union U { f1: (i32, i32), f3: i32 } + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: layout debugging: LayoutDetails { + fields: Arbitrary { + offsets: [ + Size { + raw: 0, + }, + ], + memory_index: [ + 0, + ], + }, + variants: Multiple { + discr: Scalar { + value: Int( + I32, + false, + ), + valid_range: 0..=1, + }, + discr_kind: Tag, + discr_index: 0, + variants: [ + LayoutDetails { + fields: Arbitrary { + offsets: [ + Size { + raw: 4, + }, + ], + memory_index: [ + 0, + ], + }, + variants: Single { + index: 0, + }, + abi: Aggregate { + sized: true, + }, + largest_niche: None, + align: AbiAndPrefAlign { + abi: Align { + pow2: 2, + }, + pref: Align { + pow2: 3, + }, + }, + size: Size { + raw: 8, + }, + }, + LayoutDetails { + fields: Arbitrary { + offsets: [ + Size { + raw: 4, + }, + ], + memory_index: [ + 0, + ], + }, + variants: Single { + index: 1, + }, + abi: Aggregate { + sized: true, + }, + largest_niche: None, + align: AbiAndPrefAlign { + abi: Align { + pow2: 2, + }, + pref: Align { + pow2: 3, + }, + }, + size: Size { + raw: 8, + }, + }, + ], + }, + abi: ScalarPair( + Scalar { + value: Int( + I32, + false, + ), + valid_range: 0..=1, + }, + Scalar { + value: Int( + I32, + true, + ), + valid_range: 0..=4294967295, + }, + ), + largest_niche: Some( + Niche { + offset: Size { + raw: 0, + }, + scalar: Scalar { + value: Int( + I32, + false, + ), + valid_range: 0..=1, + }, + }, + ), + align: AbiAndPrefAlign { + abi: Align { + pow2: 2, + }, + pref: Align { + pow2: 3, + }, + }, + size: Size { + raw: 8, + }, +} + --> $DIR/debug.rs:14:1 + | +LL | type Test = Result; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: aborting due to 4 previous errors From 7b49678f5f6e473e69c4a737acd1acc1b8d9a0f1 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Fri, 20 Mar 2020 23:22:36 +0100 Subject: [PATCH 5/5] fmt --- src/librustc_passes/layout_test.rs | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/librustc_passes/layout_test.rs b/src/librustc_passes/layout_test.rs index 32561c6bd87e7..9d8b1422bdf24 100644 --- a/src/librustc_passes/layout_test.rs +++ b/src/librustc_passes/layout_test.rs @@ -30,10 +30,10 @@ impl ItemLikeVisitor<'tcx> for LayoutTest<'tcx> { let item_def_id = self.tcx.hir().local_def_id(item.hir_id); match item.kind { - ItemKind::TyAlias(..) | - ItemKind::Enum(..) | - ItemKind::Struct(..) | - ItemKind::Union(..) => { + ItemKind::TyAlias(..) + | ItemKind::Enum(..) + | ItemKind::Struct(..) + | ItemKind::Union(..) => { for attr in self.tcx.get_attrs(item_def_id).iter() { if attr.check_name(sym::rustc_layout) { self.dump_layout_of(item_def_id, item, attr);