From 089475a44e9b2644a64816b899a587fa3ef2f728 Mon Sep 17 00:00:00 2001 From: Tethys Svensson Date: Mon, 14 Nov 2022 19:42:47 +0100 Subject: [PATCH 01/14] Fix doc example for `wrapping_abs` The `max` variable is unused. This change introduces the `min_plus` variable, to make the example similar to the one from `saturating_abs`. An alternative would be to remove the unused variable. --- library/core/src/num/nonzero.rs | 3 +++ 1 file changed, 3 insertions(+) diff --git a/library/core/src/num/nonzero.rs b/library/core/src/num/nonzero.rs index 5b7521220acdb..db176de5aa194 100644 --- a/library/core/src/num/nonzero.rs +++ b/library/core/src/num/nonzero.rs @@ -669,12 +669,15 @@ macro_rules! nonzero_signed_operations { #[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")] #[doc = concat!("let min = ", stringify!($Ty), "::new(", stringify!($Int), "::MIN)?;")] + #[doc = concat!("let min_plus = ", stringify!($Ty), "::new(", + stringify!($Int), "::MIN + 1)?;")] #[doc = concat!("let max = ", stringify!($Ty), "::new(", stringify!($Int), "::MAX)?;")] /// /// assert_eq!(pos, pos.wrapping_abs()); /// assert_eq!(pos, neg.wrapping_abs()); /// assert_eq!(min, min.wrapping_abs()); + /// assert_eq!(max, min_plus.wrapping_abs()); /// # // FIXME: add once Neg is implemented? /// # // assert_eq!(max, (-max).wrapping_abs()); /// # Some(()) From 8b5bfaf662916deda37254a0eeec78e9b7d1c444 Mon Sep 17 00:00:00 2001 From: Martin Nordholts Date: Wed, 16 Nov 2022 20:13:45 +0100 Subject: [PATCH 02/14] rustdoc JSON: Use `Function` everywhere and remove `Method` --- src/librustdoc/json/conversions.rs | 26 +++++-------------- src/librustdoc/json/mod.rs | 3 +-- src/rustdoc-json-types/lib.rs | 11 +------- .../rustdoc-json/impls/import_from_private.rs | 2 +- src/tools/jsondoclint/src/item_kind.rs | 7 +---- src/tools/jsondoclint/src/validator.rs | 12 +++------ 6 files changed, 13 insertions(+), 48 deletions(-) diff --git a/src/librustdoc/json/conversions.rs b/src/librustdoc/json/conversions.rs index acfbd072121a1..6995778a93d61 100644 --- a/src/librustdoc/json/conversions.rs +++ b/src/librustdoc/json/conversions.rs @@ -257,12 +257,12 @@ fn from_clean_item(item: clean::Item, tcx: TyCtxt<'_>) -> ItemEnum { StructFieldItem(f) => ItemEnum::StructField(f.into_tcx(tcx)), EnumItem(e) => ItemEnum::Enum(e.into_tcx(tcx)), VariantItem(v) => ItemEnum::Variant(v.into_tcx(tcx)), - FunctionItem(f) => ItemEnum::Function(from_function(f, header.unwrap(), tcx)), - ForeignFunctionItem(f) => ItemEnum::Function(from_function(f, header.unwrap(), tcx)), + FunctionItem(f) => ItemEnum::Function(from_function(f, true, header.unwrap(), tcx)), + ForeignFunctionItem(f) => ItemEnum::Function(from_function(f, false, header.unwrap(), tcx)), TraitItem(t) => ItemEnum::Trait((*t).into_tcx(tcx)), TraitAliasItem(t) => ItemEnum::TraitAlias(t.into_tcx(tcx)), - MethodItem(m, _) => ItemEnum::Method(from_function_method(m, true, header.unwrap(), tcx)), - TyMethodItem(m) => ItemEnum::Method(from_function_method(m, false, header.unwrap(), tcx)), + MethodItem(m, _) => ItemEnum::Function(from_function(m, true, header.unwrap(), tcx)), + TyMethodItem(m) => ItemEnum::Function(from_function(m, false, header.unwrap(), tcx)), ImplItem(i) => ItemEnum::Impl((*i).into_tcx(tcx)), StaticItem(s) => ItemEnum::Static(s.into_tcx(tcx)), ForeignStaticItem(s) => ItemEnum::Static(s.into_tcx(tcx)), @@ -618,6 +618,7 @@ impl FromWithTcx for Impl { pub(crate) fn from_function( function: Box, + has_body: bool, header: rustc_hir::FnHeader, tcx: TyCtxt<'_>, ) -> Function { @@ -626,20 +627,6 @@ pub(crate) fn from_function( decl: decl.into_tcx(tcx), generics: generics.into_tcx(tcx), header: from_fn_header(&header), - } -} - -pub(crate) fn from_function_method( - function: Box, - has_body: bool, - header: rustc_hir::FnHeader, - tcx: TyCtxt<'_>, -) -> Method { - let clean::Function { decl, generics } = *function; - Method { - decl: decl.into_tcx(tcx), - generics: generics.into_tcx(tcx), - header: from_fn_header(&header), has_body, } } @@ -759,14 +746,13 @@ impl FromWithTcx for ItemKind { Struct => ItemKind::Struct, Union => ItemKind::Union, Enum => ItemKind::Enum, - Function => ItemKind::Function, + Function | TyMethod | Method => ItemKind::Function, Typedef => ItemKind::Typedef, OpaqueTy => ItemKind::OpaqueTy, Static => ItemKind::Static, Constant => ItemKind::Constant, Trait => ItemKind::Trait, Impl => ItemKind::Impl, - TyMethod | Method => ItemKind::Method, StructField => ItemKind::StructField, Variant => ItemKind::Variant, Macro => ItemKind::Macro, diff --git a/src/librustdoc/json/mod.rs b/src/librustdoc/json/mod.rs index beb7054009138..e4df1332521a7 100644 --- a/src/librustdoc/json/mod.rs +++ b/src/librustdoc/json/mod.rs @@ -223,7 +223,7 @@ impl<'tcx> FormatRenderer<'tcx> for JsonRenderer<'tcx> { false } - types::ItemEnum::Method(_) + types::ItemEnum::Function(_) | types::ItemEnum::Module(_) | types::ItemEnum::AssocConst { .. } | types::ItemEnum::AssocType { .. } => true, @@ -231,7 +231,6 @@ impl<'tcx> FormatRenderer<'tcx> for JsonRenderer<'tcx> { | types::ItemEnum::Import(_) | types::ItemEnum::StructField(_) | types::ItemEnum::Variant(_) - | types::ItemEnum::Function(_) | types::ItemEnum::TraitAlias(_) | types::ItemEnum::Impl(_) | types::ItemEnum::Typedef(_) diff --git a/src/rustdoc-json-types/lib.rs b/src/rustdoc-json-types/lib.rs index 817b3e484194f..50004b1ca1ef8 100644 --- a/src/rustdoc-json-types/lib.rs +++ b/src/rustdoc-json-types/lib.rs @@ -9,7 +9,7 @@ use std::path::PathBuf; use serde::{Deserialize, Serialize}; /// rustdoc format-version. -pub const FORMAT_VERSION: u32 = 22; +pub const FORMAT_VERSION: u32 = 23; /// A `Crate` is the root of the emitted JSON blob. It contains all type/documentation information /// about the language items in the local crate, as well as info about external items to allow @@ -210,7 +210,6 @@ pub enum ItemKind { Constant, Trait, TraitAlias, - Method, Impl, Static, ForeignType, @@ -243,7 +242,6 @@ pub enum ItemEnum { Trait(Trait), TraitAlias(TraitAlias), - Method(Method), Impl(Impl), Typedef(Typedef), @@ -420,13 +418,6 @@ pub struct Function { pub decl: FnDecl, pub generics: Generics, pub header: Header, -} - -#[derive(Clone, Debug, PartialEq, Eq, Hash, Serialize, Deserialize)] -pub struct Method { - pub decl: FnDecl, - pub generics: Generics, - pub header: Header, pub has_body: bool, } diff --git a/src/test/rustdoc-json/impls/import_from_private.rs b/src/test/rustdoc-json/impls/import_from_private.rs index 856f7c7015b3e..fa88b6113a581 100644 --- a/src/test/rustdoc-json/impls/import_from_private.rs +++ b/src/test/rustdoc-json/impls/import_from_private.rs @@ -8,7 +8,7 @@ mod bar { pub struct Baz; // @set impl = "$.index[*][?(@.kind=='impl')].id" impl Baz { - // @set doit = "$.index[*][?(@.kind=='method')].id" + // @set doit = "$.index[*][?(@.kind=='function')].id" pub fn doit() {} } } diff --git a/src/tools/jsondoclint/src/item_kind.rs b/src/tools/jsondoclint/src/item_kind.rs index 6d986e57501a3..225651a997ed4 100644 --- a/src/tools/jsondoclint/src/item_kind.rs +++ b/src/tools/jsondoclint/src/item_kind.rs @@ -17,7 +17,6 @@ pub(crate) enum Kind { Constant, Trait, TraitAlias, - Method, Impl, Static, ForeignType, @@ -63,7 +62,6 @@ impl Kind { // Only in traits AssocConst => false, AssocType => false, - Method => false, StructField => false, // Only in structs or variants Variant => false, // Only in enums @@ -74,7 +72,7 @@ impl Kind { match self { Kind::AssocConst => true, Kind::AssocType => true, - Kind::Method => true, + Kind::Function => true, Kind::Module => false, Kind::ExternCrate => false, @@ -84,7 +82,6 @@ impl Kind { Kind::Union => false, Kind::Enum => false, Kind::Variant => false, - Kind::Function => false, Kind::Typedef => false, Kind::OpaqueTy => false, Kind::Constant => false, @@ -134,7 +131,6 @@ impl Kind { ItemEnum::Function(_) => Function, ItemEnum::Trait(_) => Trait, ItemEnum::TraitAlias(_) => TraitAlias, - ItemEnum::Method(_) => Method, ItemEnum::Impl(_) => Impl, ItemEnum::Typedef(_) => Typedef, ItemEnum::OpaqueTy(_) => OpaqueTy, @@ -164,7 +160,6 @@ impl Kind { ItemKind::Import => Import, ItemKind::Keyword => Keyword, ItemKind::Macro => Macro, - ItemKind::Method => Method, ItemKind::Module => Module, ItemKind::OpaqueTy => OpaqueTy, ItemKind::Primitive => Primitive, diff --git a/src/tools/jsondoclint/src/validator.rs b/src/tools/jsondoclint/src/validator.rs index 94af4c5e9e16d..5b293a3c4f701 100644 --- a/src/tools/jsondoclint/src/validator.rs +++ b/src/tools/jsondoclint/src/validator.rs @@ -3,9 +3,9 @@ use std::hash::Hash; use rustdoc_json_types::{ Constant, Crate, DynTrait, Enum, FnDecl, Function, FunctionPointer, GenericArg, GenericArgs, - GenericBound, GenericParamDef, Generics, Id, Impl, Import, ItemEnum, Method, Module, OpaqueTy, - Path, Primitive, ProcMacro, Static, Struct, StructKind, Term, Trait, TraitAlias, Type, - TypeBinding, TypeBindingKind, Typedef, Union, Variant, WherePredicate, + GenericBound, GenericParamDef, Generics, Id, Impl, Import, ItemEnum, Module, OpaqueTy, Path, + Primitive, ProcMacro, Static, Struct, StructKind, Term, Trait, TraitAlias, Type, TypeBinding, + TypeBindingKind, Typedef, Union, Variant, WherePredicate, }; use crate::{item_kind::Kind, Error, ErrorKind}; @@ -67,7 +67,6 @@ impl<'a> Validator<'a> { ItemEnum::Function(x) => self.check_function(x), ItemEnum::Trait(x) => self.check_trait(x), ItemEnum::TraitAlias(x) => self.check_trait_alias(x), - ItemEnum::Method(x) => self.check_method(x), ItemEnum::Impl(x) => self.check_impl(x), ItemEnum::Typedef(x) => self.check_typedef(x), ItemEnum::OpaqueTy(x) => self.check_opaque_ty(x), @@ -176,11 +175,6 @@ impl<'a> Validator<'a> { x.params.iter().for_each(|i| self.check_generic_bound(i)); } - fn check_method(&mut self, x: &'a Method) { - self.check_fn_decl(&x.decl); - self.check_generics(&x.generics); - } - fn check_impl(&mut self, x: &'a Impl) { self.check_generics(&x.generics); if let Some(path) = &x.trait_ { From e4f618fb8b3840bc9b250312fd7c6cdbd0351006 Mon Sep 17 00:00:00 2001 From: Michael Goulet Date: Fri, 11 Nov 2022 03:19:02 +0000 Subject: [PATCH 03/14] Do not need to account for overflow in predicate_can_apply --- .../src/traits/error_reporting/mod.rs | 5 ++++- .../ui/traits/predicate_can_apply-hang.rs | 6 ++++++ .../ui/traits/predicate_can_apply-hang.stderr | 21 +++++++++++++++++++ 3 files changed, 31 insertions(+), 1 deletion(-) create mode 100644 src/test/ui/traits/predicate_can_apply-hang.rs create mode 100644 src/test/ui/traits/predicate_can_apply-hang.stderr diff --git a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs index f087afa20baca..661e56b180090 100644 --- a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs +++ b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs @@ -2533,7 +2533,10 @@ impl<'tcx> InferCtxtPrivExt<'tcx> for TypeErrCtxt<'_, 'tcx> { let obligation = Obligation::new(self.tcx, ObligationCause::dummy(), param_env, cleaned_pred); - self.predicate_may_hold(&obligation) + // We don't use `InferCtxt::predicate_may_hold` because that + // will re-run predicates that overflow locally, which ends up + // taking a really long time to compute. + self.evaluate_obligation(&obligation).map_or(false, |eval| eval.may_apply()) }) } diff --git a/src/test/ui/traits/predicate_can_apply-hang.rs b/src/test/ui/traits/predicate_can_apply-hang.rs new file mode 100644 index 0000000000000..5f01645da5242 --- /dev/null +++ b/src/test/ui/traits/predicate_can_apply-hang.rs @@ -0,0 +1,6 @@ +fn f(x: Vec<[[[B; 1]; 1]; 1]>) -> impl PartialEq { + //~^ ERROR can't compare `Vec<[[[B; 1]; 1]; 1]>` with `B` + x +} + +fn main() {} diff --git a/src/test/ui/traits/predicate_can_apply-hang.stderr b/src/test/ui/traits/predicate_can_apply-hang.stderr new file mode 100644 index 0000000000000..49fe63b412ac9 --- /dev/null +++ b/src/test/ui/traits/predicate_can_apply-hang.stderr @@ -0,0 +1,21 @@ +error[E0277]: can't compare `Vec<[[[B; 1]; 1]; 1]>` with `B` + --> $DIR/predicate_can_apply-hang.rs:1:38 + | +LL | fn f(x: Vec<[[[B; 1]; 1]; 1]>) -> impl PartialEq { + | ^^^^^^^^^^^^^^^^^ no implementation for `Vec<[[[B; 1]; 1]; 1]> == B` +LL | +LL | x + | - return type was inferred to be `Vec<[[[B; 1]; 1]; 1]>` here + | + = help: the trait `PartialEq` is not implemented for `Vec<[[[B; 1]; 1]; 1]>` + = help: the following other types implement trait `PartialEq`: + as PartialEq>> + as PartialEq<&[U; N]>> + as PartialEq<&[U]>> + as PartialEq<&mut [U]>> + as PartialEq<[U; N]>> + as PartialEq<[U]>> + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0277`. From 37227880d3f5de18bacb2dc666b8775144fd1b45 Mon Sep 17 00:00:00 2001 From: Michael Goulet Date: Fri, 11 Nov 2022 03:37:04 +0000 Subject: [PATCH 04/14] Drive-by: Don't manually call evaluate_obligation_no_overflow --- .../src/traits/error_reporting/suggestions.rs | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/compiler/rustc_trait_selection/src/traits/error_reporting/suggestions.rs b/compiler/rustc_trait_selection/src/traits/error_reporting/suggestions.rs index b8609077036f4..de25dcb5084db 100644 --- a/compiler/rustc_trait_selection/src/traits/error_reporting/suggestions.rs +++ b/compiler/rustc_trait_selection/src/traits/error_reporting/suggestions.rs @@ -1340,9 +1340,8 @@ impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> { obligation.param_env, trait_pred_and_suggested_ty, ); - let suggested_ty_would_satisfy_obligation = self - .evaluate_obligation_no_overflow(&new_obligation) - .must_apply_modulo_regions(); + let suggested_ty_would_satisfy_obligation = + self.predicate_must_hold_modulo_regions(&new_obligation); if suggested_ty_would_satisfy_obligation { let sp = self .tcx From 65b3a307a1e192cd30e46781281f7c8d2b9c4915 Mon Sep 17 00:00:00 2001 From: Michael Goulet Date: Fri, 18 Nov 2022 17:23:10 +0000 Subject: [PATCH 05/14] Add fatal overflow test --- src/test/ui/typeck/hang-in-overflow.rs | 18 ++++++++++++++++++ src/test/ui/typeck/hang-in-overflow.stderr | 22 ++++++++++++++++++++++ 2 files changed, 40 insertions(+) create mode 100644 src/test/ui/typeck/hang-in-overflow.rs create mode 100644 src/test/ui/typeck/hang-in-overflow.stderr diff --git a/src/test/ui/typeck/hang-in-overflow.rs b/src/test/ui/typeck/hang-in-overflow.rs new file mode 100644 index 0000000000000..1751618a9fa30 --- /dev/null +++ b/src/test/ui/typeck/hang-in-overflow.rs @@ -0,0 +1,18 @@ +// normalize-stderr-test "the requirement `.*`" -> "the requirement `...`" +// normalize-stderr-test "required for `.*` to implement `.*`" -> "required for `...` to implement `...`" + +// Currently this fatally aborts instead of hanging. +// Make sure at least that this doesn't turn into a hang. + +fn f() { + foo::<_>(); + //~^ ERROR overflow evaluating the requirement +} + +fn foo() +where + Vec<[[[B; 1]; 1]; 1]>: PartialEq, +{ +} + +fn main() {} diff --git a/src/test/ui/typeck/hang-in-overflow.stderr b/src/test/ui/typeck/hang-in-overflow.stderr new file mode 100644 index 0000000000000..3bcfdf89ab21b --- /dev/null +++ b/src/test/ui/typeck/hang-in-overflow.stderr @@ -0,0 +1,22 @@ +error[E0275]: overflow evaluating the requirement `...` + --> $DIR/hang-in-overflow.rs:8:5 + | +LL | foo::<_>(); + | ^^^^^^^^ + | + = help: consider increasing the recursion limit by adding a `#![recursion_limit = "256"]` attribute to your crate (`hang_in_overflow`) + = note: required for `...` to implement `...` + = note: 127 redundant requirements hidden + = note: required for `...` to implement `...` +note: required by a bound in `foo` + --> $DIR/hang-in-overflow.rs:14:28 + | +LL | fn foo() + | --- required by a bound in this +LL | where +LL | Vec<[[[B; 1]; 1]; 1]>: PartialEq, + | ^^^^^^^^^^^^ required by this bound in `foo` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0275`. From 67e746cc688ec6f02a446c6e17d269ce81c1737b Mon Sep 17 00:00:00 2001 From: Daniel Paoliello Date: Wed, 16 Nov 2022 15:34:12 -0800 Subject: [PATCH 06/14] Workaround for private global symbol issue --- compiler/rustc_codegen_llvm/src/callee.rs | 15 ++++++++++++++- .../run-make/raw-dylib-import-name-type/driver.rs | 8 ++++++++ .../run-make/raw-dylib-import-name-type/extern.c | 5 +++++ .../raw-dylib-import-name-type/extern.gnu.def | 1 + .../raw-dylib-import-name-type/extern.msvc.def | 1 + .../raw-dylib-import-name-type/output.txt | 1 + 6 files changed, 30 insertions(+), 1 deletion(-) diff --git a/compiler/rustc_codegen_llvm/src/callee.rs b/compiler/rustc_codegen_llvm/src/callee.rs index 6f0d1b7ce8454..70ff5c9617b7a 100644 --- a/compiler/rustc_codegen_llvm/src/callee.rs +++ b/compiler/rustc_codegen_llvm/src/callee.rs @@ -83,7 +83,20 @@ pub fn get_fn<'ll, 'tcx>(cx: &CodegenCx<'ll, 'tcx>, instance: Instance<'tcx>) -> let llfn = if tcx.sess.target.arch == "x86" && let Some(dllimport) = common::get_dllimport(tcx, instance_def_id, sym) { - cx.declare_fn(&common::i686_decorated_name(&dllimport, common::is_mingw_gnu_toolchain(&tcx.sess.target), true), fn_abi) + // Fix for https://github.com/rust-lang/rust/issues/104453 + // On x86 Windows, LLVM uses 'L' as the prefix for any private + // global symbols, so when we create an undecorated function symbol + // that begins with an 'L' LLVM misinterprets that as a private + // global symbol that it created and so fails the compilation at a + // later stage since such a symbol must have a definition. + // + // To avoid this, we set the Storage Class to "DllImport" so that + // LLVM will prefix the name with `__imp_`. Ideally, we'd like the + // existing logic below to set the Storage Class, but it has an + // exemption for MinGW for backwards compatability. + let llfn = cx.declare_fn(&common::i686_decorated_name(&dllimport, common::is_mingw_gnu_toolchain(&tcx.sess.target), true), fn_abi); + unsafe { llvm::LLVMSetDLLStorageClass(llfn, llvm::DLLStorageClass::DllImport); } + llfn } else { cx.declare_fn(sym, fn_abi) }; diff --git a/src/test/run-make/raw-dylib-import-name-type/driver.rs b/src/test/run-make/raw-dylib-import-name-type/driver.rs index a38849fc8130a..9a3cd9ebe1b4b 100644 --- a/src/test/run-make/raw-dylib-import-name-type/driver.rs +++ b/src/test/run-make/raw-dylib-import-name-type/driver.rs @@ -3,6 +3,7 @@ #[link(name = "extern", kind = "raw-dylib", import_name_type = "undecorated")] extern "C" { + fn LooksLikeAPrivateGlobal(i: i32); fn cdecl_fn_undecorated(i: i32); #[link_name = "cdecl_fn_undecorated2"] fn cdecl_fn_undecorated_renamed(i: i32); @@ -84,6 +85,13 @@ extern { pub fn main() { unsafe { + // Regression test for #104453 + // On x86 LLVM uses 'L' as the prefix for private globals (PrivateGlobalPrefix), which + // causes it to believe that undecorated functions starting with 'L' are actually temporary + // symbols that it generated, which causes a later check to fail as the symbols we are + // creating don't have definitions (whereas all temporary symbols do). + LooksLikeAPrivateGlobal(13); + cdecl_fn_undecorated(1); cdecl_fn_undecorated_renamed(10); cdecl_fn_noprefix(2); diff --git a/src/test/run-make/raw-dylib-import-name-type/extern.c b/src/test/run-make/raw-dylib-import-name-type/extern.c index 195126d51294c..23c1e489e5ea2 100644 --- a/src/test/run-make/raw-dylib-import-name-type/extern.c +++ b/src/test/run-make/raw-dylib-import-name-type/extern.c @@ -1,6 +1,11 @@ #include #include +void _cdecl LooksLikeAPrivateGlobal(int i) { + printf("LooksLikeAPrivateGlobal(%d)\n", i); + fflush(stdout); +} + void _cdecl cdecl_fn_undecorated(int i) { printf("cdecl_fn_undecorated(%d)\n", i); fflush(stdout); diff --git a/src/test/run-make/raw-dylib-import-name-type/extern.gnu.def b/src/test/run-make/raw-dylib-import-name-type/extern.gnu.def index a523c959a4744..498e90e862d4b 100644 --- a/src/test/run-make/raw-dylib-import-name-type/extern.gnu.def +++ b/src/test/run-make/raw-dylib-import-name-type/extern.gnu.def @@ -1,5 +1,6 @@ LIBRARY extern EXPORTS + LooksLikeAPrivateGlobal cdecl_fn_undecorated cdecl_fn_undecorated2 cdecl_fn_noprefix diff --git a/src/test/run-make/raw-dylib-import-name-type/extern.msvc.def b/src/test/run-make/raw-dylib-import-name-type/extern.msvc.def index dbff32d4c90b0..cddb88bb8b5f0 100644 --- a/src/test/run-make/raw-dylib-import-name-type/extern.msvc.def +++ b/src/test/run-make/raw-dylib-import-name-type/extern.msvc.def @@ -1,5 +1,6 @@ LIBRARY extern EXPORTS + LooksLikeAPrivateGlobal cdecl_fn_undecorated cdecl_fn_undecorated2 cdecl_fn_noprefix diff --git a/src/test/run-make/raw-dylib-import-name-type/output.txt b/src/test/run-make/raw-dylib-import-name-type/output.txt index 707faf403aeca..a2a2bfeec7d97 100644 --- a/src/test/run-make/raw-dylib-import-name-type/output.txt +++ b/src/test/run-make/raw-dylib-import-name-type/output.txt @@ -1,3 +1,4 @@ +LooksLikeAPrivateGlobal(13) cdecl_fn_undecorated(1) cdecl_fn_undecorated2(10) cdecl_fn_noprefix(2) From c36ff28d4214c65df55cb1d9d8085b34d33d37fb Mon Sep 17 00:00:00 2001 From: Michael Goulet Date: Sat, 19 Nov 2022 03:28:56 +0000 Subject: [PATCH 07/14] drive-by: PolyExistentialPredicate --- .../rustc_const_eval/src/util/type_name.rs | 2 +- .../rustc_hir_analysis/src/astconv/mod.rs | 2 +- compiler/rustc_hir_typeck/src/coercion.rs | 2 +- .../src/infer/error_reporting/mod.rs | 2 +- compiler/rustc_lint/src/context.rs | 2 +- compiler/rustc_middle/src/ty/codec.rs | 4 +-- compiler/rustc_middle/src/ty/context.rs | 30 ++++++++----------- compiler/rustc_middle/src/ty/error.rs | 4 +-- compiler/rustc_middle/src/ty/mod.rs | 7 +++-- compiler/rustc_middle/src/ty/print/mod.rs | 6 ++-- compiler/rustc_middle/src/ty/print/pretty.rs | 8 ++--- compiler/rustc_middle/src/ty/relate.rs | 2 +- .../rustc_middle/src/ty/structural_impls.rs | 2 +- compiler/rustc_middle/src/ty/sty.rs | 6 ++-- compiler/rustc_symbol_mangling/src/legacy.rs | 2 +- .../src/typeid/typeid_itanium_cxx_abi.rs | 10 +++---- compiler/rustc_symbol_mangling/src/v0.rs | 2 +- .../rustc_trait_selection/src/traits/wf.rs | 4 +-- compiler/rustc_traits/src/chalk/lowering.rs | 2 +- src/tools/clippy/clippy_lints/src/ptr.rs | 2 +- 20 files changed, 48 insertions(+), 53 deletions(-) diff --git a/compiler/rustc_const_eval/src/util/type_name.rs b/compiler/rustc_const_eval/src/util/type_name.rs index 08a6d69b8e40c..14c8c88028bda 100644 --- a/compiler/rustc_const_eval/src/util/type_name.rs +++ b/compiler/rustc_const_eval/src/util/type_name.rs @@ -74,7 +74,7 @@ impl<'tcx> Printer<'tcx> for AbsolutePathPrinter<'tcx> { fn print_dyn_existential( self, - predicates: &'tcx ty::List>>, + predicates: &'tcx ty::List>, ) -> Result { self.pretty_print_dyn_existential(predicates) } diff --git a/compiler/rustc_hir_analysis/src/astconv/mod.rs b/compiler/rustc_hir_analysis/src/astconv/mod.rs index 16c40cf1299cb..e3d9ccb7d6e71 100644 --- a/compiler/rustc_hir_analysis/src/astconv/mod.rs +++ b/compiler/rustc_hir_analysis/src/astconv/mod.rs @@ -3019,7 +3019,7 @@ impl<'o, 'tcx> dyn AstConv<'tcx> + 'o { fn compute_object_lifetime_bound( &self, span: Span, - existential_predicates: &'tcx ty::List>>, + existential_predicates: &'tcx ty::List>, ) -> Option> // if None, use the default { let tcx = self.tcx(); diff --git a/compiler/rustc_hir_typeck/src/coercion.rs b/compiler/rustc_hir_typeck/src/coercion.rs index c1e4ab600f34f..894879d777425 100644 --- a/compiler/rustc_hir_typeck/src/coercion.rs +++ b/compiler/rustc_hir_typeck/src/coercion.rs @@ -748,7 +748,7 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> { &self, a: Ty<'tcx>, b: Ty<'tcx>, - predicates: &'tcx ty::List>>, + predicates: &'tcx ty::List>, b_region: ty::Region<'tcx>, ) -> CoerceResult<'tcx> { if !self.tcx.features().dyn_star { diff --git a/compiler/rustc_infer/src/infer/error_reporting/mod.rs b/compiler/rustc_infer/src/infer/error_reporting/mod.rs index 22f32251f6df0..e03a4ea824719 100644 --- a/compiler/rustc_infer/src/infer/error_reporting/mod.rs +++ b/compiler/rustc_infer/src/infer/error_reporting/mod.rs @@ -542,7 +542,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> { fn print_dyn_existential( self, - _predicates: &'tcx ty::List>>, + _predicates: &'tcx ty::List>, ) -> Result { Err(NonTrivialPath) } diff --git a/compiler/rustc_lint/src/context.rs b/compiler/rustc_lint/src/context.rs index 28f6ac61c5bdd..589b4d6a10ff1 100644 --- a/compiler/rustc_lint/src/context.rs +++ b/compiler/rustc_lint/src/context.rs @@ -1159,7 +1159,7 @@ impl<'tcx> LateContext<'tcx> { fn print_dyn_existential( self, - _predicates: &'tcx ty::List>>, + _predicates: &'tcx ty::List>, ) -> Result { Ok(()) } diff --git a/compiler/rustc_middle/src/ty/codec.rs b/compiler/rustc_middle/src/ty/codec.rs index 7263e8306cf09..b469eebfad993 100644 --- a/compiler/rustc_middle/src/ty/codec.rs +++ b/compiler/rustc_middle/src/ty/codec.rs @@ -298,7 +298,7 @@ impl<'tcx, D: TyDecoder>> RefDecodable<'tcx, D> for ty::List>> RefDecodable<'tcx, D> - for ty::List>> + for ty::List> { fn decode(decoder: &mut D) -> &'tcx Self { let len = decoder.read_usize(); @@ -379,7 +379,7 @@ impl<'tcx, D: TyDecoder>> RefDecodable<'tcx, D> impl_decodable_via_ref! { &'tcx ty::TypeckResults<'tcx>, &'tcx ty::List>, - &'tcx ty::List>>, + &'tcx ty::List>, &'tcx traits::ImplSource<'tcx, ()>, &'tcx mir::Body<'tcx>, &'tcx mir::UnsafetyCheckResult, diff --git a/compiler/rustc_middle/src/ty/context.rs b/compiler/rustc_middle/src/ty/context.rs index 1c714f594253a..13695089eb828 100644 --- a/compiler/rustc_middle/src/ty/context.rs +++ b/compiler/rustc_middle/src/ty/context.rs @@ -17,11 +17,11 @@ use crate::traits; use crate::ty::query::{self, TyCtxtAt}; use crate::ty::{ self, AdtDef, AdtDefData, AdtKind, Binder, BindingMode, BoundVar, CanonicalPolyFnSig, - ClosureSizeProfileData, Const, ConstS, ConstVid, DefIdTree, ExistentialPredicate, FloatTy, - FloatVar, FloatVid, GenericParamDefKind, InferConst, InferTy, IntTy, IntVar, IntVid, List, - ParamConst, ParamTy, PolyFnSig, Predicate, PredicateKind, PredicateS, ProjectionTy, Region, - RegionKind, ReprOptions, TraitObjectVisitor, Ty, TyKind, TyS, TyVar, TyVid, TypeAndMut, UintTy, - Visibility, + ClosureSizeProfileData, Const, ConstS, ConstVid, DefIdTree, FloatTy, FloatVar, FloatVid, + GenericParamDefKind, InferConst, InferTy, IntTy, IntVar, IntVid, List, ParamConst, ParamTy, + PolyExistentialPredicate, PolyFnSig, Predicate, PredicateKind, PredicateS, ProjectionTy, + Region, RegionKind, ReprOptions, TraitObjectVisitor, Ty, TyKind, TyS, TyVar, TyVid, TypeAndMut, + UintTy, Visibility, }; use crate::ty::{GenericArg, GenericArgKind, InternalSubsts, SubstsRef, UserSubsts}; use rustc_ast as ast; @@ -109,7 +109,7 @@ impl<'tcx> Interner for TyCtxt<'tcx> { type Mutability = hir::Mutability; type Movability = hir::Movability; type PolyFnSig = PolyFnSig<'tcx>; - type ListBinderExistentialPredicate = &'tcx List>>; + type ListBinderExistentialPredicate = &'tcx List>; type BinderListTy = Binder<'tcx, &'tcx List>>; type ListTy = &'tcx List>; type ProjectionTy = ty::ProjectionTy<'tcx>; @@ -140,8 +140,7 @@ pub struct CtxtInterners<'tcx> { substs: InternedSet<'tcx, InternalSubsts<'tcx>>, canonical_var_infos: InternedSet<'tcx, List>>, region: InternedSet<'tcx, RegionKind<'tcx>>, - poly_existential_predicates: - InternedSet<'tcx, List>>>, + poly_existential_predicates: InternedSet<'tcx, List>>, predicate: InternedSet<'tcx, PredicateS<'tcx>>, predicates: InternedSet<'tcx, List>>, projs: InternedSet<'tcx, List>, @@ -1810,7 +1809,7 @@ nop_lift! {const_; Const<'a> => Const<'tcx>} nop_lift! {const_allocation; ConstAllocation<'a> => ConstAllocation<'tcx>} nop_lift! {predicate; Predicate<'a> => Predicate<'tcx>} -nop_list_lift! {poly_existential_predicates; ty::Binder<'a, ExistentialPredicate<'a>> => ty::Binder<'tcx, ExistentialPredicate<'tcx>>} +nop_list_lift! {poly_existential_predicates; PolyExistentialPredicate<'a> => PolyExistentialPredicate<'tcx>} nop_list_lift! {predicates; Predicate<'a> => Predicate<'tcx>} nop_list_lift! {canonical_var_infos; CanonicalVarInfo<'a> => CanonicalVarInfo<'tcx>} nop_list_lift! {projs; ProjectionKind => ProjectionKind} @@ -2265,7 +2264,7 @@ slice_interners!( substs: _intern_substs(GenericArg<'tcx>), canonical_var_infos: _intern_canonical_var_infos(CanonicalVarInfo<'tcx>), poly_existential_predicates: - _intern_poly_existential_predicates(ty::Binder<'tcx, ExistentialPredicate<'tcx>>), + _intern_poly_existential_predicates(PolyExistentialPredicate<'tcx>), predicates: _intern_predicates(Predicate<'tcx>), projs: _intern_projs(ProjectionKind), place_elems: _intern_place_elems(PlaceElem<'tcx>), @@ -2544,7 +2543,7 @@ impl<'tcx> TyCtxt<'tcx> { #[inline] pub fn mk_dynamic( self, - obj: &'tcx List>>, + obj: &'tcx List>, reg: ty::Region<'tcx>, repr: DynKind, ) -> Ty<'tcx> { @@ -2682,8 +2681,8 @@ impl<'tcx> TyCtxt<'tcx> { pub fn intern_poly_existential_predicates( self, - eps: &[ty::Binder<'tcx, ExistentialPredicate<'tcx>>], - ) -> &'tcx List>> { + eps: &[PolyExistentialPredicate<'tcx>], + ) -> &'tcx List> { assert!(!eps.is_empty()); assert!( eps.array_windows() @@ -2767,10 +2766,7 @@ impl<'tcx> TyCtxt<'tcx> { } pub fn mk_poly_existential_predicates< - I: InternAs< - [ty::Binder<'tcx, ExistentialPredicate<'tcx>>], - &'tcx List>>, - >, + I: InternAs<[PolyExistentialPredicate<'tcx>], &'tcx List>>, >( self, iter: I, diff --git a/compiler/rustc_middle/src/ty/error.rs b/compiler/rustc_middle/src/ty/error.rs index dc13374f992eb..61cfcbe70192d 100644 --- a/compiler/rustc_middle/src/ty/error.rs +++ b/compiler/rustc_middle/src/ty/error.rs @@ -64,9 +64,7 @@ pub enum TypeError<'tcx> { CyclicTy(Ty<'tcx>), CyclicConst(ty::Const<'tcx>), ProjectionMismatched(ExpectedFound), - ExistentialMismatch( - ExpectedFound<&'tcx ty::List>>>, - ), + ExistentialMismatch(ExpectedFound<&'tcx ty::List>>), ObjectUnsafeCoercion(DefId), ConstMismatch(ExpectedFound>), diff --git a/compiler/rustc_middle/src/ty/mod.rs b/compiler/rustc_middle/src/ty/mod.rs index f9a762261e2ce..99b830da096d2 100644 --- a/compiler/rustc_middle/src/ty/mod.rs +++ b/compiler/rustc_middle/src/ty/mod.rs @@ -94,9 +94,10 @@ pub use self::sty::{ BoundVariableKind, CanonicalPolyFnSig, ClosureSubsts, ClosureSubstsParts, ConstVid, EarlyBoundRegion, ExistentialPredicate, ExistentialProjection, ExistentialTraitRef, FnSig, FreeRegion, GenSig, GeneratorSubsts, GeneratorSubstsParts, InlineConstSubsts, - InlineConstSubstsParts, ParamConst, ParamTy, PolyExistentialProjection, - PolyExistentialTraitRef, PolyFnSig, PolyGenSig, PolyTraitRef, ProjectionTy, Region, RegionKind, - RegionVid, TraitRef, TyKind, TypeAndMut, UpvarSubsts, VarianceDiagInfo, + InlineConstSubstsParts, ParamConst, ParamTy, PolyExistentialPredicate, + PolyExistentialProjection, PolyExistentialTraitRef, PolyFnSig, PolyGenSig, PolyTraitRef, + ProjectionTy, Region, RegionKind, RegionVid, TraitRef, TyKind, TypeAndMut, UpvarSubsts, + VarianceDiagInfo, }; pub use self::trait_def::TraitDef; diff --git a/compiler/rustc_middle/src/ty/print/mod.rs b/compiler/rustc_middle/src/ty/print/mod.rs index 44b9548db89c8..667298b9b5b13 100644 --- a/compiler/rustc_middle/src/ty/print/mod.rs +++ b/compiler/rustc_middle/src/ty/print/mod.rs @@ -63,7 +63,7 @@ pub trait Printer<'tcx>: Sized { fn print_dyn_existential( self, - predicates: &'tcx ty::List>>, + predicates: &'tcx ty::List>, ) -> Result; fn print_const(self, ct: ty::Const<'tcx>) -> Result; @@ -308,9 +308,7 @@ impl<'tcx, P: Printer<'tcx>> Print<'tcx, P> for Ty<'tcx> { } } -impl<'tcx, P: Printer<'tcx>> Print<'tcx, P> - for &'tcx ty::List>> -{ +impl<'tcx, P: Printer<'tcx>> Print<'tcx, P> for &'tcx ty::List> { type Output = P::DynExistential; type Error = P::Error; fn print(&self, cx: P) -> Result { diff --git a/compiler/rustc_middle/src/ty/print/pretty.rs b/compiler/rustc_middle/src/ty/print/pretty.rs index 48e803597b02e..ef30b743f5572 100644 --- a/compiler/rustc_middle/src/ty/print/pretty.rs +++ b/compiler/rustc_middle/src/ty/print/pretty.rs @@ -1059,7 +1059,7 @@ pub trait PrettyPrinter<'tcx>: fn pretty_print_dyn_existential( mut self, - predicates: &'tcx ty::List>>, + predicates: &'tcx ty::List>, ) -> Result { // Generate the main trait ref, including associated types. let mut first = true; @@ -1763,7 +1763,7 @@ impl<'tcx> Printer<'tcx> for FmtPrinter<'_, 'tcx> { fn print_dyn_existential( self, - predicates: &'tcx ty::List>>, + predicates: &'tcx ty::List>, ) -> Result { self.pretty_print_dyn_existential(predicates) } @@ -2523,12 +2523,12 @@ pub struct PrintClosureAsImpl<'tcx> { forward_display_to_print! { ty::Region<'tcx>, Ty<'tcx>, - &'tcx ty::List>>, + &'tcx ty::List>, ty::Const<'tcx>, // HACK(eddyb) these are exhaustive instead of generic, // because `for<'tcx>` isn't possible yet. - ty::Binder<'tcx, ty::ExistentialPredicate<'tcx>>, + ty::PolyExistentialPredicate<'tcx>, ty::Binder<'tcx, ty::TraitRef<'tcx>>, ty::Binder<'tcx, ty::ExistentialTraitRef<'tcx>>, ty::Binder<'tcx, TraitRefPrintOnlyTraitPath<'tcx>>, diff --git a/compiler/rustc_middle/src/ty/relate.rs b/compiler/rustc_middle/src/ty/relate.rs index c083a405e3cfb..5708abf0729c7 100644 --- a/compiler/rustc_middle/src/ty/relate.rs +++ b/compiler/rustc_middle/src/ty/relate.rs @@ -649,7 +649,7 @@ pub fn super_relate_consts<'tcx, R: TypeRelation<'tcx>>( if is_match { Ok(a) } else { Err(TypeError::ConstMismatch(expected_found(relation, a, b))) } } -impl<'tcx> Relate<'tcx> for &'tcx ty::List>> { +impl<'tcx> Relate<'tcx> for &'tcx ty::List> { fn relate>( relation: &mut R, a: Self, diff --git a/compiler/rustc_middle/src/ty/structural_impls.rs b/compiler/rustc_middle/src/ty/structural_impls.rs index 9f0598d0ba86b..6be8fdd7cd795 100644 --- a/compiler/rustc_middle/src/ty/structural_impls.rs +++ b/compiler/rustc_middle/src/ty/structural_impls.rs @@ -586,7 +586,7 @@ impl<'tcx, T: TypeVisitable<'tcx>> TypeSuperVisitable<'tcx> for ty::Binder<'tcx, } } -impl<'tcx> TypeFoldable<'tcx> for &'tcx ty::List>> { +impl<'tcx> TypeFoldable<'tcx> for &'tcx ty::List> { fn try_fold_with>(self, folder: &mut F) -> Result { ty::util::fold_list(self, folder, |tcx, v| tcx.intern_poly_existential_predicates(v)) } diff --git a/compiler/rustc_middle/src/ty/sty.rs b/compiler/rustc_middle/src/ty/sty.rs index 49d82b503a4bb..e2a7b09de6ab4 100644 --- a/compiler/rustc_middle/src/ty/sty.rs +++ b/compiler/rustc_middle/src/ty/sty.rs @@ -703,7 +703,9 @@ impl<'tcx> ExistentialPredicate<'tcx> { } } -impl<'tcx> Binder<'tcx, ExistentialPredicate<'tcx>> { +pub type PolyExistentialPredicate<'tcx> = Binder<'tcx, ExistentialPredicate<'tcx>>; + +impl<'tcx> PolyExistentialPredicate<'tcx> { /// Given an existential predicate like `?Self: PartialEq` (e.g., derived from `dyn PartialEq`), /// and a concrete type `self_ty`, returns a full predicate where the existentially quantified variable `?Self` /// has been replaced with `self_ty` (e.g., `self_ty: PartialEq`, in our example). @@ -727,7 +729,7 @@ impl<'tcx> Binder<'tcx, ExistentialPredicate<'tcx>> { } } -impl<'tcx> List>> { +impl<'tcx> List> { /// Returns the "principal `DefId`" of this set of existential predicates. /// /// A Rust trait object type consists (in addition to a lifetime bound) diff --git a/compiler/rustc_symbol_mangling/src/legacy.rs b/compiler/rustc_symbol_mangling/src/legacy.rs index 46c5fe78ffbf6..c60a2f4671d6c 100644 --- a/compiler/rustc_symbol_mangling/src/legacy.rs +++ b/compiler/rustc_symbol_mangling/src/legacy.rs @@ -244,7 +244,7 @@ impl<'tcx> Printer<'tcx> for &mut SymbolPrinter<'tcx> { fn print_dyn_existential( mut self, - predicates: &'tcx ty::List>>, + predicates: &'tcx ty::List>, ) -> Result { let mut first = true; for p in predicates { diff --git a/compiler/rustc_symbol_mangling/src/typeid/typeid_itanium_cxx_abi.rs b/compiler/rustc_symbol_mangling/src/typeid/typeid_itanium_cxx_abi.rs index 6aa031c8378e6..87128e0f893a2 100644 --- a/compiler/rustc_symbol_mangling/src/typeid/typeid_itanium_cxx_abi.rs +++ b/compiler/rustc_symbol_mangling/src/typeid/typeid_itanium_cxx_abi.rs @@ -12,8 +12,8 @@ use rustc_data_structures::fx::FxHashMap; use rustc_hir as hir; use rustc_middle::ty::subst::{GenericArg, GenericArgKind, SubstsRef}; use rustc_middle::ty::{ - self, Binder, Const, ExistentialPredicate, FloatTy, FnSig, IntTy, List, Region, RegionKind, - TermKind, Ty, TyCtxt, UintTy, + self, Const, ExistentialPredicate, FloatTy, FnSig, IntTy, List, Region, RegionKind, TermKind, + Ty, TyCtxt, UintTy, }; use rustc_span::def_id::DefId; use rustc_span::symbol::sym; @@ -226,7 +226,7 @@ fn encode_fnsig<'tcx>( /// Rust types that are not used at the FFI boundary. fn encode_predicate<'tcx>( tcx: TyCtxt<'tcx>, - predicate: Binder<'tcx, ExistentialPredicate<'tcx>>, + predicate: ty::PolyExistentialPredicate<'tcx>, dict: &mut FxHashMap, usize>, options: EncodeTyOptions, ) -> String { @@ -261,13 +261,13 @@ fn encode_predicate<'tcx>( /// Rust types that are not used at the FFI boundary. fn encode_predicates<'tcx>( tcx: TyCtxt<'tcx>, - predicates: &List>>, + predicates: &List>, dict: &mut FxHashMap, usize>, options: EncodeTyOptions, ) -> String { // E as part of vendor extended type let mut s = String::new(); - let predicates: Vec>> = + let predicates: Vec> = predicates.iter().map(|predicate| predicate).collect(); for predicate in predicates { s.push_str(&encode_predicate(tcx, predicate, dict, options)); diff --git a/compiler/rustc_symbol_mangling/src/v0.rs b/compiler/rustc_symbol_mangling/src/v0.rs index e540e2f2a2192..6ad0a7d29110c 100644 --- a/compiler/rustc_symbol_mangling/src/v0.rs +++ b/compiler/rustc_symbol_mangling/src/v0.rs @@ -502,7 +502,7 @@ impl<'tcx> Printer<'tcx> for &mut SymbolMangler<'tcx> { fn print_dyn_existential( mut self, - predicates: &'tcx ty::List>>, + predicates: &'tcx ty::List>, ) -> Result { // Okay, so this is a bit tricky. Imagine we have a trait object like // `dyn for<'a> Foo<'a, Bar = &'a ()>`. When we mangle this, the diff --git a/compiler/rustc_trait_selection/src/traits/wf.rs b/compiler/rustc_trait_selection/src/traits/wf.rs index d05e893de433a..fce92c66ee8c7 100644 --- a/compiler/rustc_trait_selection/src/traits/wf.rs +++ b/compiler/rustc_trait_selection/src/traits/wf.rs @@ -758,7 +758,7 @@ impl<'tcx> WfPredicates<'tcx> { fn from_object_ty( &mut self, ty: Ty<'tcx>, - data: &'tcx ty::List>>, + data: &'tcx ty::List>, region: ty::Region<'tcx>, ) { // Imagine a type like this: @@ -822,7 +822,7 @@ impl<'tcx> WfPredicates<'tcx> { /// `infer::required_region_bounds`, see that for more information. pub fn object_region_bounds<'tcx>( tcx: TyCtxt<'tcx>, - existential_predicates: &'tcx ty::List>>, + existential_predicates: &'tcx ty::List>, ) -> Vec> { // Since we don't actually *know* the self type for an object, // this "open(err)" serves as a kind of dummy standin -- basically diff --git a/compiler/rustc_traits/src/chalk/lowering.rs b/compiler/rustc_traits/src/chalk/lowering.rs index 25cedefa26127..36bd466496e12 100644 --- a/compiler/rustc_traits/src/chalk/lowering.rs +++ b/compiler/rustc_traits/src/chalk/lowering.rs @@ -634,7 +634,7 @@ impl<'tcx> LowerInto<'tcx, Option LowerInto<'tcx, chalk_ir::Binders>>> - for &'tcx ty::List>> + for &'tcx ty::List> { fn lower_into( self, diff --git a/src/tools/clippy/clippy_lints/src/ptr.rs b/src/tools/clippy/clippy_lints/src/ptr.rs index c8c6f32c6c989..180d534636e0f 100644 --- a/src/tools/clippy/clippy_lints/src/ptr.rs +++ b/src/tools/clippy/clippy_lints/src/ptr.rs @@ -687,7 +687,7 @@ fn check_ptr_arg_usage<'tcx>(cx: &LateContext<'tcx>, body: &'tcx Body<'_>, args: fn matches_preds<'tcx>( cx: &LateContext<'tcx>, ty: Ty<'tcx>, - preds: &'tcx [Binder<'tcx, ExistentialPredicate<'tcx>>], + preds: &'tcx [ty::PolyExistentialPredicate<'tcx>], ) -> bool { let infcx = cx.tcx.infer_ctxt().build(); preds.iter().all(|&p| match cx.tcx.erase_late_bound_regions(p) { From 3338244f698022611bbc77947f9eb8b5d24d56e5 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sat, 19 Nov 2022 13:41:21 +0100 Subject: [PATCH 08/14] deduplicate constant evaluation in cranelift backend also sync LLVM and cranelift structure a bit --- .../rustc_codegen_cranelift/src/constant.rs | 58 ++++++++----------- .../rustc_codegen_ssa/src/mir/constant.rs | 9 ++- compiler/rustc_middle/src/ty/consts.rs | 15 ----- 3 files changed, 31 insertions(+), 51 deletions(-) diff --git a/compiler/rustc_codegen_cranelift/src/constant.rs b/compiler/rustc_codegen_cranelift/src/constant.rs index 5478caee57d45..077f33bb99cf7 100644 --- a/compiler/rustc_codegen_cranelift/src/constant.rs +++ b/compiler/rustc_codegen_cranelift/src/constant.rs @@ -38,22 +38,8 @@ impl ConstantCx { pub(crate) fn check_constants(fx: &mut FunctionCx<'_, '_, '_>) -> bool { let mut all_constants_ok = true; for constant in &fx.mir.required_consts { - let unevaluated = match fx.monomorphize(constant.literal) { - ConstantKind::Ty(_) => unreachable!(), - ConstantKind::Unevaluated(uv, _) => uv, - ConstantKind::Val(..) => continue, - }; - - if let Err(err) = fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), unevaluated, None) { + if eval_mir_constant(fx, constant).is_none() { all_constants_ok = false; - match err { - ErrorHandled::Reported(_) => { - fx.tcx.sess.span_err(constant.span, "erroneous constant encountered"); - } - ErrorHandled::TooGeneric => { - span_bug!(constant.span, "codegen encountered polymorphic constant: {:?}", err); - } - } } } all_constants_ok @@ -80,15 +66,15 @@ pub(crate) fn codegen_tls_ref<'tcx>( } pub(crate) fn eval_mir_constant<'tcx>( - fx: &mut FunctionCx<'_, '_, 'tcx>, + fx: &FunctionCx<'_, '_, 'tcx>, constant: &Constant<'tcx>, -) -> (ConstValue<'tcx>, Ty<'tcx>) { +) -> Option<(ConstValue<'tcx>, Ty<'tcx>)> { let constant_kind = fx.monomorphize(constant.literal); let uv = match constant_kind { ConstantKind::Ty(const_) => match const_.kind() { ty::ConstKind::Unevaluated(uv) => uv.expand(), ty::ConstKind::Value(val) => { - return (fx.tcx.valtree_to_const_val((const_.ty(), val)), const_.ty()); + return Some((fx.tcx.valtree_to_const_val((const_.ty(), val)), const_.ty())); } err => span_bug!( constant.span, @@ -102,22 +88,31 @@ pub(crate) fn eval_mir_constant<'tcx>( span_bug!(constant.span, "MIR constant refers to static"); } ConstantKind::Unevaluated(uv, _) => uv, - ConstantKind::Val(val, _) => return (val, constant_kind.ty()), + ConstantKind::Val(val, _) => return Some((val, constant_kind.ty())), }; - ( - fx.tcx.const_eval_resolve(ty::ParamEnv::reveal_all(), uv, None).unwrap_or_else(|_err| { - span_bug!(constant.span, "erroneous constant not captured by required_consts"); - }), - constant_kind.ty(), - ) + let val = fx + .tcx + .const_eval_resolve(ty::ParamEnv::reveal_all(), uv, None) + .map_err(|err| match err { + ErrorHandled::Reported(_) => { + fx.tcx.sess.span_err(constant.span, "erroneous constant encountered"); + } + ErrorHandled::TooGeneric => { + span_bug!(constant.span, "codegen encountered polymorphic constant: {:?}", err); + } + }) + .ok(); + val.map(|val| (val, constant_kind.ty())) } pub(crate) fn codegen_constant_operand<'tcx>( fx: &mut FunctionCx<'_, '_, 'tcx>, constant: &Constant<'tcx>, ) -> CValue<'tcx> { - let (const_val, ty) = eval_mir_constant(fx, constant); + let (const_val, ty) = eval_mir_constant(fx, constant).unwrap_or_else(|| { + span_bug!(constant.span, "erroneous constant not captured by required_consts") + }); codegen_const_value(fx, const_val, ty) } @@ -453,20 +448,13 @@ fn define_all_allocs(tcx: TyCtxt<'_>, module: &mut dyn Module, cx: &mut Constant assert!(cx.todo.is_empty(), "{:?}", cx.todo); } +/// Used only for intrinsic implementations that need a compile-time constant pub(crate) fn mir_operand_get_const_val<'tcx>( fx: &FunctionCx<'_, '_, 'tcx>, operand: &Operand<'tcx>, ) -> Option> { match operand { - Operand::Constant(const_) => match fx.monomorphize(const_.literal) { - ConstantKind::Ty(const_) => Some( - const_.eval_for_mir(fx.tcx, ParamEnv::reveal_all()).try_to_value(fx.tcx).unwrap(), - ), - ConstantKind::Val(val, _) => Some(val), - ConstantKind::Unevaluated(uv, _) => { - Some(fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), uv, None).unwrap()) - } - }, + Operand::Constant(const_) => Some(eval_mir_constant(fx, const_).unwrap().0), // FIXME(rust-lang/rust#85105): Casts like `IMM8 as u32` result in the const being stored // inside a temporary before being passed to the intrinsic requiring the const argument. // This code tries to find a single constant defining definition of the referenced local. diff --git a/compiler/rustc_codegen_ssa/src/mir/constant.rs b/compiler/rustc_codegen_ssa/src/mir/constant.rs index 4c6ab457c4945..53ff3c2409626 100644 --- a/compiler/rustc_codegen_ssa/src/mir/constant.rs +++ b/compiler/rustc_codegen_ssa/src/mir/constant.rs @@ -42,7 +42,14 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> { }; self.cx.tcx().const_eval_resolve(ty::ParamEnv::reveal_all(), uv, None).map_err(|err| { - self.cx.tcx().sess.span_err(constant.span, "erroneous constant encountered"); + match err { + ErrorHandled::Reported(_) => { + self.cx.tcx().sess.span_err(constant.span, "erroneous constant encountered"); + } + ErrorHandled::TooGeneric => { + span_bug!(constant.span, "codegen encountered polymorphic constant: {:?}", err); + } + } err }) } diff --git a/compiler/rustc_middle/src/ty/consts.rs b/compiler/rustc_middle/src/ty/consts.rs index 37153a6394405..9a58a196ed721 100644 --- a/compiler/rustc_middle/src/ty/consts.rs +++ b/compiler/rustc_middle/src/ty/consts.rs @@ -1,5 +1,4 @@ use crate::mir::interpret::LitToConstInput; -use crate::mir::ConstantKind; use crate::ty::{self, DefIdTree, InternalSubsts, ParamEnv, ParamEnvAnd, Ty, TyCtxt}; use rustc_data_structures::intern::Interned; use rustc_hir as hir; @@ -230,20 +229,6 @@ impl<'tcx> Const<'tcx> { } } - #[inline] - /// Tries to evaluate the constant if it is `Unevaluated` and creates a ConstValue if the - /// evaluation succeeds. If it doesn't succeed, returns the unevaluated constant. - pub fn eval_for_mir(self, tcx: TyCtxt<'tcx>, param_env: ParamEnv<'tcx>) -> ConstantKind<'tcx> { - if let Some(val) = self.kind().try_eval_for_mir(tcx, param_env) { - match val { - Ok(const_val) => ConstantKind::from_value(const_val, self.ty()), - Err(guar) => ConstantKind::Ty(tcx.const_error_with_guaranteed(self.ty(), guar)), - } - } else { - ConstantKind::Ty(self) - } - } - #[inline] /// Panics if the value cannot be evaluated or doesn't contain a valid integer of the given type. pub fn eval_bits(self, tcx: TyCtxt<'tcx>, param_env: ParamEnv<'tcx>, ty: Ty<'tcx>) -> u128 { From 6f1c7b24705d8e744ddea9b445cb70e0a0d328cb Mon Sep 17 00:00:00 2001 From: Alex Pinkus Date: Sat, 19 Nov 2022 17:50:48 -0800 Subject: [PATCH 09/14] Revert "Update CI to use Android NDK r25b" This reverts commit bf7f1ca316a249cf99d722d79a0db12fef687142. --- src/bootstrap/cc_detect.rs | 24 +++++-------------- .../docker/host-x86_64/arm-android/Dockerfile | 4 ++-- .../host-x86_64/dist-android/Dockerfile | 21 ++++++++++------ src/ci/docker/scripts/android-ndk.sh | 22 +++++++++++++++-- 4 files changed, 42 insertions(+), 29 deletions(-) diff --git a/src/bootstrap/cc_detect.rs b/src/bootstrap/cc_detect.rs index 65c882fb801e5..7128d542acfe9 100644 --- a/src/bootstrap/cc_detect.rs +++ b/src/bootstrap/cc_detect.rs @@ -47,8 +47,6 @@ fn cc2ar(cc: &Path, target: TargetSelection) -> Option { Some(PathBuf::from("ar")) } else if target.contains("vxworks") { Some(PathBuf::from("wr-ar")) - } else if target.contains("android") { - Some(cc.parent().unwrap().join(PathBuf::from("llvm-ar"))) } else { let parent = cc.parent().unwrap(); let file = cc.file_name().unwrap().to_str().unwrap(); @@ -221,22 +219,12 @@ fn set_compiler( } pub(crate) fn ndk_compiler(compiler: Language, triple: &str, ndk: &Path) -> PathBuf { - let mut triple_iter = triple.split("-"); - let triple_translated = if let Some(arch) = triple_iter.next() { - let arch_new = match arch { - "arm" | "armv7" | "armv7neon" | "thumbv7" | "thumbv7neon" => "armv7a", - other => other, - }; - std::iter::once(arch_new).chain(triple_iter).collect::>().join("-") - } else { - triple.to_string() - }; - - // API 19 is the earliest API level supported by NDK r25b but AArch64 and x86_64 support - // begins at API level 21. - let api_level = - if triple.contains("aarch64") || triple.contains("x86_64") { "21" } else { "19" }; - let compiler = format!("{}{}-{}", triple_translated, api_level, compiler.clang()); + let triple_translated = triple + .replace("armv7neon", "arm") + .replace("armv7", "arm") + .replace("thumbv7neon", "arm") + .replace("thumbv7", "arm"); + let compiler = format!("{}-{}", triple_translated, compiler.clang()); ndk.join("bin").join(compiler) } diff --git a/src/ci/docker/host-x86_64/arm-android/Dockerfile b/src/ci/docker/host-x86_64/arm-android/Dockerfile index 72ab167d9249b..7a875c960e133 100644 --- a/src/ci/docker/host-x86_64/arm-android/Dockerfile +++ b/src/ci/docker/host-x86_64/arm-android/Dockerfile @@ -6,7 +6,7 @@ RUN sh /scripts/android-base-apt-get.sh COPY scripts/android-ndk.sh /scripts/ RUN . /scripts/android-ndk.sh && \ - download_ndk android-ndk-r25b-linux.zip + download_and_make_toolchain android-ndk-r15c-linux-x86_64.zip arm 14 RUN dpkg --add-architecture i386 && \ apt-get update && \ @@ -30,7 +30,7 @@ ENV PATH=$PATH:/android/sdk/platform-tools ENV TARGETS=arm-linux-androideabi -ENV RUST_CONFIGURE_ARGS --arm-linux-androideabi-ndk=/android/ndk/toolchains/llvm/prebuilt/linux-x86_64/ +ENV RUST_CONFIGURE_ARGS --arm-linux-androideabi-ndk=/android/ndk/arm-14 ENV SCRIPT python3 ../x.py --stage 2 test --host='' --target $TARGETS diff --git a/src/ci/docker/host-x86_64/dist-android/Dockerfile b/src/ci/docker/host-x86_64/dist-android/Dockerfile index 95ed1b859bb57..2328db4ab8b1d 100644 --- a/src/ci/docker/host-x86_64/dist-android/Dockerfile +++ b/src/ci/docker/host-x86_64/dist-android/Dockerfile @@ -6,7 +6,14 @@ RUN sh /scripts/android-base-apt-get.sh # ndk COPY scripts/android-ndk.sh /scripts/ RUN . /scripts/android-ndk.sh && \ - download_ndk android-ndk-r25b-linux.zip + download_ndk android-ndk-r15c-linux-x86_64.zip && \ + make_standalone_toolchain arm 14 && \ + make_standalone_toolchain x86 14 && \ + make_standalone_toolchain arm 21 && \ + make_standalone_toolchain x86 21 && \ + make_standalone_toolchain arm64 21 && \ + make_standalone_toolchain x86_64 21 && \ + remove_ndk # env ENV TARGETS=arm-linux-androideabi @@ -19,12 +26,12 @@ ENV TARGETS=$TARGETS,x86_64-linux-android ENV RUST_CONFIGURE_ARGS \ --enable-extended \ --enable-profiler \ - --arm-linux-androideabi-ndk=/android/ndk/toolchains/llvm/prebuilt/linux-x86_64/ \ - --armv7-linux-androideabi-ndk=/android/ndk/toolchains/llvm/prebuilt/linux-x86_64/ \ - --thumbv7neon-linux-androideabi-ndk=/android/ndk/toolchains/llvm/prebuilt/linux-x86_64/ \ - --i686-linux-android-ndk=/android/ndk/toolchains/llvm/prebuilt/linux-x86_64/ \ - --aarch64-linux-android-ndk=/android/ndk/toolchains/llvm/prebuilt/linux-x86_64/ \ - --x86_64-linux-android-ndk=/android/ndk/toolchains/llvm/prebuilt/linux-x86_64/ \ + --arm-linux-androideabi-ndk=/android/ndk/arm-14 \ + --armv7-linux-androideabi-ndk=/android/ndk/arm-14 \ + --thumbv7neon-linux-androideabi-ndk=/android/ndk/arm-14 \ + --i686-linux-android-ndk=/android/ndk/x86-14 \ + --aarch64-linux-android-ndk=/android/ndk/arm64-21 \ + --x86_64-linux-android-ndk=/android/ndk/x86_64-21 \ --disable-docs ENV SCRIPT python3 ../x.py dist --host='' --target $TARGETS diff --git a/src/ci/docker/scripts/android-ndk.sh b/src/ci/docker/scripts/android-ndk.sh index 4dd6ac274fd5b..ba70c62ea3081 100644 --- a/src/ci/docker/scripts/android-ndk.sh +++ b/src/ci/docker/scripts/android-ndk.sh @@ -4,10 +4,28 @@ set -ex URL=https://dl.google.com/android/repository download_ndk() { - mkdir /android/ - cd /android + mkdir -p /android/ndk + cd /android/ndk curl -fO $URL/$1 unzip -q $1 rm $1 mv android-ndk-* ndk } + +make_standalone_toolchain() { + # See https://developer.android.com/ndk/guides/standalone_toolchain.htm + python3 /android/ndk/ndk/build/tools/make_standalone_toolchain.py \ + --install-dir /android/ndk/$1-$2 \ + --arch $1 \ + --api $2 +} + +remove_ndk() { + rm -rf /android/ndk/ndk +} + +download_and_make_toolchain() { + download_ndk $1 && \ + make_standalone_toolchain $2 $3 && \ + remove_ndk +} From 00bf999fcf9b20c3c6ea2bf77eaafaebf8a761de Mon Sep 17 00:00:00 2001 From: Tethys Svensson Date: Sun, 20 Nov 2022 12:30:14 +0100 Subject: [PATCH 10/14] Incorporate review feedback --- library/core/src/num/nonzero.rs | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/library/core/src/num/nonzero.rs b/library/core/src/num/nonzero.rs index db176de5aa194..d2d915371af3e 100644 --- a/library/core/src/num/nonzero.rs +++ b/library/core/src/num/nonzero.rs @@ -669,15 +669,12 @@ macro_rules! nonzero_signed_operations { #[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")] #[doc = concat!("let min = ", stringify!($Ty), "::new(", stringify!($Int), "::MIN)?;")] - #[doc = concat!("let min_plus = ", stringify!($Ty), "::new(", - stringify!($Int), "::MIN + 1)?;")] - #[doc = concat!("let max = ", stringify!($Ty), "::new(", + #[doc = concat!("# let max = ", stringify!($Ty), "::new(", stringify!($Int), "::MAX)?;")] /// /// assert_eq!(pos, pos.wrapping_abs()); /// assert_eq!(pos, neg.wrapping_abs()); /// assert_eq!(min, min.wrapping_abs()); - /// assert_eq!(max, min_plus.wrapping_abs()); /// # // FIXME: add once Neg is implemented? /// # // assert_eq!(max, (-max).wrapping_abs()); /// # Some(()) From 30b7e44a3cabe1c21129253da54b21193f65ebe0 Mon Sep 17 00:00:00 2001 From: Martin Nordholts Date: Sun, 20 Nov 2022 13:48:45 +0100 Subject: [PATCH 11/14] rustdoc JSON: Clarify that `Function` is also used for methods --- src/rustdoc-json-types/lib.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/rustdoc-json-types/lib.rs b/src/rustdoc-json-types/lib.rs index 50004b1ca1ef8..dd40f3507523c 100644 --- a/src/rustdoc-json-types/lib.rs +++ b/src/rustdoc-json-types/lib.rs @@ -413,6 +413,7 @@ pub enum Abi { Other(String), } +/// Represents a function (including methods and other associated functions) #[derive(Clone, Debug, PartialEq, Eq, Hash, Serialize, Deserialize)] pub struct Function { pub decl: FnDecl, From a6e09a19fc20cdf9043e1b856d15170ac0f96511 Mon Sep 17 00:00:00 2001 From: Nicholas Nethercote Date: Mon, 21 Nov 2022 11:48:25 +1100 Subject: [PATCH 12/14] Streamline deriving on packed structs. The current approach to field accesses in derived code: - Normal case: `&self.0` - In a packed struct that derives `Copy`: `&{self.0}` - In a packed struct that doesn't derive `Copy`: `let Self(ref x) = *self` The `let` pattern used in the third case is equivalent to the simpler field access in the first case. This commit changes the third case to use a field access. The commit also combines two boolean arguments (`is_packed` and `always_copy`) into a single field (`copy_fields`) earlier, to save passing both around. --- .../src/deriving/generic/mod.rs | 94 +++++-------------- .../ui/deriving/deriving-all-codegen.stdout | 23 ++--- 2 files changed, 30 insertions(+), 87 deletions(-) diff --git a/compiler/rustc_builtin_macros/src/deriving/generic/mod.rs b/compiler/rustc_builtin_macros/src/deriving/generic/mod.rs index f48c49f411ce8..3309fab224fb7 100644 --- a/compiler/rustc_builtin_macros/src/deriving/generic/mod.rs +++ b/compiler/rustc_builtin_macros/src/deriving/generic/mod.rs @@ -448,7 +448,8 @@ impl<'a> TraitDef<'a> { _ => unreachable!(), }; let container_id = cx.current_expansion.id.expn_data().parent.expect_local(); - let always_copy = has_no_type_params && cx.resolver.has_derive_copy(container_id); + let copy_fields = + is_packed && has_no_type_params && cx.resolver.has_derive_copy(container_id); let newitem = match item.kind { ast::ItemKind::Struct(ref struct_def, ref generics) => self.expand_struct_def( @@ -457,16 +458,14 @@ impl<'a> TraitDef<'a> { item.ident, generics, from_scratch, - is_packed, - always_copy, + copy_fields, ), ast::ItemKind::Enum(ref enum_def, ref generics) => { - // We ignore `is_packed`/`always_copy` here, because - // `repr(packed)` enums cause an error later on. + // We ignore `is_packed` here, because `repr(packed)` + // enums cause an error later on. // // This can only cause further compilation errors - // downstream in blatantly illegal code, so it - // is fine. + // downstream in blatantly illegal code, so it is fine. self.expand_enum_def(cx, enum_def, item.ident, generics, from_scratch) } ast::ItemKind::Union(ref struct_def, ref generics) => { @@ -477,8 +476,7 @@ impl<'a> TraitDef<'a> { item.ident, generics, from_scratch, - is_packed, - always_copy, + copy_fields, ) } else { cx.span_err(mitem.span, "this trait cannot be derived for unions"); @@ -748,8 +746,7 @@ impl<'a> TraitDef<'a> { type_ident: Ident, generics: &Generics, from_scratch: bool, - is_packed: bool, - always_copy: bool, + copy_fields: bool, ) -> P { let field_tys: Vec> = struct_def.fields().iter().map(|field| field.ty.clone()).collect(); @@ -777,8 +774,7 @@ impl<'a> TraitDef<'a> { type_ident, &selflike_args, &nonselflike_args, - is_packed, - always_copy, + copy_fields, ) }; @@ -1016,19 +1012,9 @@ impl<'a> MethodDef<'a> { /// } /// } /// ``` - /// If the struct doesn't impl `Copy`, we use let-destructuring with `ref`: - /// ``` - /// # struct A { x: u8, y: u8 } - /// impl PartialEq for A { - /// fn eq(&self, other: &A) -> bool { - /// let Self { x: ref __self_0_0, y: ref __self_0_1 } = *self; - /// let Self { x: ref __self_1_0, y: ref __self_1_1 } = *other; - /// *__self_0_0 == *__self_1_0 && *__self_0_1 == *__self_1_1 - /// } - /// } - /// ``` - /// This latter case only works if the fields match the alignment required - /// by the `packed(N)` attribute. (We'll get errors later on if not.) + /// If the struct doesn't impl `Copy`, we use the normal `&self.x`. This + /// only works if the fields match the alignment required by the + /// `packed(N)` attribute. (We'll get errors later on if not.) fn expand_struct_method_body<'b>( &self, cx: &mut ExtCtxt<'_>, @@ -1037,51 +1023,19 @@ impl<'a> MethodDef<'a> { type_ident: Ident, selflike_args: &[P], nonselflike_args: &[P], - is_packed: bool, - always_copy: bool, + copy_fields: bool, ) -> BlockOrExpr { - let span = trait_.span; assert!(selflike_args.len() == 1 || selflike_args.len() == 2); - let mk_body = |cx, selflike_fields| { - self.call_substructure_method( - cx, - trait_, - type_ident, - nonselflike_args, - &Struct(struct_def, selflike_fields), - ) - }; - - if !is_packed { - let selflike_fields = - trait_.create_struct_field_access_fields(cx, selflike_args, struct_def, false); - mk_body(cx, selflike_fields) - } else if always_copy { - let selflike_fields = - trait_.create_struct_field_access_fields(cx, selflike_args, struct_def, true); - mk_body(cx, selflike_fields) - } else { - // Packed and not copy. Need to use ref patterns. - let prefixes: Vec<_> = - (0..selflike_args.len()).map(|i| format!("__self_{}", i)).collect(); - let selflike_fields = trait_.create_struct_pattern_fields(cx, struct_def, &prefixes); - let mut body = mk_body(cx, selflike_fields); - - let struct_path = cx.path(span, vec![Ident::new(kw::SelfUpper, type_ident.span)]); - let patterns = - trait_.create_struct_patterns(cx, struct_path, struct_def, &prefixes, ByRef::Yes); - - // Do the let-destructuring. - let mut stmts: Vec<_> = iter::zip(selflike_args, patterns) - .map(|(selflike_arg_expr, pat)| { - let selflike_arg_expr = cx.expr_deref(span, selflike_arg_expr.clone()); - cx.stmt_let_pat(span, pat, selflike_arg_expr) - }) - .collect(); - stmts.extend(std::mem::take(&mut body.0)); - BlockOrExpr(stmts, body.1) - } + let selflike_fields = + trait_.create_struct_field_access_fields(cx, selflike_args, struct_def, copy_fields); + self.call_substructure_method( + cx, + trait_, + type_ident, + nonselflike_args, + &Struct(struct_def, selflike_fields), + ) } fn expand_static_struct_method_body( @@ -1531,7 +1485,7 @@ impl<'a> TraitDef<'a> { cx: &mut ExtCtxt<'_>, selflike_args: &[P], struct_def: &'a VariantData, - copy: bool, + copy_fields: bool, ) -> Vec { self.create_fields(struct_def, |i, struct_field, sp| { selflike_args @@ -1550,7 +1504,7 @@ impl<'a> TraitDef<'a> { }), ), ); - if copy { + if copy_fields { field_expr = cx.expr_block( cx.block(struct_field.span, vec![cx.stmt_expr(field_expr)]), ); diff --git a/src/test/ui/deriving/deriving-all-codegen.stdout b/src/test/ui/deriving/deriving-all-codegen.stdout index 92fce6888c089..a63cbd4ca7ede 100644 --- a/src/test/ui/deriving/deriving-all-codegen.stdout +++ b/src/test/ui/deriving/deriving-all-codegen.stdout @@ -463,16 +463,14 @@ struct PackedNonCopy(u8); impl ::core::clone::Clone for PackedNonCopy { #[inline] fn clone(&self) -> PackedNonCopy { - let Self(ref __self_0_0) = *self; - PackedNonCopy(::core::clone::Clone::clone(__self_0_0)) + PackedNonCopy(::core::clone::Clone::clone(&self.0)) } } #[automatically_derived] impl ::core::fmt::Debug for PackedNonCopy { fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result { - let Self(ref __self_0_0) = *self; ::core::fmt::Formatter::debug_tuple_field1_finish(f, "PackedNonCopy", - &__self_0_0) + &&self.0) } } #[automatically_derived] @@ -485,8 +483,7 @@ impl ::core::default::Default for PackedNonCopy { #[automatically_derived] impl ::core::hash::Hash for PackedNonCopy { fn hash<__H: ::core::hash::Hasher>(&self, state: &mut __H) -> () { - let Self(ref __self_0_0) = *self; - ::core::hash::Hash::hash(__self_0_0, state) + ::core::hash::Hash::hash(&self.0, state) } } #[automatically_derived] @@ -494,11 +491,7 @@ impl ::core::marker::StructuralPartialEq for PackedNonCopy { } #[automatically_derived] impl ::core::cmp::PartialEq for PackedNonCopy { #[inline] - fn eq(&self, other: &PackedNonCopy) -> bool { - let Self(ref __self_0_0) = *self; - let Self(ref __self_1_0) = *other; - *__self_0_0 == *__self_1_0 - } + fn eq(&self, other: &PackedNonCopy) -> bool { self.0 == other.0 } } #[automatically_derived] impl ::core::marker::StructuralEq for PackedNonCopy { } @@ -516,18 +509,14 @@ impl ::core::cmp::PartialOrd for PackedNonCopy { #[inline] fn partial_cmp(&self, other: &PackedNonCopy) -> ::core::option::Option<::core::cmp::Ordering> { - let Self(ref __self_0_0) = *self; - let Self(ref __self_1_0) = *other; - ::core::cmp::PartialOrd::partial_cmp(__self_0_0, __self_1_0) + ::core::cmp::PartialOrd::partial_cmp(&self.0, &other.0) } } #[automatically_derived] impl ::core::cmp::Ord for PackedNonCopy { #[inline] fn cmp(&self, other: &PackedNonCopy) -> ::core::cmp::Ordering { - let Self(ref __self_0_0) = *self; - let Self(ref __self_1_0) = *other; - ::core::cmp::Ord::cmp(__self_0_0, __self_1_0) + ::core::cmp::Ord::cmp(&self.0, &other.0) } } From 417ed9fee20a977aaa8e3f8a8f799b8580779fb7 Mon Sep 17 00:00:00 2001 From: Maybe Waffle Date: Wed, 16 Nov 2022 19:26:38 +0000 Subject: [PATCH 13/14] Remove `ref` patterns from `rustc_ast` Also use if let chains in one case. --- compiler/rustc_ast/src/ast.rs | 44 ++--- compiler/rustc_ast/src/attr/mod.rs | 90 +++++---- compiler/rustc_ast/src/mut_visit.rs | 8 +- compiler/rustc_ast/src/token.rs | 8 +- compiler/rustc_ast/src/util/parser.rs | 22 +-- compiler/rustc_ast/src/visit.rs | 266 +++++++++++++------------- 6 files changed, 214 insertions(+), 224 deletions(-) diff --git a/compiler/rustc_ast/src/ast.rs b/compiler/rustc_ast/src/ast.rs index e6b72bd58c540..4ad9981991d30 100644 --- a/compiler/rustc_ast/src/ast.rs +++ b/compiler/rustc_ast/src/ast.rs @@ -175,9 +175,9 @@ impl GenericArgs { } pub fn span(&self) -> Span { - match *self { - AngleBracketed(ref data) => data.span, - Parenthesized(ref data) => data.span, + match self { + AngleBracketed(data) => data.span, + Parenthesized(data) => data.span, } } } @@ -312,8 +312,8 @@ pub enum GenericBound { impl GenericBound { pub fn span(&self) -> Span { match self { - GenericBound::Trait(ref t, ..) => t.span, - GenericBound::Outlives(ref l) => l.ident.span, + GenericBound::Trait(t, ..) => t.span, + GenericBound::Outlives(l) => l.ident.span, } } } @@ -1115,23 +1115,23 @@ impl Expr { /// If this is not the case, name resolution does not resolve `N` when using /// `min_const_generics` as more complex expressions are not supported. pub fn is_potential_trivial_const_param(&self) -> bool { - let this = if let ExprKind::Block(ref block, None) = self.kind { - if block.stmts.len() == 1 { - if let StmtKind::Expr(ref expr) = block.stmts[0].kind { expr } else { self } - } else { - self - } + let this = if let ExprKind::Block(block, None) = &self.kind + && block.stmts.len() == 1 + && let StmtKind::Expr(expr) = &block.stmts[0].kind + { + expr } else { self }; - if let ExprKind::Path(None, ref path) = this.kind { - if path.segments.len() == 1 && path.segments[0].args.is_none() { - return true; - } + if let ExprKind::Path(None, path) = &this.kind + && path.segments.len() == 1 + && path.segments[0].args.is_none() + { + true + } else { + false } - - false } pub fn to_bound(&self) -> Option { @@ -2393,9 +2393,9 @@ pub enum FnRetTy { impl FnRetTy { pub fn span(&self) -> Span { - match *self { - FnRetTy::Default(span) => span, - FnRetTy::Ty(ref ty) => ty.span, + match self { + &FnRetTy::Default(span) => span, + FnRetTy::Ty(ty) => ty.span, } } } @@ -2657,8 +2657,8 @@ pub enum VariantData { impl VariantData { /// Return the fields of this variant. pub fn fields(&self) -> &[FieldDef] { - match *self { - VariantData::Struct(ref fields, ..) | VariantData::Tuple(ref fields, _) => fields, + match self { + VariantData::Struct(fields, ..) | VariantData::Tuple(fields, _) => fields, _ => &[], } } diff --git a/compiler/rustc_ast/src/attr/mod.rs b/compiler/rustc_ast/src/attr/mod.rs index 09b08d5059c1c..b7be94dde480e 100644 --- a/compiler/rustc_ast/src/attr/mod.rs +++ b/compiler/rustc_ast/src/attr/mod.rs @@ -44,16 +44,16 @@ impl MarkedAttrs { impl NestedMetaItem { /// Returns the `MetaItem` if `self` is a `NestedMetaItem::MetaItem`. pub fn meta_item(&self) -> Option<&MetaItem> { - match *self { - NestedMetaItem::MetaItem(ref item) => Some(item), + match self { + NestedMetaItem::MetaItem(item) => Some(item), _ => None, } } /// Returns the `Lit` if `self` is a `NestedMetaItem::Literal`s. pub fn literal(&self) -> Option<&Lit> { - match *self { - NestedMetaItem::Literal(ref lit) => Some(lit), + match self { + NestedMetaItem::Literal(lit) => Some(lit), _ => None, } } @@ -116,18 +116,18 @@ impl NestedMetaItem { impl Attribute { #[inline] pub fn has_name(&self, name: Symbol) -> bool { - match self.kind { - AttrKind::Normal(ref normal) => normal.item.path == name, + match &self.kind { + AttrKind::Normal(normal) => normal.item.path == name, AttrKind::DocComment(..) => false, } } /// For a single-segment attribute, returns its name; otherwise, returns `None`. pub fn ident(&self) -> Option { - match self.kind { - AttrKind::Normal(ref normal) => { - if normal.item.path.segments.len() == 1 { - Some(normal.item.path.segments[0].ident) + match &self.kind { + AttrKind::Normal(normal) => { + if let [ident] = &*normal.item.path.segments { + Some(ident.ident) } else { None } @@ -140,17 +140,15 @@ impl Attribute { } pub fn value_str(&self) -> Option { - match self.kind { - AttrKind::Normal(ref normal) => { - normal.item.meta_kind().and_then(|kind| kind.value_str()) - } + match &self.kind { + AttrKind::Normal(normal) => normal.item.meta_kind().and_then(|kind| kind.value_str()), AttrKind::DocComment(..) => None, } } pub fn meta_item_list(&self) -> Option> { - match self.kind { - AttrKind::Normal(ref normal) => match normal.item.meta_kind() { + match &self.kind { + AttrKind::Normal(normal) => match normal.item.meta_kind() { Some(MetaItemKind::List(list)) => Some(list), _ => None, }, @@ -191,8 +189,8 @@ impl MetaItem { } pub fn meta_item_list(&self) -> Option<&[NestedMetaItem]> { - match self.kind { - MetaItemKind::List(ref l) => Some(&l[..]), + match &self.kind { + MetaItemKind::List(l) => Some(&**l), _ => None, } } @@ -268,9 +266,9 @@ impl Attribute { /// * `#[doc = "doc"]` returns `Some("doc")`. /// * `#[doc(...)]` returns `None`. pub fn doc_str(&self) -> Option { - match self.kind { - AttrKind::DocComment(.., data) => Some(data), - AttrKind::Normal(ref normal) if normal.item.path == sym::doc => { + match &self.kind { + AttrKind::DocComment(.., data) => Some(*data), + AttrKind::Normal(normal) if normal.item.path == sym::doc => { normal.item.meta_kind().and_then(|kind| kind.value_str()) } _ => None, @@ -282,8 +280,8 @@ impl Attribute { } pub fn get_normal_item(&self) -> &AttrItem { - match self.kind { - AttrKind::Normal(ref normal) => &normal.item, + match &self.kind { + AttrKind::Normal(normal) => &normal.item, AttrKind::DocComment(..) => panic!("unexpected doc comment"), } } @@ -297,28 +295,28 @@ impl Attribute { /// Extracts the MetaItem from inside this Attribute. pub fn meta(&self) -> Option { - match self.kind { - AttrKind::Normal(ref normal) => normal.item.meta(self.span), + match &self.kind { + AttrKind::Normal(normal) => normal.item.meta(self.span), AttrKind::DocComment(..) => None, } } pub fn meta_kind(&self) -> Option { - match self.kind { - AttrKind::Normal(ref normal) => normal.item.meta_kind(), + match &self.kind { + AttrKind::Normal(normal) => normal.item.meta_kind(), AttrKind::DocComment(..) => None, } } pub fn tokens(&self) -> TokenStream { - match self.kind { - AttrKind::Normal(ref normal) => normal + match &self.kind { + AttrKind::Normal(normal) => normal .tokens .as_ref() .unwrap_or_else(|| panic!("attribute is missing tokens: {:?}", self)) .to_attr_token_stream() .to_tokenstream(), - AttrKind::DocComment(comment_kind, data) => TokenStream::new(vec![TokenTree::Token( + &AttrKind::DocComment(comment_kind, data) => TokenStream::new(vec![TokenTree::Token( Token::new(token::DocComment(comment_kind, self.style, data), self.span), Spacing::Alone, )]), @@ -496,17 +494,17 @@ impl MetaItem { let span = span.with_hi(segments.last().unwrap().ident.span.hi()); Path { span, segments, tokens: None } } - Some(TokenTree::Token(Token { kind: token::Interpolated(nt), .. }, _)) => match *nt { - token::Nonterminal::NtMeta(ref item) => return item.meta(item.path.span), - token::Nonterminal::NtPath(ref path) => (**path).clone(), + Some(TokenTree::Token(Token { kind: token::Interpolated(nt), .. }, _)) => match &*nt { + token::Nonterminal::NtMeta(item) => return item.meta(item.path.span), + token::Nonterminal::NtPath(path) => (**path).clone(), _ => return None, }, _ => return None, }; let list_closing_paren_pos = tokens.peek().map(|tt| tt.span().hi()); let kind = MetaItemKind::from_tokens(tokens)?; - let hi = match kind { - MetaItemKind::NameValue(ref lit) => lit.span.hi(), + let hi = match &kind { + MetaItemKind::NameValue(lit) => lit.span.hi(), MetaItemKind::List(..) => list_closing_paren_pos.unwrap_or(path.span.hi()), _ => path.span.hi(), }; @@ -518,8 +516,8 @@ impl MetaItem { impl MetaItemKind { pub fn value_str(&self) -> Option { match self { - MetaItemKind::NameValue(ref v) => match v.kind { - LitKind::Str(ref s, _) => Some(*s), + MetaItemKind::NameValue(v) => match v.kind { + LitKind::Str(s, _) => Some(s), _ => None, }, _ => None, @@ -557,15 +555,15 @@ impl MetaItemKind { } fn token_trees(&self, span: Span) -> Vec { - match *self { + match self { MetaItemKind::Word => vec![], - MetaItemKind::NameValue(ref lit) => { + MetaItemKind::NameValue(lit) => { vec![ TokenTree::token_alone(token::Eq, span), TokenTree::Token(lit.to_token(), Spacing::Alone), ] } - MetaItemKind::List(ref list) => { + MetaItemKind::List(list) => { let mut tokens = Vec::new(); for (i, item) in list.iter().enumerate() { if i > 0 { @@ -648,16 +646,16 @@ impl MetaItemKind { impl NestedMetaItem { pub fn span(&self) -> Span { - match *self { - NestedMetaItem::MetaItem(ref item) => item.span, - NestedMetaItem::Literal(ref lit) => lit.span, + match self { + NestedMetaItem::MetaItem(item) => item.span, + NestedMetaItem::Literal(lit) => lit.span, } } fn token_trees(&self) -> Vec { - match *self { - NestedMetaItem::MetaItem(ref item) => item.token_trees(), - NestedMetaItem::Literal(ref lit) => { + match self { + NestedMetaItem::MetaItem(item) => item.token_trees(), + NestedMetaItem::Literal(lit) => { vec![TokenTree::Token(lit.to_token(), Spacing::Alone)] } } diff --git a/compiler/rustc_ast/src/mut_visit.rs b/compiler/rustc_ast/src/mut_visit.rs index ece4cb5556b47..f9ab5a1757085 100644 --- a/compiler/rustc_ast/src/mut_visit.rs +++ b/compiler/rustc_ast/src/mut_visit.rs @@ -439,15 +439,15 @@ pub fn noop_visit_constraint( ) { vis.visit_id(id); vis.visit_ident(ident); - if let Some(ref mut gen_args) = gen_args { + if let Some(gen_args) = gen_args { vis.visit_generic_args(gen_args); } match kind { - AssocConstraintKind::Equality { ref mut term } => match term { + AssocConstraintKind::Equality { term } => match term { Term::Ty(ty) => vis.visit_ty(ty), Term::Const(c) => vis.visit_anon_const(c), }, - AssocConstraintKind::Bound { ref mut bounds } => visit_bounds(bounds, vis), + AssocConstraintKind::Bound { bounds } => visit_bounds(bounds, vis), } vis.visit_span(span); } @@ -880,7 +880,7 @@ pub fn noop_flat_map_generic_param( let GenericParam { id, ident, attrs, bounds, kind, colon_span, is_placeholder: _ } = &mut param; vis.visit_id(id); vis.visit_ident(ident); - if let Some(ref mut colon_span) = colon_span { + if let Some(colon_span) = colon_span { vis.visit_span(colon_span); } visit_attrs(attrs, vis); diff --git a/compiler/rustc_ast/src/token.rs b/compiler/rustc_ast/src/token.rs index e0ff690e76678..cb32925584c58 100644 --- a/compiler/rustc_ast/src/token.rs +++ b/compiler/rustc_ast/src/token.rs @@ -601,9 +601,10 @@ impl Token { /// Returns `true` if the token is an interpolated path. fn is_path(&self) -> bool { - if let Interpolated(ref nt) = self.kind && let NtPath(..) = **nt { + if let Interpolated(nt) = &self.kind && let NtPath(..) = **nt { return true; } + false } @@ -611,7 +612,7 @@ impl Token { /// That is, is this a pre-parsed expression dropped into the token stream /// (which happens while parsing the result of macro expansion)? pub fn is_whole_expr(&self) -> bool { - if let Interpolated(ref nt) = self.kind + if let Interpolated(nt) = &self.kind && let NtExpr(_) | NtLiteral(_) | NtPath(_) | NtBlock(_) = **nt { return true; @@ -622,9 +623,10 @@ impl Token { // Is the token an interpolated block (`$b:block`)? pub fn is_whole_block(&self) -> bool { - if let Interpolated(ref nt) = self.kind && let NtBlock(..) = **nt { + if let Interpolated(nt) = &self.kind && let NtBlock(..) = **nt { return true; } + false } diff --git a/compiler/rustc_ast/src/util/parser.rs b/compiler/rustc_ast/src/util/parser.rs index 30c55dffb1803..f65f1f069cba2 100644 --- a/compiler/rustc_ast/src/util/parser.rs +++ b/compiler/rustc_ast/src/util/parser.rs @@ -377,26 +377,26 @@ pub fn needs_par_as_let_scrutinee(order: i8) -> bool { /// parens or other delimiters, e.g., `X { y: 1 }`, `X { y: 1 }.method()`, `foo == X { y: 1 }` and /// `X { y: 1 } == foo` all do, but `(X { y: 1 }) == foo` does not. pub fn contains_exterior_struct_lit(value: &ast::Expr) -> bool { - match value.kind { + match &value.kind { ast::ExprKind::Struct(..) => true, - ast::ExprKind::Assign(ref lhs, ref rhs, _) - | ast::ExprKind::AssignOp(_, ref lhs, ref rhs) - | ast::ExprKind::Binary(_, ref lhs, ref rhs) => { + ast::ExprKind::Assign(lhs, rhs, _) + | ast::ExprKind::AssignOp(_, lhs, rhs) + | ast::ExprKind::Binary(_, lhs, rhs) => { // X { y: 1 } + X { y: 2 } contains_exterior_struct_lit(&lhs) || contains_exterior_struct_lit(&rhs) } - ast::ExprKind::Await(ref x) - | ast::ExprKind::Unary(_, ref x) - | ast::ExprKind::Cast(ref x, _) - | ast::ExprKind::Type(ref x, _) - | ast::ExprKind::Field(ref x, _) - | ast::ExprKind::Index(ref x, _) => { + ast::ExprKind::Await(x) + | ast::ExprKind::Unary(_, x) + | ast::ExprKind::Cast(x, _) + | ast::ExprKind::Type(x, _) + | ast::ExprKind::Field(x, _) + | ast::ExprKind::Index(x, _) => { // &X { y: 1 }, X { y: 1 }.y contains_exterior_struct_lit(&x) } - ast::ExprKind::MethodCall(box ast::MethodCall { ref receiver, .. }) => { + ast::ExprKind::MethodCall(box ast::MethodCall { receiver, .. }) => { // X { y: 1 }.bar(...) contains_exterior_struct_lit(&receiver) } diff --git a/compiler/rustc_ast/src/visit.rs b/compiler/rustc_ast/src/visit.rs index ad5a2116c424a..0978fc94d698d 100644 --- a/compiler/rustc_ast/src/visit.rs +++ b/compiler/rustc_ast/src/visit.rs @@ -299,74 +299,68 @@ pub fn walk_trait_ref<'a, V: Visitor<'a>>(visitor: &mut V, trait_ref: &'a TraitR pub fn walk_item<'a, V: Visitor<'a>>(visitor: &mut V, item: &'a Item) { visitor.visit_vis(&item.vis); visitor.visit_ident(item.ident); - match item.kind { + match &item.kind { ItemKind::ExternCrate(_) => {} - ItemKind::Use(ref use_tree) => visitor.visit_use_tree(use_tree, item.id, false), - ItemKind::Static(ref typ, _, ref expr) | ItemKind::Const(_, ref typ, ref expr) => { + ItemKind::Use(use_tree) => visitor.visit_use_tree(use_tree, item.id, false), + ItemKind::Static(typ, _, expr) | ItemKind::Const(_, typ, expr) => { visitor.visit_ty(typ); walk_list!(visitor, visit_expr, expr); } - ItemKind::Fn(box Fn { defaultness: _, ref generics, ref sig, ref body }) => { + ItemKind::Fn(box Fn { defaultness: _, generics, sig, body }) => { let kind = FnKind::Fn(FnCtxt::Free, item.ident, sig, &item.vis, generics, body.as_deref()); visitor.visit_fn(kind, item.span, item.id) } - ItemKind::Mod(_unsafety, ref mod_kind) => match mod_kind { + ItemKind::Mod(_unsafety, mod_kind) => match mod_kind { ModKind::Loaded(items, _inline, _inner_span) => { walk_list!(visitor, visit_item, items) } ModKind::Unloaded => {} }, - ItemKind::ForeignMod(ref foreign_module) => { + ItemKind::ForeignMod(foreign_module) => { walk_list!(visitor, visit_foreign_item, &foreign_module.items); } - ItemKind::GlobalAsm(ref asm) => visitor.visit_inline_asm(asm), - ItemKind::TyAlias(box TyAlias { ref generics, ref bounds, ref ty, .. }) => { + ItemKind::GlobalAsm(asm) => visitor.visit_inline_asm(asm), + ItemKind::TyAlias(box TyAlias { generics, bounds, ty, .. }) => { visitor.visit_generics(generics); walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound); walk_list!(visitor, visit_ty, ty); } - ItemKind::Enum(ref enum_definition, ref generics) => { + ItemKind::Enum(enum_definition, generics) => { visitor.visit_generics(generics); visitor.visit_enum_def(enum_definition) } ItemKind::Impl(box Impl { defaultness: _, unsafety: _, - ref generics, + generics, constness: _, polarity: _, - ref of_trait, - ref self_ty, - ref items, + of_trait, + self_ty, + items, }) => { visitor.visit_generics(generics); walk_list!(visitor, visit_trait_ref, of_trait); visitor.visit_ty(self_ty); walk_list!(visitor, visit_assoc_item, items, AssocCtxt::Impl); } - ItemKind::Struct(ref struct_definition, ref generics) - | ItemKind::Union(ref struct_definition, ref generics) => { + ItemKind::Struct(struct_definition, generics) + | ItemKind::Union(struct_definition, generics) => { visitor.visit_generics(generics); visitor.visit_variant_data(struct_definition); } - ItemKind::Trait(box Trait { - unsafety: _, - is_auto: _, - ref generics, - ref bounds, - ref items, - }) => { + ItemKind::Trait(box Trait { unsafety: _, is_auto: _, generics, bounds, items }) => { visitor.visit_generics(generics); walk_list!(visitor, visit_param_bound, bounds, BoundKind::SuperTraits); walk_list!(visitor, visit_assoc_item, items, AssocCtxt::Trait); } - ItemKind::TraitAlias(ref generics, ref bounds) => { + ItemKind::TraitAlias(generics, bounds) => { visitor.visit_generics(generics); walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound); } - ItemKind::MacCall(ref mac) => visitor.visit_mac_call(mac), - ItemKind::MacroDef(ref ts) => visitor.visit_mac_def(ts, item.id), + ItemKind::MacCall(mac) => visitor.visit_mac_call(mac), + ItemKind::MacroDef(ts) => visitor.visit_mac_def(ts, item.id), } walk_list!(visitor, visit_attribute, &item.attrs); } @@ -399,39 +393,39 @@ pub fn walk_pat_field<'a, V: Visitor<'a>>(visitor: &mut V, fp: &'a PatField) { } pub fn walk_ty<'a, V: Visitor<'a>>(visitor: &mut V, typ: &'a Ty) { - match typ.kind { - TyKind::Slice(ref ty) | TyKind::Paren(ref ty) => visitor.visit_ty(ty), - TyKind::Ptr(ref mutable_type) => visitor.visit_ty(&mutable_type.ty), - TyKind::Rptr(ref opt_lifetime, ref mutable_type) => { + match &typ.kind { + TyKind::Slice(ty) | TyKind::Paren(ty) => visitor.visit_ty(ty), + TyKind::Ptr(mutable_type) => visitor.visit_ty(&mutable_type.ty), + TyKind::Rptr(opt_lifetime, mutable_type) => { walk_list!(visitor, visit_lifetime, opt_lifetime, LifetimeCtxt::Rptr); visitor.visit_ty(&mutable_type.ty) } - TyKind::Tup(ref tuple_element_types) => { + TyKind::Tup(tuple_element_types) => { walk_list!(visitor, visit_ty, tuple_element_types); } - TyKind::BareFn(ref function_declaration) => { + TyKind::BareFn(function_declaration) => { walk_list!(visitor, visit_generic_param, &function_declaration.generic_params); walk_fn_decl(visitor, &function_declaration.decl); } - TyKind::Path(ref maybe_qself, ref path) => { - if let Some(ref qself) = *maybe_qself { + TyKind::Path(maybe_qself, path) => { + if let Some(qself) = maybe_qself { visitor.visit_ty(&qself.ty); } visitor.visit_path(path, typ.id); } - TyKind::Array(ref ty, ref length) => { + TyKind::Array(ty, length) => { visitor.visit_ty(ty); visitor.visit_anon_const(length) } - TyKind::TraitObject(ref bounds, ..) => { + TyKind::TraitObject(bounds, ..) => { walk_list!(visitor, visit_param_bound, bounds, BoundKind::TraitObject); } - TyKind::ImplTrait(_, ref bounds) => { + TyKind::ImplTrait(_, bounds) => { walk_list!(visitor, visit_param_bound, bounds, BoundKind::Impl); } - TyKind::Typeof(ref expression) => visitor.visit_anon_const(expression), + TyKind::Typeof(expression) => visitor.visit_anon_const(expression), TyKind::Infer | TyKind::ImplicitSelf | TyKind::Err => {} - TyKind::MacCall(ref mac) => visitor.visit_mac_call(mac), + TyKind::MacCall(mac) => visitor.visit_mac_call(mac), TyKind::Never | TyKind::CVarArgs => {} } } @@ -444,15 +438,15 @@ pub fn walk_path<'a, V: Visitor<'a>>(visitor: &mut V, path: &'a Path) { pub fn walk_use_tree<'a, V: Visitor<'a>>(visitor: &mut V, use_tree: &'a UseTree, id: NodeId) { visitor.visit_path(&use_tree.prefix, id); - match use_tree.kind { + match &use_tree.kind { UseTreeKind::Simple(rename, ..) => { // The extra IDs are handled during HIR lowering. - if let Some(rename) = rename { + if let &Some(rename) = rename { visitor.visit_ident(rename); } } UseTreeKind::Glob => {} - UseTreeKind::Nested(ref use_trees) => { + UseTreeKind::Nested(use_trees) => { for &(ref nested_tree, nested_id) in use_trees { visitor.visit_use_tree(nested_tree, nested_id, true); } @@ -462,7 +456,7 @@ pub fn walk_use_tree<'a, V: Visitor<'a>>(visitor: &mut V, use_tree: &'a UseTree, pub fn walk_path_segment<'a, V: Visitor<'a>>(visitor: &mut V, segment: &'a PathSegment) { visitor.visit_ident(segment.ident); - if let Some(ref args) = segment.args { + if let Some(args) = &segment.args { visitor.visit_generic_args(args); } } @@ -471,8 +465,8 @@ pub fn walk_generic_args<'a, V>(visitor: &mut V, generic_args: &'a GenericArgs) where V: Visitor<'a>, { - match *generic_args { - GenericArgs::AngleBracketed(ref data) => { + match generic_args { + GenericArgs::AngleBracketed(data) => { for arg in &data.args { match arg { AngleBracketedArg::Arg(a) => visitor.visit_generic_arg(a), @@ -480,7 +474,7 @@ where } } } - GenericArgs::Parenthesized(ref data) => { + GenericArgs::Parenthesized(data) => { walk_list!(visitor, visit_ty, &data.inputs); walk_fn_ret_ty(visitor, &data.output); } @@ -500,64 +494,64 @@ where pub fn walk_assoc_constraint<'a, V: Visitor<'a>>(visitor: &mut V, constraint: &'a AssocConstraint) { visitor.visit_ident(constraint.ident); - if let Some(ref gen_args) = constraint.gen_args { + if let Some(gen_args) = &constraint.gen_args { visitor.visit_generic_args(gen_args); } - match constraint.kind { - AssocConstraintKind::Equality { ref term } => match term { + match &constraint.kind { + AssocConstraintKind::Equality { term } => match term { Term::Ty(ty) => visitor.visit_ty(ty), Term::Const(c) => visitor.visit_anon_const(c), }, - AssocConstraintKind::Bound { ref bounds } => { + AssocConstraintKind::Bound { bounds } => { walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound); } } } pub fn walk_pat<'a, V: Visitor<'a>>(visitor: &mut V, pattern: &'a Pat) { - match pattern.kind { - PatKind::TupleStruct(ref opt_qself, ref path, ref elems) => { - if let Some(ref qself) = *opt_qself { + match &pattern.kind { + PatKind::TupleStruct(opt_qself, path, elems) => { + if let Some(qself) = opt_qself { visitor.visit_ty(&qself.ty); } visitor.visit_path(path, pattern.id); walk_list!(visitor, visit_pat, elems); } - PatKind::Path(ref opt_qself, ref path) => { - if let Some(ref qself) = *opt_qself { + PatKind::Path(opt_qself, path) => { + if let Some(qself) = opt_qself { visitor.visit_ty(&qself.ty); } visitor.visit_path(path, pattern.id) } - PatKind::Struct(ref opt_qself, ref path, ref fields, _) => { - if let Some(ref qself) = *opt_qself { + PatKind::Struct(opt_qself, path, fields, _) => { + if let Some(qself) = opt_qself { visitor.visit_ty(&qself.ty); } visitor.visit_path(path, pattern.id); walk_list!(visitor, visit_pat_field, fields); } - PatKind::Box(ref subpattern) - | PatKind::Ref(ref subpattern, _) - | PatKind::Paren(ref subpattern) => visitor.visit_pat(subpattern), - PatKind::Ident(_, ident, ref optional_subpattern) => { - visitor.visit_ident(ident); + PatKind::Box(subpattern) | PatKind::Ref(subpattern, _) | PatKind::Paren(subpattern) => { + visitor.visit_pat(subpattern) + } + PatKind::Ident(_, ident, optional_subpattern) => { + visitor.visit_ident(*ident); walk_list!(visitor, visit_pat, optional_subpattern); } - PatKind::Lit(ref expression) => visitor.visit_expr(expression), - PatKind::Range(ref lower_bound, ref upper_bound, _) => { + PatKind::Lit(expression) => visitor.visit_expr(expression), + PatKind::Range(lower_bound, upper_bound, _) => { walk_list!(visitor, visit_expr, lower_bound); walk_list!(visitor, visit_expr, upper_bound); } PatKind::Wild | PatKind::Rest => {} - PatKind::Tuple(ref elems) | PatKind::Slice(ref elems) | PatKind::Or(ref elems) => { + PatKind::Tuple(elems) | PatKind::Slice(elems) | PatKind::Or(elems) => { walk_list!(visitor, visit_pat, elems); } - PatKind::MacCall(ref mac) => visitor.visit_mac_call(mac), + PatKind::MacCall(mac) => visitor.visit_mac_call(mac), } } pub fn walk_foreign_item<'a, V: Visitor<'a>>(visitor: &mut V, item: &'a ForeignItem) { - let Item { id, span, ident, ref vis, ref attrs, ref kind, tokens: _ } = *item; + let &Item { id, span, ident, ref vis, ref attrs, ref kind, tokens: _ } = item; visitor.visit_vis(vis); visitor.visit_ident(ident); walk_list!(visitor, visit_attribute, attrs); @@ -566,7 +560,7 @@ pub fn walk_foreign_item<'a, V: Visitor<'a>>(visitor: &mut V, item: &'a ForeignI visitor.visit_ty(ty); walk_list!(visitor, visit_expr, expr); } - ForeignItemKind::Fn(box Fn { defaultness: _, ref generics, ref sig, ref body }) => { + ForeignItemKind::Fn(box Fn { defaultness: _, generics, sig, body }) => { let kind = FnKind::Fn(FnCtxt::Foreign, ident, sig, vis, generics, body.as_deref()); visitor.visit_fn(kind, span, id); } @@ -582,11 +576,9 @@ pub fn walk_foreign_item<'a, V: Visitor<'a>>(visitor: &mut V, item: &'a ForeignI } pub fn walk_param_bound<'a, V: Visitor<'a>>(visitor: &mut V, bound: &'a GenericBound) { - match *bound { - GenericBound::Trait(ref typ, ref _modifier) => visitor.visit_poly_trait_ref(typ), - GenericBound::Outlives(ref lifetime) => { - visitor.visit_lifetime(lifetime, LifetimeCtxt::Bound) - } + match bound { + GenericBound::Trait(typ, _modifier) => visitor.visit_poly_trait_ref(typ), + GenericBound::Outlives(lifetime) => visitor.visit_lifetime(lifetime, LifetimeCtxt::Bound), } } @@ -594,10 +586,10 @@ pub fn walk_generic_param<'a, V: Visitor<'a>>(visitor: &mut V, param: &'a Generi visitor.visit_ident(param.ident); walk_list!(visitor, visit_attribute, param.attrs.iter()); walk_list!(visitor, visit_param_bound, ¶m.bounds, BoundKind::Bound); - match param.kind { + match ¶m.kind { GenericParamKind::Lifetime => (), - GenericParamKind::Type { ref default } => walk_list!(visitor, visit_ty, default), - GenericParamKind::Const { ref ty, ref default, .. } => { + GenericParamKind::Type { default } => walk_list!(visitor, visit_ty, default), + GenericParamKind::Const { ty, default, .. } => { visitor.visit_ty(ty); if let Some(default) = default { visitor.visit_anon_const(default); @@ -621,24 +613,22 @@ pub fn walk_closure_binder<'a, V: Visitor<'a>>(visitor: &mut V, binder: &'a Clos } pub fn walk_where_predicate<'a, V: Visitor<'a>>(visitor: &mut V, predicate: &'a WherePredicate) { - match *predicate { + match predicate { WherePredicate::BoundPredicate(WhereBoundPredicate { - ref bounded_ty, - ref bounds, - ref bound_generic_params, + bounded_ty, + bounds, + bound_generic_params, .. }) => { visitor.visit_ty(bounded_ty); walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound); walk_list!(visitor, visit_generic_param, bound_generic_params); } - WherePredicate::RegionPredicate(WhereRegionPredicate { - ref lifetime, ref bounds, .. - }) => { + WherePredicate::RegionPredicate(WhereRegionPredicate { lifetime, bounds, .. }) => { visitor.visit_lifetime(lifetime, LifetimeCtxt::Bound); walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound); } - WherePredicate::EqPredicate(WhereEqPredicate { ref lhs_ty, ref rhs_ty, .. }) => { + WherePredicate::EqPredicate(WhereEqPredicate { lhs_ty, rhs_ty, .. }) => { visitor.visit_ty(lhs_ty); visitor.visit_ty(rhs_ty); } @@ -646,7 +636,7 @@ pub fn walk_where_predicate<'a, V: Visitor<'a>>(visitor: &mut V, predicate: &'a } pub fn walk_fn_ret_ty<'a, V: Visitor<'a>>(visitor: &mut V, ret_ty: &'a FnRetTy) { - if let FnRetTy::Ty(ref output_ty) = *ret_ty { + if let FnRetTy::Ty(output_ty) = ret_ty { visitor.visit_ty(output_ty) } } @@ -675,7 +665,7 @@ pub fn walk_fn<'a, V: Visitor<'a>>(visitor: &mut V, kind: FnKind<'a>) { } pub fn walk_assoc_item<'a, V: Visitor<'a>>(visitor: &mut V, item: &'a AssocItem, ctxt: AssocCtxt) { - let Item { id, span, ident, ref vis, ref attrs, ref kind, tokens: _ } = *item; + let &Item { id, span, ident, ref vis, ref attrs, ref kind, tokens: _ } = item; visitor.visit_vis(vis); visitor.visit_ident(ident); walk_list!(visitor, visit_attribute, attrs); @@ -684,7 +674,7 @@ pub fn walk_assoc_item<'a, V: Visitor<'a>>(visitor: &mut V, item: &'a AssocItem, visitor.visit_ty(ty); walk_list!(visitor, visit_expr, expr); } - AssocItemKind::Fn(box Fn { defaultness: _, ref generics, ref sig, ref body }) => { + AssocItemKind::Fn(box Fn { defaultness: _, generics, sig, body }) => { let kind = FnKind::Fn(FnCtxt::Assoc(ctxt), ident, sig, vis, generics, body.as_deref()); visitor.visit_fn(kind, span, id); } @@ -717,13 +707,13 @@ pub fn walk_block<'a, V: Visitor<'a>>(visitor: &mut V, block: &'a Block) { } pub fn walk_stmt<'a, V: Visitor<'a>>(visitor: &mut V, statement: &'a Stmt) { - match statement.kind { - StmtKind::Local(ref local) => visitor.visit_local(local), - StmtKind::Item(ref item) => visitor.visit_item(item), - StmtKind::Expr(ref expr) | StmtKind::Semi(ref expr) => visitor.visit_expr(expr), + match &statement.kind { + StmtKind::Local(local) => visitor.visit_local(local), + StmtKind::Item(item) => visitor.visit_item(item), + StmtKind::Expr(expr) | StmtKind::Semi(expr) => visitor.visit_expr(expr), StmtKind::Empty => {} - StmtKind::MacCall(ref mac) => { - let MacCallStmt { ref mac, style: _, ref attrs, tokens: _ } = **mac; + StmtKind::MacCall(mac) => { + let MacCallStmt { mac, attrs, style: _, tokens: _ } = &**mac; visitor.visit_mac_call(mac); for attr in attrs.iter() { visitor.visit_attribute(attr); @@ -760,7 +750,7 @@ pub fn walk_inline_asm<'a, V: Visitor<'a>>(visitor: &mut V, asm: &'a InlineAsm) } pub fn walk_inline_asm_sym<'a, V: Visitor<'a>>(visitor: &mut V, sym: &'a InlineAsmSym) { - if let Some(ref qself) = sym.qself { + if let Some(qself) = &sym.qself { visitor.visit_ty(&qself.ty); } visitor.visit_path(&sym.path, sym.id); @@ -769,18 +759,18 @@ pub fn walk_inline_asm_sym<'a, V: Visitor<'a>>(visitor: &mut V, sym: &'a InlineA pub fn walk_expr<'a, V: Visitor<'a>>(visitor: &mut V, expression: &'a Expr) { walk_list!(visitor, visit_attribute, expression.attrs.iter()); - match expression.kind { - ExprKind::Box(ref subexpression) => visitor.visit_expr(subexpression), - ExprKind::Array(ref subexpressions) => { + match &expression.kind { + ExprKind::Box(subexpression) => visitor.visit_expr(subexpression), + ExprKind::Array(subexpressions) => { walk_list!(visitor, visit_expr, subexpressions); } - ExprKind::ConstBlock(ref anon_const) => visitor.visit_anon_const(anon_const), - ExprKind::Repeat(ref element, ref count) => { + ExprKind::ConstBlock(anon_const) => visitor.visit_anon_const(anon_const), + ExprKind::Repeat(element, count) => { visitor.visit_expr(element); visitor.visit_anon_const(count) } - ExprKind::Struct(ref se) => { - if let Some(ref qself) = se.qself { + ExprKind::Struct(se) => { + if let Some(qself) = &se.qself { visitor.visit_ty(&qself.ty); } visitor.visit_path(&se.path, expression.id); @@ -791,124 +781,124 @@ pub fn walk_expr<'a, V: Visitor<'a>>(visitor: &mut V, expression: &'a Expr) { StructRest::None => {} } } - ExprKind::Tup(ref subexpressions) => { + ExprKind::Tup(subexpressions) => { walk_list!(visitor, visit_expr, subexpressions); } - ExprKind::Call(ref callee_expression, ref arguments) => { + ExprKind::Call(callee_expression, arguments) => { visitor.visit_expr(callee_expression); walk_list!(visitor, visit_expr, arguments); } - ExprKind::MethodCall(box MethodCall { ref seg, ref receiver, ref args, span: _ }) => { + ExprKind::MethodCall(box MethodCall { seg, receiver, args, span: _ }) => { visitor.visit_path_segment(seg); visitor.visit_expr(receiver); walk_list!(visitor, visit_expr, args); } - ExprKind::Binary(_, ref left_expression, ref right_expression) => { + ExprKind::Binary(_, left_expression, right_expression) => { visitor.visit_expr(left_expression); visitor.visit_expr(right_expression) } - ExprKind::AddrOf(_, _, ref subexpression) | ExprKind::Unary(_, ref subexpression) => { + ExprKind::AddrOf(_, _, subexpression) | ExprKind::Unary(_, subexpression) => { visitor.visit_expr(subexpression) } - ExprKind::Cast(ref subexpression, ref typ) | ExprKind::Type(ref subexpression, ref typ) => { + ExprKind::Cast(subexpression, typ) | ExprKind::Type(subexpression, typ) => { visitor.visit_expr(subexpression); visitor.visit_ty(typ) } - ExprKind::Let(ref pat, ref expr, _) => { + ExprKind::Let(pat, expr, _) => { visitor.visit_pat(pat); visitor.visit_expr(expr); } - ExprKind::If(ref head_expression, ref if_block, ref optional_else) => { + ExprKind::If(head_expression, if_block, optional_else) => { visitor.visit_expr(head_expression); visitor.visit_block(if_block); walk_list!(visitor, visit_expr, optional_else); } - ExprKind::While(ref subexpression, ref block, ref opt_label) => { + ExprKind::While(subexpression, block, opt_label) => { walk_list!(visitor, visit_label, opt_label); visitor.visit_expr(subexpression); visitor.visit_block(block); } - ExprKind::ForLoop(ref pattern, ref subexpression, ref block, ref opt_label) => { + ExprKind::ForLoop(pattern, subexpression, block, opt_label) => { walk_list!(visitor, visit_label, opt_label); visitor.visit_pat(pattern); visitor.visit_expr(subexpression); visitor.visit_block(block); } - ExprKind::Loop(ref block, ref opt_label) => { + ExprKind::Loop(block, opt_label) => { walk_list!(visitor, visit_label, opt_label); visitor.visit_block(block); } - ExprKind::Match(ref subexpression, ref arms) => { + ExprKind::Match(subexpression, arms) => { visitor.visit_expr(subexpression); walk_list!(visitor, visit_arm, arms); } ExprKind::Closure(box Closure { - ref binder, + binder, capture_clause: _, asyncness: _, movability: _, - ref fn_decl, - ref body, + fn_decl, + body, fn_decl_span: _, }) => { visitor.visit_fn(FnKind::Closure(binder, fn_decl, body), expression.span, expression.id) } - ExprKind::Block(ref block, ref opt_label) => { + ExprKind::Block(block, opt_label) => { walk_list!(visitor, visit_label, opt_label); visitor.visit_block(block); } - ExprKind::Async(_, _, ref body) => { + ExprKind::Async(_, _, body) => { visitor.visit_block(body); } - ExprKind::Await(ref expr) => visitor.visit_expr(expr), - ExprKind::Assign(ref lhs, ref rhs, _) => { + ExprKind::Await(expr) => visitor.visit_expr(expr), + ExprKind::Assign(lhs, rhs, _) => { visitor.visit_expr(lhs); visitor.visit_expr(rhs); } - ExprKind::AssignOp(_, ref left_expression, ref right_expression) => { + ExprKind::AssignOp(_, left_expression, right_expression) => { visitor.visit_expr(left_expression); visitor.visit_expr(right_expression); } - ExprKind::Field(ref subexpression, ident) => { + ExprKind::Field(subexpression, ident) => { visitor.visit_expr(subexpression); - visitor.visit_ident(ident); + visitor.visit_ident(*ident); } - ExprKind::Index(ref main_expression, ref index_expression) => { + ExprKind::Index(main_expression, index_expression) => { visitor.visit_expr(main_expression); visitor.visit_expr(index_expression) } - ExprKind::Range(ref start, ref end, _) => { + ExprKind::Range(start, end, _) => { walk_list!(visitor, visit_expr, start); walk_list!(visitor, visit_expr, end); } ExprKind::Underscore => {} - ExprKind::Path(ref maybe_qself, ref path) => { - if let Some(ref qself) = *maybe_qself { + ExprKind::Path(maybe_qself, path) => { + if let Some(qself) = maybe_qself { visitor.visit_ty(&qself.ty); } visitor.visit_path(path, expression.id) } - ExprKind::Break(ref opt_label, ref opt_expr) => { + ExprKind::Break(opt_label, opt_expr) => { walk_list!(visitor, visit_label, opt_label); walk_list!(visitor, visit_expr, opt_expr); } - ExprKind::Continue(ref opt_label) => { + ExprKind::Continue(opt_label) => { walk_list!(visitor, visit_label, opt_label); } - ExprKind::Ret(ref optional_expression) => { + ExprKind::Ret(optional_expression) => { walk_list!(visitor, visit_expr, optional_expression); } - ExprKind::Yeet(ref optional_expression) => { + ExprKind::Yeet(optional_expression) => { walk_list!(visitor, visit_expr, optional_expression); } - ExprKind::MacCall(ref mac) => visitor.visit_mac_call(mac), - ExprKind::Paren(ref subexpression) => visitor.visit_expr(subexpression), - ExprKind::InlineAsm(ref asm) => visitor.visit_inline_asm(asm), - ExprKind::Yield(ref optional_expression) => { + ExprKind::MacCall(mac) => visitor.visit_mac_call(mac), + ExprKind::Paren(subexpression) => visitor.visit_expr(subexpression), + ExprKind::InlineAsm(asm) => visitor.visit_inline_asm(asm), + ExprKind::Yield(optional_expression) => { walk_list!(visitor, visit_expr, optional_expression); } - ExprKind::Try(ref subexpression) => visitor.visit_expr(subexpression), - ExprKind::TryBlock(ref body) => visitor.visit_block(body), + ExprKind::Try(subexpression) => visitor.visit_expr(subexpression), + ExprKind::TryBlock(body) => visitor.visit_block(body), ExprKind::Lit(_) | ExprKind::IncludedBytes(..) | ExprKind::Err => {} } @@ -935,8 +925,8 @@ pub fn walk_vis<'a, V: Visitor<'a>>(visitor: &mut V, vis: &'a Visibility) { } pub fn walk_attribute<'a, V: Visitor<'a>>(visitor: &mut V, attr: &'a Attribute) { - match attr.kind { - AttrKind::Normal(ref normal) => walk_mac_args(visitor, &normal.item.args), + match &attr.kind { + AttrKind::Normal(normal) => walk_mac_args(visitor, &normal.item.args), AttrKind::DocComment(..) => {} } } From d9f2c0b33d6851c8553ca6e30b7e4c3ad3012b75 Mon Sep 17 00:00:00 2001 From: Maybe Waffle Date: Mon, 21 Nov 2022 10:23:53 +0000 Subject: [PATCH 14/14] Revert formatting changes of a test --- src/test/ui/or-patterns/or-patterns-syntactic-pass.rs | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/test/ui/or-patterns/or-patterns-syntactic-pass.rs b/src/test/ui/or-patterns/or-patterns-syntactic-pass.rs index dda5c0bb59d23..92750bec8b20c 100644 --- a/src/test/ui/or-patterns/or-patterns-syntactic-pass.rs +++ b/src/test/ui/or-patterns/or-patterns-syntactic-pass.rs @@ -21,27 +21,27 @@ accept_pat!([p | q]); #[cfg(FALSE)] fn or_patterns() { // Top level of `let`: - let (A | B); + let (| A | B); let (A | B); let (A | B): u8; let (A | B) = 0; let (A | B): u8 = 0; // Top level of `for`: - for A | B in 0 {} + for | A | B in 0 {} for A | B in 0 {} // Top level of `while`: - while let A | B = 0 {} + while let | A | B = 0 {} while let A | B = 0 {} // Top level of `if`: - if let A | B = 0 {} + if let | A | B = 0 {} if let A | B = 0 {} // Top level of `match` arms: match 0 { - A | B => {} + | A | B => {} A | B => {} }