From 7e79dcdc06a2bbd4a1d3250b23dbfc024bf0a86f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Sat, 9 Mar 2024 20:02:47 +0000 Subject: [PATCH 01/17] Drive-by fix string fmt --- compiler/rustc_borrowck/src/diagnostics/mod.rs | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/compiler/rustc_borrowck/src/diagnostics/mod.rs b/compiler/rustc_borrowck/src/diagnostics/mod.rs index 560928d39414..4ebbe592628a 100644 --- a/compiler/rustc_borrowck/src/diagnostics/mod.rs +++ b/compiler/rustc_borrowck/src/diagnostics/mod.rs @@ -1226,20 +1226,20 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { { let msg = match &errors[..] { [] => "you can `clone` the value and consume it, but this \ - might not be your desired behavior" + might not be your desired behavior" .to_string(), [error] => { format!( - "you could `clone` the value and consume it, if \ - the `{}` trait bound could be satisfied", + "you could `clone` the value and consume it, if the \ + `{}` trait bound could be satisfied", error.obligation.predicate, ) } [errors @ .., last] => { format!( - "you could `clone` the value and consume it, if \ - the following trait bounds could be satisfied: {} \ - and `{}`", + "you could `clone` the value and consume it, if the \ + following trait bounds could be satisfied: \ + {} and `{}`", errors .iter() .map(|e| format!("`{}`", e.obligation.predicate)) From 2d3435b4df844bb0c25b86bb73519a3c867a92a0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Sat, 9 Mar 2024 20:18:43 +0000 Subject: [PATCH 02/17] Detect calls to `.clone()` on `T: !Clone` types on borrowck errors When encountering a lifetime error on a type that *holds* a type that doesn't implement `Clone`, explore the item's body for potential calls to `.clone()` that are only cloning the reference `&T` instead of `T` because `T: !Clone`. If we find this, suggest `T: Clone`. ``` error[E0502]: cannot borrow `*list` as mutable because it is also borrowed as immutable --> $DIR/clone-on-ref.rs:7:5 | LL | for v in list.iter() { | ---- immutable borrow occurs here LL | cloned_items.push(v.clone()) | ------- this call doesn't do anything, the result is still `&T` because `T` doesn't implement `Clone` LL | } LL | list.push(T::default()); | ^^^^^^^^^^^^^^^^^^^^^^^ mutable borrow occurs here LL | LL | drop(cloned_items); | ------------ immutable borrow later used here | help: consider further restricting this bound | LL | fn foo(list: &mut Vec) { | +++++++ ``` ``` error[E0505]: cannot move out of `x` because it is borrowed --> $DIR/clone-on-ref.rs:23:10 | LL | fn qux(x: A) { | - binding `x` declared here LL | let a = &x; | -- borrow of `x` occurs here LL | let b = a.clone(); | ------- this call doesn't do anything, the result is still `&A` because `A` doesn't implement `Clone` LL | drop(x); | ^ move out of `x` occurs here LL | LL | println!("{b:?}"); | ----- borrow later used here | help: consider annotating `A` with `#[derive(Clone)]` | LL + #[derive(Clone)] LL | struct A; | ``` --- .../src/diagnostics/conflict_errors.rs | 113 ++++++++++++++++-- tests/ui/borrowck/clone-on-ref.fixed | 32 +++++ tests/ui/borrowck/clone-on-ref.rs | 31 +++++ tests/ui/borrowck/clone-on-ref.stderr | 64 ++++++++++ 4 files changed, 233 insertions(+), 7 deletions(-) create mode 100644 tests/ui/borrowck/clone-on-ref.fixed create mode 100644 tests/ui/borrowck/clone-on-ref.rs create mode 100644 tests/ui/borrowck/clone-on-ref.stderr diff --git a/compiler/rustc_borrowck/src/diagnostics/conflict_errors.rs b/compiler/rustc_borrowck/src/diagnostics/conflict_errors.rs index 0776f455efd9..fcbad4724752 100644 --- a/compiler/rustc_borrowck/src/diagnostics/conflict_errors.rs +++ b/compiler/rustc_borrowck/src/diagnostics/conflict_errors.rs @@ -12,7 +12,6 @@ use rustc_hir::def::{DefKind, Res}; use rustc_hir::intravisit::{walk_block, walk_expr, Visitor}; use rustc_hir::{CoroutineDesugaring, PatField}; use rustc_hir::{CoroutineKind, CoroutineSource, LangItem}; -use rustc_infer::traits::ObligationCause; use rustc_middle::hir::nested_filter::OnlyBodies; use rustc_middle::mir::tcx::PlaceTy; use rustc_middle::mir::{ @@ -21,16 +20,21 @@ use rustc_middle::mir::{ PlaceRef, ProjectionElem, Rvalue, Statement, StatementKind, Terminator, TerminatorKind, VarBindingForm, }; -use rustc_middle::ty::{self, suggest_constraining_type_params, PredicateKind, Ty, TyCtxt}; +use rustc_middle::ty::{ + self, suggest_constraining_type_params, PredicateKind, ToPredicate, Ty, TyCtxt, + TypeSuperVisitable, TypeVisitor, +}; use rustc_middle::util::CallKind; use rustc_mir_dataflow::move_paths::{InitKind, MoveOutIndex, MovePathIndex}; +use rustc_span::def_id::DefId; use rustc_span::def_id::LocalDefId; use rustc_span::hygiene::DesugaringKind; use rustc_span::symbol::{kw, sym, Ident}; use rustc_span::{BytePos, Span, Symbol}; use rustc_trait_selection::infer::InferCtxtExt; +use rustc_trait_selection::traits::error_reporting::suggestions::TypeErrCtxtExt; use rustc_trait_selection::traits::error_reporting::FindExprBySpan; -use rustc_trait_selection::traits::ObligationCtxt; +use rustc_trait_selection::traits::{Obligation, ObligationCause, ObligationCtxt}; use std::iter; use crate::borrow_set::TwoPhaseActivation; @@ -283,7 +287,8 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { // something that already has `Fn`-like bounds (or is a closure), so we can't // restrict anyways. } else { - self.suggest_adding_copy_bounds(&mut err, ty, span); + let copy_did = self.infcx.tcx.require_lang_item(LangItem::Copy, Some(span)); + self.suggest_adding_bounds(&mut err, ty, copy_did, span); } if needs_note { @@ -775,7 +780,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { } } - fn suggest_adding_copy_bounds(&self, err: &mut Diag<'_>, ty: Ty<'tcx>, span: Span) { + fn suggest_adding_bounds(&self, err: &mut Diag<'_>, ty: Ty<'tcx>, def_id: DefId, span: Span) { let tcx = self.infcx.tcx; let generics = tcx.generics_of(self.mir_def_id()); @@ -788,10 +793,9 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { }; // Try to find predicates on *generic params* that would allow copying `ty` let ocx = ObligationCtxt::new(self.infcx); - let copy_did = tcx.require_lang_item(LangItem::Copy, Some(span)); let cause = ObligationCause::misc(span, self.mir_def_id()); - ocx.register_bound(cause, self.param_env, ty, copy_did); + ocx.register_bound(cause, self.param_env, ty, def_id); let errors = ocx.select_all_or_error(); // Only emit suggestion if all required predicates are on generic @@ -877,6 +881,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { Some(borrow_span), None, ); + self.suggest_copy_for_type_in_cloned_ref(&mut err, place); self.buffer_error(err); } @@ -1215,10 +1220,104 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { ); self.suggest_using_local_if_applicable(&mut err, location, issued_borrow, explanation); + self.suggest_copy_for_type_in_cloned_ref(&mut err, place); err } + fn suggest_copy_for_type_in_cloned_ref(&self, err: &mut Diag<'tcx>, place: Place<'tcx>) { + let tcx = self.infcx.tcx; + let hir = tcx.hir(); + let Some(body_id) = tcx.hir_node(self.mir_hir_id()).body_id() else { return }; + struct FindUselessClone<'hir> { + pub clones: Vec<&'hir hir::Expr<'hir>>, + } + impl<'hir> FindUselessClone<'hir> { + pub fn new() -> Self { + Self { clones: vec![] } + } + } + + impl<'v> Visitor<'v> for FindUselessClone<'v> { + fn visit_expr(&mut self, ex: &'v hir::Expr<'v>) { + // FIXME: use `lookup_method_for_diagnostic`? + if let hir::ExprKind::MethodCall(segment, _rcvr, args, _span) = ex.kind + && segment.ident.name == sym::clone + && args.len() == 0 + { + self.clones.push(ex); + } + hir::intravisit::walk_expr(self, ex); + } + } + let mut expr_finder = FindUselessClone::new(); + + let body = hir.body(body_id).value; + expr_finder.visit_expr(body); + + pub struct Holds<'tcx> { + ty: Ty<'tcx>, + holds: bool, + } + + impl<'tcx> TypeVisitor> for Holds<'tcx> { + type Result = std::ops::ControlFlow<()>; + + fn visit_ty(&mut self, t: Ty<'tcx>) -> Self::Result { + if t == self.ty { + self.holds = true; + } + t.super_visit_with(self) + } + } + + let mut types_to_constrain = FxIndexSet::default(); + + let local_ty = self.body.local_decls[place.local].ty; + let typeck_results = tcx.typeck(self.mir_def_id()); + let clone = tcx.require_lang_item(LangItem::Clone, Some(body.span)); + for expr in expr_finder.clones { + if let hir::ExprKind::MethodCall(_, rcvr, _, span) = expr.kind + && let Some(rcvr_ty) = typeck_results.node_type_opt(rcvr.hir_id) + && let Some(ty) = typeck_results.node_type_opt(expr.hir_id) + && rcvr_ty == ty + && let ty::Ref(_, inner, _) = rcvr_ty.kind() + && let inner = inner.peel_refs() + && let mut v = (Holds { ty: inner, holds: false }) + && let _ = v.visit_ty(local_ty) + && v.holds + && let None = self.infcx.type_implements_trait_shallow(clone, inner, self.param_env) + { + err.span_label( + span, + format!( + "this call doesn't do anything, the result is still `{rcvr_ty}` \ + because `{inner}` doesn't implement `Clone`", + ), + ); + types_to_constrain.insert(inner); + } + } + for ty in types_to_constrain { + self.suggest_adding_bounds(err, ty, clone, body.span); + if let ty::Adt(..) = ty.kind() { + // The type doesn't implement Clone. + let trait_ref = ty::Binder::dummy(ty::TraitRef::new(self.infcx.tcx, clone, [ty])); + let obligation = Obligation::new( + self.infcx.tcx, + ObligationCause::dummy(), + self.param_env, + trait_ref, + ); + self.infcx.err_ctxt().suggest_derive( + &obligation, + err, + trait_ref.to_predicate(self.infcx.tcx), + ); + } + } + } + #[instrument(level = "debug", skip(self, err))] fn suggest_using_local_if_applicable( &self, diff --git a/tests/ui/borrowck/clone-on-ref.fixed b/tests/ui/borrowck/clone-on-ref.fixed new file mode 100644 index 000000000000..b6927ba590e3 --- /dev/null +++ b/tests/ui/borrowck/clone-on-ref.fixed @@ -0,0 +1,32 @@ +//@ run-rustfix +fn foo(list: &mut Vec) { + let mut cloned_items = Vec::new(); + for v in list.iter() { + cloned_items.push(v.clone()) + } + list.push(T::default()); + //~^ ERROR cannot borrow `*list` as mutable because it is also borrowed as immutable + drop(cloned_items); +} +fn bar(x: T) { + let a = &x; + let b = a.clone(); + drop(x); + //~^ ERROR cannot move out of `x` because it is borrowed + println!("{b}"); +} +#[derive(Debug)] +#[derive(Clone)] +struct A; +fn qux(x: A) { + let a = &x; + let b = a.clone(); + drop(x); + //~^ ERROR cannot move out of `x` because it is borrowed + println!("{b:?}"); +} +fn main() { + foo(&mut vec![1, 2, 3]); + bar(""); + qux(A); +} diff --git a/tests/ui/borrowck/clone-on-ref.rs b/tests/ui/borrowck/clone-on-ref.rs new file mode 100644 index 000000000000..f8c94d3cce31 --- /dev/null +++ b/tests/ui/borrowck/clone-on-ref.rs @@ -0,0 +1,31 @@ +//@ run-rustfix +fn foo(list: &mut Vec) { + let mut cloned_items = Vec::new(); + for v in list.iter() { + cloned_items.push(v.clone()) + } + list.push(T::default()); + //~^ ERROR cannot borrow `*list` as mutable because it is also borrowed as immutable + drop(cloned_items); +} +fn bar(x: T) { + let a = &x; + let b = a.clone(); + drop(x); + //~^ ERROR cannot move out of `x` because it is borrowed + println!("{b}"); +} +#[derive(Debug)] +struct A; +fn qux(x: A) { + let a = &x; + let b = a.clone(); + drop(x); + //~^ ERROR cannot move out of `x` because it is borrowed + println!("{b:?}"); +} +fn main() { + foo(&mut vec![1, 2, 3]); + bar(""); + qux(A); +} diff --git a/tests/ui/borrowck/clone-on-ref.stderr b/tests/ui/borrowck/clone-on-ref.stderr new file mode 100644 index 000000000000..ee4fcadf55ae --- /dev/null +++ b/tests/ui/borrowck/clone-on-ref.stderr @@ -0,0 +1,64 @@ +error[E0502]: cannot borrow `*list` as mutable because it is also borrowed as immutable + --> $DIR/clone-on-ref.rs:7:5 + | +LL | for v in list.iter() { + | ---- immutable borrow occurs here +LL | cloned_items.push(v.clone()) + | ------- this call doesn't do anything, the result is still `&T` because `T` doesn't implement `Clone` +LL | } +LL | list.push(T::default()); + | ^^^^^^^^^^^^^^^^^^^^^^^ mutable borrow occurs here +LL | +LL | drop(cloned_items); + | ------------ immutable borrow later used here + | +help: consider further restricting this bound + | +LL | fn foo(list: &mut Vec) { + | +++++++ + +error[E0505]: cannot move out of `x` because it is borrowed + --> $DIR/clone-on-ref.rs:14:10 + | +LL | fn bar(x: T) { + | - binding `x` declared here +LL | let a = &x; + | -- borrow of `x` occurs here +LL | let b = a.clone(); + | ------- this call doesn't do anything, the result is still `&T` because `T` doesn't implement `Clone` +LL | drop(x); + | ^ move out of `x` occurs here +LL | +LL | println!("{b}"); + | --- borrow later used here + | +help: consider further restricting this bound + | +LL | fn bar(x: T) { + | +++++++ + +error[E0505]: cannot move out of `x` because it is borrowed + --> $DIR/clone-on-ref.rs:23:10 + | +LL | fn qux(x: A) { + | - binding `x` declared here +LL | let a = &x; + | -- borrow of `x` occurs here +LL | let b = a.clone(); + | ------- this call doesn't do anything, the result is still `&A` because `A` doesn't implement `Clone` +LL | drop(x); + | ^ move out of `x` occurs here +LL | +LL | println!("{b:?}"); + | ----- borrow later used here + | +help: consider annotating `A` with `#[derive(Clone)]` + | +LL + #[derive(Clone)] +LL | struct A; + | + +error: aborting due to 3 previous errors + +Some errors have detailed explanations: E0502, E0505. +For more information about an error, try `rustc --explain E0502`. From b367c25367117a4ada5c9a1c807b74f0efcf6d51 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Sat, 9 Mar 2024 20:32:13 +0000 Subject: [PATCH 03/17] Tweak wording --- compiler/rustc_mir_build/messages.ftl | 2 +- ...can-live-while-the-other-survives-1.stderr | 4 +- ...t-by-move-and-ref-inverse-promotion.stderr | 2 +- ...orrowck-pat-by-move-and-ref-inverse.stderr | 50 +++++++++---------- .../borrowck-pat-ref-mut-twice.stderr | 8 +-- ...inding-modes-both-sides-independent.stderr | 2 +- .../ui/suggestions/ref-pattern-binding.stderr | 4 +- 7 files changed, 36 insertions(+), 36 deletions(-) diff --git a/compiler/rustc_mir_build/messages.ftl b/compiler/rustc_mir_build/messages.ftl index 8a6ccdb85782..1de691f32a70 100644 --- a/compiler/rustc_mir_build/messages.ftl +++ b/compiler/rustc_mir_build/messages.ftl @@ -24,7 +24,7 @@ mir_build_borrow_of_layout_constrained_field_requires_unsafe_unsafe_op_in_unsafe mir_build_borrow_of_moved_value = borrow of moved value .label = value moved into `{$name}` here - .occurs_because_label = move occurs because `{$name}` has type `{$ty}` which does not implement the `Copy` trait + .occurs_because_label = move occurs because `{$name}` has type `{$ty}`, which does not implement the `Copy` trait .value_borrowed_label = value borrowed here after move .suggestion = borrow this binding in the pattern to avoid moving the value diff --git a/tests/ui/pattern/bindings-after-at/bind-by-move-neither-can-live-while-the-other-survives-1.stderr b/tests/ui/pattern/bindings-after-at/bind-by-move-neither-can-live-while-the-other-survives-1.stderr index 25838fbf0abd..16a93a0d47d2 100644 --- a/tests/ui/pattern/bindings-after-at/bind-by-move-neither-can-live-while-the-other-survives-1.stderr +++ b/tests/ui/pattern/bindings-after-at/bind-by-move-neither-can-live-while-the-other-survives-1.stderr @@ -13,7 +13,7 @@ LL | Some(_z @ ref _y) => {} | ^^ ------ value borrowed here after move | | | value moved into `_z` here - | move occurs because `_z` has type `X` which does not implement the `Copy` trait + | move occurs because `_z` has type `X`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -35,7 +35,7 @@ LL | Some(_z @ ref mut _y) => {} | ^^ ---------- value borrowed here after move | | | value moved into `_z` here - | move occurs because `_z` has type `X` which does not implement the `Copy` trait + | move occurs because `_z` has type `X`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | diff --git a/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse-promotion.stderr b/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse-promotion.stderr index 815a4ade9956..ea04d4bc055a 100644 --- a/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse-promotion.stderr +++ b/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse-promotion.stderr @@ -5,7 +5,7 @@ LL | let a @ ref b = U; | ^ ----- value borrowed here after move | | | value moved into `a` here - | move occurs because `a` has type `U` which does not implement the `Copy` trait + | move occurs because `a` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | diff --git a/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse.stderr b/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse.stderr index fd7a51388bc1..25c940a3200a 100644 --- a/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse.stderr +++ b/tests/ui/pattern/bindings-after-at/borrowck-pat-by-move-and-ref-inverse.stderr @@ -5,7 +5,7 @@ LL | let a @ ref b = U; | ^ ----- value borrowed here after move | | | value moved into `a` here - | move occurs because `a` has type `U` which does not implement the `Copy` trait + | move occurs because `a` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -20,7 +20,7 @@ LL | let a @ (mut b @ ref mut c, d @ ref e) = (U, U); | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `(U, U)` which does not implement the `Copy` trait + | move occurs because `a` has type `(U, U)`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -34,7 +34,7 @@ LL | let a @ (mut b @ ref mut c, d @ ref e) = (U, U); | ^^^^^ --------- value borrowed here after move | | | value moved into `b` here - | move occurs because `b` has type `U` which does not implement the `Copy` trait + | move occurs because `b` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -48,7 +48,7 @@ LL | let a @ (mut b @ ref mut c, d @ ref e) = (U, U); | ^ ----- value borrowed here after move | | | value moved into `d` here - | move occurs because `d` has type `U` which does not implement the `Copy` trait + | move occurs because `d` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -63,7 +63,7 @@ LL | let a @ [ref mut b, ref c] = [U, U]; | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `[U; 2]` which does not implement the `Copy` trait + | move occurs because `a` has type `[U; 2]`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -77,7 +77,7 @@ LL | let a @ ref b = u(); | ^ ----- value borrowed here after move | | | value moved into `a` here - | move occurs because `a` has type `U` which does not implement the `Copy` trait + | move occurs because `a` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -92,7 +92,7 @@ LL | let a @ (mut b @ ref mut c, d @ ref e) = (u(), u()); | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `(U, U)` which does not implement the `Copy` trait + | move occurs because `a` has type `(U, U)`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -106,7 +106,7 @@ LL | let a @ (mut b @ ref mut c, d @ ref e) = (u(), u()); | ^^^^^ --------- value borrowed here after move | | | value moved into `b` here - | move occurs because `b` has type `U` which does not implement the `Copy` trait + | move occurs because `b` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -120,7 +120,7 @@ LL | let a @ (mut b @ ref mut c, d @ ref e) = (u(), u()); | ^ ----- value borrowed here after move | | | value moved into `d` here - | move occurs because `d` has type `U` which does not implement the `Copy` trait + | move occurs because `d` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -135,7 +135,7 @@ LL | let a @ [ref mut b, ref c] = [u(), u()]; | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `[U; 2]` which does not implement the `Copy` trait + | move occurs because `a` has type `[U; 2]`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -149,7 +149,7 @@ LL | a @ Some(ref b) => {} | ^ ----- value borrowed here after move | | | value moved into `a` here - | move occurs because `a` has type `Option` which does not implement the `Copy` trait + | move occurs because `a` has type `Option`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -164,7 +164,7 @@ LL | a @ Some((mut b @ ref mut c, d @ ref e)) => {} | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `Option<(U, U)>` which does not implement the `Copy` trait + | move occurs because `a` has type `Option<(U, U)>`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -178,7 +178,7 @@ LL | a @ Some((mut b @ ref mut c, d @ ref e)) => {} | ^^^^^ --------- value borrowed here after move | | | value moved into `b` here - | move occurs because `b` has type `U` which does not implement the `Copy` trait + | move occurs because `b` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -192,7 +192,7 @@ LL | a @ Some((mut b @ ref mut c, d @ ref e)) => {} | ^ ----- value borrowed here after move | | | value moved into `d` here - | move occurs because `d` has type `U` which does not implement the `Copy` trait + | move occurs because `d` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -207,7 +207,7 @@ LL | mut a @ Some([ref b, ref mut c]) => {} | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `Option<[U; 2]>` which does not implement the `Copy` trait + | move occurs because `a` has type `Option<[U; 2]>`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -221,7 +221,7 @@ LL | a @ Some(ref b) => {} | ^ ----- value borrowed here after move | | | value moved into `a` here - | move occurs because `a` has type `Option` which does not implement the `Copy` trait + | move occurs because `a` has type `Option`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -236,7 +236,7 @@ LL | a @ Some((mut b @ ref mut c, d @ ref e)) => {} | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `Option<(U, U)>` which does not implement the `Copy` trait + | move occurs because `a` has type `Option<(U, U)>`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -250,7 +250,7 @@ LL | a @ Some((mut b @ ref mut c, d @ ref e)) => {} | ^^^^^ --------- value borrowed here after move | | | value moved into `b` here - | move occurs because `b` has type `U` which does not implement the `Copy` trait + | move occurs because `b` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -264,7 +264,7 @@ LL | a @ Some((mut b @ ref mut c, d @ ref e)) => {} | ^ ----- value borrowed here after move | | | value moved into `d` here - | move occurs because `d` has type `U` which does not implement the `Copy` trait + | move occurs because `d` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -279,7 +279,7 @@ LL | mut a @ Some([ref b, ref mut c]) => {} | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `Option<[U; 2]>` which does not implement the `Copy` trait + | move occurs because `a` has type `Option<[U; 2]>`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -349,7 +349,7 @@ LL | fn f1(a @ ref b: U) {} | ^ ----- value borrowed here after move | | | value moved into `a` here - | move occurs because `a` has type `U` which does not implement the `Copy` trait + | move occurs because `a` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -364,7 +364,7 @@ LL | fn f2(mut a @ (b @ ref c, mut d @ ref e): (U, U)) {} | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `(U, U)` which does not implement the `Copy` trait + | move occurs because `a` has type `(U, U)`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -378,7 +378,7 @@ LL | fn f2(mut a @ (b @ ref c, mut d @ ref e): (U, U)) {} | ^ ----- value borrowed here after move | | | value moved into `b` here - | move occurs because `b` has type `U` which does not implement the `Copy` trait + | move occurs because `b` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -392,7 +392,7 @@ LL | fn f2(mut a @ (b @ ref c, mut d @ ref e): (U, U)) {} | ^^^^^ ----- value borrowed here after move | | | value moved into `d` here - | move occurs because `d` has type `U` which does not implement the `Copy` trait + | move occurs because `d` has type `U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -417,7 +417,7 @@ LL | fn f3(a @ [ref mut b, ref c]: [U; 2]) {} | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `[U; 2]` which does not implement the `Copy` trait + | move occurs because `a` has type `[U; 2]`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | diff --git a/tests/ui/pattern/bindings-after-at/borrowck-pat-ref-mut-twice.stderr b/tests/ui/pattern/bindings-after-at/borrowck-pat-ref-mut-twice.stderr index 3446148d2b15..76085f897ff5 100644 --- a/tests/ui/pattern/bindings-after-at/borrowck-pat-ref-mut-twice.stderr +++ b/tests/ui/pattern/bindings-after-at/borrowck-pat-ref-mut-twice.stderr @@ -78,7 +78,7 @@ LL | let a @ (ref mut b, ref mut c) = (U, U); | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `(U, U)` which does not implement the `Copy` trait + | move occurs because `a` has type `(U, U)`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -94,7 +94,7 @@ LL | let a @ (b, [c, d]) = &mut val; // Same as ^-- | | | value borrowed here after move | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `&mut (U, [U; 2])` which does not implement the `Copy` trait + | move occurs because `a` has type `&mut (U, [U; 2])`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -108,7 +108,7 @@ LL | let a @ &mut ref mut b = &mut U; | ^ --------- value borrowed here after move | | | value moved into `a` here - | move occurs because `a` has type `&mut U` which does not implement the `Copy` trait + | move occurs because `a` has type `&mut U`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -123,7 +123,7 @@ LL | let a @ &mut (ref mut b, ref mut c) = &mut (U, U); | | | | | value borrowed here after move | value moved into `a` here - | move occurs because `a` has type `&mut (U, U)` which does not implement the `Copy` trait + | move occurs because `a` has type `&mut (U, U)`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | diff --git a/tests/ui/pattern/bindings-after-at/default-binding-modes-both-sides-independent.stderr b/tests/ui/pattern/bindings-after-at/default-binding-modes-both-sides-independent.stderr index 36515c1a29bb..a0a43e83a6a0 100644 --- a/tests/ui/pattern/bindings-after-at/default-binding-modes-both-sides-independent.stderr +++ b/tests/ui/pattern/bindings-after-at/default-binding-modes-both-sides-independent.stderr @@ -29,7 +29,7 @@ LL | Ok(ref a @ b) | Err(b @ ref a) => { | ^ ----- value borrowed here after move | | | value moved into `b` here - | move occurs because `b` has type `NotCopy` which does not implement the `Copy` trait + | move occurs because `b` has type `NotCopy`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | diff --git a/tests/ui/suggestions/ref-pattern-binding.stderr b/tests/ui/suggestions/ref-pattern-binding.stderr index 69ce5d440af8..af21c6aef700 100644 --- a/tests/ui/suggestions/ref-pattern-binding.stderr +++ b/tests/ui/suggestions/ref-pattern-binding.stderr @@ -5,7 +5,7 @@ LL | let _moved @ ref _from = String::from("foo"); | ^^^^^^ --------- value borrowed here after move | | | value moved into `_moved` here - | move occurs because `_moved` has type `String` which does not implement the `Copy` trait + | move occurs because `_moved` has type `String`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | @@ -35,7 +35,7 @@ LL | let _moved @ S { ref f } = S { f: String::from("foo") }; | ^^^^^^ ----- value borrowed here after move | | | value moved into `_moved` here - | move occurs because `_moved` has type `S` which does not implement the `Copy` trait + | move occurs because `_moved` has type `S`, which does not implement the `Copy` trait | help: borrow this binding in the pattern to avoid moving the value | From 0953608debfa9d3df955f976e7bc857584ba1ed0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Tue, 12 Mar 2024 17:21:15 +0000 Subject: [PATCH 04/17] Account for UnOps in borrowck message --- compiler/rustc_borrowck/messages.ftl | 3 +++ compiler/rustc_borrowck/src/diagnostics/mod.rs | 11 +++++++++-- compiler/rustc_borrowck/src/session_diagnostics.rs | 5 +++++ tests/ui/unop-move-semantics.stderr | 4 ++-- 4 files changed, 19 insertions(+), 4 deletions(-) diff --git a/compiler/rustc_borrowck/messages.ftl b/compiler/rustc_borrowck/messages.ftl index bf14d5eb9a0a..f2ca509e14bb 100644 --- a/compiler/rustc_borrowck/messages.ftl +++ b/compiler/rustc_borrowck/messages.ftl @@ -16,6 +16,9 @@ borrowck_borrow_due_to_use_closure = borrowck_borrow_due_to_use_coroutine = borrow occurs due to use in coroutine +borrowck_calling_operator_moves = + calling this operator moves the value + borrowck_calling_operator_moves_lhs = calling this operator moves the left-hand side diff --git a/compiler/rustc_borrowck/src/diagnostics/mod.rs b/compiler/rustc_borrowck/src/diagnostics/mod.rs index 4ebbe592628a..914f68a38b4f 100644 --- a/compiler/rustc_borrowck/src/diagnostics/mod.rs +++ b/compiler/rustc_borrowck/src/diagnostics/mod.rs @@ -1050,7 +1050,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { ); err.subdiagnostic(self.dcx(), CaptureReasonNote::FnOnceMoveInCall { var_span }); } - CallKind::Operator { self_arg, .. } => { + CallKind::Operator { self_arg, trait_id, .. } => { let self_arg = self_arg.unwrap(); err.subdiagnostic( self.dcx(), @@ -1062,9 +1062,16 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { }, ); if self.fn_self_span_reported.insert(fn_span) { + let lang = self.infcx.tcx.lang_items(); err.subdiagnostic( self.dcx(), - CaptureReasonNote::LhsMoveByOperator { span: self_arg.span }, + if [lang.not_trait(), lang.deref_trait(), lang.neg_trait()] + .contains(&Some(trait_id)) + { + CaptureReasonNote::UnOpMoveByOperator { span: self_arg.span } + } else { + CaptureReasonNote::LhsMoveByOperator { span: self_arg.span } + }, ); } } diff --git a/compiler/rustc_borrowck/src/session_diagnostics.rs b/compiler/rustc_borrowck/src/session_diagnostics.rs index a055ce95e8ef..77021ae4321d 100644 --- a/compiler/rustc_borrowck/src/session_diagnostics.rs +++ b/compiler/rustc_borrowck/src/session_diagnostics.rs @@ -368,6 +368,11 @@ pub(crate) enum CaptureReasonNote { #[primary_span] var_span: Span, }, + #[note(borrowck_calling_operator_moves)] + UnOpMoveByOperator { + #[primary_span] + span: Span, + }, #[note(borrowck_calling_operator_moves_lhs)] LhsMoveByOperator { #[primary_span] diff --git a/tests/ui/unop-move-semantics.stderr b/tests/ui/unop-move-semantics.stderr index b6de7976ac94..187dd66b2fe5 100644 --- a/tests/ui/unop-move-semantics.stderr +++ b/tests/ui/unop-move-semantics.stderr @@ -9,7 +9,7 @@ LL | LL | x.clone(); | ^ value borrowed here after move | -note: calling this operator moves the left-hand side +note: calling this operator moves the value --> $SRC_DIR/core/src/ops/bit.rs:LL:COL help: consider cloning the value if the performance cost is acceptable | @@ -57,7 +57,7 @@ LL | !*m; | |move occurs because `*m` has type `T`, which does not implement the `Copy` trait | `*m` moved due to usage in operator | -note: calling this operator moves the left-hand side +note: calling this operator moves the value --> $SRC_DIR/core/src/ops/bit.rs:LL:COL error[E0507]: cannot move out of `*n` which is behind a shared reference From 8da262139af11628512d1d9bce059310461a1fa8 Mon Sep 17 00:00:00 2001 From: Manish Goregaokar Date: Thu, 14 Mar 2024 12:15:05 +0100 Subject: [PATCH 05/17] print ghosts --- src/librustdoc/html/render/print_item.rs | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/librustdoc/html/render/print_item.rs b/src/librustdoc/html/render/print_item.rs index d588f219739f..4f74ae096fba 100644 --- a/src/librustdoc/html/render/print_item.rs +++ b/src/librustdoc/html/render/print_item.rs @@ -517,6 +517,11 @@ fn item_module(w: &mut Buffer, cx: &mut Context<'_>, item: &clean::Item, items: } _ => "", }; + let hidden_emoji = if myitem.is_doc_hidden() { + " ðŸ‘» " + } else { + "" + }; w.write_str(ITEM_TABLE_ROW_OPEN); let docs = @@ -531,6 +536,7 @@ fn item_module(w: &mut Buffer, cx: &mut Context<'_>, item: &clean::Item, items: "
\ {name}\ {visibility_emoji}\ + {hidden_emoji}\ {unsafety_flag}\ {stab_tags}\
\ From 343c77c102608e7b9090789ea365a21d0156d191 Mon Sep 17 00:00:00 2001 From: Manish Goregaokar Date: Thu, 14 Mar 2024 12:39:27 +0100 Subject: [PATCH 06/17] Refactor visibility_print_with_space to directly take an item --- src/librustdoc/clean/inline.rs | 16 ++++++-- src/librustdoc/clean/mod.rs | 3 +- src/librustdoc/clean/types.rs | 2 +- src/librustdoc/clean/utils.rs | 5 ++- src/librustdoc/html/format.rs | 12 +++--- src/librustdoc/html/render/mod.rs | 7 ++-- src/librustdoc/html/render/print_item.rs | 48 ++++++++---------------- 7 files changed, 42 insertions(+), 51 deletions(-) diff --git a/src/librustdoc/clean/inline.rs b/src/librustdoc/clean/inline.rs index 77a78f57e950..6f86c6450d96 100644 --- a/src/librustdoc/clean/inline.rs +++ b/src/librustdoc/clean/inline.rs @@ -62,6 +62,9 @@ pub(crate) fn try_inline( attrs_without_docs.as_ref().map(|(attrs, def_id)| (&attrs[..], *def_id)); let import_def_id = attrs.and_then(|(_, def_id)| def_id); + + let (attrs, cfg) = merge_attrs(cx, load_attrs(cx, did), attrs); + let kind = match res { Res::Def(DefKind::Trait, did) => { record_extern_fqn(cx, did, ItemType::Trait); @@ -131,7 +134,7 @@ pub(crate) fn try_inline( cx.with_param_env(did, |cx| clean::ConstantItem(build_const(cx, did))) } Res::Def(DefKind::Macro(kind), did) => { - let mac = build_macro(cx, did, name, import_def_id, kind); + let mac = build_macro(cx, did, name, import_def_id, kind, attrs.is_doc_hidden()); let type_kind = match kind { MacroKind::Bang => ItemType::Macro, @@ -144,7 +147,6 @@ pub(crate) fn try_inline( _ => return None, }; - let (attrs, cfg) = merge_attrs(cx, load_attrs(cx, did), attrs); cx.inlined.insert(did.into()); let mut item = clean::Item::from_def_id_and_attrs_and_parts(did, Some(name), kind, Box::new(attrs), cfg); @@ -751,6 +753,7 @@ fn build_macro( name: Symbol, import_def_id: Option, macro_kind: MacroKind, + is_doc_hidden: bool, ) -> clean::ItemKind { match CStore::from_tcx(cx.tcx).load_macro_untracked(def_id, cx.tcx) { LoadedMacro::MacroDef(item_def, _) => match macro_kind { @@ -758,7 +761,14 @@ fn build_macro( if let ast::ItemKind::MacroDef(ref def) = item_def.kind { let vis = cx.tcx.visibility(import_def_id.unwrap_or(def_id)); clean::MacroItem(clean::Macro { - source: utils::display_macro_source(cx, name, def, def_id, vis), + source: utils::display_macro_source( + cx, + name, + def, + def_id, + vis, + is_doc_hidden, + ), }) } else { unreachable!() diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index b32d3ad562d0..ec4c6d991f1a 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -2796,7 +2796,8 @@ fn clean_maybe_renamed_item<'tcx>( ItemKind::Macro(ref macro_def, MacroKind::Bang) => { let ty_vis = cx.tcx.visibility(def_id); MacroItem(Macro { - source: display_macro_source(cx, name, macro_def, def_id, ty_vis), + // FIXME this shouldn't be false + source: display_macro_source(cx, name, macro_def, def_id, ty_vis, false), }) } ItemKind::Macro(_, macro_kind) => clean_proc_macro(item, &mut name, macro_kind, cx), diff --git a/src/librustdoc/clean/types.rs b/src/librustdoc/clean/types.rs index c35baeb4cf58..a51f6360df2a 100644 --- a/src/librustdoc/clean/types.rs +++ b/src/librustdoc/clean/types.rs @@ -1161,7 +1161,7 @@ impl Attributes { false } - fn is_doc_hidden(&self) -> bool { + pub(crate) fn is_doc_hidden(&self) -> bool { self.has_doc_flag(sym::hidden) } diff --git a/src/librustdoc/clean/utils.rs b/src/librustdoc/clean/utils.rs index 57916ff0ff78..5464aa63ea80 100644 --- a/src/librustdoc/clean/utils.rs +++ b/src/librustdoc/clean/utils.rs @@ -625,6 +625,7 @@ pub(super) fn display_macro_source( def: &ast::MacroDef, def_id: DefId, vis: ty::Visibility, + is_doc_hidden: bool, ) -> String { // Extract the spans of all matchers. They represent the "interface" of the macro. let matchers = def.body.tokens.chunks(4).map(|arm| &arm[0]); @@ -635,7 +636,7 @@ pub(super) fn display_macro_source( if matchers.len() <= 1 { format!( "{vis}macro {name}{matchers} {{\n ...\n}}", - vis = visibility_to_src_with_space(Some(vis), cx.tcx, def_id), + vis = visibility_to_src_with_space(Some(vis), cx.tcx, def_id, is_doc_hidden), matchers = matchers .map(|matcher| render_macro_matcher(cx.tcx, matcher)) .collect::(), @@ -643,7 +644,7 @@ pub(super) fn display_macro_source( } else { format!( "{vis}macro {name} {{\n{arms}}}", - vis = visibility_to_src_with_space(Some(vis), cx.tcx, def_id), + vis = visibility_to_src_with_space(Some(vis), cx.tcx, def_id, is_doc_hidden), arms = render_macro_arms(cx.tcx, matchers, ","), ) } diff --git a/src/librustdoc/html/format.rs b/src/librustdoc/html/format.rs index afd5eb42d019..1973c2a6021c 100644 --- a/src/librustdoc/html/format.rs +++ b/src/librustdoc/html/format.rs @@ -29,8 +29,7 @@ use rustc_target::spec::abi::Abi; use itertools::Itertools; use crate::clean::{ - self, types::ExternalLocation, utils::find_nearest_parent_module, ExternalCrate, ItemId, - PrimitiveType, + self, types::ExternalLocation, utils::find_nearest_parent_module, ExternalCrate, PrimitiveType, }; use crate::formats::cache::Cache; use crate::formats::item_type::ItemType; @@ -1506,20 +1505,18 @@ impl clean::FnDecl { } pub(crate) fn visibility_print_with_space<'a, 'tcx: 'a>( - visibility: Option>, - item_did: ItemId, + item: &clean::Item, cx: &'a Context<'tcx>, ) -> impl Display + 'a + Captures<'tcx> { use std::fmt::Write as _; - - let to_print: Cow<'static, str> = match visibility { + let to_print: Cow<'static, str> = match item.visibility(cx.tcx()) { None => "".into(), Some(ty::Visibility::Public) => "pub ".into(), Some(ty::Visibility::Restricted(vis_did)) => { // FIXME(camelid): This may not work correctly if `item_did` is a module. // However, rustdoc currently never displays a module's // visibility, so it shouldn't matter. - let parent_module = find_nearest_parent_module(cx.tcx(), item_did.expect_def_id()); + let parent_module = find_nearest_parent_module(cx.tcx(), item.item_id.expect_def_id()); if vis_did.is_crate_root() { "pub(crate) ".into() @@ -1557,6 +1554,7 @@ pub(crate) fn visibility_to_src_with_space<'a, 'tcx: 'a>( visibility: Option>, tcx: TyCtxt<'tcx>, item_did: DefId, + _is_doc_hidden: bool, ) -> impl Display + 'a + Captures<'tcx> { let to_print: Cow<'static, str> = match visibility { None => "".into(), diff --git a/src/librustdoc/html/render/mod.rs b/src/librustdoc/html/render/mod.rs index fe83095f944a..54d51ca009b2 100644 --- a/src/librustdoc/html/render/mod.rs +++ b/src/librustdoc/html/render/mod.rs @@ -883,7 +883,7 @@ fn assoc_const( w, "{indent}{vis}const {name}{generics}: {ty}", indent = " ".repeat(indent), - vis = visibility_print_with_space(it.visibility(tcx), it.item_id, cx), + vis = visibility_print_with_space(it, cx), href = assoc_href_attr(it, link, cx), name = it.name.as_ref().unwrap(), generics = generics.print(cx), @@ -912,12 +912,11 @@ fn assoc_type( indent: usize, cx: &Context<'_>, ) { - let tcx = cx.tcx(); write!( w, "{indent}{vis}type {name}{generics}", indent = " ".repeat(indent), - vis = visibility_print_with_space(it.visibility(tcx), it.item_id, cx), + vis = visibility_print_with_space(it, cx), href = assoc_href_attr(it, link, cx), name = it.name.as_ref().unwrap(), generics = generics.print(cx), @@ -945,7 +944,7 @@ fn assoc_method( let tcx = cx.tcx(); let header = meth.fn_header(tcx).expect("Trying to get header from a non-function item"); let name = meth.name.as_ref().unwrap(); - let vis = visibility_print_with_space(meth.visibility(tcx), meth.item_id, cx).to_string(); + let vis = visibility_print_with_space(meth, cx).to_string(); let defaultness = print_default_space(meth.is_default()); // FIXME: Once https://github.com/rust-lang/rust/issues/67792 is implemented, we can remove // this condition. diff --git a/src/librustdoc/html/render/print_item.rs b/src/librustdoc/html/render/print_item.rs index 4f74ae096fba..d2a03d584027 100644 --- a/src/librustdoc/html/render/print_item.rs +++ b/src/librustdoc/html/render/print_item.rs @@ -445,14 +445,14 @@ fn item_module(w: &mut Buffer, cx: &mut Context<'_>, item: &clean::Item, items: Some(src) => write!( w, "
{}extern crate {} as {};", - visibility_print_with_space(myitem.visibility(tcx), myitem.item_id, cx), + visibility_print_with_space(myitem, cx), anchor(myitem.item_id.expect_def_id(), src, cx), myitem.name.unwrap(), ), None => write!( w, "
{}extern crate {};", - visibility_print_with_space(myitem.visibility(tcx), myitem.item_id, cx), + visibility_print_with_space(myitem, cx), anchor(myitem.item_id.expect_def_id(), myitem.name.unwrap(), cx), ), } @@ -491,7 +491,7 @@ fn item_module(w: &mut Buffer, cx: &mut Context<'_>, item: &clean::Item, items: {vis}{imp}\
\ {stab_tags_before}{stab_tags}{stab_tags_after}", - vis = visibility_print_with_space(myitem.visibility(tcx), myitem.item_id, cx), + vis = visibility_print_with_space(myitem, cx), imp = import.print(cx), ); w.write_str(ITEM_TABLE_ROW_CLOSE); @@ -631,7 +631,7 @@ fn item_function(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, f: &cle let unsafety = header.unsafety.print_with_space(); let abi = print_abi_with_space(header.abi).to_string(); let asyncness = header.asyncness.print_with_space(); - let visibility = visibility_print_with_space(it.visibility(tcx), it.item_id, cx).to_string(); + let visibility = visibility_print_with_space(it, cx).to_string(); let name = it.name.unwrap(); let generics_len = format!("{:#}", f.generics.print(cx)).len(); @@ -688,7 +688,7 @@ fn item_trait(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, t: &clean: w, "{attrs}{vis}{unsafety}{is_auto}trait {name}{generics}{bounds}", attrs = render_attributes_in_pre(it, "", cx), - vis = visibility_print_with_space(it.visibility(tcx), it.item_id, cx), + vis = visibility_print_with_space(it, cx), unsafety = t.unsafety(tcx).print_with_space(), is_auto = if t.is_auto(tcx) { "auto " } else { "" }, name = it.name.unwrap(), @@ -1243,7 +1243,7 @@ fn item_type_alias(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, t: &c w, "{attrs}{vis}type {name}{generics}{where_clause} = {type_};", attrs = render_attributes_in_pre(it, "", cx), - vis = visibility_print_with_space(it.visibility(cx.tcx()), it.item_id, cx), + vis = visibility_print_with_space(it, cx), name = it.name.unwrap(), generics = t.generics.print(cx), where_clause = print_where_clause(&t.generics, cx, 0, Ending::Newline), @@ -1522,14 +1522,13 @@ fn print_tuple_struct_fields<'a, 'cx: 'a>( } fn item_enum(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, e: &clean::Enum) { - let tcx = cx.tcx(); let count_variants = e.variants().count(); wrap_item(w, |w| { render_attributes_in_code(w, it, cx); write!( w, "{}enum {}{}", - visibility_print_with_space(it.visibility(tcx), it.item_id, cx), + visibility_print_with_space(it, cx), it.name.unwrap(), e.generics.print(cx), ); @@ -1860,7 +1859,7 @@ fn item_constant(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, c: &cle write!( w, "{vis}const {name}{generics}: {typ}{where_clause}", - vis = visibility_print_with_space(it.visibility(tcx), it.item_id, cx), + vis = visibility_print_with_space(it, cx), name = it.name.unwrap(), generics = c.generics.print(cx), typ = c.type_.print(cx), @@ -1964,7 +1963,7 @@ fn item_static(w: &mut impl fmt::Write, cx: &mut Context<'_>, it: &clean::Item, write!( buffer, "{vis}static {mutability}{name}: {typ}", - vis = visibility_print_with_space(it.visibility(cx.tcx()), it.item_id, cx), + vis = visibility_print_with_space(it, cx), mutability = s.mutability.print_with_space(), name = it.name.unwrap(), typ = s.type_.print(cx) @@ -1982,7 +1981,7 @@ fn item_foreign_type(w: &mut impl fmt::Write, cx: &mut Context<'_>, it: &clean:: write!( buffer, " {}type {};\n}}", - visibility_print_with_space(it.visibility(cx.tcx()), it.item_id, cx), + visibility_print_with_space(it, cx), it.name.unwrap(), ) .unwrap(); @@ -2139,13 +2138,7 @@ fn render_union<'a, 'cx: 'a>( cx: &'a Context<'cx>, ) -> impl fmt::Display + 'a + Captures<'cx> { display_fn(move |mut f| { - let tcx = cx.tcx(); - write!( - f, - "{}union {}", - visibility_print_with_space(it.visibility(tcx), it.item_id, cx), - it.name.unwrap(), - )?; + write!(f, "{}union {}", visibility_print_with_space(it, cx), it.name.unwrap(),)?; let where_displayed = g .map(|g| { @@ -2175,7 +2168,7 @@ fn render_union<'a, 'cx: 'a>( write!( f, " {}{}: {},\n", - visibility_print_with_space(field.visibility(tcx), field.item_id, cx), + visibility_print_with_space(field, cx), field.name.unwrap(), ty.print(cx) )?; @@ -2203,11 +2196,10 @@ fn render_struct( structhead: bool, cx: &Context<'_>, ) { - let tcx = cx.tcx(); write!( w, "{}{}{}", - visibility_print_with_space(it.visibility(tcx), it.item_id, cx), + visibility_print_with_space(it, cx), if structhead { "struct " } else { "" }, it.name.unwrap() ); @@ -2236,7 +2228,6 @@ fn render_struct_fields( has_stripped_entries: bool, cx: &Context<'_>, ) { - let tcx = cx.tcx(); match ty { None => { let where_displayed = @@ -2260,7 +2251,7 @@ fn render_struct_fields( write!( w, "\n{tab} {vis}{name}: {ty},", - vis = visibility_print_with_space(field.visibility(tcx), field.item_id, cx), + vis = visibility_print_with_space(field, cx), name = field.name.unwrap(), ty = ty.print(cx), ); @@ -2296,16 +2287,7 @@ fn render_struct_fields( match *field.kind { clean::StrippedItem(box clean::StructFieldItem(..)) => write!(w, "_"), clean::StructFieldItem(ref ty) => { - write!( - w, - "{}{}", - visibility_print_with_space( - field.visibility(tcx), - field.item_id, - cx - ), - ty.print(cx), - ) + write!(w, "{}{}", visibility_print_with_space(field, cx), ty.print(cx),) } _ => unreachable!(), } From 102015645d37579145c0ba955f22ece95d98c3bd Mon Sep 17 00:00:00 2001 From: Manish Goregaokar Date: Thu, 14 Mar 2024 13:53:03 +0100 Subject: [PATCH 07/17] print doc(hidden) --- src/librustdoc/html/format.rs | 19 ++++++++++++++----- 1 file changed, 14 insertions(+), 5 deletions(-) diff --git a/src/librustdoc/html/format.rs b/src/librustdoc/html/format.rs index 1973c2a6021c..745001e035e7 100644 --- a/src/librustdoc/html/format.rs +++ b/src/librustdoc/html/format.rs @@ -1509,7 +1509,9 @@ pub(crate) fn visibility_print_with_space<'a, 'tcx: 'a>( cx: &'a Context<'tcx>, ) -> impl Display + 'a + Captures<'tcx> { use std::fmt::Write as _; - let to_print: Cow<'static, str> = match item.visibility(cx.tcx()) { + + let hidden: &'static str = if item.is_doc_hidden() { "#[doc(hidden)] " } else { "" }; + let vis: Cow<'static, str> = match item.visibility(cx.tcx()) { None => "".into(), Some(ty::Visibility::Public) => "pub ".into(), Some(ty::Visibility::Restricted(vis_did)) => { @@ -1544,7 +1546,10 @@ pub(crate) fn visibility_print_with_space<'a, 'tcx: 'a>( } } }; - display_fn(move |f| f.write_str(&to_print)) + display_fn(move |f| { + f.write_str(&hidden)?; + f.write_str(&vis) + }) } /// This function is the same as print_with_space, except that it renders no links. @@ -1554,9 +1559,10 @@ pub(crate) fn visibility_to_src_with_space<'a, 'tcx: 'a>( visibility: Option>, tcx: TyCtxt<'tcx>, item_did: DefId, - _is_doc_hidden: bool, + is_doc_hidden: bool, ) -> impl Display + 'a + Captures<'tcx> { - let to_print: Cow<'static, str> = match visibility { + let hidden: &'static str = if is_doc_hidden { "#[doc(hidden)] " } else { "" }; + let vis: Cow<'static, str> = match visibility { None => "".into(), Some(ty::Visibility::Public) => "pub ".into(), Some(ty::Visibility::Restricted(vis_did)) => { @@ -1580,7 +1586,10 @@ pub(crate) fn visibility_to_src_with_space<'a, 'tcx: 'a>( } } }; - display_fn(move |f| f.write_str(&to_print)) + display_fn(move |f| { + f.write_str(&hidden)?; + f.write_str(&vis) + }) } pub(crate) trait PrintWithSpace { From bd03fad8ee6554fbc57758d65015361f766468dd Mon Sep 17 00:00:00 2001 From: Manish Goregaokar Date: Thu, 14 Mar 2024 14:30:38 +0100 Subject: [PATCH 08/17] Make compact --- src/librustdoc/html/render/print_item.rs | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/src/librustdoc/html/render/print_item.rs b/src/librustdoc/html/render/print_item.rs index d2a03d584027..0af3f3bc9934 100644 --- a/src/librustdoc/html/render/print_item.rs +++ b/src/librustdoc/html/render/print_item.rs @@ -511,17 +511,18 @@ fn item_module(w: &mut Buffer, cx: &mut Context<'_>, item: &clean::Item, items: _ => "", }; - let visibility_emoji = match myitem.visibility(tcx) { + let visibility_and_hidden = match myitem.visibility(tcx) { Some(ty::Visibility::Restricted(_)) => { - " ðŸ”’ " + if myitem.is_doc_hidden() { + " ðŸ”’ " + } else { + // Don't separate with a space when there are two of them + " ðŸ”’👻 " + } } + _ if myitem.is_doc_hidden() => " ðŸ‘» ", _ => "", }; - let hidden_emoji = if myitem.is_doc_hidden() { - " ðŸ‘» " - } else { - "" - }; w.write_str(ITEM_TABLE_ROW_OPEN); let docs = @@ -535,14 +536,13 @@ fn item_module(w: &mut Buffer, cx: &mut Context<'_>, item: &clean::Item, items: w, "
\ {name}\ - {visibility_emoji}\ - {hidden_emoji}\ + {visibility_and_hidden}\ {unsafety_flag}\ {stab_tags}\
\ {docs_before}{docs}{docs_after}", name = myitem.name.unwrap(), - visibility_emoji = visibility_emoji, + visibility_and_hidden = visibility_and_hidden, stab_tags = extra_info_tags(myitem, item, tcx), class = myitem.type_(), unsafety_flag = unsafety_flag, From 26028209e808377d52ea36618b2cf2d75e0bcd6c Mon Sep 17 00:00:00 2001 From: Manish Goregaokar Date: Thu, 14 Mar 2024 14:40:54 +0100 Subject: [PATCH 09/17] tests --- tests/rustdoc/display-hidden-items.rs | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/tests/rustdoc/display-hidden-items.rs b/tests/rustdoc/display-hidden-items.rs index 76124554767f..901ca17d4d2c 100644 --- a/tests/rustdoc/display-hidden-items.rs +++ b/tests/rustdoc/display-hidden-items.rs @@ -5,19 +5,22 @@ #![crate_name = "foo"] // @has 'foo/index.html' -// @has - '//*[@id="reexport.hidden_reexport"]/code' 'pub use hidden::inside_hidden as hidden_reexport;' +// @has - '//*[@class="item-name"]/span[@title="Hidden item"]' '👻' + +// @has - '//*[@id="reexport.hidden_reexport"]/code' '#[doc(hidden)] pub use hidden::inside_hidden as hidden_reexport;' #[doc(hidden)] pub use hidden::inside_hidden as hidden_reexport; // @has - '//*[@class="item-name"]/a[@class="trait"]' 'TraitHidden' // @has 'foo/trait.TraitHidden.html' +// @has - '//code' '#[doc(hidden)] pub trait TraitHidden' #[doc(hidden)] pub trait TraitHidden {} // @has 'foo/index.html' '//*[@class="item-name"]/a[@class="trait"]' 'Trait' pub trait Trait { // @has 'foo/trait.Trait.html' - // @has - '//*[@id="associatedconstant.BAR"]/*[@class="code-header"]' 'const BAR: u32 = 0u32' + // @has - '//*[@id="associatedconstant.BAR"]/*[@class="code-header"]' '#[doc(hidden)] const BAR: u32 = 0u32' #[doc(hidden)] const BAR: u32 = 0; @@ -41,14 +44,15 @@ impl Struct { } impl Trait for Struct { - // @has - '//*[@id="associatedconstant.BAR"]/*[@class="code-header"]' 'const BAR: u32 = 0u32' - // @has - '//*[@id="method.foo"]/*[@class="code-header"]' 'fn foo()' + // @has - '//*[@id="associatedconstant.BAR"]/*[@class="code-header"]' '#[doc(hidden)] const BAR: u32 = 0u32' + // @has - '//*[@id="method.foo"]/*[@class="code-header"]' '#[doc(hidden)] fn foo()' } // @has - '//*[@id="impl-TraitHidden-for-Struct"]/*[@class="code-header"]' 'impl TraitHidden for Struct' impl TraitHidden for Struct {} // @has 'foo/index.html' '//*[@class="item-name"]/a[@class="enum"]' 'HiddenEnum' // @has 'foo/enum.HiddenEnum.html' +// @has - '//code' '#[doc(hidden)] pub enum HiddenEnum' #[doc(hidden)] pub enum HiddenEnum { A, From 580e5b855d58d2076460b7a16c87e622b7d68960 Mon Sep 17 00:00:00 2001 From: Manish Goregaokar Date: Thu, 14 Mar 2024 15:07:30 +0100 Subject: [PATCH 10/17] inline --- src/librustdoc/html/format.rs | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/src/librustdoc/html/format.rs b/src/librustdoc/html/format.rs index 745001e035e7..312765d3e6d0 100644 --- a/src/librustdoc/html/format.rs +++ b/src/librustdoc/html/format.rs @@ -1509,8 +1509,6 @@ pub(crate) fn visibility_print_with_space<'a, 'tcx: 'a>( cx: &'a Context<'tcx>, ) -> impl Display + 'a + Captures<'tcx> { use std::fmt::Write as _; - - let hidden: &'static str = if item.is_doc_hidden() { "#[doc(hidden)] " } else { "" }; let vis: Cow<'static, str> = match item.visibility(cx.tcx()) { None => "".into(), Some(ty::Visibility::Public) => "pub ".into(), @@ -1546,8 +1544,13 @@ pub(crate) fn visibility_print_with_space<'a, 'tcx: 'a>( } } }; + + let is_doc_hidden = item.is_doc_hidden(); display_fn(move |f| { - f.write_str(&hidden)?; + if is_doc_hidden { + f.write_str("#[doc(hidden)] ")?; + } + f.write_str(&vis) }) } @@ -1561,7 +1564,6 @@ pub(crate) fn visibility_to_src_with_space<'a, 'tcx: 'a>( item_did: DefId, is_doc_hidden: bool, ) -> impl Display + 'a + Captures<'tcx> { - let hidden: &'static str = if is_doc_hidden { "#[doc(hidden)] " } else { "" }; let vis: Cow<'static, str> = match visibility { None => "".into(), Some(ty::Visibility::Public) => "pub ".into(), @@ -1587,7 +1589,9 @@ pub(crate) fn visibility_to_src_with_space<'a, 'tcx: 'a>( } }; display_fn(move |f| { - f.write_str(&hidden)?; + if is_doc_hidden { + f.write_str("#[doc(hidden)] ")?; + } f.write_str(&vis) }) } From 9718144599d633c95efe6459566a4f86087467ee Mon Sep 17 00:00:00 2001 From: Manish Goregaokar Date: Thu, 14 Mar 2024 15:08:16 +0100 Subject: [PATCH 11/17] fix polarity --- src/librustdoc/html/render/print_item.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/librustdoc/html/render/print_item.rs b/src/librustdoc/html/render/print_item.rs index 0af3f3bc9934..5d4f1acc4b18 100644 --- a/src/librustdoc/html/render/print_item.rs +++ b/src/librustdoc/html/render/print_item.rs @@ -514,10 +514,10 @@ fn item_module(w: &mut Buffer, cx: &mut Context<'_>, item: &clean::Item, items: let visibility_and_hidden = match myitem.visibility(tcx) { Some(ty::Visibility::Restricted(_)) => { if myitem.is_doc_hidden() { - " ðŸ”’ " - } else { // Don't separate with a space when there are two of them " ðŸ”’👻 " + } else { + " ðŸ”’ " } } _ if myitem.is_doc_hidden() => " ðŸ‘» ", From dc35339514f79f4816f5a36121c25abcfa5723e3 Mon Sep 17 00:00:00 2001 From: Jack Wrenn Date: Fri, 15 Mar 2024 17:11:11 +0000 Subject: [PATCH 12/17] Safe Transmute: Use 'not yet supported', not 'unspecified' in errors We can (and will) support analyzing the transmutability of types whose layouts aren't completely specified by its repr. This change ensures that the error messages remain sensible after this support lands. --- .../error_reporting/type_err_ctxt_ext.rs | 8 +++---- compiler/rustc_transmute/src/layout/tree.rs | 14 +++++------ compiler/rustc_transmute/src/lib.rs | 8 +++---- .../src/maybe_transmutable/mod.rs | 4 ++-- .../should_require_well_defined_layout.stderr | 12 +++++----- .../should_require_well_defined_layout.stderr | 12 +++++----- .../should_require_well_defined_layout.stderr | 24 +++++++++---------- .../should_require_well_defined_layout.stderr | 4 ++-- 8 files changed, 43 insertions(+), 43 deletions(-) diff --git a/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs b/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs index b85a05c774fa..e060803c1cb7 100644 --- a/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs +++ b/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs @@ -3073,12 +3073,12 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> { let src = trait_ref.args.type_at(1); let err_msg = format!("`{src}` cannot be safely transmuted into `{dst}`"); let safe_transmute_explanation = match reason { - rustc_transmute::Reason::SrcIsUnspecified => { - format!("`{src}` does not have a well-specified layout") + rustc_transmute::Reason::SrcIsNotYetSupported => { + format!("analyzing the transmutability of `{src}` is not yet supported.") } - rustc_transmute::Reason::DstIsUnspecified => { - format!("`{dst}` does not have a well-specified layout") + rustc_transmute::Reason::DstIsNotYetSupported => { + format!("analyzing the transmutability of `{dst}` is not yet supported.") } rustc_transmute::Reason::DstIsBitIncompatible => { diff --git a/compiler/rustc_transmute/src/layout/tree.rs b/compiler/rustc_transmute/src/layout/tree.rs index c2fc55542ffb..9a43d67d4351 100644 --- a/compiler/rustc_transmute/src/layout/tree.rs +++ b/compiler/rustc_transmute/src/layout/tree.rs @@ -186,8 +186,8 @@ pub(crate) mod rustc { #[derive(Debug, Copy, Clone)] pub(crate) enum Err { - /// The layout of the type is unspecified. - Unspecified, + /// The layout of the type is not yet supported. + NotYetSupported, /// This error will be surfaced elsewhere by rustc, so don't surface it. UnknownLayout, /// Overflow size @@ -288,14 +288,14 @@ pub(crate) mod rustc { if members.len() == 0 { Ok(Tree::unit()) } else { - Err(Err::Unspecified) + Err(Err::NotYetSupported) } } ty::Array(ty, len) => { let len = len .try_eval_target_usize(tcx, ParamEnv::reveal_all()) - .ok_or(Err::Unspecified)?; + .ok_or(Err::NotYetSupported)?; let elt = Tree::from_ty(*ty, tcx)?; Ok(std::iter::repeat(elt) .take(len as usize) @@ -307,7 +307,7 @@ pub(crate) mod rustc { // If the layout is ill-specified, halt. if !(adt_def.repr().c() || adt_def.repr().int.is_some()) { - return Err(Err::Unspecified); + return Err(Err::NotYetSupported); } // Compute a summary of the type's layout. @@ -348,7 +348,7 @@ pub(crate) mod rustc { AdtKind::Union => { // is the layout well-defined? if !adt_def.repr().c() { - return Err(Err::Unspecified); + return Err(Err::NotYetSupported); } let ty_layout = layout_of(tcx, ty)?; @@ -384,7 +384,7 @@ pub(crate) mod rustc { })) } - _ => Err(Err::Unspecified), + _ => Err(Err::NotYetSupported), } } diff --git a/compiler/rustc_transmute/src/lib.rs b/compiler/rustc_transmute/src/lib.rs index 8f3af491453e..e871c4659b4b 100644 --- a/compiler/rustc_transmute/src/lib.rs +++ b/compiler/rustc_transmute/src/lib.rs @@ -43,10 +43,10 @@ pub enum Condition { /// Answers "why wasn't the source type transmutable into the destination type?" #[derive(Debug, Hash, Eq, PartialEq, PartialOrd, Ord, Clone)] pub enum Reason { - /// The layout of the source type is unspecified. - SrcIsUnspecified, - /// The layout of the destination type is unspecified. - DstIsUnspecified, + /// The layout of the source type is not yet supported. + SrcIsNotYetSupported, + /// The layout of the destination type is not yet supported. + DstIsNotYetSupported, /// The layout of the destination type is bit-incompatible with the source type. DstIsBitIncompatible, /// The destination type may carry safety invariants. diff --git a/compiler/rustc_transmute/src/maybe_transmutable/mod.rs b/compiler/rustc_transmute/src/maybe_transmutable/mod.rs index e9f425686c4c..16d15580a05b 100644 --- a/compiler/rustc_transmute/src/maybe_transmutable/mod.rs +++ b/compiler/rustc_transmute/src/maybe_transmutable/mod.rs @@ -56,8 +56,8 @@ mod rustc { } (Err(Err::UnknownLayout), _) => Answer::No(Reason::SrcLayoutUnknown), (_, Err(Err::UnknownLayout)) => Answer::No(Reason::DstLayoutUnknown), - (Err(Err::Unspecified), _) => Answer::No(Reason::SrcIsUnspecified), - (_, Err(Err::Unspecified)) => Answer::No(Reason::DstIsUnspecified), + (Err(Err::NotYetSupported), _) => Answer::No(Reason::SrcIsNotYetSupported), + (_, Err(Err::NotYetSupported)) => Answer::No(Reason::DstIsNotYetSupported), (Err(Err::SizeOverflow), _) => Answer::No(Reason::SrcSizeOverflow), (_, Err(Err::SizeOverflow)) => Answer::No(Reason::DstSizeOverflow), (Ok(src), Ok(dst)) => MaybeTransmutableQuery { src, dst, assume, context }.answer(), diff --git a/tests/ui/transmutability/arrays/should_require_well_defined_layout.stderr b/tests/ui/transmutability/arrays/should_require_well_defined_layout.stderr index fd21ac34183f..e486928a4452 100644 --- a/tests/ui/transmutability/arrays/should_require_well_defined_layout.stderr +++ b/tests/ui/transmutability/arrays/should_require_well_defined_layout.stderr @@ -2,7 +2,7 @@ error[E0277]: `[String; 0]` cannot be safely transmuted into `()` --> $DIR/should_require_well_defined_layout.rs:25:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `[String; 0]` does not have a well-specified layout + | ^^ analyzing the transmutability of `[String; 0]` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -23,7 +23,7 @@ error[E0277]: `u128` cannot be safely transmuted into `[String; 0]` --> $DIR/should_require_well_defined_layout.rs:26:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `[String; 0]` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `[String; 0]` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -44,7 +44,7 @@ error[E0277]: `[String; 1]` cannot be safely transmuted into `()` --> $DIR/should_require_well_defined_layout.rs:31:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `[String; 1]` does not have a well-specified layout + | ^^ analyzing the transmutability of `[String; 1]` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -65,7 +65,7 @@ error[E0277]: `u128` cannot be safely transmuted into `[String; 1]` --> $DIR/should_require_well_defined_layout.rs:32:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `[String; 1]` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `[String; 1]` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -86,7 +86,7 @@ error[E0277]: `[String; 2]` cannot be safely transmuted into `()` --> $DIR/should_require_well_defined_layout.rs:37:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `[String; 2]` does not have a well-specified layout + | ^^ analyzing the transmutability of `[String; 2]` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -107,7 +107,7 @@ error[E0277]: `u128` cannot be safely transmuted into `[String; 2]` --> $DIR/should_require_well_defined_layout.rs:38:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `[String; 2]` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `[String; 2]` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 diff --git a/tests/ui/transmutability/enums/repr/should_require_well_defined_layout.stderr b/tests/ui/transmutability/enums/repr/should_require_well_defined_layout.stderr index 24730935047b..2a683de6a65c 100644 --- a/tests/ui/transmutability/enums/repr/should_require_well_defined_layout.stderr +++ b/tests/ui/transmutability/enums/repr/should_require_well_defined_layout.stderr @@ -2,7 +2,7 @@ error[E0277]: `void::repr_rust` cannot be safely transmuted into `()` --> $DIR/should_require_well_defined_layout.rs:27:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `void::repr_rust` does not have a well-specified layout + | ^^ analyzing the transmutability of `void::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:13:14 @@ -24,7 +24,7 @@ error[E0277]: `u128` cannot be safely transmuted into `void::repr_rust` --> $DIR/should_require_well_defined_layout.rs:28:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `void::repr_rust` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `void::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:13:14 @@ -46,7 +46,7 @@ error[E0277]: `singleton::repr_rust` cannot be safely transmuted into `()` --> $DIR/should_require_well_defined_layout.rs:33:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `singleton::repr_rust` does not have a well-specified layout + | ^^ analyzing the transmutability of `singleton::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:13:14 @@ -68,7 +68,7 @@ error[E0277]: `u128` cannot be safely transmuted into `singleton::repr_rust` --> $DIR/should_require_well_defined_layout.rs:34:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `singleton::repr_rust` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `singleton::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:13:14 @@ -90,7 +90,7 @@ error[E0277]: `duplex::repr_rust` cannot be safely transmuted into `()` --> $DIR/should_require_well_defined_layout.rs:39:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `duplex::repr_rust` does not have a well-specified layout + | ^^ analyzing the transmutability of `duplex::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:13:14 @@ -112,7 +112,7 @@ error[E0277]: `u128` cannot be safely transmuted into `duplex::repr_rust` --> $DIR/should_require_well_defined_layout.rs:40:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `duplex::repr_rust` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `duplex::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:13:14 diff --git a/tests/ui/transmutability/structs/repr/should_require_well_defined_layout.stderr b/tests/ui/transmutability/structs/repr/should_require_well_defined_layout.stderr index 924422de5382..77788f72c216 100644 --- a/tests/ui/transmutability/structs/repr/should_require_well_defined_layout.stderr +++ b/tests/ui/transmutability/structs/repr/should_require_well_defined_layout.stderr @@ -2,7 +2,7 @@ error[E0277]: `should_reject_repr_rust::unit::repr_rust` cannot be safely transm --> $DIR/should_require_well_defined_layout.rs:27:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `should_reject_repr_rust::unit::repr_rust` does not have a well-specified layout + | ^^ analyzing the transmutability of `should_reject_repr_rust::unit::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -24,7 +24,7 @@ error[E0277]: `u128` cannot be safely transmuted into `should_reject_repr_rust:: --> $DIR/should_require_well_defined_layout.rs:28:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `should_reject_repr_rust::unit::repr_rust` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `should_reject_repr_rust::unit::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -46,7 +46,7 @@ error[E0277]: `should_reject_repr_rust::tuple::repr_rust` cannot be safely trans --> $DIR/should_require_well_defined_layout.rs:33:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `should_reject_repr_rust::tuple::repr_rust` does not have a well-specified layout + | ^^ analyzing the transmutability of `should_reject_repr_rust::tuple::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -68,7 +68,7 @@ error[E0277]: `u128` cannot be safely transmuted into `should_reject_repr_rust:: --> $DIR/should_require_well_defined_layout.rs:34:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `should_reject_repr_rust::tuple::repr_rust` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `should_reject_repr_rust::tuple::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -90,7 +90,7 @@ error[E0277]: `should_reject_repr_rust::braces::repr_rust` cannot be safely tran --> $DIR/should_require_well_defined_layout.rs:39:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `should_reject_repr_rust::braces::repr_rust` does not have a well-specified layout + | ^^ analyzing the transmutability of `should_reject_repr_rust::braces::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -112,7 +112,7 @@ error[E0277]: `u128` cannot be safely transmuted into `should_reject_repr_rust:: --> $DIR/should_require_well_defined_layout.rs:40:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `should_reject_repr_rust::braces::repr_rust` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `should_reject_repr_rust::braces::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -134,7 +134,7 @@ error[E0277]: `aligned::repr_rust` cannot be safely transmuted into `()` --> $DIR/should_require_well_defined_layout.rs:45:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `aligned::repr_rust` does not have a well-specified layout + | ^^ analyzing the transmutability of `aligned::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -156,7 +156,7 @@ error[E0277]: `u128` cannot be safely transmuted into `aligned::repr_rust` --> $DIR/should_require_well_defined_layout.rs:46:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `aligned::repr_rust` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `aligned::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -178,7 +178,7 @@ error[E0277]: `packed::repr_rust` cannot be safely transmuted into `()` --> $DIR/should_require_well_defined_layout.rs:51:52 | LL | assert::is_maybe_transmutable::(); - | ^^ `packed::repr_rust` does not have a well-specified layout + | ^^ analyzing the transmutability of `packed::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -200,7 +200,7 @@ error[E0277]: `u128` cannot be safely transmuted into `packed::repr_rust` --> $DIR/should_require_well_defined_layout.rs:52:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `packed::repr_rust` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `packed::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -222,7 +222,7 @@ error[E0277]: `nested::repr_c` cannot be safely transmuted into `()` --> $DIR/should_require_well_defined_layout.rs:58:49 | LL | assert::is_maybe_transmutable::(); - | ^^ `nested::repr_c` does not have a well-specified layout + | ^^ analyzing the transmutability of `nested::repr_c` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -244,7 +244,7 @@ error[E0277]: `u128` cannot be safely transmuted into `nested::repr_c` --> $DIR/should_require_well_defined_layout.rs:59:47 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^ `nested::repr_c` does not have a well-specified layout + | ^^^^^^ analyzing the transmutability of `nested::repr_c` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 diff --git a/tests/ui/transmutability/unions/repr/should_require_well_defined_layout.stderr b/tests/ui/transmutability/unions/repr/should_require_well_defined_layout.stderr index ee0e8a664341..bec07f131039 100644 --- a/tests/ui/transmutability/unions/repr/should_require_well_defined_layout.stderr +++ b/tests/ui/transmutability/unions/repr/should_require_well_defined_layout.stderr @@ -2,7 +2,7 @@ error[E0277]: `should_reject_repr_rust::repr_rust` cannot be safely transmuted i --> $DIR/should_require_well_defined_layout.rs:29:48 | LL | assert::is_maybe_transmutable::(); - | ^^ `should_reject_repr_rust::repr_rust` does not have a well-specified layout + | ^^ analyzing the transmutability of `should_reject_repr_rust::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 @@ -24,7 +24,7 @@ error[E0277]: `u128` cannot be safely transmuted into `should_reject_repr_rust:: --> $DIR/should_require_well_defined_layout.rs:30:43 | LL | assert::is_maybe_transmutable::(); - | ^^^^^^^^^ `should_reject_repr_rust::repr_rust` does not have a well-specified layout + | ^^^^^^^^^ analyzing the transmutability of `should_reject_repr_rust::repr_rust` is not yet supported. | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_require_well_defined_layout.rs:12:14 From 19bc3370632c4f26be1cb16b90f72375c55879a3 Mon Sep 17 00:00:00 2001 From: Maybe Waffle Date: Fri, 15 Mar 2024 12:27:54 +0000 Subject: [PATCH 13/17] Add `rustc_never_type_mode` crate-level attribute to allow experimenting --- compiler/rustc_feature/src/builtin_attrs.rs | 7 ++ compiler/rustc_hir_typeck/src/fallback.rs | 119 ++++++++++++++------ compiler/rustc_span/src/symbol.rs | 4 + 3 files changed, 96 insertions(+), 34 deletions(-) diff --git a/compiler/rustc_feature/src/builtin_attrs.rs b/compiler/rustc_feature/src/builtin_attrs.rs index 1f77484d65ce..a5f8b0b270fc 100644 --- a/compiler/rustc_feature/src/builtin_attrs.rs +++ b/compiler/rustc_feature/src/builtin_attrs.rs @@ -580,6 +580,13 @@ pub const BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ "`may_dangle` has unstable semantics and may be removed in the future", ), + rustc_attr!( + rustc_never_type_mode, Normal, template!(NameValueStr: "fallback_to_unit|fallback_to_niko|no_fallback"), ErrorFollowing, + @only_local: true, + "`rustc_never_type_fallback` is used to experiment with never type fallback and work on \ + never type stabilization, and will never be stable" + ), + // ========================================================================== // Internal attributes: Runtime related: // ========================================================================== diff --git a/compiler/rustc_hir_typeck/src/fallback.rs b/compiler/rustc_hir_typeck/src/fallback.rs index aa8bbad1d124..5206e79177bb 100644 --- a/compiler/rustc_hir_typeck/src/fallback.rs +++ b/compiler/rustc_hir_typeck/src/fallback.rs @@ -4,8 +4,19 @@ use rustc_data_structures::{ graph::{iterate::DepthFirstSearch, vec_graph::VecGraph}, unord::{UnordBag, UnordMap, UnordSet}, }; +use rustc_hir::def_id::CRATE_DEF_ID; use rustc_infer::infer::{DefineOpaqueTypes, InferOk}; use rustc_middle::ty::{self, Ty}; +use rustc_span::sym; + +enum DivergingFallbackBehavior { + /// Always fallback to `()` (aka "always spontaneous decay") + FallbackToUnit, + /// Sometimes fallback to `!`, but mainly fallback to `()` so that most of the crates are not broken. + FallbackToNiko, + /// Don't fallback at all + NoFallback, +} impl<'tcx> FnCtxt<'_, 'tcx> { /// Performs type inference fallback, setting `FnCtxt::fallback_has_occurred` @@ -64,7 +75,9 @@ impl<'tcx> FnCtxt<'_, 'tcx> { return false; } - let diverging_fallback = self.calculate_diverging_fallback(&unresolved_variables); + let diverging_behavior = self.diverging_fallback_behavior(); + let diverging_fallback = + self.calculate_diverging_fallback(&unresolved_variables, diverging_behavior); // We do fallback in two passes, to try to generate // better error messages. @@ -78,6 +91,31 @@ impl<'tcx> FnCtxt<'_, 'tcx> { fallback_occurred } + fn diverging_fallback_behavior(&self) -> DivergingFallbackBehavior { + let Some((mode, span)) = self + .tcx + .get_attr(CRATE_DEF_ID, sym::rustc_never_type_mode) + .map(|attr| (attr.value_str().unwrap(), attr.span)) + else { + if self.tcx.features().never_type_fallback { + return DivergingFallbackBehavior::FallbackToNiko; + } + + return DivergingFallbackBehavior::FallbackToUnit; + }; + + match mode { + sym::fallback_to_unit => DivergingFallbackBehavior::FallbackToUnit, + sym::fallback_to_niko => DivergingFallbackBehavior::FallbackToNiko, + sym::no_fallback => DivergingFallbackBehavior::NoFallback, + _ => { + self.tcx.dcx().span_err(span, format!("unknown never type mode: `{mode}` (supported: `fallback_to_unit`, `fallback_to_niko`, and `no_fallback`)")); + + DivergingFallbackBehavior::FallbackToUnit + } + } + } + fn fallback_effects(&self) -> bool { let unsolved_effects = self.unsolved_effects(); @@ -232,6 +270,7 @@ impl<'tcx> FnCtxt<'_, 'tcx> { fn calculate_diverging_fallback( &self, unresolved_variables: &[Ty<'tcx>], + behavior: DivergingFallbackBehavior, ) -> UnordMap, Ty<'tcx>> { debug!("calculate_diverging_fallback({:?})", unresolved_variables); @@ -345,39 +384,51 @@ impl<'tcx> FnCtxt<'_, 'tcx> { output: infer_var_infos.items().any(|info| info.output), }; - if found_infer_var_info.self_in_trait && found_infer_var_info.output { - // This case falls back to () to ensure that the code pattern in - // tests/ui/never_type/fallback-closure-ret.rs continues to - // compile when never_type_fallback is enabled. - // - // This rule is not readily explainable from first principles, - // but is rather intended as a patchwork fix to ensure code - // which compiles before the stabilization of never type - // fallback continues to work. - // - // Typically this pattern is encountered in a function taking a - // closure as a parameter, where the return type of that closure - // (checked by `relationship.output`) is expected to implement - // some trait (checked by `relationship.self_in_trait`). This - // can come up in non-closure cases too, so we do not limit this - // rule to specifically `FnOnce`. - // - // When the closure's body is something like `panic!()`, the - // return type would normally be inferred to `!`. However, it - // needs to fall back to `()` in order to still compile, as the - // trait is specifically implemented for `()` but not `!`. - // - // For details on the requirements for these relationships to be - // set, see the relationship finding module in - // compiler/rustc_trait_selection/src/traits/relationships.rs. - debug!("fallback to () - found trait and projection: {:?}", diverging_vid); - diverging_fallback.insert(diverging_ty, self.tcx.types.unit); - } else if can_reach_non_diverging { - debug!("fallback to () - reached non-diverging: {:?}", diverging_vid); - diverging_fallback.insert(diverging_ty, self.tcx.types.unit); - } else { - debug!("fallback to ! - all diverging: {:?}", diverging_vid); - diverging_fallback.insert(diverging_ty, Ty::new_diverging_default(self.tcx)); + use DivergingFallbackBehavior::*; + match behavior { + FallbackToUnit => { + debug!("fallback to () - legacy: {:?}", diverging_vid); + diverging_fallback.insert(diverging_ty, self.tcx.types.unit); + } + FallbackToNiko => { + if found_infer_var_info.self_in_trait && found_infer_var_info.output { + // This case falls back to () to ensure that the code pattern in + // tests/ui/never_type/fallback-closure-ret.rs continues to + // compile when never_type_fallback is enabled. + // + // This rule is not readily explainable from first principles, + // but is rather intended as a patchwork fix to ensure code + // which compiles before the stabilization of never type + // fallback continues to work. + // + // Typically this pattern is encountered in a function taking a + // closure as a parameter, where the return type of that closure + // (checked by `relationship.output`) is expected to implement + // some trait (checked by `relationship.self_in_trait`). This + // can come up in non-closure cases too, so we do not limit this + // rule to specifically `FnOnce`. + // + // When the closure's body is something like `panic!()`, the + // return type would normally be inferred to `!`. However, it + // needs to fall back to `()` in order to still compile, as the + // trait is specifically implemented for `()` but not `!`. + // + // For details on the requirements for these relationships to be + // set, see the relationship finding module in + // compiler/rustc_trait_selection/src/traits/relationships.rs. + debug!("fallback to () - found trait and projection: {:?}", diverging_vid); + diverging_fallback.insert(diverging_ty, self.tcx.types.unit); + } else if can_reach_non_diverging { + debug!("fallback to () - reached non-diverging: {:?}", diverging_vid); + diverging_fallback.insert(diverging_ty, self.tcx.types.unit); + } else { + debug!("fallback to ! - all diverging: {:?}", diverging_vid); + diverging_fallback.insert(diverging_ty, self.tcx.types.never); + } + } + NoFallback => { + debug!("no fallback - `rustc_never_type_mode = "no_fallback"`: {:?}", diverging_vid); + } } } diff --git a/compiler/rustc_span/src/symbol.rs b/compiler/rustc_span/src/symbol.rs index 7de0555bb220..0df5e7873c26 100644 --- a/compiler/rustc_span/src/symbol.rs +++ b/compiler/rustc_span/src/symbol.rs @@ -815,6 +815,8 @@ symbols! { fadd_algebraic, fadd_fast, fake_variadic, + fallback_to_niko, + fallback_to_unit, fdiv_algebraic, fdiv_fast, feature, @@ -1233,6 +1235,7 @@ symbols! { no_crate_inject, no_debug, no_default_passes, + no_fallback, no_implicit_prelude, no_inline, no_link, @@ -1551,6 +1554,7 @@ symbols! { rustc_mir, rustc_must_implement_one_of, rustc_never_returns_null_ptr, + rustc_never_type_mode, rustc_no_mir_inline, rustc_nonnull_optimization_guaranteed, rustc_nounwind, From adfdd273ae2bf79aa3bb1f7b453e4df9c188a781 Mon Sep 17 00:00:00 2001 From: Maybe Waffle Date: Fri, 15 Mar 2024 14:50:45 +0000 Subject: [PATCH 14/17] Add `rustc_never_type_mode = "no_fallback"` --- compiler/rustc_feature/src/builtin_attrs.rs | 2 +- compiler/rustc_hir_typeck/src/fallback.rs | 18 ++++++++++++++++-- compiler/rustc_span/src/symbol.rs | 1 + 3 files changed, 18 insertions(+), 3 deletions(-) diff --git a/compiler/rustc_feature/src/builtin_attrs.rs b/compiler/rustc_feature/src/builtin_attrs.rs index a5f8b0b270fc..e5a29f3a8462 100644 --- a/compiler/rustc_feature/src/builtin_attrs.rs +++ b/compiler/rustc_feature/src/builtin_attrs.rs @@ -581,7 +581,7 @@ pub const BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ ), rustc_attr!( - rustc_never_type_mode, Normal, template!(NameValueStr: "fallback_to_unit|fallback_to_niko|no_fallback"), ErrorFollowing, + rustc_never_type_mode, Normal, template!(NameValueStr: "fallback_to_unit|fallback_to_niko|fallback_to_never|no_fallback"), ErrorFollowing, @only_local: true, "`rustc_never_type_fallback` is used to experiment with never type fallback and work on \ never type stabilization, and will never be stable" diff --git a/compiler/rustc_hir_typeck/src/fallback.rs b/compiler/rustc_hir_typeck/src/fallback.rs index 5206e79177bb..c16e941d4c5b 100644 --- a/compiler/rustc_hir_typeck/src/fallback.rs +++ b/compiler/rustc_hir_typeck/src/fallback.rs @@ -14,6 +14,9 @@ enum DivergingFallbackBehavior { FallbackToUnit, /// Sometimes fallback to `!`, but mainly fallback to `()` so that most of the crates are not broken. FallbackToNiko, + /// Always fallback to `!` (which should be equivalent to never falling back + not making + /// never-to-any coercions unless necessary) + FallbackToNever, /// Don't fallback at all NoFallback, } @@ -107,9 +110,10 @@ impl<'tcx> FnCtxt<'_, 'tcx> { match mode { sym::fallback_to_unit => DivergingFallbackBehavior::FallbackToUnit, sym::fallback_to_niko => DivergingFallbackBehavior::FallbackToNiko, + sym::fallback_to_never => DivergingFallbackBehavior::FallbackToNever, sym::no_fallback => DivergingFallbackBehavior::NoFallback, _ => { - self.tcx.dcx().span_err(span, format!("unknown never type mode: `{mode}` (supported: `fallback_to_unit`, `fallback_to_niko`, and `no_fallback`)")); + self.tcx.dcx().span_err(span, format!("unknown never type mode: `{mode}` (supported: `fallback_to_unit`, `fallback_to_niko`, `fallback_to_never` and `no_fallback`)")); DivergingFallbackBehavior::FallbackToUnit } @@ -426,8 +430,18 @@ impl<'tcx> FnCtxt<'_, 'tcx> { diverging_fallback.insert(diverging_ty, self.tcx.types.never); } } + FallbackToNever => { + debug!( + "fallback to ! - `rustc_never_type_mode = \"fallback_to_never\")`: {:?}", + diverging_vid + ); + diverging_fallback.insert(diverging_ty, self.tcx.types.never); + } NoFallback => { - debug!("no fallback - `rustc_never_type_mode = "no_fallback"`: {:?}", diverging_vid); + debug!( + "no fallback - `rustc_never_type_mode = \"no_fallback\"`: {:?}", + diverging_vid + ); } } } diff --git a/compiler/rustc_span/src/symbol.rs b/compiler/rustc_span/src/symbol.rs index 0df5e7873c26..e43c9533382e 100644 --- a/compiler/rustc_span/src/symbol.rs +++ b/compiler/rustc_span/src/symbol.rs @@ -815,6 +815,7 @@ symbols! { fadd_algebraic, fadd_fast, fake_variadic, + fallback_to_never, fallback_to_niko, fallback_to_unit, fdiv_algebraic, From e1e719e1a1916dee9365c390dcb640390433d078 Mon Sep 17 00:00:00 2001 From: Wilfred Hughes Date: Fri, 15 Mar 2024 10:51:41 -0700 Subject: [PATCH 15/17] Mention labelled blocks in `break` docs `break` doesn't require a loop, so note this in the docs. This is covered in the linked sections of the rust reference, but this page implied that `break` is only for loops. --- library/std/src/keyword_docs.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/library/std/src/keyword_docs.rs b/library/std/src/keyword_docs.rs index 873bfb6218b6..8415f36eba25 100644 --- a/library/std/src/keyword_docs.rs +++ b/library/std/src/keyword_docs.rs @@ -48,7 +48,7 @@ mod as_keyword {} #[doc(keyword = "break")] // -/// Exit early from a loop. +/// Exit early from a loop or labelled block. /// /// When `break` is encountered, execution of the associated loop body is /// immediately terminated. From 107807d3932c2765580725604802f76935239723 Mon Sep 17 00:00:00 2001 From: Jack Wrenn Date: Fri, 15 Mar 2024 17:55:49 +0000 Subject: [PATCH 16/17] Safe Transmute: lowercase diagnostics --- .../error_reporting/type_err_ctxt_ext.rs | 8 +- .../alignment/align-fail.stderr | 2 +- ...ve_reprs_should_have_correct_length.stderr | 40 +++--- .../enums/should_pad_variants.stderr | 2 +- .../enums/should_respect_endianness.stderr | 2 +- .../primitives/bool-mut.stderr | 2 +- .../primitives/bool.current.stderr | 2 +- .../primitives/bool.next.stderr | 2 +- .../primitives/numbers.current.stderr | 114 +++++++++--------- .../primitives/numbers.next.stderr | 114 +++++++++--------- .../primitives/unit.current.stderr | 2 +- .../primitives/unit.next.stderr | 2 +- ...sive-wrapper-types-bit-incompatible.stderr | 2 +- .../references/reject_extension.stderr | 2 +- .../references/unit-to-u8.stderr | 2 +- tests/ui/transmutability/region-infer.stderr | 2 +- .../transmute-padding-ice.stderr | 2 +- .../unions/should_pad_variants.stderr | 2 +- .../unions/should_reject_contraction.stderr | 2 +- .../unions/should_reject_disjoint.stderr | 4 +- .../unions/should_reject_intersecting.stderr | 4 +- 21 files changed, 157 insertions(+), 157 deletions(-) diff --git a/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs b/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs index e060803c1cb7..8011d725420b 100644 --- a/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs +++ b/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs @@ -3082,20 +3082,20 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> { } rustc_transmute::Reason::DstIsBitIncompatible => { - format!("At least one value of `{src}` isn't a bit-valid value of `{dst}`") + format!("at least one value of `{src}` isn't a bit-valid value of `{dst}`") } rustc_transmute::Reason::DstMayHaveSafetyInvariants => { format!("`{dst}` may carry safety invariants") } rustc_transmute::Reason::DstIsTooBig => { - format!("The size of `{src}` is smaller than the size of `{dst}`") + format!("the size of `{src}` is smaller than the size of `{dst}`") } rustc_transmute::Reason::DstRefIsTooBig { src, dst } => { let src_size = src.size; let dst_size = dst.size; format!( - "The referent size of `{src}` ({src_size} bytes) is smaller than that of `{dst}` ({dst_size} bytes)" + "the referent size of `{src}` ({src_size} bytes) is smaller than that of `{dst}` ({dst_size} bytes)" ) } rustc_transmute::Reason::SrcSizeOverflow => { @@ -3113,7 +3113,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> { dst_min_align, } => { format!( - "The minimum alignment of `{src}` ({src_min_align}) should be greater than that of `{dst}` ({dst_min_align})" + "the minimum alignment of `{src}` ({src_min_align}) should be greater than that of `{dst}` ({dst_min_align})" ) } rustc_transmute::Reason::DstIsMoreUnique => { diff --git a/tests/ui/transmutability/alignment/align-fail.stderr b/tests/ui/transmutability/alignment/align-fail.stderr index c92c3d841f29..f05e55fb024d 100644 --- a/tests/ui/transmutability/alignment/align-fail.stderr +++ b/tests/ui/transmutability/alignment/align-fail.stderr @@ -2,7 +2,7 @@ error[E0277]: `&[u8; 0]` cannot be safely transmuted into `&[u16; 0]` --> $DIR/align-fail.rs:21:55 | LL | ...tatic [u8; 0], &'static [u16; 0]>(); - | ^^^^^^^^^^^^^^^^^ The minimum alignment of `&[u8; 0]` (1) should be greater than that of `&[u16; 0]` (2) + | ^^^^^^^^^^^^^^^^^ the minimum alignment of `&[u8; 0]` (1) should be greater than that of `&[u16; 0]` (2) | note: required by a bound in `is_maybe_transmutable` --> $DIR/align-fail.rs:9:14 diff --git a/tests/ui/transmutability/enums/repr/primitive_reprs_should_have_correct_length.stderr b/tests/ui/transmutability/enums/repr/primitive_reprs_should_have_correct_length.stderr index b2ff04eeed9e..6c88bf4ff968 100644 --- a/tests/ui/transmutability/enums/repr/primitive_reprs_should_have_correct_length.stderr +++ b/tests/ui/transmutability/enums/repr/primitive_reprs_should_have_correct_length.stderr @@ -2,7 +2,7 @@ error[E0277]: `Zst` cannot be safely transmuted into `V0i8` --> $DIR/primitive_reprs_should_have_correct_length.rs:46:44 | LL | assert::is_transmutable::(); - | ^^^^^^^ The size of `Zst` is smaller than the size of `V0i8` + | ^^^^^^^ the size of `Zst` is smaller than the size of `V0i8` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -24,7 +24,7 @@ error[E0277]: `V0i8` cannot be safely transmuted into `u16` --> $DIR/primitive_reprs_should_have_correct_length.rs:48:44 | LL | assert::is_transmutable::(); - | ^^^^^^ The size of `V0i8` is smaller than the size of `u16` + | ^^^^^^ the size of `V0i8` is smaller than the size of `u16` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -46,7 +46,7 @@ error[E0277]: `Zst` cannot be safely transmuted into `V0u8` --> $DIR/primitive_reprs_should_have_correct_length.rs:54:44 | LL | assert::is_transmutable::(); - | ^^^^^^^ The size of `Zst` is smaller than the size of `V0u8` + | ^^^^^^^ the size of `Zst` is smaller than the size of `V0u8` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -68,7 +68,7 @@ error[E0277]: `V0u8` cannot be safely transmuted into `u16` --> $DIR/primitive_reprs_should_have_correct_length.rs:56:44 | LL | assert::is_transmutable::(); - | ^^^^^^ The size of `V0u8` is smaller than the size of `u16` + | ^^^^^^ the size of `V0u8` is smaller than the size of `u16` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -90,7 +90,7 @@ error[E0277]: `u8` cannot be safely transmuted into `V0i16` --> $DIR/primitive_reprs_should_have_correct_length.rs:68:44 | LL | assert::is_transmutable::(); - | ^^^^^^^ The size of `u8` is smaller than the size of `V0i16` + | ^^^^^^^ the size of `u8` is smaller than the size of `V0i16` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -112,7 +112,7 @@ error[E0277]: `V0i16` cannot be safely transmuted into `u32` --> $DIR/primitive_reprs_should_have_correct_length.rs:70:44 | LL | assert::is_transmutable::(); - | ^^^^^^ The size of `V0i16` is smaller than the size of `u32` + | ^^^^^^ the size of `V0i16` is smaller than the size of `u32` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -134,7 +134,7 @@ error[E0277]: `u8` cannot be safely transmuted into `V0u16` --> $DIR/primitive_reprs_should_have_correct_length.rs:76:44 | LL | assert::is_transmutable::(); - | ^^^^^^^ The size of `u8` is smaller than the size of `V0u16` + | ^^^^^^^ the size of `u8` is smaller than the size of `V0u16` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -156,7 +156,7 @@ error[E0277]: `V0u16` cannot be safely transmuted into `u32` --> $DIR/primitive_reprs_should_have_correct_length.rs:78:44 | LL | assert::is_transmutable::(); - | ^^^^^^ The size of `V0u16` is smaller than the size of `u32` + | ^^^^^^ the size of `V0u16` is smaller than the size of `u32` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -178,7 +178,7 @@ error[E0277]: `u16` cannot be safely transmuted into `V0i32` --> $DIR/primitive_reprs_should_have_correct_length.rs:90:44 | LL | assert::is_transmutable::(); - | ^^^^^^^ The size of `u16` is smaller than the size of `V0i32` + | ^^^^^^^ the size of `u16` is smaller than the size of `V0i32` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -200,7 +200,7 @@ error[E0277]: `V0i32` cannot be safely transmuted into `u64` --> $DIR/primitive_reprs_should_have_correct_length.rs:92:44 | LL | assert::is_transmutable::(); - | ^^^^^^ The size of `V0i32` is smaller than the size of `u64` + | ^^^^^^ the size of `V0i32` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -222,7 +222,7 @@ error[E0277]: `u16` cannot be safely transmuted into `V0u32` --> $DIR/primitive_reprs_should_have_correct_length.rs:98:44 | LL | assert::is_transmutable::(); - | ^^^^^^^ The size of `u16` is smaller than the size of `V0u32` + | ^^^^^^^ the size of `u16` is smaller than the size of `V0u32` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -244,7 +244,7 @@ error[E0277]: `V0u32` cannot be safely transmuted into `u64` --> $DIR/primitive_reprs_should_have_correct_length.rs:100:44 | LL | assert::is_transmutable::(); - | ^^^^^^ The size of `V0u32` is smaller than the size of `u64` + | ^^^^^^ the size of `V0u32` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -266,7 +266,7 @@ error[E0277]: `u32` cannot be safely transmuted into `V0i64` --> $DIR/primitive_reprs_should_have_correct_length.rs:112:44 | LL | assert::is_transmutable::(); - | ^^^^^^^ The size of `u32` is smaller than the size of `V0i64` + | ^^^^^^^ the size of `u32` is smaller than the size of `V0i64` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -288,7 +288,7 @@ error[E0277]: `V0i64` cannot be safely transmuted into `u128` --> $DIR/primitive_reprs_should_have_correct_length.rs:114:44 | LL | assert::is_transmutable::(); - | ^^^^^^ The size of `V0i64` is smaller than the size of `u128` + | ^^^^^^ the size of `V0i64` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -310,7 +310,7 @@ error[E0277]: `u32` cannot be safely transmuted into `V0u64` --> $DIR/primitive_reprs_should_have_correct_length.rs:120:44 | LL | assert::is_transmutable::(); - | ^^^^^^^ The size of `u32` is smaller than the size of `V0u64` + | ^^^^^^^ the size of `u32` is smaller than the size of `V0u64` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -332,7 +332,7 @@ error[E0277]: `V0u64` cannot be safely transmuted into `u128` --> $DIR/primitive_reprs_should_have_correct_length.rs:122:44 | LL | assert::is_transmutable::(); - | ^^^^^^ The size of `V0u64` is smaller than the size of `u128` + | ^^^^^^ the size of `V0u64` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -354,7 +354,7 @@ error[E0277]: `u8` cannot be safely transmuted into `V0isize` --> $DIR/primitive_reprs_should_have_correct_length.rs:134:44 | LL | assert::is_transmutable::(); - | ^^^^^^^ The size of `u8` is smaller than the size of `V0isize` + | ^^^^^^^ the size of `u8` is smaller than the size of `V0isize` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -376,7 +376,7 @@ error[E0277]: `V0isize` cannot be safely transmuted into `[usize; 2]` --> $DIR/primitive_reprs_should_have_correct_length.rs:136:44 | LL | assert::is_transmutable::(); - | ^^^^^^ The size of `V0isize` is smaller than the size of `[usize; 2]` + | ^^^^^^ the size of `V0isize` is smaller than the size of `[usize; 2]` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -398,7 +398,7 @@ error[E0277]: `u8` cannot be safely transmuted into `V0usize` --> $DIR/primitive_reprs_should_have_correct_length.rs:142:44 | LL | assert::is_transmutable::(); - | ^^^^^^^ The size of `u8` is smaller than the size of `V0usize` + | ^^^^^^^ the size of `u8` is smaller than the size of `V0usize` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 @@ -420,7 +420,7 @@ error[E0277]: `V0usize` cannot be safely transmuted into `[usize; 2]` --> $DIR/primitive_reprs_should_have_correct_length.rs:144:44 | LL | assert::is_transmutable::(); - | ^^^^^^ The size of `V0usize` is smaller than the size of `[usize; 2]` + | ^^^^^^ the size of `V0usize` is smaller than the size of `[usize; 2]` | note: required by a bound in `is_transmutable` --> $DIR/primitive_reprs_should_have_correct_length.rs:12:14 diff --git a/tests/ui/transmutability/enums/should_pad_variants.stderr b/tests/ui/transmutability/enums/should_pad_variants.stderr index 13b4c8053adb..da4294bdbce8 100644 --- a/tests/ui/transmutability/enums/should_pad_variants.stderr +++ b/tests/ui/transmutability/enums/should_pad_variants.stderr @@ -2,7 +2,7 @@ error[E0277]: `Src` cannot be safely transmuted into `Dst` --> $DIR/should_pad_variants.rs:43:36 | LL | assert::is_transmutable::(); - | ^^^ The size of `Src` is smaller than the size of `Dst` + | ^^^ the size of `Src` is smaller than the size of `Dst` | note: required by a bound in `is_transmutable` --> $DIR/should_pad_variants.rs:13:14 diff --git a/tests/ui/transmutability/enums/should_respect_endianness.stderr b/tests/ui/transmutability/enums/should_respect_endianness.stderr index c2a2eb53458e..9f88bb068134 100644 --- a/tests/ui/transmutability/enums/should_respect_endianness.stderr +++ b/tests/ui/transmutability/enums/should_respect_endianness.stderr @@ -2,7 +2,7 @@ error[E0277]: `Src` cannot be safely transmuted into `Unexpected` --> $DIR/should_respect_endianness.rs:35:36 | LL | assert::is_transmutable::(); - | ^^^^^^^^^^ At least one value of `Src` isn't a bit-valid value of `Unexpected` + | ^^^^^^^^^^ at least one value of `Src` isn't a bit-valid value of `Unexpected` | note: required by a bound in `is_transmutable` --> $DIR/should_respect_endianness.rs:13:14 diff --git a/tests/ui/transmutability/primitives/bool-mut.stderr b/tests/ui/transmutability/primitives/bool-mut.stderr index c4f295fc70a2..464c2755e11b 100644 --- a/tests/ui/transmutability/primitives/bool-mut.stderr +++ b/tests/ui/transmutability/primitives/bool-mut.stderr @@ -2,7 +2,7 @@ error[E0277]: `u8` cannot be safely transmuted into `bool` --> $DIR/bool-mut.rs:15:50 | LL | assert::is_transmutable::<&'static mut bool, &'static mut u8>() - | ^^^^^^^^^^^^^^^ At least one value of `u8` isn't a bit-valid value of `bool` + | ^^^^^^^^^^^^^^^ at least one value of `u8` isn't a bit-valid value of `bool` | note: required by a bound in `is_transmutable` --> $DIR/bool-mut.rs:10:14 diff --git a/tests/ui/transmutability/primitives/bool.current.stderr b/tests/ui/transmutability/primitives/bool.current.stderr index 98e4a1029c90..da6a4a44e95e 100644 --- a/tests/ui/transmutability/primitives/bool.current.stderr +++ b/tests/ui/transmutability/primitives/bool.current.stderr @@ -2,7 +2,7 @@ error[E0277]: `u8` cannot be safely transmuted into `bool` --> $DIR/bool.rs:21:35 | LL | assert::is_transmutable::(); - | ^^^^ At least one value of `u8` isn't a bit-valid value of `bool` + | ^^^^ at least one value of `u8` isn't a bit-valid value of `bool` | note: required by a bound in `is_transmutable` --> $DIR/bool.rs:11:14 diff --git a/tests/ui/transmutability/primitives/bool.next.stderr b/tests/ui/transmutability/primitives/bool.next.stderr index 98e4a1029c90..da6a4a44e95e 100644 --- a/tests/ui/transmutability/primitives/bool.next.stderr +++ b/tests/ui/transmutability/primitives/bool.next.stderr @@ -2,7 +2,7 @@ error[E0277]: `u8` cannot be safely transmuted into `bool` --> $DIR/bool.rs:21:35 | LL | assert::is_transmutable::(); - | ^^^^ At least one value of `u8` isn't a bit-valid value of `bool` + | ^^^^ at least one value of `u8` isn't a bit-valid value of `bool` | note: required by a bound in `is_transmutable` --> $DIR/bool.rs:11:14 diff --git a/tests/ui/transmutability/primitives/numbers.current.stderr b/tests/ui/transmutability/primitives/numbers.current.stderr index 7a80e444149d..0a9b9d182f85 100644 --- a/tests/ui/transmutability/primitives/numbers.current.stderr +++ b/tests/ui/transmutability/primitives/numbers.current.stderr @@ -2,7 +2,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i16` --> $DIR/numbers.rs:64:40 | LL | assert::is_transmutable::< i8, i16>(); - | ^^^ The size of `i8` is smaller than the size of `i16` + | ^^^ the size of `i8` is smaller than the size of `i16` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -17,7 +17,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u16` --> $DIR/numbers.rs:65:40 | LL | assert::is_transmutable::< i8, u16>(); - | ^^^ The size of `i8` is smaller than the size of `u16` + | ^^^ the size of `i8` is smaller than the size of `u16` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -32,7 +32,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i32` --> $DIR/numbers.rs:66:40 | LL | assert::is_transmutable::< i8, i32>(); - | ^^^ The size of `i8` is smaller than the size of `i32` + | ^^^ the size of `i8` is smaller than the size of `i32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -47,7 +47,7 @@ error[E0277]: `i8` cannot be safely transmuted into `f32` --> $DIR/numbers.rs:67:40 | LL | assert::is_transmutable::< i8, f32>(); - | ^^^ The size of `i8` is smaller than the size of `f32` + | ^^^ the size of `i8` is smaller than the size of `f32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -62,7 +62,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u32` --> $DIR/numbers.rs:68:40 | LL | assert::is_transmutable::< i8, u32>(); - | ^^^ The size of `i8` is smaller than the size of `u32` + | ^^^ the size of `i8` is smaller than the size of `u32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -77,7 +77,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:69:40 | LL | assert::is_transmutable::< i8, u64>(); - | ^^^ The size of `i8` is smaller than the size of `u64` + | ^^^ the size of `i8` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -92,7 +92,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:70:40 | LL | assert::is_transmutable::< i8, i64>(); - | ^^^ The size of `i8` is smaller than the size of `i64` + | ^^^ the size of `i8` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -107,7 +107,7 @@ error[E0277]: `i8` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:71:40 | LL | assert::is_transmutable::< i8, f64>(); - | ^^^ The size of `i8` is smaller than the size of `f64` + | ^^^ the size of `i8` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -122,7 +122,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:72:39 | LL | assert::is_transmutable::< i8, u128>(); - | ^^^^ The size of `i8` is smaller than the size of `u128` + | ^^^^ the size of `i8` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -137,7 +137,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:73:39 | LL | assert::is_transmutable::< i8, i128>(); - | ^^^^ The size of `i8` is smaller than the size of `i128` + | ^^^^ the size of `i8` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -152,7 +152,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i16` --> $DIR/numbers.rs:75:40 | LL | assert::is_transmutable::< u8, i16>(); - | ^^^ The size of `u8` is smaller than the size of `i16` + | ^^^ the size of `u8` is smaller than the size of `i16` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -167,7 +167,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u16` --> $DIR/numbers.rs:76:40 | LL | assert::is_transmutable::< u8, u16>(); - | ^^^ The size of `u8` is smaller than the size of `u16` + | ^^^ the size of `u8` is smaller than the size of `u16` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -182,7 +182,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i32` --> $DIR/numbers.rs:77:40 | LL | assert::is_transmutable::< u8, i32>(); - | ^^^ The size of `u8` is smaller than the size of `i32` + | ^^^ the size of `u8` is smaller than the size of `i32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -197,7 +197,7 @@ error[E0277]: `u8` cannot be safely transmuted into `f32` --> $DIR/numbers.rs:78:40 | LL | assert::is_transmutable::< u8, f32>(); - | ^^^ The size of `u8` is smaller than the size of `f32` + | ^^^ the size of `u8` is smaller than the size of `f32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -212,7 +212,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u32` --> $DIR/numbers.rs:79:40 | LL | assert::is_transmutable::< u8, u32>(); - | ^^^ The size of `u8` is smaller than the size of `u32` + | ^^^ the size of `u8` is smaller than the size of `u32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -227,7 +227,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:80:40 | LL | assert::is_transmutable::< u8, u64>(); - | ^^^ The size of `u8` is smaller than the size of `u64` + | ^^^ the size of `u8` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -242,7 +242,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:81:40 | LL | assert::is_transmutable::< u8, i64>(); - | ^^^ The size of `u8` is smaller than the size of `i64` + | ^^^ the size of `u8` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -257,7 +257,7 @@ error[E0277]: `u8` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:82:40 | LL | assert::is_transmutable::< u8, f64>(); - | ^^^ The size of `u8` is smaller than the size of `f64` + | ^^^ the size of `u8` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -272,7 +272,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:83:39 | LL | assert::is_transmutable::< u8, u128>(); - | ^^^^ The size of `u8` is smaller than the size of `u128` + | ^^^^ the size of `u8` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -287,7 +287,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:84:39 | LL | assert::is_transmutable::< u8, i128>(); - | ^^^^ The size of `u8` is smaller than the size of `i128` + | ^^^^ the size of `u8` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -302,7 +302,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i32` --> $DIR/numbers.rs:86:40 | LL | assert::is_transmutable::< i16, i32>(); - | ^^^ The size of `i16` is smaller than the size of `i32` + | ^^^ the size of `i16` is smaller than the size of `i32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -317,7 +317,7 @@ error[E0277]: `i16` cannot be safely transmuted into `f32` --> $DIR/numbers.rs:87:40 | LL | assert::is_transmutable::< i16, f32>(); - | ^^^ The size of `i16` is smaller than the size of `f32` + | ^^^ the size of `i16` is smaller than the size of `f32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -332,7 +332,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u32` --> $DIR/numbers.rs:88:40 | LL | assert::is_transmutable::< i16, u32>(); - | ^^^ The size of `i16` is smaller than the size of `u32` + | ^^^ the size of `i16` is smaller than the size of `u32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -347,7 +347,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:89:40 | LL | assert::is_transmutable::< i16, u64>(); - | ^^^ The size of `i16` is smaller than the size of `u64` + | ^^^ the size of `i16` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -362,7 +362,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:90:40 | LL | assert::is_transmutable::< i16, i64>(); - | ^^^ The size of `i16` is smaller than the size of `i64` + | ^^^ the size of `i16` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -377,7 +377,7 @@ error[E0277]: `i16` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:91:40 | LL | assert::is_transmutable::< i16, f64>(); - | ^^^ The size of `i16` is smaller than the size of `f64` + | ^^^ the size of `i16` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -392,7 +392,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:92:39 | LL | assert::is_transmutable::< i16, u128>(); - | ^^^^ The size of `i16` is smaller than the size of `u128` + | ^^^^ the size of `i16` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -407,7 +407,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:93:39 | LL | assert::is_transmutable::< i16, i128>(); - | ^^^^ The size of `i16` is smaller than the size of `i128` + | ^^^^ the size of `i16` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -422,7 +422,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i32` --> $DIR/numbers.rs:95:40 | LL | assert::is_transmutable::< u16, i32>(); - | ^^^ The size of `u16` is smaller than the size of `i32` + | ^^^ the size of `u16` is smaller than the size of `i32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -437,7 +437,7 @@ error[E0277]: `u16` cannot be safely transmuted into `f32` --> $DIR/numbers.rs:96:40 | LL | assert::is_transmutable::< u16, f32>(); - | ^^^ The size of `u16` is smaller than the size of `f32` + | ^^^ the size of `u16` is smaller than the size of `f32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -452,7 +452,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u32` --> $DIR/numbers.rs:97:40 | LL | assert::is_transmutable::< u16, u32>(); - | ^^^ The size of `u16` is smaller than the size of `u32` + | ^^^ the size of `u16` is smaller than the size of `u32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -467,7 +467,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:98:40 | LL | assert::is_transmutable::< u16, u64>(); - | ^^^ The size of `u16` is smaller than the size of `u64` + | ^^^ the size of `u16` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -482,7 +482,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:99:40 | LL | assert::is_transmutable::< u16, i64>(); - | ^^^ The size of `u16` is smaller than the size of `i64` + | ^^^ the size of `u16` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -497,7 +497,7 @@ error[E0277]: `u16` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:100:40 | LL | assert::is_transmutable::< u16, f64>(); - | ^^^ The size of `u16` is smaller than the size of `f64` + | ^^^ the size of `u16` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -512,7 +512,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:101:39 | LL | assert::is_transmutable::< u16, u128>(); - | ^^^^ The size of `u16` is smaller than the size of `u128` + | ^^^^ the size of `u16` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -527,7 +527,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:102:39 | LL | assert::is_transmutable::< u16, i128>(); - | ^^^^ The size of `u16` is smaller than the size of `i128` + | ^^^^ the size of `u16` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -542,7 +542,7 @@ error[E0277]: `i32` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:104:40 | LL | assert::is_transmutable::< i32, u64>(); - | ^^^ The size of `i32` is smaller than the size of `u64` + | ^^^ the size of `i32` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -557,7 +557,7 @@ error[E0277]: `i32` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:105:40 | LL | assert::is_transmutable::< i32, i64>(); - | ^^^ The size of `i32` is smaller than the size of `i64` + | ^^^ the size of `i32` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -572,7 +572,7 @@ error[E0277]: `i32` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:106:40 | LL | assert::is_transmutable::< i32, f64>(); - | ^^^ The size of `i32` is smaller than the size of `f64` + | ^^^ the size of `i32` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -587,7 +587,7 @@ error[E0277]: `i32` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:107:39 | LL | assert::is_transmutable::< i32, u128>(); - | ^^^^ The size of `i32` is smaller than the size of `u128` + | ^^^^ the size of `i32` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -602,7 +602,7 @@ error[E0277]: `i32` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:108:39 | LL | assert::is_transmutable::< i32, i128>(); - | ^^^^ The size of `i32` is smaller than the size of `i128` + | ^^^^ the size of `i32` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -617,7 +617,7 @@ error[E0277]: `f32` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:110:40 | LL | assert::is_transmutable::< f32, u64>(); - | ^^^ The size of `f32` is smaller than the size of `u64` + | ^^^ the size of `f32` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -632,7 +632,7 @@ error[E0277]: `f32` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:111:40 | LL | assert::is_transmutable::< f32, i64>(); - | ^^^ The size of `f32` is smaller than the size of `i64` + | ^^^ the size of `f32` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -647,7 +647,7 @@ error[E0277]: `f32` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:112:40 | LL | assert::is_transmutable::< f32, f64>(); - | ^^^ The size of `f32` is smaller than the size of `f64` + | ^^^ the size of `f32` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -662,7 +662,7 @@ error[E0277]: `f32` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:113:39 | LL | assert::is_transmutable::< f32, u128>(); - | ^^^^ The size of `f32` is smaller than the size of `u128` + | ^^^^ the size of `f32` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -677,7 +677,7 @@ error[E0277]: `f32` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:114:39 | LL | assert::is_transmutable::< f32, i128>(); - | ^^^^ The size of `f32` is smaller than the size of `i128` + | ^^^^ the size of `f32` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -692,7 +692,7 @@ error[E0277]: `u32` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:116:40 | LL | assert::is_transmutable::< u32, u64>(); - | ^^^ The size of `u32` is smaller than the size of `u64` + | ^^^ the size of `u32` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -707,7 +707,7 @@ error[E0277]: `u32` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:117:40 | LL | assert::is_transmutable::< u32, i64>(); - | ^^^ The size of `u32` is smaller than the size of `i64` + | ^^^ the size of `u32` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -722,7 +722,7 @@ error[E0277]: `u32` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:118:40 | LL | assert::is_transmutable::< u32, f64>(); - | ^^^ The size of `u32` is smaller than the size of `f64` + | ^^^ the size of `u32` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -737,7 +737,7 @@ error[E0277]: `u32` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:119:39 | LL | assert::is_transmutable::< u32, u128>(); - | ^^^^ The size of `u32` is smaller than the size of `u128` + | ^^^^ the size of `u32` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -752,7 +752,7 @@ error[E0277]: `u32` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:120:39 | LL | assert::is_transmutable::< u32, i128>(); - | ^^^^ The size of `u32` is smaller than the size of `i128` + | ^^^^ the size of `u32` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -767,7 +767,7 @@ error[E0277]: `u64` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:122:39 | LL | assert::is_transmutable::< u64, u128>(); - | ^^^^ The size of `u64` is smaller than the size of `u128` + | ^^^^ the size of `u64` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -782,7 +782,7 @@ error[E0277]: `u64` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:123:39 | LL | assert::is_transmutable::< u64, i128>(); - | ^^^^ The size of `u64` is smaller than the size of `i128` + | ^^^^ the size of `u64` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -797,7 +797,7 @@ error[E0277]: `i64` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:125:39 | LL | assert::is_transmutable::< i64, u128>(); - | ^^^^ The size of `i64` is smaller than the size of `u128` + | ^^^^ the size of `i64` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -812,7 +812,7 @@ error[E0277]: `i64` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:126:39 | LL | assert::is_transmutable::< i64, i128>(); - | ^^^^ The size of `i64` is smaller than the size of `i128` + | ^^^^ the size of `i64` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -827,7 +827,7 @@ error[E0277]: `f64` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:128:39 | LL | assert::is_transmutable::< f64, u128>(); - | ^^^^ The size of `f64` is smaller than the size of `u128` + | ^^^^ the size of `f64` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -842,7 +842,7 @@ error[E0277]: `f64` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:129:39 | LL | assert::is_transmutable::< f64, i128>(); - | ^^^^ The size of `f64` is smaller than the size of `i128` + | ^^^^ the size of `f64` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 diff --git a/tests/ui/transmutability/primitives/numbers.next.stderr b/tests/ui/transmutability/primitives/numbers.next.stderr index 7a80e444149d..0a9b9d182f85 100644 --- a/tests/ui/transmutability/primitives/numbers.next.stderr +++ b/tests/ui/transmutability/primitives/numbers.next.stderr @@ -2,7 +2,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i16` --> $DIR/numbers.rs:64:40 | LL | assert::is_transmutable::< i8, i16>(); - | ^^^ The size of `i8` is smaller than the size of `i16` + | ^^^ the size of `i8` is smaller than the size of `i16` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -17,7 +17,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u16` --> $DIR/numbers.rs:65:40 | LL | assert::is_transmutable::< i8, u16>(); - | ^^^ The size of `i8` is smaller than the size of `u16` + | ^^^ the size of `i8` is smaller than the size of `u16` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -32,7 +32,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i32` --> $DIR/numbers.rs:66:40 | LL | assert::is_transmutable::< i8, i32>(); - | ^^^ The size of `i8` is smaller than the size of `i32` + | ^^^ the size of `i8` is smaller than the size of `i32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -47,7 +47,7 @@ error[E0277]: `i8` cannot be safely transmuted into `f32` --> $DIR/numbers.rs:67:40 | LL | assert::is_transmutable::< i8, f32>(); - | ^^^ The size of `i8` is smaller than the size of `f32` + | ^^^ the size of `i8` is smaller than the size of `f32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -62,7 +62,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u32` --> $DIR/numbers.rs:68:40 | LL | assert::is_transmutable::< i8, u32>(); - | ^^^ The size of `i8` is smaller than the size of `u32` + | ^^^ the size of `i8` is smaller than the size of `u32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -77,7 +77,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:69:40 | LL | assert::is_transmutable::< i8, u64>(); - | ^^^ The size of `i8` is smaller than the size of `u64` + | ^^^ the size of `i8` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -92,7 +92,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:70:40 | LL | assert::is_transmutable::< i8, i64>(); - | ^^^ The size of `i8` is smaller than the size of `i64` + | ^^^ the size of `i8` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -107,7 +107,7 @@ error[E0277]: `i8` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:71:40 | LL | assert::is_transmutable::< i8, f64>(); - | ^^^ The size of `i8` is smaller than the size of `f64` + | ^^^ the size of `i8` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -122,7 +122,7 @@ error[E0277]: `i8` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:72:39 | LL | assert::is_transmutable::< i8, u128>(); - | ^^^^ The size of `i8` is smaller than the size of `u128` + | ^^^^ the size of `i8` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -137,7 +137,7 @@ error[E0277]: `i8` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:73:39 | LL | assert::is_transmutable::< i8, i128>(); - | ^^^^ The size of `i8` is smaller than the size of `i128` + | ^^^^ the size of `i8` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -152,7 +152,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i16` --> $DIR/numbers.rs:75:40 | LL | assert::is_transmutable::< u8, i16>(); - | ^^^ The size of `u8` is smaller than the size of `i16` + | ^^^ the size of `u8` is smaller than the size of `i16` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -167,7 +167,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u16` --> $DIR/numbers.rs:76:40 | LL | assert::is_transmutable::< u8, u16>(); - | ^^^ The size of `u8` is smaller than the size of `u16` + | ^^^ the size of `u8` is smaller than the size of `u16` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -182,7 +182,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i32` --> $DIR/numbers.rs:77:40 | LL | assert::is_transmutable::< u8, i32>(); - | ^^^ The size of `u8` is smaller than the size of `i32` + | ^^^ the size of `u8` is smaller than the size of `i32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -197,7 +197,7 @@ error[E0277]: `u8` cannot be safely transmuted into `f32` --> $DIR/numbers.rs:78:40 | LL | assert::is_transmutable::< u8, f32>(); - | ^^^ The size of `u8` is smaller than the size of `f32` + | ^^^ the size of `u8` is smaller than the size of `f32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -212,7 +212,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u32` --> $DIR/numbers.rs:79:40 | LL | assert::is_transmutable::< u8, u32>(); - | ^^^ The size of `u8` is smaller than the size of `u32` + | ^^^ the size of `u8` is smaller than the size of `u32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -227,7 +227,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:80:40 | LL | assert::is_transmutable::< u8, u64>(); - | ^^^ The size of `u8` is smaller than the size of `u64` + | ^^^ the size of `u8` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -242,7 +242,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:81:40 | LL | assert::is_transmutable::< u8, i64>(); - | ^^^ The size of `u8` is smaller than the size of `i64` + | ^^^ the size of `u8` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -257,7 +257,7 @@ error[E0277]: `u8` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:82:40 | LL | assert::is_transmutable::< u8, f64>(); - | ^^^ The size of `u8` is smaller than the size of `f64` + | ^^^ the size of `u8` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -272,7 +272,7 @@ error[E0277]: `u8` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:83:39 | LL | assert::is_transmutable::< u8, u128>(); - | ^^^^ The size of `u8` is smaller than the size of `u128` + | ^^^^ the size of `u8` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -287,7 +287,7 @@ error[E0277]: `u8` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:84:39 | LL | assert::is_transmutable::< u8, i128>(); - | ^^^^ The size of `u8` is smaller than the size of `i128` + | ^^^^ the size of `u8` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -302,7 +302,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i32` --> $DIR/numbers.rs:86:40 | LL | assert::is_transmutable::< i16, i32>(); - | ^^^ The size of `i16` is smaller than the size of `i32` + | ^^^ the size of `i16` is smaller than the size of `i32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -317,7 +317,7 @@ error[E0277]: `i16` cannot be safely transmuted into `f32` --> $DIR/numbers.rs:87:40 | LL | assert::is_transmutable::< i16, f32>(); - | ^^^ The size of `i16` is smaller than the size of `f32` + | ^^^ the size of `i16` is smaller than the size of `f32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -332,7 +332,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u32` --> $DIR/numbers.rs:88:40 | LL | assert::is_transmutable::< i16, u32>(); - | ^^^ The size of `i16` is smaller than the size of `u32` + | ^^^ the size of `i16` is smaller than the size of `u32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -347,7 +347,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:89:40 | LL | assert::is_transmutable::< i16, u64>(); - | ^^^ The size of `i16` is smaller than the size of `u64` + | ^^^ the size of `i16` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -362,7 +362,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:90:40 | LL | assert::is_transmutable::< i16, i64>(); - | ^^^ The size of `i16` is smaller than the size of `i64` + | ^^^ the size of `i16` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -377,7 +377,7 @@ error[E0277]: `i16` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:91:40 | LL | assert::is_transmutable::< i16, f64>(); - | ^^^ The size of `i16` is smaller than the size of `f64` + | ^^^ the size of `i16` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -392,7 +392,7 @@ error[E0277]: `i16` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:92:39 | LL | assert::is_transmutable::< i16, u128>(); - | ^^^^ The size of `i16` is smaller than the size of `u128` + | ^^^^ the size of `i16` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -407,7 +407,7 @@ error[E0277]: `i16` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:93:39 | LL | assert::is_transmutable::< i16, i128>(); - | ^^^^ The size of `i16` is smaller than the size of `i128` + | ^^^^ the size of `i16` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -422,7 +422,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i32` --> $DIR/numbers.rs:95:40 | LL | assert::is_transmutable::< u16, i32>(); - | ^^^ The size of `u16` is smaller than the size of `i32` + | ^^^ the size of `u16` is smaller than the size of `i32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -437,7 +437,7 @@ error[E0277]: `u16` cannot be safely transmuted into `f32` --> $DIR/numbers.rs:96:40 | LL | assert::is_transmutable::< u16, f32>(); - | ^^^ The size of `u16` is smaller than the size of `f32` + | ^^^ the size of `u16` is smaller than the size of `f32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -452,7 +452,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u32` --> $DIR/numbers.rs:97:40 | LL | assert::is_transmutable::< u16, u32>(); - | ^^^ The size of `u16` is smaller than the size of `u32` + | ^^^ the size of `u16` is smaller than the size of `u32` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -467,7 +467,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:98:40 | LL | assert::is_transmutable::< u16, u64>(); - | ^^^ The size of `u16` is smaller than the size of `u64` + | ^^^ the size of `u16` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -482,7 +482,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:99:40 | LL | assert::is_transmutable::< u16, i64>(); - | ^^^ The size of `u16` is smaller than the size of `i64` + | ^^^ the size of `u16` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -497,7 +497,7 @@ error[E0277]: `u16` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:100:40 | LL | assert::is_transmutable::< u16, f64>(); - | ^^^ The size of `u16` is smaller than the size of `f64` + | ^^^ the size of `u16` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -512,7 +512,7 @@ error[E0277]: `u16` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:101:39 | LL | assert::is_transmutable::< u16, u128>(); - | ^^^^ The size of `u16` is smaller than the size of `u128` + | ^^^^ the size of `u16` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -527,7 +527,7 @@ error[E0277]: `u16` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:102:39 | LL | assert::is_transmutable::< u16, i128>(); - | ^^^^ The size of `u16` is smaller than the size of `i128` + | ^^^^ the size of `u16` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -542,7 +542,7 @@ error[E0277]: `i32` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:104:40 | LL | assert::is_transmutable::< i32, u64>(); - | ^^^ The size of `i32` is smaller than the size of `u64` + | ^^^ the size of `i32` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -557,7 +557,7 @@ error[E0277]: `i32` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:105:40 | LL | assert::is_transmutable::< i32, i64>(); - | ^^^ The size of `i32` is smaller than the size of `i64` + | ^^^ the size of `i32` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -572,7 +572,7 @@ error[E0277]: `i32` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:106:40 | LL | assert::is_transmutable::< i32, f64>(); - | ^^^ The size of `i32` is smaller than the size of `f64` + | ^^^ the size of `i32` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -587,7 +587,7 @@ error[E0277]: `i32` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:107:39 | LL | assert::is_transmutable::< i32, u128>(); - | ^^^^ The size of `i32` is smaller than the size of `u128` + | ^^^^ the size of `i32` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -602,7 +602,7 @@ error[E0277]: `i32` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:108:39 | LL | assert::is_transmutable::< i32, i128>(); - | ^^^^ The size of `i32` is smaller than the size of `i128` + | ^^^^ the size of `i32` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -617,7 +617,7 @@ error[E0277]: `f32` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:110:40 | LL | assert::is_transmutable::< f32, u64>(); - | ^^^ The size of `f32` is smaller than the size of `u64` + | ^^^ the size of `f32` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -632,7 +632,7 @@ error[E0277]: `f32` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:111:40 | LL | assert::is_transmutable::< f32, i64>(); - | ^^^ The size of `f32` is smaller than the size of `i64` + | ^^^ the size of `f32` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -647,7 +647,7 @@ error[E0277]: `f32` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:112:40 | LL | assert::is_transmutable::< f32, f64>(); - | ^^^ The size of `f32` is smaller than the size of `f64` + | ^^^ the size of `f32` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -662,7 +662,7 @@ error[E0277]: `f32` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:113:39 | LL | assert::is_transmutable::< f32, u128>(); - | ^^^^ The size of `f32` is smaller than the size of `u128` + | ^^^^ the size of `f32` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -677,7 +677,7 @@ error[E0277]: `f32` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:114:39 | LL | assert::is_transmutable::< f32, i128>(); - | ^^^^ The size of `f32` is smaller than the size of `i128` + | ^^^^ the size of `f32` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -692,7 +692,7 @@ error[E0277]: `u32` cannot be safely transmuted into `u64` --> $DIR/numbers.rs:116:40 | LL | assert::is_transmutable::< u32, u64>(); - | ^^^ The size of `u32` is smaller than the size of `u64` + | ^^^ the size of `u32` is smaller than the size of `u64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -707,7 +707,7 @@ error[E0277]: `u32` cannot be safely transmuted into `i64` --> $DIR/numbers.rs:117:40 | LL | assert::is_transmutable::< u32, i64>(); - | ^^^ The size of `u32` is smaller than the size of `i64` + | ^^^ the size of `u32` is smaller than the size of `i64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -722,7 +722,7 @@ error[E0277]: `u32` cannot be safely transmuted into `f64` --> $DIR/numbers.rs:118:40 | LL | assert::is_transmutable::< u32, f64>(); - | ^^^ The size of `u32` is smaller than the size of `f64` + | ^^^ the size of `u32` is smaller than the size of `f64` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -737,7 +737,7 @@ error[E0277]: `u32` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:119:39 | LL | assert::is_transmutable::< u32, u128>(); - | ^^^^ The size of `u32` is smaller than the size of `u128` + | ^^^^ the size of `u32` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -752,7 +752,7 @@ error[E0277]: `u32` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:120:39 | LL | assert::is_transmutable::< u32, i128>(); - | ^^^^ The size of `u32` is smaller than the size of `i128` + | ^^^^ the size of `u32` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -767,7 +767,7 @@ error[E0277]: `u64` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:122:39 | LL | assert::is_transmutable::< u64, u128>(); - | ^^^^ The size of `u64` is smaller than the size of `u128` + | ^^^^ the size of `u64` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -782,7 +782,7 @@ error[E0277]: `u64` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:123:39 | LL | assert::is_transmutable::< u64, i128>(); - | ^^^^ The size of `u64` is smaller than the size of `i128` + | ^^^^ the size of `u64` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -797,7 +797,7 @@ error[E0277]: `i64` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:125:39 | LL | assert::is_transmutable::< i64, u128>(); - | ^^^^ The size of `i64` is smaller than the size of `u128` + | ^^^^ the size of `i64` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -812,7 +812,7 @@ error[E0277]: `i64` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:126:39 | LL | assert::is_transmutable::< i64, i128>(); - | ^^^^ The size of `i64` is smaller than the size of `i128` + | ^^^^ the size of `i64` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -827,7 +827,7 @@ error[E0277]: `f64` cannot be safely transmuted into `u128` --> $DIR/numbers.rs:128:39 | LL | assert::is_transmutable::< f64, u128>(); - | ^^^^ The size of `f64` is smaller than the size of `u128` + | ^^^^ the size of `f64` is smaller than the size of `u128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 @@ -842,7 +842,7 @@ error[E0277]: `f64` cannot be safely transmuted into `i128` --> $DIR/numbers.rs:129:39 | LL | assert::is_transmutable::< f64, i128>(); - | ^^^^ The size of `f64` is smaller than the size of `i128` + | ^^^^ the size of `f64` is smaller than the size of `i128` | note: required by a bound in `is_transmutable` --> $DIR/numbers.rs:14:14 diff --git a/tests/ui/transmutability/primitives/unit.current.stderr b/tests/ui/transmutability/primitives/unit.current.stderr index b2831dbf8425..52b708d680e8 100644 --- a/tests/ui/transmutability/primitives/unit.current.stderr +++ b/tests/ui/transmutability/primitives/unit.current.stderr @@ -2,7 +2,7 @@ error[E0277]: `()` cannot be safely transmuted into `u8` --> $DIR/unit.rs:31:35 | LL | assert::is_transmutable::<(), u8>(); - | ^^ The size of `()` is smaller than the size of `u8` + | ^^ the size of `()` is smaller than the size of `u8` | note: required by a bound in `is_transmutable` --> $DIR/unit.rs:16:14 diff --git a/tests/ui/transmutability/primitives/unit.next.stderr b/tests/ui/transmutability/primitives/unit.next.stderr index b2831dbf8425..52b708d680e8 100644 --- a/tests/ui/transmutability/primitives/unit.next.stderr +++ b/tests/ui/transmutability/primitives/unit.next.stderr @@ -2,7 +2,7 @@ error[E0277]: `()` cannot be safely transmuted into `u8` --> $DIR/unit.rs:31:35 | LL | assert::is_transmutable::<(), u8>(); - | ^^ The size of `()` is smaller than the size of `u8` + | ^^ the size of `()` is smaller than the size of `u8` | note: required by a bound in `is_transmutable` --> $DIR/unit.rs:16:14 diff --git a/tests/ui/transmutability/references/recursive-wrapper-types-bit-incompatible.stderr b/tests/ui/transmutability/references/recursive-wrapper-types-bit-incompatible.stderr index 305fca30939c..2b7cab1660d1 100644 --- a/tests/ui/transmutability/references/recursive-wrapper-types-bit-incompatible.stderr +++ b/tests/ui/transmutability/references/recursive-wrapper-types-bit-incompatible.stderr @@ -2,7 +2,7 @@ error[E0277]: `B` cannot be safely transmuted into `A` --> $DIR/recursive-wrapper-types-bit-incompatible.rs:23:49 | LL | assert::is_maybe_transmutable::<&'static B, &'static A>(); - | ^^^^^^^^^^ At least one value of `B` isn't a bit-valid value of `A` + | ^^^^^^^^^^ at least one value of `B` isn't a bit-valid value of `A` | note: required by a bound in `is_maybe_transmutable` --> $DIR/recursive-wrapper-types-bit-incompatible.rs:9:14 diff --git a/tests/ui/transmutability/references/reject_extension.stderr b/tests/ui/transmutability/references/reject_extension.stderr index e02ef89c4a03..88dd0313e3c8 100644 --- a/tests/ui/transmutability/references/reject_extension.stderr +++ b/tests/ui/transmutability/references/reject_extension.stderr @@ -2,7 +2,7 @@ error[E0277]: `&Packed` cannot be safely transmuted into `&Packed` --> $DIR/reject_extension.rs:48:37 | LL | assert::is_transmutable::<&Src, &Dst>(); - | ^^^^ The referent size of `&Packed` (2 bytes) is smaller than that of `&Packed` (4 bytes) + | ^^^^ the referent size of `&Packed` (2 bytes) is smaller than that of `&Packed` (4 bytes) | note: required by a bound in `is_transmutable` --> $DIR/reject_extension.rs:13:14 diff --git a/tests/ui/transmutability/references/unit-to-u8.stderr b/tests/ui/transmutability/references/unit-to-u8.stderr index 7cb45e24e0a4..5d73dfdc8eb7 100644 --- a/tests/ui/transmutability/references/unit-to-u8.stderr +++ b/tests/ui/transmutability/references/unit-to-u8.stderr @@ -2,7 +2,7 @@ error[E0277]: `&Unit` cannot be safely transmuted into `&u8` --> $DIR/unit-to-u8.rs:22:52 | LL | assert::is_maybe_transmutable::<&'static Unit, &'static u8>(); - | ^^^^^^^^^^^ The referent size of `&Unit` (0 bytes) is smaller than that of `&u8` (1 bytes) + | ^^^^^^^^^^^ the referent size of `&Unit` (0 bytes) is smaller than that of `&u8` (1 bytes) | note: required by a bound in `is_maybe_transmutable` --> $DIR/unit-to-u8.rs:9:14 diff --git a/tests/ui/transmutability/region-infer.stderr b/tests/ui/transmutability/region-infer.stderr index 5497af2429e5..03c46823838d 100644 --- a/tests/ui/transmutability/region-infer.stderr +++ b/tests/ui/transmutability/region-infer.stderr @@ -2,7 +2,7 @@ error[E0277]: `()` cannot be safely transmuted into `W<'_>` --> $DIR/region-infer.rs:18:5 | LL | test(); - | ^^^^^^ The size of `()` is smaller than the size of `W<'_>` + | ^^^^^^ the size of `()` is smaller than the size of `W<'_>` | note: required by a bound in `test` --> $DIR/region-infer.rs:10:12 diff --git a/tests/ui/transmutability/transmute-padding-ice.stderr b/tests/ui/transmutability/transmute-padding-ice.stderr index c48a5cd80ce7..4c121d463c60 100644 --- a/tests/ui/transmutability/transmute-padding-ice.stderr +++ b/tests/ui/transmutability/transmute-padding-ice.stderr @@ -2,7 +2,7 @@ error[E0277]: `B` cannot be safely transmuted into `A` --> $DIR/transmute-padding-ice.rs:25:40 | LL | assert::is_maybe_transmutable::(); - | ^ The size of `B` is smaller than the size of `A` + | ^ the size of `B` is smaller than the size of `A` | note: required by a bound in `is_maybe_transmutable` --> $DIR/transmute-padding-ice.rs:10:14 diff --git a/tests/ui/transmutability/unions/should_pad_variants.stderr b/tests/ui/transmutability/unions/should_pad_variants.stderr index 13b4c8053adb..da4294bdbce8 100644 --- a/tests/ui/transmutability/unions/should_pad_variants.stderr +++ b/tests/ui/transmutability/unions/should_pad_variants.stderr @@ -2,7 +2,7 @@ error[E0277]: `Src` cannot be safely transmuted into `Dst` --> $DIR/should_pad_variants.rs:43:36 | LL | assert::is_transmutable::(); - | ^^^ The size of `Src` is smaller than the size of `Dst` + | ^^^ the size of `Src` is smaller than the size of `Dst` | note: required by a bound in `is_transmutable` --> $DIR/should_pad_variants.rs:13:14 diff --git a/tests/ui/transmutability/unions/should_reject_contraction.stderr b/tests/ui/transmutability/unions/should_reject_contraction.stderr index a3e387a0f846..20eaa3a6b095 100644 --- a/tests/ui/transmutability/unions/should_reject_contraction.stderr +++ b/tests/ui/transmutability/unions/should_reject_contraction.stderr @@ -2,7 +2,7 @@ error[E0277]: `Superset` cannot be safely transmuted into `Subset` --> $DIR/should_reject_contraction.rs:34:41 | LL | assert::is_transmutable::(); - | ^^^^^^ At least one value of `Superset` isn't a bit-valid value of `Subset` + | ^^^^^^ at least one value of `Superset` isn't a bit-valid value of `Subset` | note: required by a bound in `is_transmutable` --> $DIR/should_reject_contraction.rs:12:14 diff --git a/tests/ui/transmutability/unions/should_reject_disjoint.stderr b/tests/ui/transmutability/unions/should_reject_disjoint.stderr index 447ab6d9de7a..ea47797c9705 100644 --- a/tests/ui/transmutability/unions/should_reject_disjoint.stderr +++ b/tests/ui/transmutability/unions/should_reject_disjoint.stderr @@ -2,7 +2,7 @@ error[E0277]: `A` cannot be safely transmuted into `B` --> $DIR/should_reject_disjoint.rs:32:40 | LL | assert::is_maybe_transmutable::(); - | ^ At least one value of `A` isn't a bit-valid value of `B` + | ^ at least one value of `A` isn't a bit-valid value of `B` | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_reject_disjoint.rs:12:14 @@ -17,7 +17,7 @@ error[E0277]: `B` cannot be safely transmuted into `A` --> $DIR/should_reject_disjoint.rs:33:40 | LL | assert::is_maybe_transmutable::(); - | ^ At least one value of `B` isn't a bit-valid value of `A` + | ^ at least one value of `B` isn't a bit-valid value of `A` | note: required by a bound in `is_maybe_transmutable` --> $DIR/should_reject_disjoint.rs:12:14 diff --git a/tests/ui/transmutability/unions/should_reject_intersecting.stderr b/tests/ui/transmutability/unions/should_reject_intersecting.stderr index f0763bc8be78..79dec659d9db 100644 --- a/tests/ui/transmutability/unions/should_reject_intersecting.stderr +++ b/tests/ui/transmutability/unions/should_reject_intersecting.stderr @@ -2,7 +2,7 @@ error[E0277]: `A` cannot be safely transmuted into `B` --> $DIR/should_reject_intersecting.rs:35:34 | LL | assert::is_transmutable::(); - | ^ At least one value of `A` isn't a bit-valid value of `B` + | ^ at least one value of `A` isn't a bit-valid value of `B` | note: required by a bound in `is_transmutable` --> $DIR/should_reject_intersecting.rs:13:14 @@ -17,7 +17,7 @@ error[E0277]: `B` cannot be safely transmuted into `A` --> $DIR/should_reject_intersecting.rs:36:34 | LL | assert::is_transmutable::(); - | ^ At least one value of `B` isn't a bit-valid value of `A` + | ^ at least one value of `B` isn't a bit-valid value of `A` | note: required by a bound in `is_transmutable` --> $DIR/should_reject_intersecting.rs:13:14 From 07545959c5cf2557ed0a6045c2e85a9c8b4a080c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jakub=20Ber=C3=A1nek?= Date: Fri, 15 Mar 2024 19:03:28 +0100 Subject: [PATCH 17/17] CI: cache PR CI Docker builds --- src/ci/docker/run.sh | 41 +++++++++++++++++++++++++++++------------ 1 file changed, 29 insertions(+), 12 deletions(-) diff --git a/src/ci/docker/run.sh b/src/ci/docker/run.sh index bd5447ac835d..740eb7504f87 100755 --- a/src/ci/docker/run.sh +++ b/src/ci/docker/run.sh @@ -92,21 +92,38 @@ if [ -f "$docker_dir/$image/Dockerfile" ]; then # Print docker version docker --version - # On non-CI or PR jobs, we don't have permissions to write to the registry cache, so we should - # not use `docker login` nor caching. - if [[ "$CI" == "" ]] || [[ "$PR_CI_JOB" == "1" ]]; + REGISTRY=ghcr.io + # PR CI runs on rust-lang, but we want to use the cache from rust-lang-ci + REGISTRY_USERNAME=rust-lang-ci + # Tag used to push the final Docker image, so that it can be pulled by e.g. rustup + IMAGE_TAG=${REGISTRY}/${REGISTRY_USERNAME}/rust-ci:${cksum} + # Tag used to cache the Docker build + # It seems that it cannot be the same as $IMAGE_TAG, otherwise it overwrites the cache + CACHE_IMAGE_TAG=${REGISTRY}/${REGISTRY_USERNAME}/rust-ci-cache:${cksum} + + # On non-CI jobs, we don't do any caching. + if [[ "$CI" == "" ]]; then retry docker build --rm -t rust-ci -f "$dockerfile" "$context" - else - REGISTRY=ghcr.io - # Most probably rust-lang-ci, but in general the owner of the repository where CI runs - REGISTRY_USERNAME=${GITHUB_REPOSITORY_OWNER} - # Tag used to push the final Docker image, so that it can be pulled by e.g. rustup - IMAGE_TAG=${REGISTRY}/${REGISTRY_USERNAME}/rust-ci:${cksum} - # Tag used to cache the Docker build - # It seems that it cannot be the same as $IMAGE_TAG, otherwise it overwrites the cache - CACHE_IMAGE_TAG=${REGISTRY}/${REGISTRY_USERNAME}/rust-ci-cache:${cksum} + # On PR CI jobs, we don't have permissions to write to the registry cache, + # but we can still read from it. + elif [[ "$PR_CI_JOB" == "1" ]]; + then + # Enable a new Docker driver so that --cache-from works with a registry backend + docker buildx create --use --driver docker-container + # Build the image using registry caching backend + retry docker \ + buildx \ + build \ + --rm \ + -t rust-ci \ + -f "$dockerfile" \ + --cache-from type=registry,ref=${CACHE_IMAGE_TAG} \ + --output=type=docker \ + "$context" + # On auto/try builds, we can also write to the cache. + else # Log into the Docker registry, so that we can read/write cache and the final image echo ${DOCKER_TOKEN} | docker login ${REGISTRY} \ --username ${REGISTRY_USERNAME} \