From b72f55580cf78fb93f05a04ec10e9ae34ea58202 Mon Sep 17 00:00:00 2001 From: Eric Huss Date: Fri, 4 Feb 2022 11:48:18 -0800 Subject: Document -C symbol-mangling-version --- src/doc/rustc/src/codegen-options/index.md | 15 +++++++++++++++ 1 file changed, 15 insertions(+) (limited to 'src') diff --git a/src/doc/rustc/src/codegen-options/index.md b/src/doc/rustc/src/codegen-options/index.md index 0201b88417a..3e3d68da4c9 100644 --- a/src/doc/rustc/src/codegen-options/index.md +++ b/src/doc/rustc/src/codegen-options/index.md @@ -541,6 +541,21 @@ Supported values for this option are: - `symbols` - same as `debuginfo`, but the rest of the symbol table section is stripped as well if the linker supports it. +## symbol-mangling-version + +This option controls the [name mangling] format for encoding Rust item names +for the purpose of generating object code and linking. + +Supported values for this option are: + +* `v0` — The "v0" mangling scheme. The specific format is not specified at + this time. + +The default if not specified will use a compiler-chosen default which may +change in the future. + +[name mangling]: https://en.wikipedia.org/wiki/Name_mangling + ## target-cpu This instructs `rustc` to generate code specifically for a particular processor. -- cgit 1.4.1-3-g733a5 From 800e0e2cfa845be5a01c611c8f370172b3a7cea5 Mon Sep 17 00:00:00 2001 From: Eric Huss Date: Fri, 4 Feb 2022 12:10:05 -0800 Subject: Document --json=future-incompat --- src/doc/rustc/src/command-line-arguments.md | 3 +++ src/doc/rustc/src/json.md | 26 ++++++++++++++++++++++++++ 2 files changed, 29 insertions(+) (limited to 'src') diff --git a/src/doc/rustc/src/command-line-arguments.md b/src/doc/rustc/src/command-line-arguments.md index 11925ab9785..6ed28f1a845 100644 --- a/src/doc/rustc/src/command-line-arguments.md +++ b/src/doc/rustc/src/command-line-arguments.md @@ -384,6 +384,9 @@ to customize the output: argument](#option-emit), and as soon as the artifact is available on the filesystem a notification will be emitted. +- `future-incompat` - includes a JSON message that contains a report if the + crate contains any code that may fail to compile in the future. + Note that it is invalid to combine the `--json` argument with the [`--color`](#option-color) argument, and it is required to combine `--json` with `--error-format=json`. diff --git a/src/doc/rustc/src/json.md b/src/doc/rustc/src/json.md index 5dee603142d..efbf861eaa6 100644 --- a/src/doc/rustc/src/json.md +++ b/src/doc/rustc/src/json.md @@ -229,6 +229,32 @@ flag][option-emit] documentation. } ``` +## Future-incompatible reports + +If the [`--json=future-incompat`][option-json] flag is used, then a separate +JSON structure will be emitted if the crate may stop compiling in the future. +This contains diagnostic information about the particular warnings that may be +turned into a hard error in the future. This will include the diagnostic +information, even if the diagnostics have been suppressed (such as with an +`#[allow]` attribute or the `--cap-lints` option). + +```javascript +{ + /* An array of objects describing a warning that will become a hard error + in the future. + */ + "future_incompat_report": + [ + { + /* A diagnostic structure as defined in + https://doc.rust-lang.org/rustc/json.html#diagnostics + */ + "diagnostic": {...}, + } + ] +} +``` + [option-emit]: command-line-arguments.md#option-emit [option-error-format]: command-line-arguments.md#option-error-format [option-json]: command-line-arguments.md#option-json -- cgit 1.4.1-3-g733a5 From 89f15bfd907b0b44a851c5810ab463fe91a206e5 Mon Sep 17 00:00:00 2001 From: Camille GILLOT Date: Sat, 7 May 2022 13:08:04 +0200 Subject: Add test. --- .../auxiliary/edition-lint-infer-outlives-macro.rs | 6 +++++ .../rust-2018/edition-lint-infer-outlives-macro.rs | 28 ++++++++++++++++++++++ .../edition-lint-infer-outlives-macro.stderr | 14 +++++++++++ 3 files changed, 48 insertions(+) create mode 100644 src/test/ui/rust-2018/auxiliary/edition-lint-infer-outlives-macro.rs create mode 100644 src/test/ui/rust-2018/edition-lint-infer-outlives-macro.rs create mode 100644 src/test/ui/rust-2018/edition-lint-infer-outlives-macro.stderr (limited to 'src') diff --git a/src/test/ui/rust-2018/auxiliary/edition-lint-infer-outlives-macro.rs b/src/test/ui/rust-2018/auxiliary/edition-lint-infer-outlives-macro.rs new file mode 100644 index 00000000000..d45fa10f022 --- /dev/null +++ b/src/test/ui/rust-2018/auxiliary/edition-lint-infer-outlives-macro.rs @@ -0,0 +1,6 @@ +pub fn foo() {} + +#[macro_export] +macro_rules! gimme_a { + ($($mac:tt)*) => { $($mac)* { 'a } } +} diff --git a/src/test/ui/rust-2018/edition-lint-infer-outlives-macro.rs b/src/test/ui/rust-2018/edition-lint-infer-outlives-macro.rs new file mode 100644 index 00000000000..d7a832831c1 --- /dev/null +++ b/src/test/ui/rust-2018/edition-lint-infer-outlives-macro.rs @@ -0,0 +1,28 @@ +// edition:2018 +// aux-build:edition-lint-infer-outlives-macro.rs + +// Test that the lint does not fire if the where predicate +// is from the local crate, but all the bounds are from an +// external macro. + +#![deny(explicit_outlives_requirements)] + +#[macro_use] +extern crate edition_lint_infer_outlives_macro; + +macro_rules! make_foo { + ($a:tt) => { + struct Foo<$a, 'b> where 'b: $a { + foo: &$a &'b (), + } + } +} + +gimme_a! {make_foo!} + +struct Bar<'a, 'b: 'a> { + //~^ ERROR: outlives requirements can be inferred + bar: &'a &'b (), +} + +fn main() {} diff --git a/src/test/ui/rust-2018/edition-lint-infer-outlives-macro.stderr b/src/test/ui/rust-2018/edition-lint-infer-outlives-macro.stderr new file mode 100644 index 00000000000..553b1cd976a --- /dev/null +++ b/src/test/ui/rust-2018/edition-lint-infer-outlives-macro.stderr @@ -0,0 +1,14 @@ +error: outlives requirements can be inferred + --> $DIR/edition-lint-infer-outlives-macro.rs:23:18 + | +LL | struct Bar<'a, 'b: 'a> { + | ^^^^ help: remove this bound + | +note: the lint level is defined here + --> $DIR/edition-lint-infer-outlives-macro.rs:8:9 + | +LL | #![deny(explicit_outlives_requirements)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: aborting due to previous error + -- cgit 1.4.1-3-g733a5 From 2c11c3d86cd067d929634852749904a9674c8e49 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Mon, 9 May 2022 17:29:59 +0200 Subject: make sure ScalarPair enums have ScalarPair variants; add some layout sanity checks --- compiler/rustc_middle/src/ty/layout.rs | 123 +++++++++++++++++++-- src/test/ui/layout/debug.stderr | 38 ++++++- ...96158-scalarpair-payload-might-be-uninit.stderr | 92 ++++++++++++--- 3 files changed, 221 insertions(+), 32 deletions(-) (limited to 'src') diff --git a/compiler/rustc_middle/src/ty/layout.rs b/compiler/rustc_middle/src/ty/layout.rs index cd4b23fca39..1a1b795b0a4 100644 --- a/compiler/rustc_middle/src/ty/layout.rs +++ b/compiler/rustc_middle/src/ty/layout.rs @@ -220,6 +220,91 @@ impl<'tcx> fmt::Display for LayoutError<'tcx> { } } +/// Enforce some basic invariants on layouts. +fn sanity_check_layout<'tcx>( + tcx: TyCtxt<'tcx>, + param_env: ty::ParamEnv<'tcx>, + layout: &TyAndLayout<'tcx>, +) { + // Type-level uninhabitedness should always imply ABI uninhabitedness. + if tcx.conservative_is_privately_uninhabited(param_env.and(layout.ty)) { + assert!(layout.abi.is_uninhabited()); + } + + if cfg!(debug_assertions) { + fn check_layout_abi<'tcx>(tcx: TyCtxt<'tcx>, layout: Layout<'tcx>) { + match layout.abi() { + Abi::Scalar(_scalar) => { + // No padding in scalars. + /* FIXME(#96185): + assert_eq!( + layout.align().abi, + scalar.align(&tcx).abi, + "alignment mismatch between ABI and layout in {layout:#?}" + ); + assert_eq!( + layout.size(), + scalar.size(&tcx), + "size mismatch between ABI and layout in {layout:#?}" + );*/ + } + Abi::ScalarPair(scalar1, scalar2) => { + // Sanity-check scalar pair size. + let field2_offset = scalar1.size(&tcx).align_to(scalar2.align(&tcx).abi); + let total = field2_offset + scalar2.size(&tcx); + assert!( + layout.size() >= total, + "size mismatch between ABI and layout in {layout:#?}" + ); + } + _ => {} + } + } + + check_layout_abi(tcx, layout.layout); + + if let Variants::Multiple { variants, .. } = &layout.variants { + for variant in variants { + check_layout_abi(tcx, *variant); + // No nested "multiple". + assert!(matches!(variant.variants(), Variants::Single { .. })); + // Skip empty variants. + if variant.size() == Size::ZERO + || variant.fields().count() == 0 + || variant.abi().is_uninhabited() + { + // These are never actually accessed anyway, so we can skip them. (Note that + // sometimes, variants with fields have size 0, and sometimes, variants without + // fields have non-0 size.) + continue; + } + // Variants should have the same or a smaller size as the full thing. + if variant.size() > layout.size { + bug!( + "Type with size {} bytes has variant with size {} bytes: {layout:#?}", + layout.size.bytes(), + variant.size().bytes(), + ) + } + // The top-level ABI and the ABI of the variants should be coherent. + let abi_coherent = match (layout.abi, variant.abi()) { + (Abi::Scalar(..), Abi::Scalar(..)) => true, + (Abi::ScalarPair(..), Abi::ScalarPair(..)) => true, + (Abi::Uninhabited, _) => true, + (Abi::Aggregate { .. }, _) => true, + _ => false, + }; + if !abi_coherent { + bug!( + "Variant ABI is incompatible with top-level ABI:\nvariant={:#?}\nTop-level: {layout:#?}", + variant + ); + } + } + } + } +} + #[instrument(skip(tcx, query), level = "debug")] fn layout_of<'tcx>( tcx: TyCtxt<'tcx>, @@ -263,10 +348,7 @@ fn layout_of<'tcx>( cx.record_layout_for_printing(layout); - // Type-level uninhabitedness should always imply ABI uninhabitedness. - if tcx.conservative_is_privately_uninhabited(param_env.and(ty)) { - assert!(layout.abi.is_uninhabited()); - } + sanity_check_layout(tcx, param_env, &layout); Ok(layout) }) @@ -1313,10 +1395,22 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> { }; let mut abi = Abi::Aggregate { sized: true }; - // Without latter check aligned enums with custom discriminant values - // Would result in ICE see the issue #92464 for more info - if tag.size(dl) == size || variants.iter().all(|layout| layout.is_empty()) { + if layout_variants.iter().all(|v| v.abi.is_uninhabited()) { + abi = Abi::Uninhabited; + } else if tag.size(dl) == size || variants.iter().all(|layout| layout.is_empty()) { + // Without latter check aligned enums with custom discriminant values + // Would result in ICE see the issue #92464 for more info abi = Abi::Scalar(tag); + // Make sure the variants with fields have the same ABI as the enum itself + // (since downcasting to them is a NOP). + for variant in &mut layout_variants { + if variant.fields.count() > 0 + && matches!(variant.abi, Abi::Aggregate { .. }) + { + assert_eq!(variant.size, size); + variant.abi = abi; + } + } } else { // Try to use a ScalarPair for all tagged enums. let mut common_prim = None; @@ -1385,14 +1479,21 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> { // We can use `ScalarPair` only when it matches our // already computed layout (including `#[repr(C)]`). abi = pair.abi; + // Make sure the variants with fields have the same ABI as the enum itself + // (since downcasting to them is a NOP). + for variant in &mut layout_variants { + if variant.fields.count() > 0 + && matches!(variant.abi, Abi::Aggregate { .. }) + { + variant.abi = abi; + // Also need to bump up the size, so that the pair fits inside. + variant.size = size; + } + } } } } - if layout_variants.iter().all(|v| v.abi.is_uninhabited()) { - abi = Abi::Uninhabited; - } - let largest_niche = Niche::from_scalar(dl, Size::ZERO, tag); let layout_variants = diff --git a/src/test/ui/layout/debug.stderr b/src/test/ui/layout/debug.stderr index 56a1337e6a5..7dbcc151855 100644 --- a/src/test/ui/layout/debug.stderr +++ b/src/test/ui/layout/debug.stderr @@ -184,9 +184,22 @@ error: layout_of(std::result::Result) = Layout { variants: Single { index: 0, }, - abi: Aggregate { - sized: true, - }, + abi: ScalarPair( + Initialized { + value: Int( + I32, + false, + ), + valid_range: 0..=1, + }, + Initialized { + value: Int( + I32, + true, + ), + valid_range: 0..=4294967295, + }, + ), largest_niche: None, align: AbiAndPrefAlign { abi: Align(4 bytes), @@ -206,9 +219,22 @@ error: layout_of(std::result::Result) = Layout { variants: Single { index: 1, }, - abi: Aggregate { - sized: true, - }, + abi: ScalarPair( + Initialized { + value: Int( + I32, + false, + ), + valid_range: 0..=1, + }, + Initialized { + value: Int( + I32, + true, + ), + valid_range: 0..=4294967295, + }, + ), largest_niche: None, align: AbiAndPrefAlign { abi: Align(4 bytes), diff --git a/src/test/ui/layout/issue-96158-scalarpair-payload-might-be-uninit.stderr b/src/test/ui/layout/issue-96158-scalarpair-payload-might-be-uninit.stderr index 1a724e6f59b..33dfa307c1d 100644 --- a/src/test/ui/layout/issue-96158-scalarpair-payload-might-be-uninit.stderr +++ b/src/test/ui/layout/issue-96158-scalarpair-payload-might-be-uninit.stderr @@ -30,9 +30,21 @@ error: layout_of(MissingPayloadField) = Layout { variants: Single { index: 0, }, - abi: Aggregate { - sized: true, - }, + abi: ScalarPair( + Initialized { + value: Int( + I8, + false, + ), + valid_range: 0..=1, + }, + Union { + value: Int( + I8, + false, + ), + }, + ), largest_niche: None, align: AbiAndPrefAlign { abi: Align(1 bytes), @@ -131,9 +143,22 @@ error: layout_of(CommonPayloadField) = Layout { variants: Single { index: 0, }, - abi: Aggregate { - sized: true, - }, + abi: ScalarPair( + Initialized { + value: Int( + I8, + false, + ), + valid_range: 0..=1, + }, + Initialized { + value: Int( + I8, + false, + ), + valid_range: 0..=255, + }, + ), largest_niche: None, align: AbiAndPrefAlign { abi: Align(1 bytes), @@ -153,9 +178,22 @@ error: layout_of(CommonPayloadField) = Layout { variants: Single { index: 1, }, - abi: Aggregate { - sized: true, - }, + abi: ScalarPair( + Initialized { + value: Int( + I8, + false, + ), + valid_range: 0..=1, + }, + Initialized { + value: Int( + I8, + false, + ), + valid_range: 0..=255, + }, + ), largest_niche: None, align: AbiAndPrefAlign { abi: Align(1 bytes), @@ -237,9 +275,21 @@ error: layout_of(CommonPayloadFieldIsMaybeUninit) = Layout { variants: Single { index: 0, }, - abi: Aggregate { - sized: true, - }, + abi: ScalarPair( + Initialized { + value: Int( + I8, + false, + ), + valid_range: 0..=1, + }, + Union { + value: Int( + I8, + false, + ), + }, + ), largest_niche: None, align: AbiAndPrefAlign { abi: Align(1 bytes), @@ -259,9 +309,21 @@ error: layout_of(CommonPayloadFieldIsMaybeUninit) = Layout { variants: Single { index: 1, }, - abi: Aggregate { - sized: true, - }, + abi: ScalarPair( + Initialized { + value: Int( + I8, + false, + ), + valid_range: 0..=1, + }, + Union { + value: Int( + I8, + false, + ), + }, + ), largest_niche: None, align: AbiAndPrefAlign { abi: Align(1 bytes), -- cgit 1.4.1-3-g733a5 From 04fb9222f861607b749a04e91e832475a5c8dc0f Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Mon, 9 May 2022 18:10:21 +0200 Subject: fix codegen test failure --- src/test/codegen/align-struct.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/test/codegen/align-struct.rs b/src/test/codegen/align-struct.rs index acc5a2d5499..f129f073e98 100644 --- a/src/test/codegen/align-struct.rs +++ b/src/test/codegen/align-struct.rs @@ -19,7 +19,7 @@ pub enum Enum4 { A(i32), B(i32), } -// CHECK: %"Enum4::A" = type { [1 x i32], i32 } +// No Aggregate type, and hence nothing in LLVM IR. pub enum Enum64 { A(Align64), -- cgit 1.4.1-3-g733a5