about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--Cargo.toml2
-rw-r--r--compiler/rustc_expand/src/config.rs2
-rw-r--r--compiler/rustc_parse/src/parser/item.rs1
-rw-r--r--compiler/rustc_resolve/src/diagnostics.rs31
-rw-r--r--compiler/rustc_resolve/src/imports.rs16
-rw-r--r--compiler/rustc_trait_selection/src/traits/error_reporting/suggestions.rs10
-rw-r--r--compiler/rustc_traits/src/evaluate_obligation.rs6
-rw-r--r--compiler/rustc_traits/src/type_op.rs15
-rw-r--r--library/core/src/char/methods.rs12
-rw-r--r--library/core/src/macros/mod.rs14
-rw-r--r--library/std/src/os/fd/raw.rs4
-rw-r--r--library/std/src/os/wasi/io/raw.rs15
-rw-r--r--src/librustdoc/clean/mod.rs115
-rw-r--r--src/librustdoc/html/static/css/settings.css3
-rw-r--r--src/test/rustdoc-gui/settings.goml9
-rw-r--r--src/test/ui/impl-trait/issue-99642-2.rs8
-rw-r--r--src/test/ui/impl-trait/issue-99642.rs7
-rw-r--r--src/test/ui/linkage-attr/issue-10755.rs5
-rw-r--r--src/test/ui/macros/format-args-temporaries-async.rs37
-rw-r--r--src/test/ui/macros/format-args-temporaries-in-write.rs50
-rw-r--r--src/test/ui/macros/format-args-temporaries-in-write.stderr43
-rw-r--r--src/test/ui/macros/format-args-temporaries.rs16
-rw-r--r--src/test/ui/process/process-spawn-nonexistent.rs12
-rw-r--r--src/test/ui/type-alias-impl-trait/issue-53398-cyclic-types.stderr4
24 files changed, 302 insertions, 135 deletions
diff --git a/Cargo.toml b/Cargo.toml
index ed024192c15..ffc886d47f3 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -60,7 +60,7 @@ exclude = [
 # verify that this is the case. This requires, however, that the crate is built
 # without overflow checks and debug assertions. Forcefully disable debug
 # assertions and overflow checks here which should ensure that even if these
-# assertions are enabled for libstd we won't enable then for compiler_builtins
+# assertions are enabled for libstd we won't enable them for compiler_builtins
 # which should ensure we still link everything correctly.
 debug-assertions = false
 overflow-checks = false
diff --git a/compiler/rustc_expand/src/config.rs b/compiler/rustc_expand/src/config.rs
index 2b941ec6809..ccc29adc015 100644
--- a/compiler/rustc_expand/src/config.rs
+++ b/compiler/rustc_expand/src/config.rs
@@ -129,7 +129,7 @@ fn get_features(
                         .span_suggestion(
                             mi.span(),
                             "expected just one word",
-                            format!("{}", ident.name),
+                            ident.name,
                             Applicability::MaybeIncorrect,
                         )
                         .emit();
diff --git a/compiler/rustc_parse/src/parser/item.rs b/compiler/rustc_parse/src/parser/item.rs
index 87bc0d9762e..a14a7fc0610 100644
--- a/compiler/rustc_parse/src/parser/item.rs
+++ b/compiler/rustc_parse/src/parser/item.rs
@@ -1677,7 +1677,6 @@ impl<'a> Parser<'a> {
     }
 
     /// Is this a possibly malformed start of a `macro_rules! foo` item definition?
-
     fn is_macro_rules_item(&mut self) -> IsMacroRulesItem {
         if self.check_keyword(kw::MacroRules) {
             let macro_rules_span = self.token.span;
diff --git a/compiler/rustc_resolve/src/diagnostics.rs b/compiler/rustc_resolve/src/diagnostics.rs
index 0343e8d9b8e..22a307a15ed 100644
--- a/compiler/rustc_resolve/src/diagnostics.rs
+++ b/compiler/rustc_resolve/src/diagnostics.rs
@@ -2023,7 +2023,7 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
         span: Span,
         mut path: Vec<Segment>,
         parent_scope: &ParentScope<'b>,
-    ) -> Option<(Vec<Segment>, Vec<String>)> {
+    ) -> Option<(Vec<Segment>, Option<String>)> {
         debug!("make_path_suggestion: span={:?} path={:?}", span, path);
 
         match (path.get(0), path.get(1)) {
@@ -2058,12 +2058,12 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
         &mut self,
         mut path: Vec<Segment>,
         parent_scope: &ParentScope<'b>,
-    ) -> Option<(Vec<Segment>, Vec<String>)> {
+    ) -> Option<(Vec<Segment>, Option<String>)> {
         // Replace first ident with `self` and check if that is valid.
         path[0].ident.name = kw::SelfLower;
         let result = self.r.maybe_resolve_path(&path, None, parent_scope);
         debug!("make_missing_self_suggestion: path={:?} result={:?}", path, result);
-        if let PathResult::Module(..) = result { Some((path, Vec::new())) } else { None }
+        if let PathResult::Module(..) = result { Some((path, None)) } else { None }
     }
 
     /// Suggests a missing `crate::` if that resolves to an correct module.
@@ -2077,7 +2077,7 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
         &mut self,
         mut path: Vec<Segment>,
         parent_scope: &ParentScope<'b>,
-    ) -> Option<(Vec<Segment>, Vec<String>)> {
+    ) -> Option<(Vec<Segment>, Option<String>)> {
         // Replace first ident with `crate` and check if that is valid.
         path[0].ident.name = kw::Crate;
         let result = self.r.maybe_resolve_path(&path, None, parent_scope);
@@ -2085,12 +2085,12 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
         if let PathResult::Module(..) = result {
             Some((
                 path,
-                vec![
+                Some(
                     "`use` statements changed in Rust 2018; read more at \
                      <https://doc.rust-lang.org/edition-guide/rust-2018/module-system/path-\
                      clarity.html>"
                         .to_string(),
-                ],
+                ),
             ))
         } else {
             None
@@ -2108,12 +2108,12 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
         &mut self,
         mut path: Vec<Segment>,
         parent_scope: &ParentScope<'b>,
-    ) -> Option<(Vec<Segment>, Vec<String>)> {
+    ) -> Option<(Vec<Segment>, Option<String>)> {
         // Replace first ident with `crate` and check if that is valid.
         path[0].ident.name = kw::Super;
         let result = self.r.maybe_resolve_path(&path, None, parent_scope);
         debug!("make_missing_super_suggestion:  path={:?} result={:?}", path, result);
-        if let PathResult::Module(..) = result { Some((path, Vec::new())) } else { None }
+        if let PathResult::Module(..) = result { Some((path, None)) } else { None }
     }
 
     /// Suggests a missing external crate name if that resolves to an correct module.
@@ -2130,7 +2130,7 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
         &mut self,
         mut path: Vec<Segment>,
         parent_scope: &ParentScope<'b>,
-    ) -> Option<(Vec<Segment>, Vec<String>)> {
+    ) -> Option<(Vec<Segment>, Option<String>)> {
         if path[1].ident.span.rust_2015() {
             return None;
         }
@@ -2151,7 +2151,7 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
                 name, path, result
             );
             if let PathResult::Module(..) = result {
-                return Some((path, Vec::new()));
+                return Some((path, None));
             }
         }
 
@@ -2175,7 +2175,7 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
         import: &'b Import<'b>,
         module: ModuleOrUniformRoot<'b>,
         ident: Ident,
-    ) -> Option<(Option<Suggestion>, Vec<String>)> {
+    ) -> Option<(Option<Suggestion>, Option<String>)> {
         let ModuleOrUniformRoot::Module(mut crate_module) = module else {
             return None;
         };
@@ -2287,12 +2287,9 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
                 String::from("a macro with this name exists at the root of the crate"),
                 Applicability::MaybeIncorrect,
             ));
-            let note = vec![
-                "this could be because a macro annotated with `#[macro_export]` will be exported \
-                 at the root of the crate instead of the module where it is defined"
-                    .to_string(),
-            ];
-            Some((suggestion, note))
+            Some((suggestion, Some("this could be because a macro annotated with `#[macro_export]` will be exported \
+            at the root of the crate instead of the module where it is defined"
+               .to_string())))
         } else {
             None
         }
diff --git a/compiler/rustc_resolve/src/imports.rs b/compiler/rustc_resolve/src/imports.rs
index e6060ad4665..b89273990d8 100644
--- a/compiler/rustc_resolve/src/imports.rs
+++ b/compiler/rustc_resolve/src/imports.rs
@@ -336,7 +336,7 @@ impl<'a> Resolver<'a> {
 struct UnresolvedImportError {
     span: Span,
     label: Option<String>,
-    note: Vec<String>,
+    note: Option<String>,
     suggestion: Option<Suggestion>,
 }
 
@@ -427,7 +427,7 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
                 let err = UnresolvedImportError {
                     span: import.span,
                     label: None,
-                    note: Vec::new(),
+                    note: None,
                     suggestion: None,
                 };
                 if path.contains("::") {
@@ -463,10 +463,8 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
 
         let mut diag = struct_span_err!(self.r.session, span, E0432, "{}", &msg);
 
-        if let Some((_, UnresolvedImportError { note, .. })) = errors.iter().last() {
-            for message in note {
-                diag.note(message);
-            }
+        if let Some((_, UnresolvedImportError { note: Some(note), .. })) = errors.iter().last() {
+            diag.note(note);
         }
 
         for (_, err) in errors.into_iter().take(MAX_LABEL_COUNT) {
@@ -644,7 +642,7 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
                         None => UnresolvedImportError {
                             span,
                             label: Some(label),
-                            note: Vec::new(),
+                            note: None,
                             suggestion,
                         },
                     };
@@ -686,7 +684,7 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
                         return Some(UnresolvedImportError {
                             span: import.span,
                             label: Some(String::from("cannot glob-import a module into itself")),
-                            note: Vec::new(),
+                            note: None,
                             suggestion: None,
                         });
                     }
@@ -830,7 +828,7 @@ impl<'a, 'b> ImportResolver<'a, 'b> {
                 let (suggestion, note) =
                     match self.check_for_module_export_macro(import, module, ident) {
                         Some((suggestion, note)) => (suggestion.or(lev_suggestion), note),
-                        _ => (lev_suggestion, Vec::new()),
+                        _ => (lev_suggestion, None),
                     };
 
                 let label = match module {
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 89d7c050c40..6c8faed0df4 100644
--- a/compiler/rustc_trait_selection/src/traits/error_reporting/suggestions.rs
+++ b/compiler/rustc_trait_selection/src/traits/error_reporting/suggestions.rs
@@ -184,7 +184,7 @@ pub trait InferCtxtExt<'tcx> {
         trait_pred: ty::PolyTraitPredicate<'tcx>,
     ) -> bool;
 
-    fn get_closure_name(&self, def_id: DefId, err: &mut Diagnostic, msg: &str) -> Option<String>;
+    fn get_closure_name(&self, def_id: DefId, err: &mut Diagnostic, msg: &str) -> Option<Symbol>;
 
     fn suggest_fn_call(
         &self,
@@ -737,13 +737,13 @@ impl<'a, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'a, 'tcx> {
     /// Given a closure's `DefId`, return the given name of the closure.
     ///
     /// This doesn't account for reassignments, but it's only used for suggestions.
-    fn get_closure_name(&self, def_id: DefId, err: &mut Diagnostic, msg: &str) -> Option<String> {
-        let get_name = |err: &mut Diagnostic, kind: &hir::PatKind<'_>| -> Option<String> {
+    fn get_closure_name(&self, def_id: DefId, err: &mut Diagnostic, msg: &str) -> Option<Symbol> {
+        let get_name = |err: &mut Diagnostic, kind: &hir::PatKind<'_>| -> Option<Symbol> {
             // Get the local name of this closure. This can be inaccurate because
             // of the possibility of reassignment, but this should be good enough.
             match &kind {
-                hir::PatKind::Binding(hir::BindingAnnotation::Unannotated, _, name, None) => {
-                    Some(format!("{}", name))
+                hir::PatKind::Binding(hir::BindingAnnotation::Unannotated, _, ident, None) => {
+                    Some(ident.name)
                 }
                 _ => {
                     err.note(msg);
diff --git a/compiler/rustc_traits/src/evaluate_obligation.rs b/compiler/rustc_traits/src/evaluate_obligation.rs
index 3fc141471b9..49c9ba45963 100644
--- a/compiler/rustc_traits/src/evaluate_obligation.rs
+++ b/compiler/rustc_traits/src/evaluate_obligation.rs
@@ -1,4 +1,4 @@
-use rustc_infer::infer::TyCtxtInferExt;
+use rustc_infer::infer::{DefiningAnchor, TyCtxtInferExt};
 use rustc_middle::ty::query::Providers;
 use rustc_middle::ty::{ParamEnvAnd, TyCtxt};
 use rustc_span::source_map::DUMMY_SP;
@@ -16,7 +16,9 @@ fn evaluate_obligation<'tcx>(
     canonical_goal: CanonicalPredicateGoal<'tcx>,
 ) -> Result<EvaluationResult, OverflowError> {
     debug!("evaluate_obligation(canonical_goal={:#?})", canonical_goal);
-    tcx.infer_ctxt().enter_with_canonical(
+    // HACK This bubble is required for this tests to pass:
+    // impl-trait/issue99642.rs
+    tcx.infer_ctxt().with_opaque_type_inference(DefiningAnchor::Bubble).enter_with_canonical(
         DUMMY_SP,
         &canonical_goal,
         |ref infcx, goal, _canonical_inference_vars| {
diff --git a/compiler/rustc_traits/src/type_op.rs b/compiler/rustc_traits/src/type_op.rs
index f8bac1d7b26..d895b647db0 100644
--- a/compiler/rustc_traits/src/type_op.rs
+++ b/compiler/rustc_traits/src/type_op.rs
@@ -2,7 +2,7 @@ use rustc_hir as hir;
 use rustc_hir::def_id::DefId;
 use rustc_infer::infer::at::ToTrace;
 use rustc_infer::infer::canonical::{Canonical, QueryResponse};
-use rustc_infer::infer::{InferCtxt, TyCtxtInferExt};
+use rustc_infer::infer::{DefiningAnchor, InferCtxt, TyCtxtInferExt};
 use rustc_infer::traits::TraitEngineExt as _;
 use rustc_middle::ty::query::Providers;
 use rustc_middle::ty::subst::{GenericArg, Subst, UserSelfTy, UserSubsts};
@@ -258,10 +258,15 @@ fn type_op_prove_predicate<'tcx>(
     tcx: TyCtxt<'tcx>,
     canonicalized: Canonical<'tcx, ParamEnvAnd<'tcx, ProvePredicate<'tcx>>>,
 ) -> Result<&'tcx Canonical<'tcx, QueryResponse<'tcx, ()>>, NoSolution> {
-    tcx.infer_ctxt().enter_canonical_trait_query(&canonicalized, |infcx, fulfill_cx, key| {
-        type_op_prove_predicate_with_cause(infcx, fulfill_cx, key, ObligationCause::dummy());
-        Ok(())
-    })
+    // HACK This bubble is required for this test to pass:
+    // impl-trait/issue-99642.rs
+    tcx.infer_ctxt().with_opaque_type_inference(DefiningAnchor::Bubble).enter_canonical_trait_query(
+        &canonicalized,
+        |infcx, fulfill_cx, key| {
+            type_op_prove_predicate_with_cause(infcx, fulfill_cx, key, ObligationCause::dummy());
+            Ok(())
+        },
+    )
 }
 
 /// The core of the `type_op_prove_predicate` query: for diagnostics purposes in NLL HRTB errors,
diff --git a/library/core/src/char/methods.rs b/library/core/src/char/methods.rs
index 0bec38a877e..eae567cad00 100644
--- a/library/core/src/char/methods.rs
+++ b/library/core/src/char/methods.rs
@@ -892,7 +892,16 @@ impl char {
     ///
     /// The general categories for numbers (`Nd` for decimal digits, `Nl` for letter-like numeric
     /// characters, and `No` for other numeric characters) are specified in the [Unicode Character
-    /// Database][ucd] [`UnicodeData.txt`].
+    /// Database][ucd] [`UnicodeData.txt`]. Note that this means ideographic numbers like '三'
+    /// are considered alphabetic, not numeric. Please consider to use `is_ascii_digit` or `is_digit`.
+    ///
+    /// This method doesn't cover everything that could be considered a number, e.g. ideographic numbers like '三'.
+    /// If you want everything including characters with overlapping purposes then you might want to use
+    /// a unicode or language-processing library that exposes the appropriate character properties instead
+    /// of looking at the unicode categories.
+    ///
+    /// If you want to parse ASCII decimal digits (0-9) or ASCII base-N, use
+    /// `is_ascii_digit` or `is_digit` instead.
     ///
     /// [Unicode Standard]: https://www.unicode.org/versions/latest/
     /// [ucd]: https://www.unicode.org/reports/tr44/
@@ -911,6 +920,7 @@ impl char {
     /// assert!(!'K'.is_numeric());
     /// assert!(!'و'.is_numeric());
     /// assert!(!'藏'.is_numeric());
+    /// assert!(!'三'.is_numeric());
     /// ```
     #[must_use]
     #[stable(feature = "rust1", since = "1.0.0")]
diff --git a/library/core/src/macros/mod.rs b/library/core/src/macros/mod.rs
index bd62bc5c305..3a115a8b8b6 100644
--- a/library/core/src/macros/mod.rs
+++ b/library/core/src/macros/mod.rs
@@ -496,10 +496,9 @@ macro_rules! r#try {
 #[stable(feature = "rust1", since = "1.0.0")]
 #[cfg_attr(not(test), rustc_diagnostic_item = "write_macro")]
 macro_rules! write {
-    ($dst:expr, $($arg:tt)*) => {{
-        let result = $dst.write_fmt($crate::format_args!($($arg)*));
-        result
-    }};
+    ($dst:expr, $($arg:tt)*) => {
+        $dst.write_fmt($crate::format_args!($($arg)*))
+    };
 }
 
 /// Write formatted data into a buffer, with a newline appended.
@@ -554,10 +553,9 @@ macro_rules! writeln {
     ($dst:expr $(,)?) => {
         $crate::write!($dst, "\n")
     };
-    ($dst:expr, $($arg:tt)*) => {{
-        let result = $dst.write_fmt($crate::format_args_nl!($($arg)*));
-        result
-    }};
+    ($dst:expr, $($arg:tt)*) => {
+        $dst.write_fmt($crate::format_args_nl!($($arg)*))
+    };
 }
 
 /// Indicates unreachable code.
diff --git a/library/std/src/os/fd/raw.rs b/library/std/src/os/fd/raw.rs
index ff4e25b792a..081915ed148 100644
--- a/library/std/src/os/fd/raw.rs
+++ b/library/std/src/os/fd/raw.rs
@@ -14,6 +14,7 @@ use crate::os::wasi::io::OwnedFd;
 use crate::sys_common::{AsInner, IntoInner};
 
 /// Raw file descriptors.
+#[cfg_attr(not(bootstrap), rustc_allowed_through_unstable_modules)]
 #[stable(feature = "rust1", since = "1.0.0")]
 pub type RawFd = raw::c_int;
 
@@ -22,6 +23,7 @@ pub type RawFd = raw::c_int;
 /// This is only available on unix and WASI platforms and must be imported in
 /// order to call the method. Windows platforms have a corresponding
 /// `AsRawHandle` and `AsRawSocket` set of traits.
+#[cfg_attr(not(bootstrap), rustc_allowed_through_unstable_modules)]
 #[stable(feature = "rust1", since = "1.0.0")]
 pub trait AsRawFd {
     /// Extracts the raw file descriptor.
@@ -57,6 +59,7 @@ pub trait AsRawFd {
 
 /// A trait to express the ability to construct an object from a raw file
 /// descriptor.
+#[cfg_attr(not(bootstrap), rustc_allowed_through_unstable_modules)]
 #[stable(feature = "from_raw_os", since = "1.1.0")]
 pub trait FromRawFd {
     /// Constructs a new instance of `Self` from the given raw file
@@ -100,6 +103,7 @@ pub trait FromRawFd {
 
 /// A trait to express the ability to consume an object and acquire ownership of
 /// its raw file descriptor.
+#[cfg_attr(not(bootstrap), rustc_allowed_through_unstable_modules)]
 #[stable(feature = "into_raw_os", since = "1.4.0")]
 pub trait IntoRawFd {
     /// Consumes this object, returning the raw underlying file descriptor.
diff --git a/library/std/src/os/wasi/io/raw.rs b/library/std/src/os/wasi/io/raw.rs
index 0e0c5824e34..da3b36adad4 100644
--- a/library/std/src/os/wasi/io/raw.rs
+++ b/library/std/src/os/wasi/io/raw.rs
@@ -2,4 +2,19 @@
 
 #![unstable(feature = "wasi_ext", issue = "71213")]
 
+// NOTE: despite the fact that this module is unstable,
+// stable Rust had the capability to access the stable
+// re-exported items from os::fd::raw through this
+// unstable module.
+// In PR #95956 the stability checker was changed to check
+// all path segments of an item rather than just the last,
+// which caused the aforementioned stable usage to regress
+// (see issue #99502).
+// As a result, the items in os::fd::raw were given the
+// rustc_allowed_through_unstable_modules attribute.
+// No regression tests were added to ensure this property,
+// as CI is not configured to test wasm32-wasi.
+// If this module is stabilized,
+// you may want to remove those attributes
+// (assuming no other unstable modules need them).
 pub use crate::os::fd::raw::*;
diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs
index 2f3ca41723d..2f2fbc9d4ba 100644
--- a/src/librustdoc/clean/mod.rs
+++ b/src/librustdoc/clean/mod.rs
@@ -398,23 +398,19 @@ fn clean_type_outlives_predicate<'tcx>(
     })
 }
 
-impl<'tcx> Clean<'tcx, Term> for ty::Term<'tcx> {
-    fn clean(&self, cx: &mut DocContext<'tcx>) -> Term {
-        match self {
-            ty::Term::Ty(ty) => Term::Type(clean_middle_ty(*ty, cx, None)),
-            ty::Term::Const(c) => Term::Constant(clean_middle_const(*c, cx)),
-        }
+fn clean_middle_term<'tcx>(term: ty::Term<'tcx>, cx: &mut DocContext<'tcx>) -> Term {
+    match term {
+        ty::Term::Ty(ty) => Term::Type(clean_middle_ty(ty, cx, None)),
+        ty::Term::Const(c) => Term::Constant(clean_middle_const(c, cx)),
     }
 }
 
-impl<'tcx> Clean<'tcx, Term> for hir::Term<'tcx> {
-    fn clean(&self, cx: &mut DocContext<'tcx>) -> Term {
-        match self {
-            hir::Term::Ty(ty) => Term::Type(clean_ty(ty, cx)),
-            hir::Term::Const(c) => {
-                let def_id = cx.tcx.hir().local_def_id(c.hir_id);
-                Term::Constant(clean_middle_const(ty::Const::from_anon_const(cx.tcx, def_id), cx))
-            }
+fn clean_hir_term<'tcx>(term: &hir::Term<'tcx>, cx: &mut DocContext<'tcx>) -> Term {
+    match term {
+        hir::Term::Ty(ty) => Term::Type(clean_ty(ty, cx)),
+        hir::Term::Const(c) => {
+            let def_id = cx.tcx.hir().local_def_id(c.hir_id);
+            Term::Constant(clean_middle_const(ty::Const::from_anon_const(cx.tcx, def_id), cx))
         }
     }
 }
@@ -426,7 +422,7 @@ fn clean_projection_predicate<'tcx>(
     let ty::ProjectionPredicate { projection_ty, term } = pred;
     WherePredicate::EqPredicate {
         lhs: clean_projection(projection_ty, cx, None),
-        rhs: term.clean(cx),
+        rhs: clean_middle_term(term, cx),
     }
 }
 
@@ -474,47 +470,44 @@ fn projection_to_path_segment<'tcx>(
     }
 }
 
-impl<'tcx> Clean<'tcx, GenericParamDef> for ty::GenericParamDef {
-    fn clean(&self, cx: &mut DocContext<'tcx>) -> GenericParamDef {
-        let (name, kind) = match self.kind {
-            ty::GenericParamDefKind::Lifetime => {
-                (self.name, GenericParamDefKind::Lifetime { outlives: vec![] })
-            }
-            ty::GenericParamDefKind::Type { has_default, synthetic, .. } => {
-                let default = if has_default {
-                    Some(clean_middle_ty(cx.tcx.type_of(self.def_id), cx, Some(self.def_id)))
-                } else {
-                    None
-                };
-                (
-                    self.name,
-                    GenericParamDefKind::Type {
-                        did: self.def_id,
-                        bounds: vec![], // These are filled in from the where-clauses.
-                        default: default.map(Box::new),
-                        synthetic,
-                    },
-                )
-            }
-            ty::GenericParamDefKind::Const { has_default } => (
-                self.name,
-                GenericParamDefKind::Const {
-                    did: self.def_id,
-                    ty: Box::new(clean_middle_ty(
-                        cx.tcx.type_of(self.def_id),
-                        cx,
-                        Some(self.def_id),
-                    )),
-                    default: match has_default {
-                        true => Some(Box::new(cx.tcx.const_param_default(self.def_id).to_string())),
-                        false => None,
-                    },
+fn clean_generic_param_def<'tcx>(
+    def: &ty::GenericParamDef,
+    cx: &mut DocContext<'tcx>,
+) -> GenericParamDef {
+    let (name, kind) = match def.kind {
+        ty::GenericParamDefKind::Lifetime => {
+            (def.name, GenericParamDefKind::Lifetime { outlives: vec![] })
+        }
+        ty::GenericParamDefKind::Type { has_default, synthetic, .. } => {
+            let default = if has_default {
+                Some(clean_middle_ty(cx.tcx.type_of(def.def_id), cx, Some(def.def_id)))
+            } else {
+                None
+            };
+            (
+                def.name,
+                GenericParamDefKind::Type {
+                    did: def.def_id,
+                    bounds: vec![], // These are filled in from the where-clauses.
+                    default: default.map(Box::new),
+                    synthetic,
                 },
-            ),
-        };
+            )
+        }
+        ty::GenericParamDefKind::Const { has_default } => (
+            def.name,
+            GenericParamDefKind::Const {
+                did: def.def_id,
+                ty: Box::new(clean_middle_ty(cx.tcx.type_of(def.def_id), cx, Some(def.def_id))),
+                default: match has_default {
+                    true => Some(Box::new(cx.tcx.const_param_default(def.def_id).to_string())),
+                    false => None,
+                },
+            },
+        ),
+    };
 
-        GenericParamDef { name, kind }
-    }
+    GenericParamDef { name, kind }
 }
 
 fn clean_generic_param<'tcx>(
@@ -672,7 +665,7 @@ fn clean_ty_generics<'tcx>(
         .iter()
         .filter_map(|param| match param.kind {
             ty::GenericParamDefKind::Lifetime if param.name == kw::UnderscoreLifetime => None,
-            ty::GenericParamDefKind::Lifetime => Some(param.clean(cx)),
+            ty::GenericParamDefKind::Lifetime => Some(clean_generic_param_def(param, cx)),
             ty::GenericParamDefKind::Type { synthetic, .. } => {
                 if param.name == kw::SelfUpper {
                     assert_eq!(param.index, 0);
@@ -682,9 +675,9 @@ fn clean_ty_generics<'tcx>(
                     impl_trait.insert(param.index.into(), vec![]);
                     return None;
                 }
-                Some(param.clean(cx))
+                Some(clean_generic_param_def(param, cx))
             }
-            ty::GenericParamDefKind::Const { .. } => Some(param.clean(cx)),
+            ty::GenericParamDefKind::Const { .. } => Some(clean_generic_param_def(param, cx)),
         })
         .collect::<Vec<GenericParamDef>>();
 
@@ -1682,7 +1675,9 @@ pub(crate) fn clean_middle_ty<'tcx>(
                             .projection_ty,
                         cx,
                     ),
-                    kind: TypeBindingKind::Equality { term: pb.skip_binder().term.clean(cx) },
+                    kind: TypeBindingKind::Equality {
+                        term: clean_middle_term(pb.skip_binder().term, cx),
+                    },
                 });
             }
 
@@ -1746,7 +1741,7 @@ pub(crate) fn clean_middle_ty<'tcx>(
                                     Some(TypeBinding {
                                         assoc: projection_to_path_segment(proj.projection_ty, cx),
                                         kind: TypeBindingKind::Equality {
-                                            term: proj.term.clean(cx),
+                                            term: clean_middle_term(proj.term, cx),
                                         },
                                     })
                                 } else {
@@ -2283,7 +2278,7 @@ impl<'tcx> Clean<'tcx, TypeBindingKind> for hir::TypeBindingKind<'tcx> {
     fn clean(&self, cx: &mut DocContext<'tcx>) -> TypeBindingKind {
         match *self {
             hir::TypeBindingKind::Equality { ref term } => {
-                TypeBindingKind::Equality { term: term.clean(cx) }
+                TypeBindingKind::Equality { term: clean_hir_term(term, cx) }
             }
             hir::TypeBindingKind::Constraint { bounds } => TypeBindingKind::Constraint {
                 bounds: bounds.iter().filter_map(|b| b.clean(cx)).collect(),
diff --git a/src/librustdoc/html/static/css/settings.css b/src/librustdoc/html/static/css/settings.css
index e531e6ce6bb..e82ec042637 100644
--- a/src/librustdoc/html/static/css/settings.css
+++ b/src/librustdoc/html/static/css/settings.css
@@ -41,9 +41,7 @@
 
 .toggle {
 	position: relative;
-	display: inline-block;
 	width: 100%;
-	height: 27px;
 	margin-right: 20px;
 	display: flex;
 	align-items: center;
@@ -58,6 +56,7 @@
 .slider {
 	position: relative;
 	width: 45px;
+	min-width: 45px;
 	display: block;
 	height: 28px;
 	margin-right: 20px;
diff --git a/src/test/rustdoc-gui/settings.goml b/src/test/rustdoc-gui/settings.goml
index 8a3365d3cc2..d9cf5ee6614 100644
--- a/src/test/rustdoc-gui/settings.goml
+++ b/src/test/rustdoc-gui/settings.goml
@@ -147,3 +147,12 @@ assert-false: "noscript section"
 javascript: false
 reload:
 assert-css: ("noscript section", {"display": "block"})
+javascript: true
+
+// Check for the display on small screen
+show-text: true
+reload:
+size: (300, 1000)
+click: "#settings-menu"
+wait-for: "#settings"
+assert-css: ("#settings .slider", {"width": "45px"}, ALL)
diff --git a/src/test/ui/impl-trait/issue-99642-2.rs b/src/test/ui/impl-trait/issue-99642-2.rs
new file mode 100644
index 00000000000..0e88b363338
--- /dev/null
+++ b/src/test/ui/impl-trait/issue-99642-2.rs
@@ -0,0 +1,8 @@
+// check-pass
+
+#![feature(type_alias_impl_trait)]
+type Opq = impl Sized;
+fn test() -> impl Iterator<Item = Opq> {
+    Box::new(0..) as Box<dyn Iterator<Item = _>>
+}
+fn main(){}
diff --git a/src/test/ui/impl-trait/issue-99642.rs b/src/test/ui/impl-trait/issue-99642.rs
new file mode 100644
index 00000000000..75af60491e4
--- /dev/null
+++ b/src/test/ui/impl-trait/issue-99642.rs
@@ -0,0 +1,7 @@
+// check-pass
+
+fn test() -> impl Iterator<Item = impl Sized> {
+    Box::new(0..) as Box<dyn Iterator<Item = _>>
+}
+
+fn main() {}
diff --git a/src/test/ui/linkage-attr/issue-10755.rs b/src/test/ui/linkage-attr/issue-10755.rs
index 5ce69bceed3..afd2dc46ca3 100644
--- a/src/test/ui/linkage-attr/issue-10755.rs
+++ b/src/test/ui/linkage-attr/issue-10755.rs
@@ -1,7 +1,10 @@
 // build-fail
 // dont-check-compiler-stderr
 // compile-flags: -C linker=llllll -C linker-flavor=ld
-// error-pattern: linker `llllll` not found
+// error-pattern: `llllll`
+
+// Before, the error-pattern checked for "not found". On WSL with appendWindowsPath=true, running
+// in invalid command returns a PermissionDenied instead.
 
 fn main() {
 }
diff --git a/src/test/ui/macros/format-args-temporaries-async.rs b/src/test/ui/macros/format-args-temporaries-async.rs
new file mode 100644
index 00000000000..d959329b9fc
--- /dev/null
+++ b/src/test/ui/macros/format-args-temporaries-async.rs
@@ -0,0 +1,37 @@
+// check-pass
+// edition:2021
+
+use std::fmt::{self, Display};
+use std::future::Future;
+use std::io;
+use std::pin::Pin;
+use std::task::{Context, Poll};
+
+struct AsyncStdout;
+
+impl AsyncStdout {
+    fn write_fmt<'a>(&'a mut self, _args: fmt::Arguments) -> WriteFmtFuture<'a, Self>
+    where
+        Self: Unpin,
+    {
+        WriteFmtFuture(self)
+    }
+}
+
+struct WriteFmtFuture<'a, T>(&'a mut T);
+
+impl<'a, T> Future for WriteFmtFuture<'a, T> {
+    type Output = io::Result<()>;
+    fn poll(self: Pin<&mut Self>, cx: &mut Context) -> Poll<Self::Output> {
+        unimplemented!()
+    }
+}
+
+async fn async_main() {
+    let _write = write!(&mut AsyncStdout, "...").await;
+    let _writeln = writeln!(&mut AsyncStdout, "...").await;
+}
+
+fn main() {
+    let _ = async_main;
+}
diff --git a/src/test/ui/macros/format-args-temporaries-in-write.rs b/src/test/ui/macros/format-args-temporaries-in-write.rs
new file mode 100644
index 00000000000..339ccbc33ac
--- /dev/null
+++ b/src/test/ui/macros/format-args-temporaries-in-write.rs
@@ -0,0 +1,50 @@
+// check-fail
+
+use std::fmt::{self, Display};
+
+struct Mutex;
+
+impl Mutex {
+    fn lock(&self) -> MutexGuard {
+        MutexGuard(self)
+    }
+}
+
+struct MutexGuard<'a>(&'a Mutex);
+
+impl<'a> Drop for MutexGuard<'a> {
+    fn drop(&mut self) {
+        // Empty but this is a necessary part of the repro. Otherwise borrow
+        // checker is fine with 'a dangling at the time that MutexGuard goes out
+        // of scope.
+    }
+}
+
+struct Out;
+
+impl Out {
+    fn write_fmt(&self, _args: fmt::Arguments) {}
+}
+
+impl<'a> Display for MutexGuard<'a> {
+    fn fmt(&self, _formatter: &mut fmt::Formatter) -> fmt::Result {
+        Ok(())
+    }
+}
+
+fn main() {
+    // FIXME(dtolnay): We actually want both of these to work. I think it's
+    // sadly unimplementable today though.
+
+    let _write = {
+        let mutex = Mutex;
+        write!(Out, "{}", mutex.lock()) /* no semicolon */
+        //~^ ERROR `mutex` does not live long enough
+    };
+
+    let _writeln = {
+        let mutex = Mutex;
+        writeln!(Out, "{}", mutex.lock()) /* no semicolon */
+        //~^ ERROR `mutex` does not live long enough
+    };
+}
diff --git a/src/test/ui/macros/format-args-temporaries-in-write.stderr b/src/test/ui/macros/format-args-temporaries-in-write.stderr
new file mode 100644
index 00000000000..03ecc4b4418
--- /dev/null
+++ b/src/test/ui/macros/format-args-temporaries-in-write.stderr
@@ -0,0 +1,43 @@
+error[E0597]: `mutex` does not live long enough
+  --> $DIR/format-args-temporaries-in-write.rs:41:27
+   |
+LL |         write!(Out, "{}", mutex.lock()) /* no semicolon */
+   |                           ^^^^^^^^^^^^
+   |                           |
+   |                           borrowed value does not live long enough
+   |                           a temporary with access to the borrow is created here ...
+LL |
+LL |     };
+   |     -- ... and the borrow might be used here, when that temporary is dropped and runs the `Drop` code for type `MutexGuard`
+   |     |
+   |     `mutex` dropped here while still borrowed
+   |
+help: consider adding semicolon after the expression so its temporaries are dropped sooner, before the local variables declared by the block are dropped
+  --> $SRC_DIR/core/src/macros/mod.rs:LL:COL
+   |
+LL |         $dst.write_fmt($crate::format_args!($($arg)*));
+   |                                                       +
+
+error[E0597]: `mutex` does not live long enough
+  --> $DIR/format-args-temporaries-in-write.rs:47:29
+   |
+LL |         writeln!(Out, "{}", mutex.lock()) /* no semicolon */
+   |                             ^^^^^^^^^^^^
+   |                             |
+   |                             borrowed value does not live long enough
+   |                             a temporary with access to the borrow is created here ...
+LL |
+LL |     };
+   |     -- ... and the borrow might be used here, when that temporary is dropped and runs the `Drop` code for type `MutexGuard`
+   |     |
+   |     `mutex` dropped here while still borrowed
+   |
+help: consider adding semicolon after the expression so its temporaries are dropped sooner, before the local variables declared by the block are dropped
+  --> $SRC_DIR/core/src/macros/mod.rs:LL:COL
+   |
+LL |         $dst.write_fmt($crate::format_args_nl!($($arg)*));
+   |                                                          +
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0597`.
diff --git a/src/test/ui/macros/format-args-temporaries.rs b/src/test/ui/macros/format-args-temporaries.rs
index ddd4c9754bf..59323828bc3 100644
--- a/src/test/ui/macros/format-args-temporaries.rs
+++ b/src/test/ui/macros/format-args-temporaries.rs
@@ -20,10 +20,6 @@ impl<'a> Drop for MutexGuard<'a> {
     }
 }
 
-impl<'a> MutexGuard<'a> {
-    fn write_fmt(&self, _args: fmt::Arguments) {}
-}
-
 impl<'a> Display for MutexGuard<'a> {
     fn fmt(&self, _formatter: &mut fmt::Formatter) -> fmt::Result {
         Ok(())
@@ -31,18 +27,6 @@ impl<'a> Display for MutexGuard<'a> {
 }
 
 fn main() {
-    let _write = {
-        let out = Mutex;
-        let mutex = Mutex;
-        write!(out.lock(), "{}", mutex.lock()) /* no semicolon */
-    };
-
-    let _writeln = {
-        let out = Mutex;
-        let mutex = Mutex;
-        writeln!(out.lock(), "{}", mutex.lock()) /* no semicolon */
-    };
-
     let _print = {
         let mutex = Mutex;
         print!("{}", mutex.lock()) /* no semicolon */
diff --git a/src/test/ui/process/process-spawn-nonexistent.rs b/src/test/ui/process/process-spawn-nonexistent.rs
index 70de7316a81..a513722639a 100644
--- a/src/test/ui/process/process-spawn-nonexistent.rs
+++ b/src/test/ui/process/process-spawn-nonexistent.rs
@@ -6,9 +6,11 @@ use std::io::ErrorKind;
 use std::process::Command;
 
 fn main() {
-    assert_eq!(Command::new("nonexistent")
-                   .spawn()
-                   .unwrap_err()
-                   .kind(),
-               ErrorKind::NotFound);
+    let result = Command::new("nonexistent").spawn().unwrap_err().kind();
+
+    assert!(matches!(
+        result,
+        // Under WSL with appendWindowsPath=true, this fails with PermissionDenied
+        ErrorKind::NotFound | ErrorKind::PermissionDenied
+    ));
 }
diff --git a/src/test/ui/type-alias-impl-trait/issue-53398-cyclic-types.stderr b/src/test/ui/type-alias-impl-trait/issue-53398-cyclic-types.stderr
index 00c682b2193..d20b1cc6d85 100644
--- a/src/test/ui/type-alias-impl-trait/issue-53398-cyclic-types.stderr
+++ b/src/test/ui/type-alias-impl-trait/issue-53398-cyclic-types.stderr
@@ -1,8 +1,10 @@
-error[E0275]: overflow evaluating the requirement `<fn() -> Foo {foo} as FnOnce<()>>::Output == fn() -> Foo {foo}`
+error[E0275]: overflow evaluating the requirement `fn() -> Foo {foo}: Sized`
   --> $DIR/issue-53398-cyclic-types.rs:5:13
    |
 LL | fn foo() -> Foo {
    |             ^^^
+   |
+   = help: consider increasing the recursion limit by adding a `#![recursion_limit = "256"]` attribute to your crate (`issue_53398_cyclic_types`)
 
 error: aborting due to previous error