From f39eb7e658a5b52175e75d065f2e0720f1460d6f Mon Sep 17 00:00:00 2001 From: Urgau Date: Thu, 6 Jul 2023 21:45:24 +0200 Subject: [PATCH 01/17] Rename cast_ref_to_mut lint to invalid_reference_casting (cherry picked from commit 3dbbf23e29516218863bda29d2983bd503e6b7fd) --- compiler/rustc_lint/messages.ftl | 4 ++-- compiler/rustc_lint/src/lib.rs | 6 ++--- compiler/rustc_lint/src/lints.rs | 6 ++--- ...ast_ref_to_mut.rs => reference_casting.rs} | 12 +++++----- .../both_borrows/shr_frozen_violation1.rs | 2 +- .../miri/tests/fail/modifying_constants.rs | 2 +- .../const-generics/issues/issue-100313.stderr | 2 +- ...ast_ref_to_mut.rs => reference_casting.rs} | 0 ...to_mut.stderr => reference_casting.stderr} | 22 +++++++++---------- 9 files changed, 28 insertions(+), 28 deletions(-) rename compiler/rustc_lint/src/{cast_ref_to_mut.rs => reference_casting.rs} (82%) rename tests/ui/lint/{cast_ref_to_mut.rs => reference_casting.rs} (100%) rename tests/ui/lint/{cast_ref_to_mut.stderr => reference_casting.stderr} (85%) diff --git a/compiler/rustc_lint/messages.ftl b/compiler/rustc_lint/messages.ftl index 34b7e09576af5..a3453cbc0264b 100644 --- a/compiler/rustc_lint/messages.ftl +++ b/compiler/rustc_lint/messages.ftl @@ -155,8 +155,6 @@ lint_builtin_unused_doc_comment = unused doc comment lint_builtin_while_true = denote infinite loops with `loop {"{"} ... {"}"}` .suggestion = use `loop` -lint_cast_ref_to_mut = casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - lint_check_name_deprecated = lint name `{$lint_name}` is deprecated and does not have an effect anymore. Use: {$new_name} lint_check_name_unknown = unknown lint: `{$lint_name}` @@ -319,6 +317,8 @@ lint_invalid_nan_comparisons_eq_ne = incorrect NaN comparison, NaN cannot be dir lint_invalid_nan_comparisons_lt_le_gt_ge = incorrect NaN comparison, NaN is not orderable +lint_invalid_reference_casting = casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` + lint_lintpass_by_hand = implementing `LintPass` by hand .help = try using `declare_lint_pass!` or `impl_lint_pass!` instead diff --git a/compiler/rustc_lint/src/lib.rs b/compiler/rustc_lint/src/lib.rs index 5e3f057d42834..602071a55e541 100644 --- a/compiler/rustc_lint/src/lib.rs +++ b/compiler/rustc_lint/src/lib.rs @@ -50,7 +50,6 @@ extern crate tracing; mod array_into_iter; pub mod builtin; -mod cast_ref_to_mut; mod context; mod deref_into_dyn_supertrait; mod drop_forget_useless; @@ -77,6 +76,7 @@ mod opaque_hidden_inferred_bound; mod pass_by_value; mod passes; mod redundant_semicolon; +mod reference_casting; mod traits; mod types; mod unused; @@ -98,7 +98,6 @@ use rustc_span::Span; use array_into_iter::ArrayIntoIter; use builtin::*; -use cast_ref_to_mut::*; use deref_into_dyn_supertrait::*; use drop_forget_useless::*; use enum_intrinsics_non_enums::EnumIntrinsicsNonEnums; @@ -117,6 +116,7 @@ use noop_method_call::*; use opaque_hidden_inferred_bound::*; use pass_by_value::*; use redundant_semicolon::*; +use reference_casting::*; use traits::*; use types::*; use unused::*; @@ -216,7 +216,7 @@ late_lint_methods!( BoxPointers: BoxPointers, PathStatements: PathStatements, LetUnderscore: LetUnderscore, - CastRefToMut: CastRefToMut, + InvalidReferenceCasting: InvalidReferenceCasting, // Depends on referenced function signatures in expressions UnusedResults: UnusedResults, NonUpperCaseGlobals: NonUpperCaseGlobals, diff --git a/compiler/rustc_lint/src/lints.rs b/compiler/rustc_lint/src/lints.rs index 0613ef2c5e958..9260237fbeead 100644 --- a/compiler/rustc_lint/src/lints.rs +++ b/compiler/rustc_lint/src/lints.rs @@ -737,10 +737,10 @@ pub enum InvalidFromUtf8Diag { }, } -// cast_ref_to_mut.rs +// reference_casting.rs #[derive(LintDiagnostic)] -#[diag(lint_cast_ref_to_mut)] -pub struct CastRefToMutDiag; +#[diag(lint_invalid_reference_casting)] +pub struct InvalidReferenceCastingDiag; // hidden_unicode_codepoints.rs #[derive(LintDiagnostic)] diff --git a/compiler/rustc_lint/src/cast_ref_to_mut.rs b/compiler/rustc_lint/src/reference_casting.rs similarity index 82% rename from compiler/rustc_lint/src/cast_ref_to_mut.rs rename to compiler/rustc_lint/src/reference_casting.rs index 84308d48c10bc..34b916eef90de 100644 --- a/compiler/rustc_lint/src/cast_ref_to_mut.rs +++ b/compiler/rustc_lint/src/reference_casting.rs @@ -3,10 +3,10 @@ use rustc_hir::{Expr, ExprKind, MutTy, TyKind, UnOp}; use rustc_middle::ty; use rustc_span::sym; -use crate::{lints::CastRefToMutDiag, LateContext, LateLintPass, LintContext}; +use crate::{lints::InvalidReferenceCastingDiag, LateContext, LateLintPass, LintContext}; declare_lint! { - /// The `cast_ref_to_mut` lint checks for casts of `&T` to `&mut T` + /// The `invalid_reference_casting` lint checks for casts of `&T` to `&mut T` /// without using interior mutability. /// /// ### Example @@ -28,14 +28,14 @@ declare_lint! { /// /// `UnsafeCell` is the only way to obtain aliasable data that is considered /// mutable. - CAST_REF_TO_MUT, + INVALID_REFERENCE_CASTING, Deny, "casts of `&T` to `&mut T` without interior mutability" } -declare_lint_pass!(CastRefToMut => [CAST_REF_TO_MUT]); +declare_lint_pass!(InvalidReferenceCasting => [INVALID_REFERENCE_CASTING]); -impl<'tcx> LateLintPass<'tcx> for CastRefToMut { +impl<'tcx> LateLintPass<'tcx> for InvalidReferenceCasting { fn check_expr(&mut self, cx: &LateContext<'tcx>, expr: &'tcx Expr<'tcx>) { let ExprKind::Unary(UnOp::Deref, e) = &expr.kind else { return; }; @@ -66,7 +66,7 @@ impl<'tcx> LateLintPass<'tcx> for CastRefToMut { let e = e.peel_blocks(); if let ty::Ref(..) = cx.typeck_results().node_type(e.hir_id).kind() { - cx.emit_spanned_lint(CAST_REF_TO_MUT, expr.span, CastRefToMutDiag); + cx.emit_spanned_lint(INVALID_REFERENCE_CASTING, expr.span, InvalidReferenceCastingDiag); } } } diff --git a/src/tools/miri/tests/fail/both_borrows/shr_frozen_violation1.rs b/src/tools/miri/tests/fail/both_borrows/shr_frozen_violation1.rs index 1edd7748cde11..0c7f4b89711ae 100644 --- a/src/tools/miri/tests/fail/both_borrows/shr_frozen_violation1.rs +++ b/src/tools/miri/tests/fail/both_borrows/shr_frozen_violation1.rs @@ -1,7 +1,7 @@ //@revisions: stack tree //@[tree]compile-flags: -Zmiri-tree-borrows -#![allow(cast_ref_to_mut)] +#![allow(invalid_reference_casting)] fn foo(x: &mut i32) -> i32 { *x = 5; diff --git a/src/tools/miri/tests/fail/modifying_constants.rs b/src/tools/miri/tests/fail/modifying_constants.rs index 40ba31dad8f68..0d1bd7929b5b8 100644 --- a/src/tools/miri/tests/fail/modifying_constants.rs +++ b/src/tools/miri/tests/fail/modifying_constants.rs @@ -1,7 +1,7 @@ // This should fail even without validation/SB //@compile-flags: -Zmiri-disable-validation -Zmiri-disable-stacked-borrows -#![allow(cast_ref_to_mut)] +#![allow(invalid_reference_casting)] fn main() { let x = &1; // the `&1` is promoted to a constant, but it used to be that only the pointer is marked static, not the pointee diff --git a/tests/ui/const-generics/issues/issue-100313.stderr b/tests/ui/const-generics/issues/issue-100313.stderr index ffc34a3a41e24..17e4850bd12a4 100644 --- a/tests/ui/const-generics/issues/issue-100313.stderr +++ b/tests/ui/const-generics/issues/issue-100313.stderr @@ -4,7 +4,7 @@ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is LL | *(B as *const bool as *mut bool) = false; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | - = note: `#[deny(cast_ref_to_mut)]` on by default + = note: `#[deny(invalid_reference_casting)]` on by default error[E0080]: evaluation of constant value failed --> $DIR/issue-100313.rs:10:13 diff --git a/tests/ui/lint/cast_ref_to_mut.rs b/tests/ui/lint/reference_casting.rs similarity index 100% rename from tests/ui/lint/cast_ref_to_mut.rs rename to tests/ui/lint/reference_casting.rs diff --git a/tests/ui/lint/cast_ref_to_mut.stderr b/tests/ui/lint/reference_casting.stderr similarity index 85% rename from tests/ui/lint/cast_ref_to_mut.stderr rename to tests/ui/lint/reference_casting.stderr index baff00d6c0419..d1dd1b32ff44d 100644 --- a/tests/ui/lint/cast_ref_to_mut.stderr +++ b/tests/ui/lint/reference_casting.stderr @@ -1,61 +1,61 @@ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/cast_ref_to_mut.rs:19:9 + --> $DIR/reference_casting.rs:19:9 | LL | (*(a as *const _ as *mut String)).push_str(" world"); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | - = note: `#[deny(cast_ref_to_mut)]` on by default + = note: `#[deny(invalid_reference_casting)]` on by default error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/cast_ref_to_mut.rs:21:9 + --> $DIR/reference_casting.rs:21:9 | LL | *(a as *const _ as *mut _) = String::from("Replaced"); | ^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/cast_ref_to_mut.rs:23:9 + --> $DIR/reference_casting.rs:23:9 | LL | *(a as *const _ as *mut String) += " world"; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/cast_ref_to_mut.rs:25:25 + --> $DIR/reference_casting.rs:25:25 | LL | let _num = &mut *(num as *const i32 as *mut i32); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/cast_ref_to_mut.rs:27:25 + --> $DIR/reference_casting.rs:27:25 | LL | let _num = &mut *(num as *const i32).cast_mut(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/cast_ref_to_mut.rs:29:20 + --> $DIR/reference_casting.rs:29:20 | LL | let _num = *{ num as *const i32 }.cast_mut(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/cast_ref_to_mut.rs:31:9 + --> $DIR/reference_casting.rs:31:9 | LL | *std::ptr::from_ref(num).cast_mut() += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/cast_ref_to_mut.rs:33:9 + --> $DIR/reference_casting.rs:33:9 | LL | *std::ptr::from_ref({ num }).cast_mut() += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/cast_ref_to_mut.rs:35:9 + --> $DIR/reference_casting.rs:35:9 | LL | *{ std::ptr::from_ref(num) }.cast_mut() += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/cast_ref_to_mut.rs:37:9 + --> $DIR/reference_casting.rs:37:9 | LL | *(std::ptr::from_ref({ num }) as *mut i32) += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ From b3458da65ba36753ae311d795bb9070e771c7539 Mon Sep 17 00:00:00 2001 From: Urgau Date: Thu, 8 Jun 2023 18:47:44 +0200 Subject: [PATCH 02/17] Rename cast_ref_to_mut to invalid_reference_casting (clippy side) (cherry picked from commit fa15df6f5a85ceb5919a47bb721a337c7b8f0adc) --- src/tools/clippy/clippy_lints/src/renamed_lints.rs | 2 +- src/tools/clippy/tests/ui/rename.fixed | 4 ++-- src/tools/clippy/tests/ui/rename.rs | 2 +- src/tools/clippy/tests/ui/rename.stderr | 4 ++-- 4 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/tools/clippy/clippy_lints/src/renamed_lints.rs b/src/tools/clippy/clippy_lints/src/renamed_lints.rs index cbcd11debfd76..44e7cbfba08aa 100644 --- a/src/tools/clippy/clippy_lints/src/renamed_lints.rs +++ b/src/tools/clippy/clippy_lints/src/renamed_lints.rs @@ -31,7 +31,7 @@ pub static RENAMED_LINTS: &[(&str, &str)] = &[ ("clippy::stutter", "clippy::module_name_repetitions"), ("clippy::to_string_in_display", "clippy::recursive_format_impl"), ("clippy::zero_width_space", "clippy::invisible_characters"), - ("clippy::cast_ref_to_mut", "cast_ref_to_mut"), + ("clippy::cast_ref_to_mut", "invalid_reference_casting"), ("clippy::clone_double_ref", "suspicious_double_ref_op"), ("clippy::cmp_nan", "invalid_nan_comparisons"), ("clippy::drop_bounds", "drop_bounds"), diff --git a/src/tools/clippy/tests/ui/rename.fixed b/src/tools/clippy/tests/ui/rename.fixed index b24c83d9a0da2..cc2295ea50729 100644 --- a/src/tools/clippy/tests/ui/rename.fixed +++ b/src/tools/clippy/tests/ui/rename.fixed @@ -28,9 +28,9 @@ #![allow(clippy::module_name_repetitions)] #![allow(clippy::recursive_format_impl)] #![allow(clippy::invisible_characters)] -#![allow(cast_ref_to_mut)] #![allow(suspicious_double_ref_op)] #![allow(invalid_nan_comparisons)] +#![allow(invalid_reference_casting)] #![allow(drop_bounds)] #![allow(dropping_copy_types)] #![allow(dropping_references)] @@ -78,7 +78,7 @@ #![warn(clippy::module_name_repetitions)] #![warn(clippy::recursive_format_impl)] #![warn(clippy::invisible_characters)] -#![warn(cast_ref_to_mut)] +#![warn(invalid_reference_casting)] #![warn(suspicious_double_ref_op)] #![warn(invalid_nan_comparisons)] #![warn(drop_bounds)] diff --git a/src/tools/clippy/tests/ui/rename.rs b/src/tools/clippy/tests/ui/rename.rs index baa6345a64f83..399335aff4ef0 100644 --- a/src/tools/clippy/tests/ui/rename.rs +++ b/src/tools/clippy/tests/ui/rename.rs @@ -28,9 +28,9 @@ #![allow(clippy::module_name_repetitions)] #![allow(clippy::recursive_format_impl)] #![allow(clippy::invisible_characters)] -#![allow(cast_ref_to_mut)] #![allow(suspicious_double_ref_op)] #![allow(invalid_nan_comparisons)] +#![allow(invalid_reference_casting)] #![allow(drop_bounds)] #![allow(dropping_copy_types)] #![allow(dropping_references)] diff --git a/src/tools/clippy/tests/ui/rename.stderr b/src/tools/clippy/tests/ui/rename.stderr index ae25c3b46bd24..079371330bea0 100644 --- a/src/tools/clippy/tests/ui/rename.stderr +++ b/src/tools/clippy/tests/ui/rename.stderr @@ -174,11 +174,11 @@ error: lint `clippy::zero_width_space` has been renamed to `clippy::invisible_ch LL | #![warn(clippy::zero_width_space)] | ^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::invisible_characters` -error: lint `clippy::cast_ref_to_mut` has been renamed to `cast_ref_to_mut` +error: lint `clippy::cast_ref_to_mut` has been renamed to `invalid_reference_casting` --> $DIR/rename.rs:81:9 | LL | #![warn(clippy::cast_ref_to_mut)] - | ^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `cast_ref_to_mut` + | ^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `invalid_reference_casting` error: lint `clippy::clone_double_ref` has been renamed to `suspicious_double_ref_op` --> $DIR/rename.rs:82:9 From e20288d2afa4be259454eae32bcf492330c7c393 Mon Sep 17 00:00:00 2001 From: Urgau Date: Thu, 6 Jul 2023 21:50:34 +0200 Subject: [PATCH 03/17] Temporarily switch invalid_reference_casting lint to allow-by-default (cherry picked from commit f25ad54a4d0febbcb2b7e951835228b7b2320b49) --- compiler/rustc_lint/src/reference_casting.rs | 3 ++- .../ui/const-generics/issues/issue-100313.rs | 1 - .../const-generics/issues/issue-100313.stderr | 12 ++------- tests/ui/lint/reference_casting.rs | 1 + tests/ui/lint/reference_casting.stderr | 26 +++++++++++-------- 5 files changed, 20 insertions(+), 23 deletions(-) diff --git a/compiler/rustc_lint/src/reference_casting.rs b/compiler/rustc_lint/src/reference_casting.rs index 34b916eef90de..db8d7302a252d 100644 --- a/compiler/rustc_lint/src/reference_casting.rs +++ b/compiler/rustc_lint/src/reference_casting.rs @@ -12,6 +12,7 @@ declare_lint! { /// ### Example /// /// ```rust,compile_fail + /// # #![deny(invalid_reference_casting)] /// fn x(r: &i32) { /// unsafe { /// *(r as *const i32 as *mut i32) += 1; @@ -29,7 +30,7 @@ declare_lint! { /// `UnsafeCell` is the only way to obtain aliasable data that is considered /// mutable. INVALID_REFERENCE_CASTING, - Deny, + Allow, "casts of `&T` to `&mut T` without interior mutability" } diff --git a/tests/ui/const-generics/issues/issue-100313.rs b/tests/ui/const-generics/issues/issue-100313.rs index 9a9d4721c8494..4e9d3626aa89c 100644 --- a/tests/ui/const-generics/issues/issue-100313.rs +++ b/tests/ui/const-generics/issues/issue-100313.rs @@ -9,7 +9,6 @@ impl T { unsafe { *(B as *const bool as *mut bool) = false; //~^ ERROR evaluation of constant value failed [E0080] - //~| ERROR casting `&T` to `&mut T` is undefined behavior } } } diff --git a/tests/ui/const-generics/issues/issue-100313.stderr b/tests/ui/const-generics/issues/issue-100313.stderr index 17e4850bd12a4..d4b486376cac8 100644 --- a/tests/ui/const-generics/issues/issue-100313.stderr +++ b/tests/ui/const-generics/issues/issue-100313.stderr @@ -1,11 +1,3 @@ -error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/issue-100313.rs:10:13 - | -LL | *(B as *const bool as *mut bool) = false; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - | - = note: `#[deny(invalid_reference_casting)]` on by default - error[E0080]: evaluation of constant value failed --> $DIR/issue-100313.rs:10:13 | @@ -18,11 +10,11 @@ note: inside `T::<&true>::set_false` LL | *(B as *const bool as *mut bool) = false; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ note: inside `_` - --> $DIR/issue-100313.rs:19:5 + --> $DIR/issue-100313.rs:18:5 | LL | x.set_false(); | ^^^^^^^^^^^^^ -error: aborting due to 2 previous errors +error: aborting due to previous error For more information about this error, try `rustc --explain E0080`. diff --git a/tests/ui/lint/reference_casting.rs b/tests/ui/lint/reference_casting.rs index 745d707014366..9963820499edd 100644 --- a/tests/ui/lint/reference_casting.rs +++ b/tests/ui/lint/reference_casting.rs @@ -1,6 +1,7 @@ // check-fail #![feature(ptr_from_ref)] +#![deny(invalid_reference_casting)] extern "C" { // N.B., mutability can be easily incorrect in FFI calls -- as diff --git a/tests/ui/lint/reference_casting.stderr b/tests/ui/lint/reference_casting.stderr index d1dd1b32ff44d..d5b9bbef6439f 100644 --- a/tests/ui/lint/reference_casting.stderr +++ b/tests/ui/lint/reference_casting.stderr @@ -1,61 +1,65 @@ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:19:9 + --> $DIR/reference_casting.rs:20:9 | LL | (*(a as *const _ as *mut String)).push_str(" world"); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | - = note: `#[deny(invalid_reference_casting)]` on by default +note: the lint level is defined here + --> $DIR/reference_casting.rs:4:9 + | +LL | #![deny(invalid_reference_casting)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:21:9 + --> $DIR/reference_casting.rs:22:9 | LL | *(a as *const _ as *mut _) = String::from("Replaced"); | ^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:23:9 + --> $DIR/reference_casting.rs:24:9 | LL | *(a as *const _ as *mut String) += " world"; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:25:25 + --> $DIR/reference_casting.rs:26:25 | LL | let _num = &mut *(num as *const i32 as *mut i32); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:27:25 + --> $DIR/reference_casting.rs:28:25 | LL | let _num = &mut *(num as *const i32).cast_mut(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:29:20 + --> $DIR/reference_casting.rs:30:20 | LL | let _num = *{ num as *const i32 }.cast_mut(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:31:9 + --> $DIR/reference_casting.rs:32:9 | LL | *std::ptr::from_ref(num).cast_mut() += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:33:9 + --> $DIR/reference_casting.rs:34:9 | LL | *std::ptr::from_ref({ num }).cast_mut() += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:35:9 + --> $DIR/reference_casting.rs:36:9 | LL | *{ std::ptr::from_ref(num) }.cast_mut() += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:37:9 + --> $DIR/reference_casting.rs:38:9 | LL | *(std::ptr::from_ref({ num }) as *mut i32) += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ From 7744a86963216f9e5b4171997563a8fe293fc2ca Mon Sep 17 00:00:00 2001 From: David Wood Date: Fri, 7 Jul 2023 18:27:16 +0100 Subject: [PATCH 04/17] lint/ctypes: stricter `()` return type checks `()` is normally FFI-unsafe, but is FFI-safe when used as a return type. It is also desirable that a transparent newtype for `()` is FFI-safe when used as a return type. In order to support this, when an type was deemed FFI-unsafe, because of a `()` type, and was used in return type - then the type was considered FFI-safe. However, this was the wrong approach - it didn't check that the `()` was part of a transparent newtype! The consequence of this is that the presence of a `()` type in a more complex return type would make it the entire type be considered safe (as long as the `()` type was the first that the lint found) - which is obviously incorrect. Instead, this logic is removed, and a unit return type or a transparent wrapper around a unit is checked for directly for functions and fn-ptrs. Signed-off-by: David Wood (cherry picked from commit f53cef31f5ea41c9a5ab8e5335637a6873b9f0b5) --- compiler/rustc_lint/src/types.rs | 55 ++++++++++++++++--------- tests/ui/lint/lint-ctypes-113436.rs | 37 +++++++++++++++++ tests/ui/lint/lint-ctypes-113436.stderr | 43 +++++++++++++++++++ 3 files changed, 115 insertions(+), 20 deletions(-) create mode 100644 tests/ui/lint/lint-ctypes-113436.rs create mode 100644 tests/ui/lint/lint-ctypes-113436.stderr diff --git a/compiler/rustc_lint/src/types.rs b/compiler/rustc_lint/src/types.rs index 2509d493a4c3d..cabd7f4ad41f9 100644 --- a/compiler/rustc_lint/src/types.rs +++ b/compiler/rustc_lint/src/types.rs @@ -940,6 +940,30 @@ pub(crate) fn repr_nullable_ptr<'tcx>( } impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { + // Returns `true` if `ty` is a `()`, or a `repr(transparent)` type whose only non-ZST field + // is a generic substituted for `()` - in either case, the type is FFI-safe when used as a + // return type. + pub fn is_unit_or_equivalent(&self, ty: Ty<'tcx>) -> bool { + if ty.is_unit() { + return true; + } + + if let ty::Adt(def, substs) = ty.kind() && def.repr().transparent() { + return def.variants() + .iter() + .filter_map(|variant| transparent_newtype_field(self.cx.tcx, variant)) + .all(|field| { + let field_ty = field.ty(self.cx.tcx, substs); + !field_ty.has_opaque_types() && { + let field_ty = self.cx.tcx.normalize_erasing_regions(self.cx.param_env, field_ty); + self.is_unit_or_equivalent(field_ty) + } + }); + } + + false + } + /// Check if the type is array and emit an unsafe type lint. fn check_for_array_ty(&mut self, sp: Span, ty: Ty<'tcx>) -> bool { if let ty::Array(..) = ty.kind() { @@ -1217,25 +1241,19 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { } let sig = tcx.erase_late_bound_regions(sig); - if !sig.output().is_unit() { - let r = self.check_type_for_ffi(cache, sig.output()); - match r { - FfiSafe => {} - _ => { - return r; - } - } - } for arg in sig.inputs() { - let r = self.check_type_for_ffi(cache, *arg); - match r { + match self.check_type_for_ffi(cache, *arg) { FfiSafe => {} - _ => { - return r; - } + r => return r, } } - FfiSafe + + let ret_ty = sig.output(); + if self.is_unit_or_equivalent(ret_ty) { + return FfiSafe; + } + + self.check_type_for_ffi(cache, ret_ty) } ty::Foreign(..) => FfiSafe, @@ -1354,9 +1372,9 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { } // Don't report FFI errors for unit return types. This check exists here, and not in - // `check_foreign_fn` (where it would make more sense) so that normalization has definitely + // the caller (where it would make more sense) so that normalization has definitely // happened. - if is_return_type && ty.is_unit() { + if is_return_type && self.is_unit_or_equivalent(ty) { return; } @@ -1370,9 +1388,6 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { None, ); } - // If `ty` is a `repr(transparent)` newtype, and the non-zero-sized type is a generic - // argument, which after substitution, is `()`, then this branch can be hit. - FfiResult::FfiUnsafe { ty, .. } if is_return_type && ty.is_unit() => {} FfiResult::FfiUnsafe { ty, reason, help } => { self.emit_ffi_unsafe_type_lint(ty, sp, reason, help); } diff --git a/tests/ui/lint/lint-ctypes-113436.rs b/tests/ui/lint/lint-ctypes-113436.rs new file mode 100644 index 0000000000000..d1328af9924be --- /dev/null +++ b/tests/ui/lint/lint-ctypes-113436.rs @@ -0,0 +1,37 @@ +#![deny(improper_ctypes_definitions)] + +#[repr(C)] +pub struct Wrap(T); + +#[repr(transparent)] +pub struct TransparentWrap(T); + +pub extern "C" fn f() -> Wrap<()> { + //~^ ERROR `extern` fn uses type `()`, which is not FFI-safe + todo!() +} + +const _: extern "C" fn() -> Wrap<()> = f; +//~^ ERROR `extern` fn uses type `()`, which is not FFI-safe + +pub extern "C" fn ff() -> Wrap> { + //~^ ERROR `extern` fn uses type `()`, which is not FFI-safe + todo!() +} + +const _: extern "C" fn() -> Wrap> = ff; +//~^ ERROR `extern` fn uses type `()`, which is not FFI-safe + +pub extern "C" fn g() -> TransparentWrap<()> { + todo!() +} + +const _: extern "C" fn() -> TransparentWrap<()> = g; + +pub extern "C" fn gg() -> TransparentWrap> { + todo!() +} + +const _: extern "C" fn() -> TransparentWrap> = gg; + +fn main() {} diff --git a/tests/ui/lint/lint-ctypes-113436.stderr b/tests/ui/lint/lint-ctypes-113436.stderr new file mode 100644 index 0000000000000..72f92c1a49c1d --- /dev/null +++ b/tests/ui/lint/lint-ctypes-113436.stderr @@ -0,0 +1,43 @@ +error: `extern` fn uses type `()`, which is not FFI-safe + --> $DIR/lint-ctypes-113436.rs:9:26 + | +LL | pub extern "C" fn f() -> Wrap<()> { + | ^^^^^^^^ not FFI-safe + | + = help: consider using a struct instead + = note: tuples have unspecified layout +note: the lint level is defined here + --> $DIR/lint-ctypes-113436.rs:1:9 + | +LL | #![deny(improper_ctypes_definitions)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: `extern` fn uses type `()`, which is not FFI-safe + --> $DIR/lint-ctypes-113436.rs:14:10 + | +LL | const _: extern "C" fn() -> Wrap<()> = f; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe + | + = help: consider using a struct instead + = note: tuples have unspecified layout + +error: `extern` fn uses type `()`, which is not FFI-safe + --> $DIR/lint-ctypes-113436.rs:17:27 + | +LL | pub extern "C" fn ff() -> Wrap> { + | ^^^^^^^^^^^^^^ not FFI-safe + | + = help: consider using a struct instead + = note: tuples have unspecified layout + +error: `extern` fn uses type `()`, which is not FFI-safe + --> $DIR/lint-ctypes-113436.rs:22:10 + | +LL | const _: extern "C" fn() -> Wrap> = ff; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe + | + = help: consider using a struct instead + = note: tuples have unspecified layout + +error: aborting due to 4 previous errors + From e9cd65033115298611f92982859d88a28ac3419d Mon Sep 17 00:00:00 2001 From: David Wood Date: Fri, 7 Jul 2023 19:18:28 +0100 Subject: [PATCH 05/17] lint: refactor `check_variant_for_ffi` Simplify this function a bit, it was quite hard to reason about. Signed-off-by: David Wood (cherry picked from commit 99b1897cf640d5f6dac74416761c9b3c75e1ef7a) --- compiler/rustc_lint/messages.ftl | 2 - compiler/rustc_lint/src/types.rs | 47 +++++++++---------- tests/ui/repr/repr-transparent-issue-87496.rs | 2 +- .../repr/repr-transparent-issue-87496.stderr | 10 ++-- 4 files changed, 26 insertions(+), 35 deletions(-) diff --git a/compiler/rustc_lint/messages.ftl b/compiler/rustc_lint/messages.ftl index a3453cbc0264b..22e22c833acbe 100644 --- a/compiler/rustc_lint/messages.ftl +++ b/compiler/rustc_lint/messages.ftl @@ -262,8 +262,6 @@ lint_improper_ctypes_char_help = consider using `u32` or `libc::wchar_t` instead lint_improper_ctypes_char_reason = the `char` type has no C equivalent lint_improper_ctypes_dyn = trait objects have no C equivalent -lint_improper_ctypes_enum_phantomdata = this enum contains a PhantomData field - lint_improper_ctypes_enum_repr_help = consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum diff --git a/compiler/rustc_lint/src/types.rs b/compiler/rustc_lint/src/types.rs index cabd7f4ad41f9..327e226a9f19a 100644 --- a/compiler/rustc_lint/src/types.rs +++ b/compiler/rustc_lint/src/types.rs @@ -1006,39 +1006,36 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { ) -> FfiResult<'tcx> { use FfiResult::*; - let transparent_safety = def.repr().transparent().then(|| { - // Can assume that at most one field is not a ZST, so only check - // that field's type for FFI-safety. + let transparent_with_all_zst_fields = if def.repr().transparent() { + // Transparent newtypes have at most one non-ZST field which needs to be checked.. if let Some(field) = transparent_newtype_field(self.cx.tcx, variant) { return self.check_field_type_for_ffi(cache, field, substs); - } else { - // All fields are ZSTs; this means that the type should behave - // like (), which is FFI-unsafe... except if all fields are PhantomData, - // which is tested for below - FfiUnsafe { ty, reason: fluent::lint_improper_ctypes_struct_zst, help: None } } - }); - // We can't completely trust repr(C) markings; make sure the fields are - // actually safe. + + // ..or have only ZST fields, which is FFI-unsafe (unless those fields are all + // `PhantomData`). + true + } else { + false + }; + + // We can't completely trust `repr(C)` markings, so make sure the fields are actually safe. let mut all_phantom = !variant.fields.is_empty(); for field in &variant.fields { - match self.check_field_type_for_ffi(cache, &field, substs) { - FfiSafe => { - all_phantom = false; - } - FfiPhantom(..) if !def.repr().transparent() && def.is_enum() => { - return FfiUnsafe { - ty, - reason: fluent::lint_improper_ctypes_enum_phantomdata, - help: None, - }; - } - FfiPhantom(..) => {} - r => return transparent_safety.unwrap_or(r), + all_phantom &= match self.check_field_type_for_ffi(cache, &field, substs) { + FfiSafe => false, + FfiPhantom(..) => true, + r @ FfiUnsafe { .. } => return r, } } - if all_phantom { FfiPhantom(ty) } else { transparent_safety.unwrap_or(FfiSafe) } + if all_phantom { + FfiPhantom(ty) + } else if transparent_with_all_zst_fields { + FfiUnsafe { ty, reason: fluent::lint_improper_ctypes_struct_zst, help: None } + } else { + FfiSafe + } } /// Checks if the given type is "ffi-safe" (has a stable, well-defined diff --git a/tests/ui/repr/repr-transparent-issue-87496.rs b/tests/ui/repr/repr-transparent-issue-87496.rs index a4dd45c63f564..0ce6fb2c19f3c 100644 --- a/tests/ui/repr/repr-transparent-issue-87496.rs +++ b/tests/ui/repr/repr-transparent-issue-87496.rs @@ -6,7 +6,7 @@ struct TransparentCustomZst(()); extern "C" { fn good17(p: TransparentCustomZst); - //~^ WARNING: `extern` block uses type `TransparentCustomZst`, which is not FFI-safe + //~^ WARNING: `extern` block uses type `()`, which is not FFI-safe } fn main() {} diff --git a/tests/ui/repr/repr-transparent-issue-87496.stderr b/tests/ui/repr/repr-transparent-issue-87496.stderr index aee31212b4ed2..03c62f8514e12 100644 --- a/tests/ui/repr/repr-transparent-issue-87496.stderr +++ b/tests/ui/repr/repr-transparent-issue-87496.stderr @@ -1,15 +1,11 @@ -warning: `extern` block uses type `TransparentCustomZst`, which is not FFI-safe +warning: `extern` block uses type `()`, which is not FFI-safe --> $DIR/repr-transparent-issue-87496.rs:8:18 | LL | fn good17(p: TransparentCustomZst); | ^^^^^^^^^^^^^^^^^^^^ not FFI-safe | - = note: this struct contains only zero-sized fields -note: the type is defined here - --> $DIR/repr-transparent-issue-87496.rs:6:1 - | -LL | struct TransparentCustomZst(()); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ + = help: consider using a struct instead + = note: tuples have unspecified layout = note: `#[warn(improper_ctypes)]` on by default warning: 1 warning emitted From 91e377c286933d561211a347d504c9c14c8ca8d2 Mon Sep 17 00:00:00 2001 From: David Wood Date: Wed, 19 Jul 2023 09:42:11 +0100 Subject: [PATCH 06/17] lint/ctypes: allow `()` within types Consider `()` within types to be FFI-safe, and `()` to be FFI-safe as a return type (incl. when in a transparent newtype). Signed-off-by: David Wood (cherry picked from commit 24f90fdd2654e9c5437a684d3a72a4e70826a985) --- compiler/rustc_lint/src/types.rs | 47 ++++++------------- tests/ui/lint/lint-ctypes-113436-1.rs | 28 +++++++++++ tests/ui/lint/lint-ctypes-113436-1.stderr | 35 ++++++++++++++ tests/ui/lint/lint-ctypes-113436.rs | 5 +- tests/ui/lint/lint-ctypes-113436.stderr | 43 ----------------- tests/ui/repr/repr-transparent-issue-87496.rs | 2 +- .../repr/repr-transparent-issue-87496.stderr | 10 ++-- 7 files changed, 87 insertions(+), 83 deletions(-) create mode 100644 tests/ui/lint/lint-ctypes-113436-1.rs create mode 100644 tests/ui/lint/lint-ctypes-113436-1.stderr delete mode 100644 tests/ui/lint/lint-ctypes-113436.stderr diff --git a/compiler/rustc_lint/src/types.rs b/compiler/rustc_lint/src/types.rs index 327e226a9f19a..99430794668d9 100644 --- a/compiler/rustc_lint/src/types.rs +++ b/compiler/rustc_lint/src/types.rs @@ -940,30 +940,6 @@ pub(crate) fn repr_nullable_ptr<'tcx>( } impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { - // Returns `true` if `ty` is a `()`, or a `repr(transparent)` type whose only non-ZST field - // is a generic substituted for `()` - in either case, the type is FFI-safe when used as a - // return type. - pub fn is_unit_or_equivalent(&self, ty: Ty<'tcx>) -> bool { - if ty.is_unit() { - return true; - } - - if let ty::Adt(def, substs) = ty.kind() && def.repr().transparent() { - return def.variants() - .iter() - .filter_map(|variant| transparent_newtype_field(self.cx.tcx, variant)) - .all(|field| { - let field_ty = field.ty(self.cx.tcx, substs); - !field_ty.has_opaque_types() && { - let field_ty = self.cx.tcx.normalize_erasing_regions(self.cx.param_env, field_ty); - self.is_unit_or_equivalent(field_ty) - } - }); - } - - false - } - /// Check if the type is array and emit an unsafe type lint. fn check_for_array_ty(&mut self, sp: Span, ty: Ty<'tcx>) -> bool { if let ty::Array(..) = ty.kind() { @@ -1007,14 +983,19 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { use FfiResult::*; let transparent_with_all_zst_fields = if def.repr().transparent() { - // Transparent newtypes have at most one non-ZST field which needs to be checked.. if let Some(field) = transparent_newtype_field(self.cx.tcx, variant) { - return self.check_field_type_for_ffi(cache, field, substs); - } + // Transparent newtypes have at most one non-ZST field which needs to be checked.. + match self.check_field_type_for_ffi(cache, field, substs) { + FfiUnsafe { ty, .. } if ty.is_unit() => (), + r => return r, + } - // ..or have only ZST fields, which is FFI-unsafe (unless those fields are all - // `PhantomData`). - true + false + } else { + // ..or have only ZST fields, which is FFI-unsafe (unless those fields are all + // `PhantomData`). + true + } } else { false }; @@ -1024,6 +1005,8 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { for field in &variant.fields { all_phantom &= match self.check_field_type_for_ffi(cache, &field, substs) { FfiSafe => false, + // `()` fields are FFI-safe! + FfiUnsafe { ty, .. } if ty.is_unit() => false, FfiPhantom(..) => true, r @ FfiUnsafe { .. } => return r, } @@ -1246,7 +1229,7 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { } let ret_ty = sig.output(); - if self.is_unit_or_equivalent(ret_ty) { + if ret_ty.is_unit() { return FfiSafe; } @@ -1371,7 +1354,7 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { // Don't report FFI errors for unit return types. This check exists here, and not in // the caller (where it would make more sense) so that normalization has definitely // happened. - if is_return_type && self.is_unit_or_equivalent(ty) { + if is_return_type && ty.is_unit() { return; } diff --git a/tests/ui/lint/lint-ctypes-113436-1.rs b/tests/ui/lint/lint-ctypes-113436-1.rs new file mode 100644 index 0000000000000..1ca59c6868d6d --- /dev/null +++ b/tests/ui/lint/lint-ctypes-113436-1.rs @@ -0,0 +1,28 @@ +#![deny(improper_ctypes_definitions)] + +#[repr(C)] +pub struct Foo { + a: u8, + b: (), +} + +extern "C" fn foo(x: Foo) -> Foo { + todo!() +} + +struct NotSafe(u32); + +#[repr(C)] +pub struct Bar { + a: u8, + b: (), + c: NotSafe, +} + +extern "C" fn bar(x: Bar) -> Bar { + //~^ ERROR `extern` fn uses type `NotSafe`, which is not FFI-safe + //~^^ ERROR `extern` fn uses type `NotSafe`, which is not FFI-safe + todo!() +} + +fn main() {} diff --git a/tests/ui/lint/lint-ctypes-113436-1.stderr b/tests/ui/lint/lint-ctypes-113436-1.stderr new file mode 100644 index 0000000000000..7b63043f05756 --- /dev/null +++ b/tests/ui/lint/lint-ctypes-113436-1.stderr @@ -0,0 +1,35 @@ +error: `extern` fn uses type `NotSafe`, which is not FFI-safe + --> $DIR/lint-ctypes-113436-1.rs:22:22 + | +LL | extern "C" fn bar(x: Bar) -> Bar { + | ^^^ not FFI-safe + | + = help: consider adding a `#[repr(C)]` or `#[repr(transparent)]` attribute to this struct + = note: this struct has unspecified layout +note: the type is defined here + --> $DIR/lint-ctypes-113436-1.rs:13:1 + | +LL | struct NotSafe(u32); + | ^^^^^^^^^^^^^^ +note: the lint level is defined here + --> $DIR/lint-ctypes-113436-1.rs:1:9 + | +LL | #![deny(improper_ctypes_definitions)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: `extern` fn uses type `NotSafe`, which is not FFI-safe + --> $DIR/lint-ctypes-113436-1.rs:22:30 + | +LL | extern "C" fn bar(x: Bar) -> Bar { + | ^^^ not FFI-safe + | + = help: consider adding a `#[repr(C)]` or `#[repr(transparent)]` attribute to this struct + = note: this struct has unspecified layout +note: the type is defined here + --> $DIR/lint-ctypes-113436-1.rs:13:1 + | +LL | struct NotSafe(u32); + | ^^^^^^^^^^^^^^ + +error: aborting due to 2 previous errors + diff --git a/tests/ui/lint/lint-ctypes-113436.rs b/tests/ui/lint/lint-ctypes-113436.rs index d1328af9924be..4f733b5bb16f2 100644 --- a/tests/ui/lint/lint-ctypes-113436.rs +++ b/tests/ui/lint/lint-ctypes-113436.rs @@ -1,3 +1,4 @@ +// check-pass #![deny(improper_ctypes_definitions)] #[repr(C)] @@ -7,20 +8,16 @@ pub struct Wrap(T); pub struct TransparentWrap(T); pub extern "C" fn f() -> Wrap<()> { - //~^ ERROR `extern` fn uses type `()`, which is not FFI-safe todo!() } const _: extern "C" fn() -> Wrap<()> = f; -//~^ ERROR `extern` fn uses type `()`, which is not FFI-safe pub extern "C" fn ff() -> Wrap> { - //~^ ERROR `extern` fn uses type `()`, which is not FFI-safe todo!() } const _: extern "C" fn() -> Wrap> = ff; -//~^ ERROR `extern` fn uses type `()`, which is not FFI-safe pub extern "C" fn g() -> TransparentWrap<()> { todo!() diff --git a/tests/ui/lint/lint-ctypes-113436.stderr b/tests/ui/lint/lint-ctypes-113436.stderr deleted file mode 100644 index 72f92c1a49c1d..0000000000000 --- a/tests/ui/lint/lint-ctypes-113436.stderr +++ /dev/null @@ -1,43 +0,0 @@ -error: `extern` fn uses type `()`, which is not FFI-safe - --> $DIR/lint-ctypes-113436.rs:9:26 - | -LL | pub extern "C" fn f() -> Wrap<()> { - | ^^^^^^^^ not FFI-safe - | - = help: consider using a struct instead - = note: tuples have unspecified layout -note: the lint level is defined here - --> $DIR/lint-ctypes-113436.rs:1:9 - | -LL | #![deny(improper_ctypes_definitions)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -error: `extern` fn uses type `()`, which is not FFI-safe - --> $DIR/lint-ctypes-113436.rs:14:10 - | -LL | const _: extern "C" fn() -> Wrap<()> = f; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe - | - = help: consider using a struct instead - = note: tuples have unspecified layout - -error: `extern` fn uses type `()`, which is not FFI-safe - --> $DIR/lint-ctypes-113436.rs:17:27 - | -LL | pub extern "C" fn ff() -> Wrap> { - | ^^^^^^^^^^^^^^ not FFI-safe - | - = help: consider using a struct instead - = note: tuples have unspecified layout - -error: `extern` fn uses type `()`, which is not FFI-safe - --> $DIR/lint-ctypes-113436.rs:22:10 - | -LL | const _: extern "C" fn() -> Wrap> = ff; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe - | - = help: consider using a struct instead - = note: tuples have unspecified layout - -error: aborting due to 4 previous errors - diff --git a/tests/ui/repr/repr-transparent-issue-87496.rs b/tests/ui/repr/repr-transparent-issue-87496.rs index 0ce6fb2c19f3c..a4dd45c63f564 100644 --- a/tests/ui/repr/repr-transparent-issue-87496.rs +++ b/tests/ui/repr/repr-transparent-issue-87496.rs @@ -6,7 +6,7 @@ struct TransparentCustomZst(()); extern "C" { fn good17(p: TransparentCustomZst); - //~^ WARNING: `extern` block uses type `()`, which is not FFI-safe + //~^ WARNING: `extern` block uses type `TransparentCustomZst`, which is not FFI-safe } fn main() {} diff --git a/tests/ui/repr/repr-transparent-issue-87496.stderr b/tests/ui/repr/repr-transparent-issue-87496.stderr index 03c62f8514e12..aee31212b4ed2 100644 --- a/tests/ui/repr/repr-transparent-issue-87496.stderr +++ b/tests/ui/repr/repr-transparent-issue-87496.stderr @@ -1,11 +1,15 @@ -warning: `extern` block uses type `()`, which is not FFI-safe +warning: `extern` block uses type `TransparentCustomZst`, which is not FFI-safe --> $DIR/repr-transparent-issue-87496.rs:8:18 | LL | fn good17(p: TransparentCustomZst); | ^^^^^^^^^^^^^^^^^^^^ not FFI-safe | - = help: consider using a struct instead - = note: tuples have unspecified layout + = note: this struct contains only zero-sized fields +note: the type is defined here + --> $DIR/repr-transparent-issue-87496.rs:6:1 + | +LL | struct TransparentCustomZst(()); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ = note: `#[warn(improper_ctypes)]` on by default warning: 1 warning emitted From 64b4a54227e9186cd35fe15980699414b3b9523f Mon Sep 17 00:00:00 2001 From: ekusiadadus Date: Wed, 12 Jul 2023 00:54:27 +0900 Subject: [PATCH 07/17] Revert "fix: :bug: etc/bash_complettion -> src/etc/... to avoid copy error" This reverts commit 08ce68b6a6bad360e9c3611ad60cf6598401f878. (cherry picked from commit 05bc71cfaf9eb35caab425126d4fa8dcb8c62072) --- src/bootstrap/dist.rs | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/src/bootstrap/dist.rs b/src/bootstrap/dist.rs index 4522819f996e8..b34a4b2dc63ba 100644 --- a/src/bootstrap/dist.rs +++ b/src/bootstrap/dist.rs @@ -1074,11 +1074,7 @@ impl Step for Cargo { tarball.add_file(&cargo, "bin", 0o755); tarball.add_file(etc.join("_cargo"), "share/zsh/site-functions", 0o644); - tarball.add_renamed_file( - etc.join("cargo.bashcomp.sh"), - "src/etc/bash_completion.d", - "cargo", - ); + tarball.add_renamed_file(etc.join("cargo.bashcomp.sh"), "etc/bash_completion.d", "cargo"); tarball.add_dir(etc.join("man"), "share/man/man1"); tarball.add_legal_and_readme_to("share/doc/cargo"); From 33322e06da679835f48a01e775a4329a1843453f Mon Sep 17 00:00:00 2001 From: Camille GILLOT Date: Mon, 17 Jul 2023 18:55:07 +0000 Subject: [PATCH 08/17] Substitute types before checking compatibility. (cherry picked from commit 45ffe41d144e3e5bc8993abcbcdd54d870a2ff53) --- compiler/rustc_mir_transform/src/inline.rs | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/compiler/rustc_mir_transform/src/inline.rs b/compiler/rustc_mir_transform/src/inline.rs index 240beabfc1a98..b6578cb259ac0 100644 --- a/compiler/rustc_mir_transform/src/inline.rs +++ b/compiler/rustc_mir_transform/src/inline.rs @@ -440,6 +440,10 @@ impl<'tcx> Inliner<'tcx> { validation: Ok(()), }; + for var_debug_info in callee_body.var_debug_info.iter() { + checker.visit_var_debug_info(var_debug_info); + } + // Traverse the MIR manually so we can account for the effects of inlining on the CFG. let mut work_list = vec![START_BLOCK]; let mut visited = BitSet::new_empty(callee_body.basic_blocks.len()); @@ -847,7 +851,16 @@ impl<'tcx> Visitor<'tcx> for CostChecker<'_, 'tcx> { if let ProjectionElem::Field(f, ty) = elem { let parent_ty = place_ref.ty(&self.callee_body.local_decls, self.tcx); let check_equal = |this: &mut Self, f_ty| { - if !util::is_equal_up_to_subtyping(this.tcx, this.param_env, ty, f_ty) { + // Fast path if there is nothing to substitute. + if ty == f_ty { + return; + } + let ty = this.instance.subst_mir(this.tcx, ty::EarlyBinder::bind(&ty)); + let f_ty = this.instance.subst_mir(this.tcx, ty::EarlyBinder::bind(&f_ty)); + if ty == f_ty { + return; + } + if !util::is_subtype(this.tcx, this.param_env, ty, f_ty) { trace!(?ty, ?f_ty); this.validation = Err("failed to normalize projection type"); return; From fc3ed7c2980b3f1181c1872a49be90df66ec4abf Mon Sep 17 00:00:00 2001 From: Ibraheem Ahmed Date: Wed, 19 Jul 2023 11:50:29 -0400 Subject: [PATCH 09/17] avoid tls access while iterating through mpsc thread entries (cherry picked from commit fb31a1ac21833b205196128b7425f5c587cd883c) --- library/std/src/sync/mpmc/waker.rs | 46 +++++++++++++++++------------- 1 file changed, 26 insertions(+), 20 deletions(-) diff --git a/library/std/src/sync/mpmc/waker.rs b/library/std/src/sync/mpmc/waker.rs index 4912ca4f8150b..9aab1b9417edb 100644 --- a/library/std/src/sync/mpmc/waker.rs +++ b/library/std/src/sync/mpmc/waker.rs @@ -66,26 +66,32 @@ impl Waker { /// Attempts to find another thread's entry, select the operation, and wake it up. #[inline] pub(crate) fn try_select(&mut self) -> Option { - self.selectors - .iter() - .position(|selector| { - // Does the entry belong to a different thread? - selector.cx.thread_id() != current_thread_id() - && selector // Try selecting this operation. - .cx - .try_select(Selected::Operation(selector.oper)) - .is_ok() - && { - // Provide the packet. - selector.cx.store_packet(selector.packet); - // Wake the thread up. - selector.cx.unpark(); - true - } - }) - // Remove the entry from the queue to keep it clean and improve - // performance. - .map(|pos| self.selectors.remove(pos)) + if self.selectors.is_empty() { + None + } else { + let thread_id = current_thread_id(); + + self.selectors + .iter() + .position(|selector| { + // Does the entry belong to a different thread? + selector.cx.thread_id() != thread_id + && selector // Try selecting this operation. + .cx + .try_select(Selected::Operation(selector.oper)) + .is_ok() + && { + // Provide the packet. + selector.cx.store_packet(selector.packet); + // Wake the thread up. + selector.cx.unpark(); + true + } + }) + // Remove the entry from the queue to keep it clean and improve + // performance. + .map(|pos| self.selectors.remove(pos)) + } } /// Notifies all operations waiting to be ready. From 0426c1f1d5cc7ed7e9fb4b2918b157def17f8477 Mon Sep 17 00:00:00 2001 From: David Wood Date: Fri, 21 Jul 2023 15:42:25 +0100 Subject: [PATCH 10/17] lint/ctypes: only try normalize Now that this lint runs on any external-ABI fn-ptr, normalization won't always succeed, so use `try_normalize_erasing_regions` instead. Signed-off-by: David Wood (cherry picked from commit 09434a2575cee12b241c516ad91f21d4b4f9c3fd) --- compiler/rustc_lint/src/types.rs | 21 +++++++++------------ tests/ui/lint/lint-ctypes-113900.rs | 12 ++++++++++++ 2 files changed, 21 insertions(+), 12 deletions(-) create mode 100644 tests/ui/lint/lint-ctypes-113900.rs diff --git a/compiler/rustc_lint/src/types.rs b/compiler/rustc_lint/src/types.rs index 99430794668d9..ed4fb98605c8d 100644 --- a/compiler/rustc_lint/src/types.rs +++ b/compiler/rustc_lint/src/types.rs @@ -963,12 +963,12 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { substs: SubstsRef<'tcx>, ) -> FfiResult<'tcx> { let field_ty = field.ty(self.cx.tcx, substs); - if field_ty.has_opaque_types() { - self.check_type_for_ffi(cache, field_ty) - } else { - let field_ty = self.cx.tcx.normalize_erasing_regions(self.cx.param_env, field_ty); - self.check_type_for_ffi(cache, field_ty) - } + let field_ty = self + .cx + .tcx + .try_normalize_erasing_regions(self.cx.param_env, field_ty) + .unwrap_or(field_ty); + self.check_type_for_ffi(cache, field_ty) } /// Checks if the given `VariantDef`'s field types are "ffi-safe". @@ -1315,7 +1315,8 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { if let Some(ty) = self .cx .tcx - .normalize_erasing_regions(self.cx.param_env, ty) + .try_normalize_erasing_regions(self.cx.param_env, ty) + .unwrap_or(ty) .visit_with(&mut ProhibitOpaqueTypes) .break_value() { @@ -1333,16 +1334,12 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> { is_static: bool, is_return_type: bool, ) { - // We have to check for opaque types before `normalize_erasing_regions`, - // which will replace opaque types with their underlying concrete type. if self.check_for_opaque_ty(sp, ty) { // We've already emitted an error due to an opaque type. return; } - // it is only OK to use this function because extern fns cannot have - // any generic types right now: - let ty = self.cx.tcx.normalize_erasing_regions(self.cx.param_env, ty); + let ty = self.cx.tcx.try_normalize_erasing_regions(self.cx.param_env, ty).unwrap_or(ty); // C doesn't really support passing arrays by value - the only way to pass an array by value // is through a struct. So, first test that the top level isn't an array, and then diff --git a/tests/ui/lint/lint-ctypes-113900.rs b/tests/ui/lint/lint-ctypes-113900.rs new file mode 100644 index 0000000000000..ac4ff1ae2dfd0 --- /dev/null +++ b/tests/ui/lint/lint-ctypes-113900.rs @@ -0,0 +1,12 @@ +// check-pass + +// Extending `improper_ctypes` to check external-ABI fn-ptrs means that it can encounter +// projections which cannot be normalized - unsurprisingly, this shouldn't crash the compiler. + +trait Bar { + type Assoc; +} + +type Foo = extern "C" fn() -> ::Assoc; + +fn main() {} From a3d2871102eadf1e8e1486365c2923eb7e6a54f9 Mon Sep 17 00:00:00 2001 From: Ariadne Conill Date: Thu, 3 Aug 2023 15:05:40 -0700 Subject: [PATCH 11/17] bootstrap: config: fix version comparison bug Rust requires a previous version of Rust to build, such as the current version, or the previous version. However, the version comparison logic did not take patch releases into consideration when doing the version comparison for the current branch, e.g. Rust 1.71.1 could not be built by Rust 1.71.0 because it is neither an exact version match, or the previous version. Adjust the version comparison logic to tolerate mismatches in the patch version. Signed-off-by: Ariadne Conill (cherry picked from commit 31a81a08786826cc6e832bd0b49fb8b934e29648) --- src/bootstrap/config.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/bootstrap/config.rs b/src/bootstrap/config.rs index 5f5f7ea25fb95..fe932fd6bd30b 100644 --- a/src/bootstrap/config.rs +++ b/src/bootstrap/config.rs @@ -1925,7 +1925,8 @@ impl Config { .unwrap(); if !(source_version == rustc_version || (source_version.major == rustc_version.major - && source_version.minor == rustc_version.minor + 1)) + && (source_version.minor == rustc_version.minor + || source_version.minor == rustc_version.minor + 1))) { let prev_version = format!("{}.{}.x", source_version.major, source_version.minor - 1); eprintln!( From 8f4613ea7715cd1646d1632cc748fa6015b4f29c Mon Sep 17 00:00:00 2001 From: "Felix S. Klock II" Date: Fri, 21 Jul 2023 09:41:07 -0400 Subject: [PATCH 12/17] special-case proc-macro crates in rustc_codegen_ssa::back::linker::exported_symbols to only export the two symbols that proc-macros need. (cherry picked from commit 3000c24afc37fe09c65772a71331002a7505dc11) --- compiler/rustc_codegen_ssa/src/back/linker.rs | 32 +++++++++++++++++-- 1 file changed, 29 insertions(+), 3 deletions(-) diff --git a/compiler/rustc_codegen_ssa/src/back/linker.rs b/compiler/rustc_codegen_ssa/src/back/linker.rs index cd56f85cccdea..f622ed32c38c8 100644 --- a/compiler/rustc_codegen_ssa/src/back/linker.rs +++ b/compiler/rustc_codegen_ssa/src/back/linker.rs @@ -13,6 +13,7 @@ use std::{env, mem, str}; use rustc_hir::def_id::{CrateNum, LOCAL_CRATE}; use rustc_metadata::find_native_static_library; use rustc_middle::middle::dependency_format::Linkage; +use rustc_middle::middle::exported_symbols; use rustc_middle::middle::exported_symbols::{ExportedSymbol, SymbolExportInfo, SymbolExportKind}; use rustc_middle::ty::TyCtxt; use rustc_session::config::{self, CrateType, DebugInfo, LinkerPluginLto, Lto, OptLevel, Strip}; @@ -659,8 +660,6 @@ impl<'a> Linker for GccLinker<'a> { return; } - // FIXME(#99978) hide #[no_mangle] symbols for proc-macros - let is_windows = self.sess.target.is_like_windows; let path = tmpdir.join(if is_windows { "list.def" } else { "list" }); @@ -1679,8 +1678,15 @@ pub(crate) fn exported_symbols(tcx: TyCtxt<'_>, crate_type: CrateType) -> Vec, crate_type: CrateType) -> Vec { + let mut symbols = Vec::new(); let export_threshold = symbol_export::crates_export_threshold(&[crate_type]); for_each_exported_symbols_include_dep(tcx, crate_type, |symbol, info, cnum| { if info.level.is_below_threshold(export_threshold) { @@ -1691,6 +1697,26 @@ pub(crate) fn exported_symbols(tcx: TyCtxt<'_>, crate_type: CrateType) -> Vec) -> Vec { + let mut symbols = Vec::new(); + + let stable_crate_id = tcx.sess.local_stable_crate_id(); + let proc_macro_decls_name = tcx.sess.generate_proc_macro_decls_symbol(stable_crate_id); + let metadata_symbol_name = exported_symbols::metadata_symbol_name(tcx); + + // You would think that both the two names would always be there, but in + // pnkfelix's local experiments that was not case. So instead we walk the + // list and only add them if they *are* there. + for_each_exported_symbols_include_dep(tcx, CrateType::ProcMacro, |symbol, _info, cnum| { + let name = symbol_export::symbol_name_for_instance_in_crate(tcx, symbol, cnum); + if name == proc_macro_decls_name || name == metadata_symbol_name { + symbols.push(name); + } + }); + + return symbols; +} + pub(crate) fn linked_symbols( tcx: TyCtxt<'_>, crate_type: CrateType, From 6afdab5c6885ab87b3c077a8ea35207bfa1d063e Mon Sep 17 00:00:00 2001 From: "Felix S. Klock II" Date: Fri, 4 Aug 2023 11:29:41 -0400 Subject: [PATCH 13/17] regression test for issue 111888. (cherry picked from commit 7a0e2ee133dacf4e2dbda64a316a95746a469c58) --- .../proc-macro/auxiliary/exports_no_mangle.rs | 9 +++++++++ .../no-mangle-in-proc-macro-issue-111888.rs | 20 +++++++++++++++++++ 2 files changed, 29 insertions(+) create mode 100644 tests/ui/proc-macro/auxiliary/exports_no_mangle.rs create mode 100644 tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs diff --git a/tests/ui/proc-macro/auxiliary/exports_no_mangle.rs b/tests/ui/proc-macro/auxiliary/exports_no_mangle.rs new file mode 100644 index 0000000000000..ef5bf94b0358c --- /dev/null +++ b/tests/ui/proc-macro/auxiliary/exports_no_mangle.rs @@ -0,0 +1,9 @@ +#![crate_type="lib"] + +// Issue 111888: this crate (1.) is imported by a proc-macro crate and (2.) +// exports a no_mangle function; that combination of acts was broken for some +// period of time. See further discussion in the test file that imports this +// crate. + +#[no_mangle] +pub fn some_no_mangle_function() { } diff --git a/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs b/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs new file mode 100644 index 0000000000000..087c9a2f0652a --- /dev/null +++ b/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs @@ -0,0 +1,20 @@ +// run-pass +// aux-build:exports_no_mangle.rs +#![crate_type = "proc-macro"] + +// Issue #111888: this proc-macro crate imports another crate that itself +// exports a no_mangle function. +// +// That combination was broken for a period of time, because: +// +// In PR #99944 we *stopped* exporting no_mangle symbols from +// proc-macro crates. The constructed linker version script still referred +// to them, but resolving that discrepancy was left as a FIXME in the code. +// +// In PR #108017 we started telling the linker to check (via the +// `--no-undefined-version` linker invocation flag) that every symbol referenced +// in the "linker version script" is actually present in the linker input. So +// the unresolved discrepancy from #99944 started surfacing as a compile-time +// error. + +extern crate exports_no_mangle; From fecb6b277c99f250654fa2cff204df2e773ade08 Mon Sep 17 00:00:00 2001 From: Felix S Klock II Date: Fri, 4 Aug 2023 12:11:34 -0400 Subject: [PATCH 14/17] Update tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs fix to test as proposed by wesleywiser Co-authored-by: Wesley Wiser (cherry picked from commit 5881e5f88d9245ef9259ca600b32af80d5972a7f) --- tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs b/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs index 087c9a2f0652a..de2ca496cafba 100644 --- a/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs +++ b/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs @@ -1,4 +1,4 @@ -// run-pass +// build-pass // aux-build:exports_no_mangle.rs #![crate_type = "proc-macro"] From a94c607997d4b4389c53b5198e4fe5f3f0a093ed Mon Sep 17 00:00:00 2001 From: "Felix S. Klock II" Date: Mon, 7 Aug 2023 13:31:14 -0400 Subject: [PATCH 15/17] Review feedback: return empty iff !should_codegen, and use simpler unconditional logic otherwise. (cherry picked from commit a2058ddbed82adda55ce39f0e0915996706cb2b9) --- compiler/rustc_codegen_ssa/src/back/linker.rs | 17 +++++------------ 1 file changed, 5 insertions(+), 12 deletions(-) diff --git a/compiler/rustc_codegen_ssa/src/back/linker.rs b/compiler/rustc_codegen_ssa/src/back/linker.rs index f622ed32c38c8..8ac86fa4b26b2 100644 --- a/compiler/rustc_codegen_ssa/src/back/linker.rs +++ b/compiler/rustc_codegen_ssa/src/back/linker.rs @@ -1698,23 +1698,16 @@ fn exported_symbols_for_non_proc_macro(tcx: TyCtxt<'_>, crate_type: CrateType) - } fn exported_symbols_for_proc_macro_crate(tcx: TyCtxt<'_>) -> Vec { - let mut symbols = Vec::new(); + // `exported_symbols` will be empty when !should_codegen. + if !tcx.sess.opts.output_types.should_codegen() { + return Vec::new(); + } let stable_crate_id = tcx.sess.local_stable_crate_id(); let proc_macro_decls_name = tcx.sess.generate_proc_macro_decls_symbol(stable_crate_id); let metadata_symbol_name = exported_symbols::metadata_symbol_name(tcx); - // You would think that both the two names would always be there, but in - // pnkfelix's local experiments that was not case. So instead we walk the - // list and only add them if they *are* there. - for_each_exported_symbols_include_dep(tcx, CrateType::ProcMacro, |symbol, _info, cnum| { - let name = symbol_export::symbol_name_for_instance_in_crate(tcx, symbol, cnum); - if name == proc_macro_decls_name || name == metadata_symbol_name { - symbols.push(name); - } - }); - - return symbols; + vec![proc_macro_decls_name, metadata_symbol_name] } pub(crate) fn linked_symbols( From bc3491f99e204b8ff881666661773e786b72de00 Mon Sep 17 00:00:00 2001 From: "Felix S. Klock II" Date: Tue, 8 Aug 2023 11:40:35 -0400 Subject: [PATCH 16/17] fix proc-macro test added here to solely be exercised as a build product for the host. thus we should no longer see test failures for e.g. wasm32 target. (cherry picked from commit a2a7f27fd2548874b203f1f577f64cf61627e0a5) --- tests/ui/proc-macro/auxiliary/exports_no_mangle.rs | 2 ++ tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs | 2 ++ 2 files changed, 4 insertions(+) diff --git a/tests/ui/proc-macro/auxiliary/exports_no_mangle.rs b/tests/ui/proc-macro/auxiliary/exports_no_mangle.rs index ef5bf94b0358c..a8a478ffc74c4 100644 --- a/tests/ui/proc-macro/auxiliary/exports_no_mangle.rs +++ b/tests/ui/proc-macro/auxiliary/exports_no_mangle.rs @@ -1,3 +1,5 @@ +// force-host +// no-prefer-dynamic #![crate_type="lib"] // Issue 111888: this crate (1.) is imported by a proc-macro crate and (2.) diff --git a/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs b/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs index de2ca496cafba..4e5208e50580b 100644 --- a/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs +++ b/tests/ui/proc-macro/no-mangle-in-proc-macro-issue-111888.rs @@ -1,4 +1,6 @@ // build-pass +// force-host +// no-prefer-dynamic // aux-build:exports_no_mangle.rs #![crate_type = "proc-macro"] From 4d0501412a3216ee4a495e071f4b5fdf43f56c4e Mon Sep 17 00:00:00 2001 From: Eric Huss Date: Wed, 12 Jul 2023 06:59:57 -0700 Subject: [PATCH 17/17] Ignore flaky clippy tests. (cherry picked from commit fb5efd7008c698a821e9c50c3f3a04d48abd8295) --- src/tools/clippy/tests/ui/empty_line_after_doc_comments.rs | 3 +++ src/tools/clippy/tests/ui/empty_line_after_outer_attribute.rs | 3 +++ .../clippy/tests/ui/needless_arbitrary_self_type_unfixable.rs | 3 +++ 3 files changed, 9 insertions(+) diff --git a/src/tools/clippy/tests/ui/empty_line_after_doc_comments.rs b/src/tools/clippy/tests/ui/empty_line_after_doc_comments.rs index 83db2a07d334e..cc36ce5f48791 100644 --- a/src/tools/clippy/tests/ui/empty_line_after_doc_comments.rs +++ b/src/tools/clippy/tests/ui/empty_line_after_doc_comments.rs @@ -1,4 +1,7 @@ //@aux-build:proc_macro_attr.rs:proc-macro +// Flaky test, see https://github.com/rust-lang/rust/issues/113585. +//@ignore-32bit +//@ignore-64bit #![warn(clippy::empty_line_after_doc_comments)] #![allow(clippy::assertions_on_constants)] #![feature(custom_inner_attributes)] diff --git a/src/tools/clippy/tests/ui/empty_line_after_outer_attribute.rs b/src/tools/clippy/tests/ui/empty_line_after_outer_attribute.rs index b2d7ddae42746..bc54e0fd2de14 100644 --- a/src/tools/clippy/tests/ui/empty_line_after_outer_attribute.rs +++ b/src/tools/clippy/tests/ui/empty_line_after_outer_attribute.rs @@ -1,4 +1,7 @@ //@aux-build:proc_macro_attr.rs:proc-macro +// Flaky test, see https://github.com/rust-lang/rust/issues/113585. +//@ignore-32bit +//@ignore-64bit #![warn(clippy::empty_line_after_outer_attr)] #![allow(clippy::assertions_on_constants)] #![feature(custom_inner_attributes)] diff --git a/src/tools/clippy/tests/ui/needless_arbitrary_self_type_unfixable.rs b/src/tools/clippy/tests/ui/needless_arbitrary_self_type_unfixable.rs index 876f16a3854d9..321aa69a1a527 100644 --- a/src/tools/clippy/tests/ui/needless_arbitrary_self_type_unfixable.rs +++ b/src/tools/clippy/tests/ui/needless_arbitrary_self_type_unfixable.rs @@ -1,4 +1,7 @@ //@aux-build:proc_macro_attr.rs:proc-macro +// Flaky test, see https://github.com/rust-lang/rust/issues/113585. +//@ignore-32bit +//@ignore-64bit #![warn(clippy::needless_arbitrary_self_type)]