about summary refs log tree commit diff
path: root/clippy_lints/src
diff options
context:
space:
mode:
authorPhilipp Krones <hello@philkrones.com>2025-01-28 18:28:57 +0100
committerPhilipp Krones <hello@philkrones.com>2025-01-28 19:14:45 +0100
commit145d5adf04fecbc48bdf2ab2a356ca4c8df0c149 (patch)
tree1783d720a01e7ef83d143293961fd83200728556 /clippy_lints/src
parentc5196736b27a32b688b957f2937dd4affadbe14f (diff)
parent25509e71359ea0b218309d4b7e94bf40e1ef716e (diff)
downloadrust-145d5adf04fecbc48bdf2ab2a356ca4c8df0c149.tar.gz
rust-145d5adf04fecbc48bdf2ab2a356ca4c8df0c149.zip
Merge remote-tracking branch 'upstream/master' into rustup
Diffstat (limited to 'clippy_lints/src')
-rw-r--r--clippy_lints/src/arbitrary_source_item_ordering.rs4
-rw-r--r--clippy_lints/src/assigning_clones.rs2
-rw-r--r--clippy_lints/src/attrs/mixed_attributes_style.rs2
-rw-r--r--clippy_lints/src/cargo/mod.rs9
-rw-r--r--clippy_lints/src/casts/cast_possible_wrap.rs2
-rw-r--r--clippy_lints/src/casts/cast_sign_loss.rs4
-rw-r--r--clippy_lints/src/checked_conversions.rs2
-rw-r--r--clippy_lints/src/declared_lints.rs8
-rw-r--r--clippy_lints/src/default_constructed_unit_structs.rs2
-rw-r--r--clippy_lints/src/default_numeric_fallback.rs22
-rw-r--r--clippy_lints/src/dereference.rs2
-rw-r--r--clippy_lints/src/doc/lazy_continuation.rs110
-rw-r--r--clippy_lints/src/doc/mod.rs34
-rw-r--r--clippy_lints/src/enum_clike.rs2
-rw-r--r--clippy_lints/src/eta_reduction.rs31
-rw-r--r--clippy_lints/src/extra_unused_type_parameters.rs2
-rw-r--r--clippy_lints/src/functions/impl_trait_in_params.rs2
-rw-r--r--clippy_lints/src/functions/must_use.rs2
-rw-r--r--clippy_lints/src/implicit_saturating_add.rs2
-rw-r--r--clippy_lints/src/implicit_saturating_sub.rs2
-rw-r--r--clippy_lints/src/iter_over_hash_type.rs2
-rw-r--r--clippy_lints/src/let_with_type_underscore.rs2
-rw-r--r--clippy_lints/src/lib.rs8
-rw-r--r--clippy_lints/src/lifetimes.rs93
-rw-r--r--clippy_lints/src/literal_representation.rs2
-rw-r--r--clippy_lints/src/literal_string_with_formatting_args.rs4
-rw-r--r--clippy_lints/src/loops/mod.rs2
-rw-r--r--clippy_lints/src/loops/same_item_push.rs34
-rw-r--r--clippy_lints/src/manual_bits.rs4
-rw-r--r--clippy_lints/src/manual_div_ceil.rs36
-rw-r--r--clippy_lints/src/manual_is_ascii_check.rs12
-rw-r--r--clippy_lints/src/manual_let_else.rs4
-rw-r--r--clippy_lints/src/manual_rem_euclid.rs2
-rw-r--r--clippy_lints/src/manual_strip.rs2
-rw-r--r--clippy_lints/src/matches/manual_filter.rs8
-rw-r--r--clippy_lints/src/matches/manual_ok_err.rs135
-rw-r--r--clippy_lints/src/matches/manual_utils.rs2
-rw-r--r--clippy_lints/src/matches/match_bool.rs53
-rw-r--r--clippy_lints/src/matches/match_like_matches.rs2
-rw-r--r--clippy_lints/src/matches/match_str_case_mismatch.rs2
-rw-r--r--clippy_lints/src/matches/match_wild_enum.rs2
-rw-r--r--clippy_lints/src/matches/mod.rs45
-rw-r--r--clippy_lints/src/matches/significant_drop_in_scrutinee.rs9
-rw-r--r--clippy_lints/src/matches/try_err.rs2
-rw-r--r--clippy_lints/src/matches/wild_in_or_pats.rs2
-rw-r--r--clippy_lints/src/methods/bytecount.rs2
-rw-r--r--clippy_lints/src/methods/bytes_count_to_len.rs2
-rw-r--r--clippy_lints/src/methods/bytes_nth.rs2
-rw-r--r--clippy_lints/src/methods/cloned_instead_of_copied.rs2
-rw-r--r--clippy_lints/src/methods/drain_collect.rs7
-rw-r--r--clippy_lints/src/methods/err_expect.rs2
-rw-r--r--clippy_lints/src/methods/expect_fun_call.rs2
-rw-r--r--clippy_lints/src/methods/iter_with_drain.rs2
-rw-r--r--clippy_lints/src/methods/manual_repeat_n.rs43
-rw-r--r--clippy_lints/src/methods/map_with_unused_argument_over_ranges.rs5
-rw-r--r--clippy_lints/src/methods/mod.rs105
-rw-r--r--clippy_lints/src/methods/needless_as_bytes.rs10
-rw-r--r--clippy_lints/src/methods/obfuscated_if_else.rs31
-rw-r--r--clippy_lints/src/methods/path_ends_with_ext.rs2
-rw-r--r--clippy_lints/src/methods/sliced_string_as_bytes.rs29
-rw-r--r--clippy_lints/src/methods/unnecessary_iter_cloned.rs2
-rw-r--r--clippy_lints/src/methods/unnecessary_map_or.rs37
-rw-r--r--clippy_lints/src/methods/unnecessary_sort_by.rs6
-rw-r--r--clippy_lints/src/methods/unnecessary_to_owned.rs3
-rw-r--r--clippy_lints/src/methods/useless_nonzero_new_unchecked.rs59
-rw-r--r--clippy_lints/src/misc.rs23
-rw-r--r--clippy_lints/src/mismatching_type_param_order.rs2
-rw-r--r--clippy_lints/src/missing_doc.rs2
-rw-r--r--clippy_lints/src/missing_fields_in_debug.rs2
-rw-r--r--clippy_lints/src/missing_inline.rs2
-rw-r--r--clippy_lints/src/multi_assignments.rs4
-rw-r--r--clippy_lints/src/multiple_unsafe_ops_per_block.rs2
-rw-r--r--clippy_lints/src/mutable_debug_assertion.rs4
-rw-r--r--clippy_lints/src/mutex_atomic.rs2
-rw-r--r--clippy_lints/src/needless_late_init.rs6
-rw-r--r--clippy_lints/src/no_mangle_with_rust_abi.rs4
-rw-r--r--clippy_lints/src/non_copy_const.rs10
-rw-r--r--clippy_lints/src/non_octal_unix_permissions.rs2
-rw-r--r--clippy_lints/src/non_std_lazy_statics.rs306
-rw-r--r--clippy_lints/src/operators/arithmetic_side_effects.rs10
-rw-r--r--clippy_lints/src/operators/cmp_owned.rs2
-rw-r--r--clippy_lints/src/operators/const_comparisons.rs2
-rw-r--r--clippy_lints/src/operators/double_comparison.rs2
-rw-r--r--clippy_lints/src/operators/float_cmp.rs2
-rw-r--r--clippy_lints/src/operators/mod.rs4
-rw-r--r--clippy_lints/src/operators/modulo_arithmetic.rs2
-rw-r--r--clippy_lints/src/operators/modulo_one.rs2
-rw-r--r--clippy_lints/src/partialeq_ne_impl.rs2
-rw-r--r--clippy_lints/src/precedence.rs2
-rw-r--r--clippy_lints/src/redundant_closure_call.rs2
-rw-r--r--clippy_lints/src/redundant_pub_crate.rs3
-rw-r--r--clippy_lints/src/redundant_type_annotations.rs2
-rw-r--r--clippy_lints/src/repeat_vec_with_capacity.rs8
-rw-r--r--clippy_lints/src/returns.rs25
-rw-r--r--clippy_lints/src/single_range_in_vec_init.rs4
-rw-r--r--clippy_lints/src/size_of_in_element_count.rs6
-rw-r--r--clippy_lints/src/slow_vector_initialization.rs13
-rw-r--r--clippy_lints/src/swap.rs2
-rw-r--r--clippy_lints/src/transmute/missing_transmute_annotations.rs5
-rw-r--r--clippy_lints/src/transmute/transmute_int_to_non_zero.rs2
-rw-r--r--clippy_lints/src/tuple_array_conversions.rs2
-rw-r--r--clippy_lints/src/types/borrowed_box.rs2
-rw-r--r--clippy_lints/src/unnecessary_semicolon.rs109
-rw-r--r--clippy_lints/src/unneeded_struct_pattern.rs76
-rw-r--r--clippy_lints/src/unused_io_amount.rs2
-rw-r--r--clippy_lints/src/useless_conversion.rs39
-rw-r--r--clippy_lints/src/utils/internal_lints/slow_symbol_comparisons.rs2
-rw-r--r--clippy_lints/src/vec.rs2
108 files changed, 1445 insertions, 330 deletions
diff --git a/clippy_lints/src/arbitrary_source_item_ordering.rs b/clippy_lints/src/arbitrary_source_item_ordering.rs
index 380b094d017..0389223c3e0 100644
--- a/clippy_lints/src/arbitrary_source_item_ordering.rs
+++ b/clippy_lints/src/arbitrary_source_item_ordering.rs
@@ -445,8 +445,8 @@ fn convert_assoc_item_kind(value: AssocItemKind) -> SourceItemOrderingTraitAssoc
     #[allow(clippy::enum_glob_use)] // Very local glob use for legibility.
     use SourceItemOrderingTraitAssocItemKind::*;
     match value {
-        AssocItemKind::Const { .. } => Const,
-        AssocItemKind::Type { .. } => Type,
+        AssocItemKind::Const => Const,
+        AssocItemKind::Type => Type,
         AssocItemKind::Fn { .. } => Fn,
     }
 }
diff --git a/clippy_lints/src/assigning_clones.rs b/clippy_lints/src/assigning_clones.rs
index c8dd77d9578..c01155ca86e 100644
--- a/clippy_lints/src/assigning_clones.rs
+++ b/clippy_lints/src/assigning_clones.rs
@@ -257,7 +257,7 @@ fn build_sugg<'tcx>(
                         // The receiver may have been a value type, so we need to add an `&` to
                         // be sure the argument to clone_from will be a reference.
                         arg_sugg = arg_sugg.addr();
-                    };
+                    }
 
                     format!("{receiver_sugg}.clone_from({arg_sugg})")
                 },
diff --git a/clippy_lints/src/attrs/mixed_attributes_style.rs b/clippy_lints/src/attrs/mixed_attributes_style.rs
index 8c91c65eaf7..3e4bcfbfc19 100644
--- a/clippy_lints/src/attrs/mixed_attributes_style.rs
+++ b/clippy_lints/src/attrs/mixed_attributes_style.rs
@@ -60,7 +60,7 @@ pub(super) fn check(cx: &EarlyContext<'_>, item_span: Span, attrs: &[Attribute])
                 }
                 outer_attr_kind.insert(kind);
             },
-        };
+        }
     }
 }
 
diff --git a/clippy_lints/src/cargo/mod.rs b/clippy_lints/src/cargo/mod.rs
index 96a2b161464..60371dcd771 100644
--- a/clippy_lints/src/cargo/mod.rs
+++ b/clippy_lints/src/cargo/mod.rs
@@ -161,6 +161,15 @@ declare_clippy_lint! {
     /// [dependencies]
     /// regex = "*"
     /// ```
+    /// Use instead:
+    /// ```toml
+    /// [dependencies]
+    /// # allow patch updates, but not minor or major version changes
+    /// some_crate_1 = "~1.2.3"
+    ///
+    /// # pin the version to a specific version
+    /// some_crate_2 = "=1.2.3"
+    /// ```
     #[clippy::version = "1.32.0"]
     pub WILDCARD_DEPENDENCIES,
     cargo,
diff --git a/clippy_lints/src/casts/cast_possible_wrap.rs b/clippy_lints/src/casts/cast_possible_wrap.rs
index 3cf4a43b0d4..504d0a267e4 100644
--- a/clippy_lints/src/casts/cast_possible_wrap.rs
+++ b/clippy_lints/src/casts/cast_possible_wrap.rs
@@ -84,6 +84,6 @@ pub(super) fn check(cx: &LateContext<'_>, expr: &Expr<'_>, cast_from: Ty<'_>, ca
             diag
                 .note("`usize` and `isize` may be as small as 16 bits on some platforms")
                 .note("for more information see https://doc.rust-lang.org/reference/types/numeric.html#machine-dependent-integer-types");
-        };
+        }
     });
 }
diff --git a/clippy_lints/src/casts/cast_sign_loss.rs b/clippy_lints/src/casts/cast_sign_loss.rs
index 4be53ace687..45045e58ac7 100644
--- a/clippy_lints/src/casts/cast_sign_loss.rs
+++ b/clippy_lints/src/casts/cast_sign_loss.rs
@@ -205,7 +205,7 @@ fn expr_muldiv_sign(cx: &LateContext<'_>, expr: &Expr<'_>) -> Sign {
             // - uncertain if there are any uncertain values (because they could be negative or positive),
             Sign::Uncertain => return Sign::Uncertain,
             Sign::ZeroOrPositive => (),
-        };
+        }
     }
 
     // A mul/div is:
@@ -236,7 +236,7 @@ fn expr_add_sign(cx: &LateContext<'_>, expr: &Expr<'_>) -> Sign {
             // - uncertain if there are any uncertain values (because they could be negative or positive),
             Sign::Uncertain => return Sign::Uncertain,
             Sign::ZeroOrPositive => positive_count += 1,
-        };
+        }
     }
 
     // A sum is:
diff --git a/clippy_lints/src/checked_conversions.rs b/clippy_lints/src/checked_conversions.rs
index 364f5c7dc7a..1edfde97422 100644
--- a/clippy_lints/src/checked_conversions.rs
+++ b/clippy_lints/src/checked_conversions.rs
@@ -273,7 +273,7 @@ fn get_types_from_cast<'a>(
             },
             _ => {},
         }
-    };
+    }
     None
 }
 
diff --git a/clippy_lints/src/declared_lints.rs b/clippy_lints/src/declared_lints.rs
index 87e546fbf01..86bcf8edd57 100644
--- a/clippy_lints/src/declared_lints.rs
+++ b/clippy_lints/src/declared_lints.rs
@@ -142,6 +142,7 @@ pub static LINTS: &[&crate::LintInfo] = &[
     crate::doc::DOC_LINK_WITH_QUOTES_INFO,
     crate::doc::DOC_MARKDOWN_INFO,
     crate::doc::DOC_NESTED_REFDEFS_INFO,
+    crate::doc::DOC_OVERINDENTED_LIST_ITEMS_INFO,
     crate::doc::EMPTY_DOCS_INFO,
     crate::doc::EMPTY_LINE_AFTER_DOC_COMMENTS_INFO,
     crate::doc::EMPTY_LINE_AFTER_OUTER_ATTR_INFO,
@@ -335,6 +336,7 @@ pub static LINTS: &[&crate::LintInfo] = &[
     crate::matches::INFALLIBLE_DESTRUCTURING_MATCH_INFO,
     crate::matches::MANUAL_FILTER_INFO,
     crate::matches::MANUAL_MAP_INFO,
+    crate::matches::MANUAL_OK_ERR_INFO,
     crate::matches::MANUAL_UNWRAP_OR_INFO,
     crate::matches::MATCH_AS_REF_INFO,
     crate::matches::MATCH_BOOL_INFO,
@@ -419,6 +421,7 @@ pub static LINTS: &[&crate::LintInfo] = &[
     crate::methods::MANUAL_IS_VARIANT_AND_INFO,
     crate::methods::MANUAL_NEXT_BACK_INFO,
     crate::methods::MANUAL_OK_OR_INFO,
+    crate::methods::MANUAL_REPEAT_N_INFO,
     crate::methods::MANUAL_SATURATING_ARITHMETIC_INFO,
     crate::methods::MANUAL_SPLIT_ONCE_INFO,
     crate::methods::MANUAL_STR_REPEAT_INFO,
@@ -466,6 +469,7 @@ pub static LINTS: &[&crate::LintInfo] = &[
     crate::methods::SHOULD_IMPLEMENT_TRAIT_INFO,
     crate::methods::SINGLE_CHAR_ADD_STR_INFO,
     crate::methods::SKIP_WHILE_NEXT_INFO,
+    crate::methods::SLICED_STRING_AS_BYTES_INFO,
     crate::methods::STABLE_SORT_PRIMITIVE_INFO,
     crate::methods::STRING_EXTEND_CHARS_INFO,
     crate::methods::STRING_LIT_CHARS_ANY_INFO,
@@ -495,6 +499,7 @@ pub static LINTS: &[&crate::LintInfo] = &[
     crate::methods::UNWRAP_OR_DEFAULT_INFO,
     crate::methods::UNWRAP_USED_INFO,
     crate::methods::USELESS_ASREF_INFO,
+    crate::methods::USELESS_NONZERO_NEW_UNCHECKED_INFO,
     crate::methods::VEC_RESIZE_TO_ZERO_INFO,
     crate::methods::VERBOSE_FILE_READS_INFO,
     crate::methods::WAKER_CLONE_WAKE_INFO,
@@ -572,6 +577,7 @@ pub static LINTS: &[&crate::LintInfo] = &[
     crate::non_expressive_names::SIMILAR_NAMES_INFO,
     crate::non_octal_unix_permissions::NON_OCTAL_UNIX_PERMISSIONS_INFO,
     crate::non_send_fields_in_send_ty::NON_SEND_FIELDS_IN_SEND_TY_INFO,
+    crate::non_std_lazy_statics::NON_STD_LAZY_STATICS_INFO,
     crate::non_zero_suggestions::NON_ZERO_SUGGESTIONS_INFO,
     crate::nonstandard_macro_braces::NONSTANDARD_MACRO_BRACES_INFO,
     crate::octal_escapes::OCTAL_ESCAPES_INFO,
@@ -753,8 +759,10 @@ pub static LINTS: &[&crate::LintInfo] = &[
     crate::unnecessary_map_on_constructor::UNNECESSARY_MAP_ON_CONSTRUCTOR_INFO,
     crate::unnecessary_owned_empty_strings::UNNECESSARY_OWNED_EMPTY_STRINGS_INFO,
     crate::unnecessary_self_imports::UNNECESSARY_SELF_IMPORTS_INFO,
+    crate::unnecessary_semicolon::UNNECESSARY_SEMICOLON_INFO,
     crate::unnecessary_struct_initialization::UNNECESSARY_STRUCT_INITIALIZATION_INFO,
     crate::unnecessary_wraps::UNNECESSARY_WRAPS_INFO,
+    crate::unneeded_struct_pattern::UNNEEDED_STRUCT_PATTERN_INFO,
     crate::unnested_or_patterns::UNNESTED_OR_PATTERNS_INFO,
     crate::unsafe_removed_from_name::UNSAFE_REMOVED_FROM_NAME_INFO,
     crate::unused_async::UNUSED_ASYNC_INFO,
diff --git a/clippy_lints/src/default_constructed_unit_structs.rs b/clippy_lints/src/default_constructed_unit_structs.rs
index 33a97222b8f..bbd5dc15542 100644
--- a/clippy_lints/src/default_constructed_unit_structs.rs
+++ b/clippy_lints/src/default_constructed_unit_structs.rs
@@ -80,6 +80,6 @@ impl LateLintPass<'_> for DefaultConstructedUnitStructs {
                 String::new(),
                 Applicability::MachineApplicable,
             );
-        };
+        }
     }
 }
diff --git a/clippy_lints/src/default_numeric_fallback.rs b/clippy_lints/src/default_numeric_fallback.rs
index c04a73c890f..ca3eaae7b85 100644
--- a/clippy_lints/src/default_numeric_fallback.rs
+++ b/clippy_lints/src/default_numeric_fallback.rs
@@ -223,19 +223,17 @@ impl<'tcx> Visitor<'tcx> for NumericFallbackVisitor<'_, 'tcx> {
     }
 
     fn visit_pat(&mut self, pat: &'tcx Pat<'_>) {
-        match pat.kind {
-            PatKind::Expr(&PatExpr {
-                hir_id,
-                kind: PatExprKind::Lit { lit, .. },
-                ..
-            }) => {
-                let ty = self.cx.typeck_results().node_type(hir_id);
-                self.check_lit(lit, ty, hir_id);
-                return;
-            },
-            _ => {},
+        if let PatKind::Expr(&PatExpr {
+            hir_id,
+            kind: PatExprKind::Lit { lit, .. },
+            ..
+        }) = pat.kind
+        {
+            let ty = self.cx.typeck_results().node_type(hir_id);
+            self.check_lit(lit, ty, hir_id);
+            return;
         }
-        walk_pat(self, pat)
+        walk_pat(self, pat);
     }
 
     fn visit_stmt(&mut self, stmt: &'tcx Stmt<'_>) {
diff --git a/clippy_lints/src/dereference.rs b/clippy_lints/src/dereference.rs
index f5589d8f8e2..123e358d7c3 100644
--- a/clippy_lints/src/dereference.rs
+++ b/clippy_lints/src/dereference.rs
@@ -331,7 +331,7 @@ impl<'tcx> LateLintPass<'tcx> for Dereferencing<'tcx> {
                                     deref_count += 1;
                                 },
                                 None => break None,
-                            };
+                            }
                         };
 
                         let use_node = use_cx.use_node(cx);
diff --git a/clippy_lints/src/doc/lazy_continuation.rs b/clippy_lints/src/doc/lazy_continuation.rs
index f9e4a43c0e7..2577324f23d 100644
--- a/clippy_lints/src/doc/lazy_continuation.rs
+++ b/clippy_lints/src/doc/lazy_continuation.rs
@@ -1,11 +1,12 @@
-use clippy_utils::diagnostics::span_lint_and_then;
+use clippy_utils::diagnostics::{span_lint_and_sugg, span_lint_and_then};
 use itertools::Itertools;
 use rustc_errors::Applicability;
 use rustc_lint::LateContext;
 use rustc_span::{BytePos, Span};
+use std::cmp::Ordering;
 use std::ops::Range;
 
-use super::DOC_LAZY_CONTINUATION;
+use super::{DOC_LAZY_CONTINUATION, DOC_OVERINDENTED_LIST_ITEMS};
 
 fn map_container_to_text(c: &super::Container) -> &'static str {
     match c {
@@ -28,12 +29,57 @@ pub(super) fn check(
         return;
     }
 
+    // Blockquote
     let ccount = doc[range.clone()].chars().filter(|c| *c == '>').count();
     let blockquote_level = containers
         .iter()
         .filter(|c| matches!(c, super::Container::Blockquote))
         .count();
-    let lcount = doc[range.clone()].chars().filter(|c| *c == ' ').count();
+    if ccount < blockquote_level {
+        span_lint_and_then(
+            cx,
+            DOC_LAZY_CONTINUATION,
+            span,
+            "doc quote line without `>` marker",
+            |diag| {
+                let mut doc_start_range = &doc[range];
+                let mut suggested = String::new();
+                for c in containers {
+                    let text = map_container_to_text(c);
+                    if doc_start_range.starts_with(text) {
+                        doc_start_range = &doc_start_range[text.len()..];
+                        span = span.with_lo(
+                            span.lo() + BytePos(u32::try_from(text.len()).expect("text is not 2**32 or bigger")),
+                        );
+                    } else if matches!(c, super::Container::Blockquote)
+                        && let Some(i) = doc_start_range.find('>')
+                    {
+                        doc_start_range = &doc_start_range[i + 1..];
+                        span = span
+                            .with_lo(span.lo() + BytePos(u32::try_from(i).expect("text is not 2**32 or bigger") + 1));
+                    } else {
+                        suggested.push_str(text);
+                    }
+                }
+                diag.span_suggestion_verbose(
+                    span,
+                    "add markers to start of line",
+                    suggested,
+                    Applicability::MachineApplicable,
+                );
+                diag.help("if this not intended to be a quote at all, escape it with `\\>`");
+            },
+        );
+        return;
+    }
+
+    if ccount != 0 && blockquote_level != 0 {
+        // If this doc is a blockquote, we don't go further.
+        return;
+    }
+
+    // List
+    let leading_spaces = doc[range].chars().filter(|c| *c == ' ').count();
     let list_indentation = containers
         .iter()
         .map(|c| {
@@ -44,50 +90,36 @@ pub(super) fn check(
             }
         })
         .sum();
-    if ccount < blockquote_level || lcount < list_indentation {
-        let msg = if ccount < blockquote_level {
-            "doc quote line without `>` marker"
-        } else {
-            "doc list item without indentation"
-        };
-        span_lint_and_then(cx, DOC_LAZY_CONTINUATION, span, msg, |diag| {
-            if ccount == 0 && blockquote_level == 0 {
+    match leading_spaces.cmp(&list_indentation) {
+        Ordering::Less => span_lint_and_then(
+            cx,
+            DOC_LAZY_CONTINUATION,
+            span,
+            "doc list item without indentation",
+            |diag| {
                 // simpler suggestion style for indentation
-                let indent = list_indentation - lcount;
+                let indent = list_indentation - leading_spaces;
                 diag.span_suggestion_verbose(
                     span.shrink_to_hi(),
                     "indent this line",
-                    std::iter::repeat(" ").take(indent).join(""),
+                    std::iter::repeat_n(" ", indent).join(""),
                     Applicability::MaybeIncorrect,
                 );
                 diag.help("if this is supposed to be its own paragraph, add a blank line");
-                return;
-            }
-            let mut doc_start_range = &doc[range];
-            let mut suggested = String::new();
-            for c in containers {
-                let text = map_container_to_text(c);
-                if doc_start_range.starts_with(text) {
-                    doc_start_range = &doc_start_range[text.len()..];
-                    span = span
-                        .with_lo(span.lo() + BytePos(u32::try_from(text.len()).expect("text is not 2**32 or bigger")));
-                } else if matches!(c, super::Container::Blockquote)
-                    && let Some(i) = doc_start_range.find('>')
-                {
-                    doc_start_range = &doc_start_range[i + 1..];
-                    span =
-                        span.with_lo(span.lo() + BytePos(u32::try_from(i).expect("text is not 2**32 or bigger") + 1));
-                } else {
-                    suggested.push_str(text);
-                }
-            }
-            diag.span_suggestion_verbose(
+            },
+        ),
+        Ordering::Greater => {
+            let sugg = std::iter::repeat_n(" ", list_indentation).join("");
+            span_lint_and_sugg(
+                cx,
+                DOC_OVERINDENTED_LIST_ITEMS,
                 span,
-                "add markers to start of line",
-                suggested,
-                Applicability::MachineApplicable,
+                "doc list item overindented",
+                format!("try using `{sugg}` ({list_indentation} spaces)"),
+                sugg,
+                Applicability::MaybeIncorrect,
             );
-            diag.help("if this not intended to be a quote at all, escape it with `\\>`");
-        });
+        },
+        Ordering::Equal => {},
     }
 }
diff --git a/clippy_lints/src/doc/mod.rs b/clippy_lints/src/doc/mod.rs
index 7561a6cf2a7..15530c3dbc5 100644
--- a/clippy_lints/src/doc/mod.rs
+++ b/clippy_lints/src/doc/mod.rs
@@ -430,6 +430,39 @@ declare_clippy_lint! {
 
 declare_clippy_lint! {
     /// ### What it does
+    ///
+    /// Detects overindented list items in doc comments where the continuation
+    /// lines are indented more than necessary.
+    ///
+    /// ### Why is this bad?
+    ///
+    /// Overindented list items in doc comments can lead to inconsistent and
+    /// poorly formatted documentation when rendered. Excessive indentation may
+    /// cause the text to be misinterpreted as a nested list item or code block,
+    /// affecting readability and the overall structure of the documentation.
+    ///
+    /// ### Example
+    ///
+    /// ```no_run
+    /// /// - This is the first item in a list
+    /// ///      and this line is overindented.
+    /// # fn foo() {}
+    /// ```
+    ///
+    /// Fixes this into:
+    /// ```no_run
+    /// /// - This is the first item in a list
+    /// ///   and this line is overindented.
+    /// # fn foo() {}
+    /// ```
+    #[clippy::version = "1.80.0"]
+    pub DOC_OVERINDENTED_LIST_ITEMS,
+    style,
+    "ensure list items are not overindented"
+}
+
+declare_clippy_lint! {
+    /// ### What it does
     /// Checks if the first paragraph in the documentation of items listed in the module page is too long.
     ///
     /// ### Why is this bad?
@@ -617,6 +650,7 @@ impl_lint_pass!(Documentation => [
     SUSPICIOUS_DOC_COMMENTS,
     EMPTY_DOCS,
     DOC_LAZY_CONTINUATION,
+    DOC_OVERINDENTED_LIST_ITEMS,
     EMPTY_LINE_AFTER_OUTER_ATTR,
     EMPTY_LINE_AFTER_DOC_COMMENTS,
     TOO_LONG_FIRST_DOC_PARAGRAPH,
diff --git a/clippy_lints/src/enum_clike.rs b/clippy_lints/src/enum_clike.rs
index e9e9d00907e..a090a987d4f 100644
--- a/clippy_lints/src/enum_clike.rs
+++ b/clippy_lints/src/enum_clike.rs
@@ -70,7 +70,7 @@ impl<'tcx> LateLintPass<'tcx> for UnportableVariant {
                             var.span,
                             "C-like enum variant discriminant is not portable to 32-bit targets",
                         );
-                    };
+                    }
                 }
             }
         }
diff --git a/clippy_lints/src/eta_reduction.rs b/clippy_lints/src/eta_reduction.rs
index 57a30de7ad1..52b699274bb 100644
--- a/clippy_lints/src/eta_reduction.rs
+++ b/clippy_lints/src/eta_reduction.rs
@@ -3,7 +3,9 @@ use clippy_utils::higher::VecArgs;
 use clippy_utils::source::snippet_opt;
 use clippy_utils::ty::get_type_diagnostic_name;
 use clippy_utils::usage::{local_used_after_expr, local_used_in};
-use clippy_utils::{get_path_from_caller_to_method_type, is_adjusted, path_to_local, path_to_local_id};
+use clippy_utils::{
+    get_path_from_caller_to_method_type, is_adjusted, is_no_std_crate, path_to_local, path_to_local_id,
+};
 use rustc_errors::Applicability;
 use rustc_hir::{BindingMode, Expr, ExprKind, FnRetTy, Param, PatKind, QPath, Safety, TyKind};
 use rustc_infer::infer::TyCtxtInferExt;
@@ -101,19 +103,20 @@ fn check_closure<'tcx>(cx: &LateContext<'tcx>, outer_receiver: Option<&Expr<'tcx
     };
 
     if body.value.span.from_expansion() {
-        if body.params.is_empty() {
-            if let Some(VecArgs::Vec(&[])) = VecArgs::hir(cx, body.value) {
-                // replace `|| vec![]` with `Vec::new`
-                span_lint_and_sugg(
-                    cx,
-                    REDUNDANT_CLOSURE,
-                    expr.span,
-                    "redundant closure",
-                    "replace the closure with `Vec::new`",
-                    "std::vec::Vec::new".into(),
-                    Applicability::MachineApplicable,
-                );
-            }
+        if body.params.is_empty()
+            && let Some(VecArgs::Vec(&[])) = VecArgs::hir(cx, body.value)
+        {
+            let vec_crate = if is_no_std_crate(cx) { "alloc" } else { "std" };
+            // replace `|| vec![]` with `Vec::new`
+            span_lint_and_sugg(
+                cx,
+                REDUNDANT_CLOSURE,
+                expr.span,
+                "redundant closure",
+                "replace the closure with `Vec::new`",
+                format!("{vec_crate}::vec::Vec::new"),
+                Applicability::MachineApplicable,
+            );
         }
         // skip `foo(|| macro!())`
         return;
diff --git a/clippy_lints/src/extra_unused_type_parameters.rs b/clippy_lints/src/extra_unused_type_parameters.rs
index 688979311c8..cdbfe7af8f9 100644
--- a/clippy_lints/src/extra_unused_type_parameters.rs
+++ b/clippy_lints/src/extra_unused_type_parameters.rs
@@ -183,7 +183,7 @@ impl<'cx, 'tcx> TypeWalker<'cx, 'tcx> {
                     .collect()
             };
             self.emit_sugg(spans, msg, help);
-        };
+        }
     }
 }
 
diff --git a/clippy_lints/src/functions/impl_trait_in_params.rs b/clippy_lints/src/functions/impl_trait_in_params.rs
index 05e341e06fd..752dbc0db4d 100644
--- a/clippy_lints/src/functions/impl_trait_in_params.rs
+++ b/clippy_lints/src/functions/impl_trait_in_params.rs
@@ -45,7 +45,7 @@ pub(super) fn check_fn<'tcx>(cx: &LateContext<'_>, kind: &'tcx FnKind<'_>, body:
         for param in generics.params {
             if param.is_impl_trait() {
                 report(cx, param, generics);
-            };
+            }
         }
     }
 }
diff --git a/clippy_lints/src/functions/must_use.rs b/clippy_lints/src/functions/must_use.rs
index 1a01f5f885c..90d3db2700f 100644
--- a/clippy_lints/src/functions/must_use.rs
+++ b/clippy_lints/src/functions/must_use.rs
@@ -160,7 +160,7 @@ fn check_needless_must_use(
                 && !is_must_use_ty(cx, future_ty)
             {
                 return;
-            };
+            }
         }
 
         span_lint_and_help(
diff --git a/clippy_lints/src/implicit_saturating_add.rs b/clippy_lints/src/implicit_saturating_add.rs
index dd5908553e5..41d2b18803d 100644
--- a/clippy_lints/src/implicit_saturating_add.rs
+++ b/clippy_lints/src/implicit_saturating_add.rs
@@ -120,7 +120,7 @@ fn get_const<'tcx>(cx: &LateContext<'tcx>, expr: &Expr<'tcx>) -> Option<(u128, B
         let ecx = ConstEvalCtxt::new(cx);
         if let Some(Constant::Int(c)) = ecx.eval(r) {
             return Some((c, op.node, l));
-        };
+        }
         if let Some(Constant::Int(c)) = ecx.eval(l) {
             return Some((c, invert_op(op.node)?, r));
         }
diff --git a/clippy_lints/src/implicit_saturating_sub.rs b/clippy_lints/src/implicit_saturating_sub.rs
index 37481dc7feb..152d506a7c0 100644
--- a/clippy_lints/src/implicit_saturating_sub.rs
+++ b/clippy_lints/src/implicit_saturating_sub.rs
@@ -350,7 +350,7 @@ fn check_with_condition<'tcx>(
                     if cx.typeck_results().expr_ty(cond_left).is_signed() {
                     } else {
                         print_lint_and_sugg(cx, var_name, expr);
-                    };
+                    }
                 }
             },
             ExprKind::Path(QPath::TypeRelative(_, name)) => {
diff --git a/clippy_lints/src/iter_over_hash_type.rs b/clippy_lints/src/iter_over_hash_type.rs
index 5131f5b7269..b1cb6da9475 100644
--- a/clippy_lints/src/iter_over_hash_type.rs
+++ b/clippy_lints/src/iter_over_hash_type.rs
@@ -65,6 +65,6 @@ impl LateLintPass<'_> for IterOverHashType {
                 expr.span,
                 "iteration over unordered hash-based type",
             );
-        };
+        }
     }
 }
diff --git a/clippy_lints/src/let_with_type_underscore.rs b/clippy_lints/src/let_with_type_underscore.rs
index 2d2438514cc..34ded6c6500 100644
--- a/clippy_lints/src/let_with_type_underscore.rs
+++ b/clippy_lints/src/let_with_type_underscore.rs
@@ -41,6 +41,6 @@ impl<'tcx> LateLintPass<'tcx> for UnderscoreTyped {
                 Some(ty.span.with_lo(local.pat.span.hi())),
                 "remove the explicit type `_` declaration",
             );
-        };
+        }
     }
 }
diff --git a/clippy_lints/src/lib.rs b/clippy_lints/src/lib.rs
index fad6f9d0880..4b700673d0f 100644
--- a/clippy_lints/src/lib.rs
+++ b/clippy_lints/src/lib.rs
@@ -279,6 +279,7 @@ mod non_copy_const;
 mod non_expressive_names;
 mod non_octal_unix_permissions;
 mod non_send_fields_in_send_ty;
+mod non_std_lazy_statics;
 mod non_zero_suggestions;
 mod nonstandard_macro_braces;
 mod octal_escapes;
@@ -372,8 +373,10 @@ mod unnecessary_literal_bound;
 mod unnecessary_map_on_constructor;
 mod unnecessary_owned_empty_strings;
 mod unnecessary_self_imports;
+mod unnecessary_semicolon;
 mod unnecessary_struct_initialization;
 mod unnecessary_wraps;
+mod unneeded_struct_pattern;
 mod unnested_or_patterns;
 mod unsafe_removed_from_name;
 mod unused_async;
@@ -680,7 +683,7 @@ pub fn register_lints(store: &mut rustc_lint::LintStore, conf: &'static Conf) {
     store.register_late_pass(|_| Box::new(unit_types::UnitTypes));
     store.register_late_pass(move |_| Box::new(loops::Loops::new(conf)));
     store.register_late_pass(|_| Box::<main_recursion::MainRecursion>::default());
-    store.register_late_pass(|_| Box::new(lifetimes::Lifetimes));
+    store.register_late_pass(move |_| Box::new(lifetimes::Lifetimes::new(conf)));
     store.register_late_pass(|_| Box::new(entry::HashMapPass));
     store.register_late_pass(|_| Box::new(minmax::MinMaxPass));
     store.register_late_pass(|_| Box::new(zero_div_zero::ZeroDiv));
@@ -970,5 +973,8 @@ pub fn register_lints(store: &mut rustc_lint::LintStore, conf: &'static Conf) {
     store.register_late_pass(|_| Box::new(manual_ignore_case_cmp::ManualIgnoreCaseCmp));
     store.register_late_pass(|_| Box::new(unnecessary_literal_bound::UnnecessaryLiteralBound));
     store.register_late_pass(move |_| Box::new(arbitrary_source_item_ordering::ArbitrarySourceItemOrdering::new(conf)));
+    store.register_late_pass(|_| Box::new(unneeded_struct_pattern::UnneededStructPattern));
+    store.register_late_pass(|_| Box::<unnecessary_semicolon::UnnecessarySemicolon>::default());
+    store.register_late_pass(move |_| Box::new(non_std_lazy_statics::NonStdLazyStatic::new(conf)));
     // add lints here, do not remove this comment, it's used in `new_lint`
 }
diff --git a/clippy_lints/src/lifetimes.rs b/clippy_lints/src/lifetimes.rs
index e6761ea5c67..c9ab0beb5df 100644
--- a/clippy_lints/src/lifetimes.rs
+++ b/clippy_lints/src/lifetimes.rs
@@ -1,4 +1,6 @@
+use clippy_config::Conf;
 use clippy_utils::diagnostics::{span_lint, span_lint_and_then};
+use clippy_utils::msrvs::{self, Msrv};
 use clippy_utils::trait_ref_of_method;
 use itertools::Itertools;
 use rustc_ast::visit::{try_visit, walk_list};
@@ -20,7 +22,7 @@ use rustc_lint::{LateContext, LateLintPass, LintContext};
 use rustc_middle::hir::map::Map;
 use rustc_middle::hir::nested_filter as middle_nested_filter;
 use rustc_middle::lint::in_external_macro;
-use rustc_session::declare_lint_pass;
+use rustc_session::impl_lint_pass;
 use rustc_span::Span;
 use rustc_span::def_id::LocalDefId;
 use rustc_span::symbol::{Ident, kw};
@@ -91,7 +93,19 @@ declare_clippy_lint! {
     "unused lifetimes in function definitions"
 }
 
-declare_lint_pass!(Lifetimes => [NEEDLESS_LIFETIMES, EXTRA_UNUSED_LIFETIMES]);
+pub struct Lifetimes {
+    msrv: Msrv,
+}
+
+impl Lifetimes {
+    pub fn new(conf: &'static Conf) -> Self {
+        Self {
+            msrv: conf.msrv.clone(),
+        }
+    }
+}
+
+impl_lint_pass!(Lifetimes => [NEEDLESS_LIFETIMES, EXTRA_UNUSED_LIFETIMES]);
 
 impl<'tcx> LateLintPass<'tcx> for Lifetimes {
     fn check_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx Item<'_>) {
@@ -102,7 +116,7 @@ impl<'tcx> LateLintPass<'tcx> for Lifetimes {
             ..
         } = item.kind
         {
-            check_fn_inner(cx, sig, Some(id), None, generics, item.span, true);
+            check_fn_inner(cx, sig, Some(id), None, generics, item.span, true, &self.msrv);
         } else if let ItemKind::Impl(impl_) = item.kind {
             if !item.span.from_expansion() {
                 report_extra_impl_lifetimes(cx, impl_);
@@ -121,6 +135,7 @@ impl<'tcx> LateLintPass<'tcx> for Lifetimes {
                 item.generics,
                 item.span,
                 report_extra_lifetimes,
+                &self.msrv,
             );
         }
     }
@@ -131,11 +146,14 @@ impl<'tcx> LateLintPass<'tcx> for Lifetimes {
                 TraitFn::Required(sig) => (None, Some(sig)),
                 TraitFn::Provided(id) => (Some(id), None),
             };
-            check_fn_inner(cx, sig, body, trait_sig, item.generics, item.span, true);
+            check_fn_inner(cx, sig, body, trait_sig, item.generics, item.span, true, &self.msrv);
         }
     }
+
+    extract_msrv_attr!(LateContext);
 }
 
+#[allow(clippy::too_many_arguments)]
 fn check_fn_inner<'tcx>(
     cx: &LateContext<'tcx>,
     sig: &'tcx FnSig<'_>,
@@ -144,6 +162,7 @@ fn check_fn_inner<'tcx>(
     generics: &'tcx Generics<'_>,
     span: Span,
     report_extra_lifetimes: bool,
+    msrv: &Msrv,
 ) {
     if in_external_macro(cx.sess(), span) || has_where_lifetimes(cx, generics) {
         return;
@@ -195,7 +214,7 @@ fn check_fn_inner<'tcx>(
         }
     }
 
-    if let Some((elidable_lts, usages)) = could_use_elision(cx, sig.decl, body, trait_sig, generics.params) {
+    if let Some((elidable_lts, usages)) = could_use_elision(cx, sig.decl, body, trait_sig, generics.params, msrv) {
         if usages.iter().any(|usage| !usage.ident.span.eq_ctxt(span)) {
             return;
         }
@@ -216,6 +235,7 @@ fn could_use_elision<'tcx>(
     body: Option<BodyId>,
     trait_sig: Option<&[Ident]>,
     named_generics: &'tcx [GenericParam<'_>],
+    msrv: &Msrv,
 ) -> Option<(Vec<LocalDefId>, Vec<Lifetime>)> {
     // There are two scenarios where elision works:
     // * no output references, all input references have different LT
@@ -249,17 +269,17 @@ fn could_use_elision<'tcx>(
     let input_lts = input_visitor.lts;
     let output_lts = output_visitor.lts;
 
-    if let Some(trait_sig) = trait_sig {
-        if explicit_self_type(cx, func, trait_sig.first().copied()) {
-            return None;
-        }
+    if let Some(trait_sig) = trait_sig
+        && non_elidable_self_type(cx, func, trait_sig.first().copied(), msrv)
+    {
+        return None;
     }
 
     if let Some(body_id) = body {
         let body = cx.tcx.hir().body(body_id);
 
         let first_ident = body.params.first().and_then(|param| param.pat.simple_ident());
-        if explicit_self_type(cx, func, first_ident) {
+        if non_elidable_self_type(cx, func, first_ident, msrv) {
             return None;
         }
 
@@ -332,9 +352,15 @@ fn allowed_lts_from(named_generics: &[GenericParam<'_>]) -> FxIndexSet<LocalDefI
         .collect()
 }
 
-// elision doesn't work for explicit self types, see rust-lang/rust#69064
-fn explicit_self_type<'tcx>(cx: &LateContext<'tcx>, func: &FnDecl<'tcx>, ident: Option<Ident>) -> bool {
-    if let Some(ident) = ident
+// elision doesn't work for explicit self types before Rust 1.81, see rust-lang/rust#69064
+fn non_elidable_self_type<'tcx>(
+    cx: &LateContext<'tcx>,
+    func: &FnDecl<'tcx>,
+    ident: Option<Ident>,
+    msrv: &Msrv,
+) -> bool {
+    if !msrv.meets(msrvs::EXPLICIT_SELF_TYPE_ELISION)
+        && let Some(ident) = ident
         && ident.name == kw::SelfLower
         && !func.implicit_self.has_implicit_self()
         && let Some(self_ty) = func.inputs.first()
@@ -488,11 +514,13 @@ fn has_where_lifetimes<'tcx>(cx: &LateContext<'tcx>, generics: &'tcx Generics<'_
     false
 }
 
+#[allow(clippy::struct_excessive_bools)]
 struct Usage {
     lifetime: Lifetime,
     in_where_predicate: bool,
     in_bounded_ty: bool,
     in_generics_arg: bool,
+    lifetime_elision_impossible: bool,
 }
 
 struct LifetimeChecker<'cx, 'tcx, F> {
@@ -501,6 +529,7 @@ struct LifetimeChecker<'cx, 'tcx, F> {
     where_predicate_depth: usize,
     bounded_ty_depth: usize,
     generic_args_depth: usize,
+    lifetime_elision_impossible: bool,
     phantom: std::marker::PhantomData<F>,
 }
 
@@ -525,6 +554,7 @@ where
             where_predicate_depth: 0,
             bounded_ty_depth: 0,
             generic_args_depth: 0,
+            lifetime_elision_impossible: false,
             phantom: std::marker::PhantomData,
         }
     }
@@ -566,6 +596,7 @@ where
                 in_where_predicate: self.where_predicate_depth != 0,
                 in_bounded_ty: self.bounded_ty_depth != 0,
                 in_generics_arg: self.generic_args_depth != 0,
+                lifetime_elision_impossible: self.lifetime_elision_impossible,
             });
         }
     }
@@ -592,11 +623,44 @@ where
         self.generic_args_depth -= 1;
     }
 
+    fn visit_fn_decl(&mut self, fd: &'tcx FnDecl<'tcx>) -> Self::Result {
+        self.lifetime_elision_impossible = !is_candidate_for_elision(fd);
+        walk_fn_decl(self, fd);
+        self.lifetime_elision_impossible = false;
+    }
+
     fn nested_visit_map(&mut self) -> Self::Map {
         self.cx.tcx.hir()
     }
 }
 
+/// Check if `fd` supports function elision with an anonymous (or elided) lifetime,
+/// and has a lifetime somewhere in its output type.
+fn is_candidate_for_elision(fd: &FnDecl<'_>) -> bool {
+    struct V;
+
+    impl Visitor<'_> for V {
+        type Result = ControlFlow<bool>;
+
+        fn visit_lifetime(&mut self, lifetime: &Lifetime) -> Self::Result {
+            ControlFlow::Break(lifetime.is_elided() || lifetime.is_anonymous())
+        }
+    }
+
+    if fd.lifetime_elision_allowed
+        && let Return(ret_ty) = fd.output
+        && walk_unambig_ty(&mut V, ret_ty).is_break()
+    {
+        // The first encountered input lifetime will either be one on `self`, or will be the only lifetime.
+        fd.inputs
+            .iter()
+            .find_map(|ty| walk_unambig_ty(&mut V, ty).break_value())
+            .unwrap()
+    } else {
+        false
+    }
+}
+
 fn report_extra_lifetimes<'tcx>(cx: &LateContext<'tcx>, func: &'tcx FnDecl<'_>, generics: &'tcx Generics<'_>) {
     let mut checker = LifetimeChecker::<hir_nested_filter::None>::new(cx, generics);
 
@@ -662,6 +726,7 @@ fn report_elidable_impl_lifetimes<'tcx>(
                 Usage {
                     lifetime,
                     in_where_predicate: false,
+                    lifetime_elision_impossible: false,
                     ..
                 },
             ] = usages.as_slice()
@@ -719,7 +784,7 @@ fn report_elidable_lifetimes(
         |diag| {
             if !include_suggestions {
                 return;
-            };
+            }
 
             if let Some(suggestions) = elision_suggestions(cx, generics, elidable_lts, usages) {
                 diag.multipart_suggestion("elide the lifetimes", suggestions, Applicability::MachineApplicable);
diff --git a/clippy_lints/src/literal_representation.rs b/clippy_lints/src/literal_representation.rs
index e2dcb20f906..a4cedf3bed3 100644
--- a/clippy_lints/src/literal_representation.rs
+++ b/clippy_lints/src/literal_representation.rs
@@ -251,7 +251,7 @@ impl LiteralDigitGrouping {
                     );
                     if !consistent {
                         return Err(WarningType::InconsistentDigitGrouping);
-                    };
+                    }
                 }
 
                 Ok(())
diff --git a/clippy_lints/src/literal_string_with_formatting_args.rs b/clippy_lints/src/literal_string_with_formatting_args.rs
index 49353a1b76b..a957c0e22a2 100644
--- a/clippy_lints/src/literal_string_with_formatting_args.rs
+++ b/clippy_lints/src/literal_string_with_formatting_args.rs
@@ -29,9 +29,9 @@ declare_clippy_lint! {
     /// let y = "hello";
     /// x.expect(&format!("{y:?}"));
     /// ```
-    #[clippy::version = "1.83.0"]
+    #[clippy::version = "1.85.0"]
     pub LITERAL_STRING_WITH_FORMATTING_ARGS,
-    suspicious,
+    nursery,
     "Checks if string literals have formatting arguments"
 }
 
diff --git a/clippy_lints/src/loops/mod.rs b/clippy_lints/src/loops/mod.rs
index f3ca4a4a571..c5e75af2303 100644
--- a/clippy_lints/src/loops/mod.rs
+++ b/clippy_lints/src/loops/mod.rs
@@ -830,7 +830,7 @@ impl Loops {
         for_kv_map::check(cx, pat, arg, body);
         mut_range_bound::check(cx, arg, body);
         single_element_loop::check(cx, pat, arg, body, expr);
-        same_item_push::check(cx, pat, arg, body, expr);
+        same_item_push::check(cx, pat, arg, body, expr, &self.msrv);
         manual_flatten::check(cx, pat, arg, body, span);
         manual_find::check(cx, pat, arg, body, span, expr);
         unused_enumerate_index::check(cx, pat, arg, body);
diff --git a/clippy_lints/src/loops/same_item_push.rs b/clippy_lints/src/loops/same_item_push.rs
index 951ebc9caef..c27e930c99a 100644
--- a/clippy_lints/src/loops/same_item_push.rs
+++ b/clippy_lints/src/loops/same_item_push.rs
@@ -1,8 +1,9 @@
 use super::SAME_ITEM_PUSH;
-use clippy_utils::diagnostics::span_lint_and_help;
-use clippy_utils::path_to_local;
+use clippy_utils::diagnostics::span_lint_and_then;
+use clippy_utils::msrvs::Msrv;
 use clippy_utils::source::snippet_with_context;
 use clippy_utils::ty::{implements_trait, is_type_diagnostic_item};
+use clippy_utils::{msrvs, path_to_local, std_or_core};
 use rustc_data_structures::fx::FxHashSet;
 use rustc_errors::Applicability;
 use rustc_hir::def::{DefKind, Res};
@@ -19,19 +20,30 @@ pub(super) fn check<'tcx>(
     _: &'tcx Expr<'_>,
     body: &'tcx Expr<'_>,
     _: &'tcx Expr<'_>,
+    msrv: &Msrv,
 ) {
-    fn emit_lint(cx: &LateContext<'_>, vec: &Expr<'_>, pushed_item: &Expr<'_>, ctxt: SyntaxContext) {
+    fn emit_lint(cx: &LateContext<'_>, vec: &Expr<'_>, pushed_item: &Expr<'_>, ctxt: SyntaxContext, msrv: &Msrv) {
         let mut app = Applicability::Unspecified;
         let vec_str = snippet_with_context(cx, vec.span, ctxt, "", &mut app).0;
         let item_str = snippet_with_context(cx, pushed_item.span, ctxt, "", &mut app).0;
 
-        span_lint_and_help(
+        let secondary_help = if msrv.meets(msrvs::REPEAT_N)
+            && let Some(std_or_core) = std_or_core(cx)
+        {
+            format!("or `{vec_str}.extend({std_or_core}::iter::repeat_n({item_str}, SIZE))`")
+        } else {
+            format!("or `{vec_str}.resize(NEW_SIZE, {item_str})`")
+        };
+
+        span_lint_and_then(
             cx,
             SAME_ITEM_PUSH,
             vec.span,
-            "it looks like the same item is being pushed into this Vec",
-            None,
-            format!("consider using vec![{item_str};SIZE] or {vec_str}.resize(NEW_SIZE, {item_str})"),
+            "it looks like the same item is being pushed into this `Vec`",
+            |diag| {
+                diag.help(format!("consider using `vec![{item_str};SIZE]`"))
+                    .help(secondary_help);
+            },
         );
     }
 
@@ -67,11 +79,11 @@ pub(super) fn check<'tcx>(
                         {
                             match init.kind {
                                 // immutable bindings that are initialized with literal
-                                ExprKind::Lit(..) => emit_lint(cx, vec, pushed_item, ctxt),
+                                ExprKind::Lit(..) => emit_lint(cx, vec, pushed_item, ctxt, msrv),
                                 // immutable bindings that are initialized with constant
                                 ExprKind::Path(ref path) => {
                                     if let Res::Def(DefKind::Const, ..) = cx.qpath_res(path, init.hir_id) {
-                                        emit_lint(cx, vec, pushed_item, ctxt);
+                                        emit_lint(cx, vec, pushed_item, ctxt, msrv);
                                     }
                                 },
                                 _ => {},
@@ -79,11 +91,11 @@ pub(super) fn check<'tcx>(
                         }
                     },
                     // constant
-                    Res::Def(DefKind::Const, ..) => emit_lint(cx, vec, pushed_item, ctxt),
+                    Res::Def(DefKind::Const, ..) => emit_lint(cx, vec, pushed_item, ctxt, msrv),
                     _ => {},
                 }
             },
-            ExprKind::Lit(..) => emit_lint(cx, vec, pushed_item, ctxt),
+            ExprKind::Lit(..) => emit_lint(cx, vec, pushed_item, ctxt, msrv),
             _ => {},
         }
     }
diff --git a/clippy_lints/src/manual_bits.rs b/clippy_lints/src/manual_bits.rs
index d2a2321dae8..17e25635ce1 100644
--- a/clippy_lints/src/manual_bits.rs
+++ b/clippy_lints/src/manual_bits.rs
@@ -6,7 +6,7 @@ use clippy_utils::source::snippet_with_context;
 use rustc_ast::ast::LitKind;
 use rustc_data_structures::packed::Pu128;
 use rustc_errors::Applicability;
-use rustc_hir::{BinOpKind, Expr, ExprKind, QPath};
+use rustc_hir::{BinOpKind, Expr, ExprKind, GenericArg, QPath};
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::ty::{self, Ty};
 use rustc_session::impl_lint_pass;
@@ -99,7 +99,7 @@ fn get_size_of_ty<'tcx>(cx: &LateContext<'tcx>, expr: &'tcx Expr<'_>) -> Option<
         && let QPath::Resolved(_, count_func_path) = count_func_qpath
         && let Some(segment_zero) = count_func_path.segments.first()
         && let Some(args) = segment_zero.args
-        && let Some(real_ty_span) = args.args.first().map(|arg| arg.span())
+        && let Some(real_ty_span) = args.args.first().map(GenericArg::span)
         && let Some(def_id) = cx.qpath_res(count_func_qpath, count_func.hir_id).opt_def_id()
         && cx.tcx.is_diagnostic_item(sym::mem_size_of, def_id)
     {
diff --git a/clippy_lints/src/manual_div_ceil.rs b/clippy_lints/src/manual_div_ceil.rs
index aa59b047b16..816ca17b3d2 100644
--- a/clippy_lints/src/manual_div_ceil.rs
+++ b/clippy_lints/src/manual_div_ceil.rs
@@ -102,12 +102,48 @@ impl<'tcx> LateLintPass<'tcx> for ManualDivCeil {
             {
                 build_suggestion(cx, expr, add_lhs, div_rhs, &mut applicability);
             }
+
+            // (x + (Y - 1)) / Y
+            if inner_op.node == BinOpKind::Add && differ_by_one(inner_rhs, div_rhs) {
+                build_suggestion(cx, expr, inner_lhs, div_rhs, &mut applicability);
+            }
+
+            // ((Y - 1) + x) / Y
+            if inner_op.node == BinOpKind::Add && differ_by_one(inner_lhs, div_rhs) {
+                build_suggestion(cx, expr, inner_rhs, div_rhs, &mut applicability);
+            }
+
+            // (x - (-Y - 1)) / Y
+            if inner_op.node == BinOpKind::Sub
+                && let ExprKind::Unary(UnOp::Neg, abs_div_rhs) = div_rhs.kind
+                && differ_by_one(abs_div_rhs, inner_rhs)
+            {
+                build_suggestion(cx, expr, inner_lhs, div_rhs, &mut applicability);
+            }
         }
     }
 
     extract_msrv_attr!(LateContext);
 }
 
+/// Checks if two expressions represent non-zero integer literals such that `small_expr + 1 ==
+/// large_expr`.
+fn differ_by_one(small_expr: &Expr<'_>, large_expr: &Expr<'_>) -> bool {
+    if let ExprKind::Lit(small) = small_expr.kind
+        && let ExprKind::Lit(large) = large_expr.kind
+        && let LitKind::Int(s, _) = small.node
+        && let LitKind::Int(l, _) = large.node
+    {
+        Some(l.get()) == s.get().checked_add(1)
+    } else if let ExprKind::Unary(UnOp::Neg, small_inner_expr) = small_expr.kind
+        && let ExprKind::Unary(UnOp::Neg, large_inner_expr) = large_expr.kind
+    {
+        differ_by_one(large_inner_expr, small_inner_expr)
+    } else {
+        false
+    }
+}
+
 fn check_int_ty_and_feature(cx: &LateContext<'_>, expr: &Expr<'_>) -> bool {
     let expr_ty = cx.typeck_results().expr_ty(expr);
     match expr_ty.peel_refs().kind() {
diff --git a/clippy_lints/src/manual_is_ascii_check.rs b/clippy_lints/src/manual_is_ascii_check.rs
index 9860deba843..38106277a88 100644
--- a/clippy_lints/src/manual_is_ascii_check.rs
+++ b/clippy_lints/src/manual_is_ascii_check.rs
@@ -7,7 +7,7 @@ use clippy_utils::{higher, is_in_const_context, path_to_local, peel_ref_operator
 use rustc_ast::LitKind::{Byte, Char};
 use rustc_ast::ast::RangeLimits;
 use rustc_errors::Applicability;
-use rustc_hir::{Expr, ExprKind, Node, Param, PatKind, RangeEnd, PatExpr, PatExprKind, Lit};
+use rustc_hir::{Expr, ExprKind, Lit, Node, Param, PatExpr, PatExprKind, PatKind, RangeEnd};
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::ty::{self, Ty};
 use rustc_session::impl_lint_pass;
@@ -202,8 +202,14 @@ fn check_expr_range(start: &Expr<'_>, end: &Expr<'_>) -> CharRange {
 }
 
 fn check_range(start: &PatExpr<'_>, end: &PatExpr<'_>) -> CharRange {
-    if let PatExprKind::Lit{ lit: start_lit, negated: false } = &start.kind
-        && let PatExprKind::Lit{ lit: end_lit, negated: false  } = &end.kind
+    if let PatExprKind::Lit {
+        lit: start_lit,
+        negated: false,
+    } = &start.kind
+        && let PatExprKind::Lit {
+            lit: end_lit,
+            negated: false,
+        } = &end.kind
     {
         check_lit_range(start_lit, end_lit)
     } else {
diff --git a/clippy_lints/src/manual_let_else.rs b/clippy_lints/src/manual_let_else.rs
index a70955a7c78..8503dde3fb6 100644
--- a/clippy_lints/src/manual_let_else.rs
+++ b/clippy_lints/src/manual_let_else.rs
@@ -106,7 +106,7 @@ impl<'tcx> QuestionMark {
                     emit_manual_let_else(cx, stmt.span, match_expr, &ident_map, pat_arm.pat, diverging_arm.body);
                 },
             }
-        };
+        }
     }
 }
 
@@ -295,7 +295,7 @@ fn pat_allowed_for_else(cx: &LateContext<'_>, pat: &'_ Pat<'_>, check_types: boo
             PatKind::Struct(..) | PatKind::TupleStruct(..) | PatKind::Path(..)
         ) {
             return;
-        };
+        }
         let ty = typeck_results.pat_ty(pat);
         // Option and Result are allowed, everything else isn't.
         if !(is_type_diagnostic_item(cx, ty, sym::Option) || is_type_diagnostic_item(cx, ty, sym::Result)) {
diff --git a/clippy_lints/src/manual_rem_euclid.rs b/clippy_lints/src/manual_rem_euclid.rs
index ebfd946b07e..8aeec89f0bf 100644
--- a/clippy_lints/src/manual_rem_euclid.rs
+++ b/clippy_lints/src/manual_rem_euclid.rs
@@ -85,7 +85,7 @@ impl<'tcx> LateLintPass<'tcx> for ManualRemEuclid {
                     }
                 },
                 _ => return,
-            };
+            }
 
             let mut app = Applicability::MachineApplicable;
             let rem_of = snippet_with_context(cx, rem2_lhs.span, ctxt, "_", &mut app).0;
diff --git a/clippy_lints/src/manual_strip.rs b/clippy_lints/src/manual_strip.rs
index 79de41db343..d69384a2cb7 100644
--- a/clippy_lints/src/manual_strip.rs
+++ b/clippy_lints/src/manual_strip.rs
@@ -86,7 +86,7 @@ impl<'tcx> LateLintPass<'tcx> for ManualStrip {
             let target_res = cx.qpath_res(target_path, target_arg.hir_id);
             if target_res == Res::Err {
                 return;
-            };
+            }
 
             if let Res::Local(hir_id) = target_res
                 && let Some(used_mutably) = mutated_variables(then, cx)
diff --git a/clippy_lints/src/matches/manual_filter.rs b/clippy_lints/src/matches/manual_filter.rs
index cfa054706d6..4cc43e427ec 100644
--- a/clippy_lints/src/matches/manual_filter.rs
+++ b/clippy_lints/src/matches/manual_filter.rs
@@ -34,7 +34,7 @@ fn get_cond_expr<'tcx>(
             needs_negated: is_none_expr(cx, then_expr), /* if the `then_expr` resolves to `None`, need to negate the
                                                          * cond */
         });
-    };
+    }
     None
 }
 
@@ -45,7 +45,7 @@ fn peels_blocks_incl_unsafe_opt<'a>(expr: &'a Expr<'a>) -> Option<&'a Expr<'a>>
         if block.stmts.is_empty() {
             return block.expr;
         }
-    };
+    }
     None
 }
 
@@ -68,14 +68,14 @@ fn is_some_expr(cx: &LateContext<'_>, target: HirId, ctxt: SyntaxContext, expr:
                 && is_res_lang_ctor(cx, path_res(cx, callee), OptionSome)
                 && path_to_local_id(arg, target);
         }
-    };
+    }
     false
 }
 
 fn is_none_expr(cx: &LateContext<'_>, expr: &Expr<'_>) -> bool {
     if let Some(inner_expr) = peels_blocks_incl_unsafe_opt(expr) {
         return is_res_lang_ctor(cx, path_res(cx, inner_expr), OptionNone);
-    };
+    }
     false
 }
 
diff --git a/clippy_lints/src/matches/manual_ok_err.rs b/clippy_lints/src/matches/manual_ok_err.rs
new file mode 100644
index 00000000000..b1a555b91d1
--- /dev/null
+++ b/clippy_lints/src/matches/manual_ok_err.rs
@@ -0,0 +1,135 @@
+use clippy_utils::diagnostics::span_lint_and_sugg;
+use clippy_utils::sugg::Sugg;
+use clippy_utils::ty::option_arg_ty;
+use clippy_utils::{is_res_lang_ctor, path_res, peel_blocks, span_contains_comment};
+use rustc_ast::BindingMode;
+use rustc_errors::Applicability;
+use rustc_hir::LangItem::{OptionNone, OptionSome, ResultErr};
+use rustc_hir::def::{DefKind, Res};
+use rustc_hir::{Arm, Expr, ExprKind, Pat, PatKind, Path, QPath};
+use rustc_lint::{LateContext, LintContext};
+use rustc_middle::ty::Ty;
+use rustc_span::symbol::Ident;
+
+use super::MANUAL_OK_ERR;
+
+pub(crate) fn check_if_let(
+    cx: &LateContext<'_>,
+    expr: &Expr<'_>,
+    let_pat: &Pat<'_>,
+    let_expr: &Expr<'_>,
+    if_then: &Expr<'_>,
+    else_expr: &Expr<'_>,
+) {
+    if let Some(inner_expr_ty) = option_arg_ty(cx, cx.typeck_results().expr_ty(expr))
+        && let Some((is_ok, ident)) = is_ok_or_err(cx, let_pat)
+        && is_some_ident(cx, if_then, ident, inner_expr_ty)
+        && is_none(cx, else_expr)
+    {
+        apply_lint(cx, expr, let_expr, is_ok);
+    }
+}
+
+pub(crate) fn check_match(cx: &LateContext<'_>, expr: &Expr<'_>, scrutinee: &Expr<'_>, arms: &[Arm<'_>]) {
+    if let Some(inner_expr_ty) = option_arg_ty(cx, cx.typeck_results().expr_ty(expr))
+        && arms.len() == 2
+        && arms.iter().all(|arm| arm.guard.is_none())
+        && let Some((idx, is_ok)) = arms.iter().enumerate().find_map(|(arm_idx, arm)| {
+            // Check if the arm is a `Ok(x) => x` or `Err(x) => x` alternative.
+            // In this case, return its index and whether it uses `Ok` or `Err`.
+             if let Some((is_ok, ident)) = is_ok_or_err(cx, arm.pat)
+                && is_some_ident(cx, arm.body, ident, inner_expr_ty)
+            {
+                Some((arm_idx, is_ok))
+            } else {
+                None
+            }
+        })
+        // Accept wildcard only as the second arm
+        && is_variant_or_wildcard(cx, arms[1-idx].pat, idx == 0, is_ok)
+        // Check that the body of the non `Ok`/`Err` arm is `None`
+        && is_none(cx, arms[1 - idx].body)
+    {
+        apply_lint(cx, expr, scrutinee, is_ok);
+    }
+}
+
+/// Check that `pat` applied to a `Result` only matches `Ok(_)`, `Err(_)`, not a subset or a
+/// superset of it. If `can_be_wild` is `true`, wildcards are also accepted. In the case of
+/// a non-wildcard, `must_match_err` indicates whether the `Err` or the `Ok` variant should be
+/// accepted.
+fn is_variant_or_wildcard(cx: &LateContext<'_>, pat: &Pat<'_>, can_be_wild: bool, must_match_err: bool) -> bool {
+    match pat.kind {
+        PatKind::Wild | PatKind::Path(..) | PatKind::Binding(_, _, _, None) if can_be_wild => true,
+        PatKind::TupleStruct(qpath, ..) => {
+            is_res_lang_ctor(cx, cx.qpath_res(&qpath, pat.hir_id), ResultErr) == must_match_err
+        },
+        PatKind::Binding(_, _, _, Some(pat)) | PatKind::Ref(pat, _) => {
+            is_variant_or_wildcard(cx, pat, can_be_wild, must_match_err)
+        },
+        _ => false,
+    }
+}
+
+/// Return `Some((true, IDENT))` if `pat` contains `Ok(IDENT)`, `Some((false, IDENT))` if it
+/// contains `Err(IDENT)`, `None` otherwise.
+fn is_ok_or_err<'hir>(cx: &LateContext<'_>, pat: &Pat<'hir>) -> Option<(bool, &'hir Ident)> {
+    if let PatKind::TupleStruct(qpath, [arg], _) = &pat.kind
+        && let PatKind::Binding(BindingMode::NONE, _, ident, _) = &arg.kind
+        && let res = cx.qpath_res(qpath, pat.hir_id)
+        && let Res::Def(DefKind::Ctor(..), id) = res
+        && let id @ Some(_) = cx.tcx.opt_parent(id)
+    {
+        let lang_items = cx.tcx.lang_items();
+        if id == lang_items.result_ok_variant() {
+            return Some((true, ident));
+        } else if id == lang_items.result_err_variant() {
+            return Some((false, ident));
+        }
+    }
+    None
+}
+
+/// Check if `expr` contains `Some(ident)`, possibly as a block
+fn is_some_ident<'tcx>(cx: &LateContext<'tcx>, expr: &Expr<'_>, ident: &Ident, ty: Ty<'tcx>) -> bool {
+    if let ExprKind::Call(body_callee, [body_arg]) = peel_blocks(expr).kind
+        && is_res_lang_ctor(cx, path_res(cx, body_callee), OptionSome)
+        && cx.typeck_results().expr_ty(body_arg) == ty
+        && let ExprKind::Path(QPath::Resolved(
+            _,
+            Path {
+                segments: [segment], ..
+            },
+        )) = body_arg.kind
+    {
+        segment.ident.name == ident.name
+    } else {
+        false
+    }
+}
+
+/// Check if `expr` is `None`, possibly as a block
+fn is_none(cx: &LateContext<'_>, expr: &Expr<'_>) -> bool {
+    is_res_lang_ctor(cx, path_res(cx, peel_blocks(expr)), OptionNone)
+}
+
+/// Suggest replacing `expr` by `scrutinee.METHOD()`, where `METHOD` is either `ok` or
+/// `err`, depending on `is_ok`.
+fn apply_lint(cx: &LateContext<'_>, expr: &Expr<'_>, scrutinee: &Expr<'_>, is_ok: bool) {
+    let method = if is_ok { "ok" } else { "err" };
+    let mut app = if span_contains_comment(cx.sess().source_map(), expr.span) {
+        Applicability::MaybeIncorrect
+    } else {
+        Applicability::MachineApplicable
+    };
+    let scrut = Sugg::hir_with_applicability(cx, scrutinee, "..", &mut app).maybe_par();
+    span_lint_and_sugg(
+        cx,
+        MANUAL_OK_ERR,
+        expr.span,
+        format!("manual implementation of `{method}`"),
+        "replace with",
+        format!("{scrut}.{method}()"),
+        app,
+    );
+}
diff --git a/clippy_lints/src/matches/manual_utils.rs b/clippy_lints/src/matches/manual_utils.rs
index bac5cf88cfb..0b57740064c 100644
--- a/clippy_lints/src/matches/manual_utils.rs
+++ b/clippy_lints/src/matches/manual_utils.rs
@@ -109,7 +109,7 @@ where
             }
         },
         None => return None,
-    };
+    }
 
     let mut app = Applicability::MachineApplicable;
 
diff --git a/clippy_lints/src/matches/match_bool.rs b/clippy_lints/src/matches/match_bool.rs
index 7e43d222a66..b90cf6357c5 100644
--- a/clippy_lints/src/matches/match_bool.rs
+++ b/clippy_lints/src/matches/match_bool.rs
@@ -1,6 +1,6 @@
 use clippy_utils::diagnostics::span_lint_and_then;
 use clippy_utils::is_unit_expr;
-use clippy_utils::source::{expr_block, snippet};
+use clippy_utils::source::expr_block;
 use clippy_utils::sugg::Sugg;
 use rustc_ast::LitKind;
 use rustc_errors::Applicability;
@@ -17,17 +17,28 @@ pub(crate) fn check(cx: &LateContext<'_>, scrutinee: &Expr<'_>, arms: &[Arm<'_>]
             cx,
             MATCH_BOOL,
             expr.span,
-            "you seem to be trying to match on a boolean expression",
+            "`match` on a boolean expression",
             move |diag| {
                 if arms.len() == 2 {
-                    // no guards
-                    let exprs = if let PatKind::Expr(arm_bool) = arms[0].pat.kind {
+                    let mut app = Applicability::MachineApplicable;
+                    let test_sugg = if let PatKind::Expr(arm_bool) = arms[0].pat.kind {
+                        let test = Sugg::hir_with_applicability(cx, scrutinee, "_", &mut app);
                         if let PatExprKind::Lit { lit, .. } = arm_bool.kind {
-                            match lit.node {
-                                LitKind::Bool(true) => Some((arms[0].body, arms[1].body)),
-                                LitKind::Bool(false) => Some((arms[1].body, arms[0].body)),
+                            match &lit.node {
+                                LitKind::Bool(true) => Some(test),
+                                LitKind::Bool(false) => Some(!test),
                                 _ => None,
                             }
+                            .map(|test| {
+                                if let Some(guard) = &arms[0]
+                                    .guard
+                                    .map(|g| Sugg::hir_with_applicability(cx, g, "_", &mut app))
+                                {
+                                    test.and(guard)
+                                } else {
+                                    test
+                                }
+                            })
                         } else {
                             None
                         }
@@ -35,39 +46,31 @@ pub(crate) fn check(cx: &LateContext<'_>, scrutinee: &Expr<'_>, arms: &[Arm<'_>]
                         None
                     };
 
-                    if let Some((true_expr, false_expr)) = exprs {
-                        let mut app = Applicability::HasPlaceholders;
+                    if let Some(test_sugg) = test_sugg {
                         let ctxt = expr.span.ctxt();
+                        let (true_expr, false_expr) = (arms[0].body, arms[1].body);
                         let sugg = match (is_unit_expr(true_expr), is_unit_expr(false_expr)) {
                             (false, false) => Some(format!(
                                 "if {} {} else {}",
-                                snippet(cx, scrutinee.span, "b"),
+                                test_sugg,
                                 expr_block(cx, true_expr, ctxt, "..", Some(expr.span), &mut app),
                                 expr_block(cx, false_expr, ctxt, "..", Some(expr.span), &mut app)
                             )),
                             (false, true) => Some(format!(
                                 "if {} {}",
-                                snippet(cx, scrutinee.span, "b"),
+                                test_sugg,
                                 expr_block(cx, true_expr, ctxt, "..", Some(expr.span), &mut app)
                             )),
-                            (true, false) => {
-                                let test = Sugg::hir(cx, scrutinee, "..");
-                                Some(format!(
-                                    "if {} {}",
-                                    !test,
-                                    expr_block(cx, false_expr, ctxt, "..", Some(expr.span), &mut app)
-                                ))
-                            },
+                            (true, false) => Some(format!(
+                                "if {} {}",
+                                !test_sugg,
+                                expr_block(cx, false_expr, ctxt, "..", Some(expr.span), &mut app)
+                            )),
                             (true, true) => None,
                         };
 
                         if let Some(sugg) = sugg {
-                            diag.span_suggestion(
-                                expr.span,
-                                "consider using an `if`/`else` expression",
-                                sugg,
-                                Applicability::HasPlaceholders,
-                            );
+                            diag.span_suggestion(expr.span, "consider using an `if`/`else` expression", sugg, app);
                         }
                     }
                 }
diff --git a/clippy_lints/src/matches/match_like_matches.rs b/clippy_lints/src/matches/match_like_matches.rs
index 223d0dc7656..d697f427c70 100644
--- a/clippy_lints/src/matches/match_like_matches.rs
+++ b/clippy_lints/src/matches/match_like_matches.rs
@@ -117,7 +117,7 @@ where
             if let ty::Ref(..) = cx.typeck_results().expr_ty(ex_inner).kind() {
                 ex_new = ex_inner;
             }
-        };
+        }
         span_lint_and_sugg(
             cx,
             MATCH_LIKE_MATCHES_MACRO,
diff --git a/clippy_lints/src/matches/match_str_case_mismatch.rs b/clippy_lints/src/matches/match_str_case_mismatch.rs
index 9f5b7c855a1..df1b83cbb51 100644
--- a/clippy_lints/src/matches/match_str_case_mismatch.rs
+++ b/clippy_lints/src/matches/match_str_case_mismatch.rs
@@ -5,7 +5,7 @@ use clippy_utils::ty::is_type_lang_item;
 use rustc_ast::ast::LitKind;
 use rustc_errors::Applicability;
 use rustc_hir::intravisit::{Visitor, walk_expr};
-use rustc_hir::{Arm, Expr, ExprKind, PatExpr, PatExprKind, LangItem, PatKind};
+use rustc_hir::{Arm, Expr, ExprKind, LangItem, PatExpr, PatExprKind, PatKind};
 use rustc_lint::LateContext;
 use rustc_middle::ty;
 use rustc_span::Span;
diff --git a/clippy_lints/src/matches/match_wild_enum.rs b/clippy_lints/src/matches/match_wild_enum.rs
index 91e40e4275c..59565560089 100644
--- a/clippy_lints/src/matches/match_wild_enum.rs
+++ b/clippy_lints/src/matches/match_wild_enum.rs
@@ -170,7 +170,7 @@ pub(crate) fn check(cx: &LateContext<'_>, ex: &Expr<'_>, arms: &[Arm<'_>]) {
                 );
             });
         },
-    };
+    }
 }
 
 enum CommonPrefixSearcher<'a> {
diff --git a/clippy_lints/src/matches/mod.rs b/clippy_lints/src/matches/mod.rs
index ac1eae07eff..a7fdd483c16 100644
--- a/clippy_lints/src/matches/mod.rs
+++ b/clippy_lints/src/matches/mod.rs
@@ -2,6 +2,7 @@ mod collapsible_match;
 mod infallible_destructuring_match;
 mod manual_filter;
 mod manual_map;
+mod manual_ok_err;
 mod manual_unwrap_or;
 mod manual_utils;
 mod match_as_ref;
@@ -972,6 +973,40 @@ declare_clippy_lint! {
     "checks for unnecessary guards in match expressions"
 }
 
+declare_clippy_lint! {
+    /// ### What it does
+    /// Checks for manual implementation of `.ok()` or `.err()`
+    /// on `Result` values.
+    ///
+    /// ### Why is this bad?
+    /// Using `.ok()` or `.err()` rather than a `match` or
+    /// `if let` is less complex and more readable.
+    ///
+    /// ### Example
+    /// ```no_run
+    /// # fn func() -> Result<u32, &'static str> { Ok(0) }
+    /// let a = match func() {
+    ///     Ok(v) => Some(v),
+    ///     Err(_) => None,
+    /// };
+    /// let b = if let Err(v) = func() {
+    ///     Some(v)
+    /// } else {
+    ///     None
+    /// };
+    /// ```
+    /// Use instead:
+    /// ```no_run
+    /// # fn func() -> Result<u32, &'static str> { Ok(0) }
+    /// let a = func().ok();
+    /// let b = func().err();
+    /// ```
+    #[clippy::version = "1.86.0"]
+    pub MANUAL_OK_ERR,
+    complexity,
+    "find manual implementations of `.ok()` or `.err()` on `Result`"
+}
+
 pub struct Matches {
     msrv: Msrv,
     infallible_destructuring_match_linted: bool,
@@ -1013,6 +1048,7 @@ impl_lint_pass!(Matches => [
     MANUAL_MAP,
     MANUAL_FILTER,
     REDUNDANT_GUARDS,
+    MANUAL_OK_ERR,
 ]);
 
 impl<'tcx> LateLintPass<'tcx> for Matches {
@@ -1091,6 +1127,7 @@ impl<'tcx> LateLintPass<'tcx> for Matches {
                         manual_unwrap_or::check_match(cx, expr, ex, arms);
                         manual_map::check_match(cx, expr, ex, arms);
                         manual_filter::check_match(cx, ex, arms, expr);
+                        manual_ok_err::check_match(cx, expr, ex, arms);
                     }
 
                     if self.infallible_destructuring_match_linted {
@@ -1134,6 +1171,14 @@ impl<'tcx> LateLintPass<'tcx> for Matches {
                             if_let.if_then,
                             else_expr,
                         );
+                        manual_ok_err::check_if_let(
+                            cx,
+                            expr,
+                            if_let.let_pat,
+                            if_let.let_expr,
+                            if_let.if_then,
+                            else_expr,
+                        );
                     }
                 }
                 redundant_pattern_match::check_if_let(
diff --git a/clippy_lints/src/matches/significant_drop_in_scrutinee.rs b/clippy_lints/src/matches/significant_drop_in_scrutinee.rs
index 2ce6a8a85a5..35f2e780d2e 100644
--- a/clippy_lints/src/matches/significant_drop_in_scrutinee.rs
+++ b/clippy_lints/src/matches/significant_drop_in_scrutinee.rs
@@ -2,7 +2,7 @@ use std::ops::ControlFlow;
 
 use crate::FxHashSet;
 use clippy_utils::diagnostics::span_lint_and_then;
-use clippy_utils::source::{indent_of, snippet};
+use clippy_utils::source::{first_line_of_span, indent_of, snippet};
 use clippy_utils::ty::{for_each_top_level_late_bound_region, is_copy};
 use clippy_utils::{get_attr, is_lint_allowed};
 use itertools::Itertools;
@@ -152,7 +152,7 @@ fn set_suggestion<'tcx>(diag: &mut Diag<'_, ()>, cx: &LateContext<'tcx>, expr: &
     diag.multipart_suggestion(
         suggestion_message,
         vec![
-            (expr.span.shrink_to_lo(), replacement),
+            (first_line_of_span(cx, expr.span).shrink_to_lo(), replacement),
             (found.found_span, scrutinee_replacement),
         ],
         Applicability::MaybeIncorrect,
@@ -441,8 +441,9 @@ impl<'tcx> Visitor<'tcx> for SigDropHelper<'_, 'tcx> {
         let parent_expr_before = self.parent_expr.replace(ex);
 
         match ex.kind {
-            // Skip blocks because values in blocks will be dropped as usual.
-            ExprKind::Block(..) => (),
+            // Skip blocks because values in blocks will be dropped as usual, and await
+            // desugaring because temporary insides the future will have been dropped.
+            ExprKind::Block(..) | ExprKind::Match(_, _, MatchSource::AwaitDesugar) => (),
             _ => walk_expr(self, ex),
         }
 
diff --git a/clippy_lints/src/matches/try_err.rs b/clippy_lints/src/matches/try_err.rs
index 6c02207af49..ff7769af1df 100644
--- a/clippy_lints/src/matches/try_err.rs
+++ b/clippy_lints/src/matches/try_err.rs
@@ -46,7 +46,7 @@ pub(super) fn check<'tcx>(cx: &LateContext<'tcx>, expr: &'tcx Expr<'_>, scrutine
             err_ty = ty;
         } else {
             return;
-        };
+        }
 
         span_lint_and_then(
             cx,
diff --git a/clippy_lints/src/matches/wild_in_or_pats.rs b/clippy_lints/src/matches/wild_in_or_pats.rs
index 390ba889fd2..b75d1ab9a7a 100644
--- a/clippy_lints/src/matches/wild_in_or_pats.rs
+++ b/clippy_lints/src/matches/wild_in_or_pats.rs
@@ -13,7 +13,7 @@ pub(crate) fn check(cx: &LateContext<'_>, expr: &Expr<'_>, arms: &[Arm<'_>]) {
         && has_non_exhaustive_attr(cx.tcx, *adt_def)
     {
         return;
-    };
+    }
     for arm in arms {
         if let PatKind::Or(fields) = arm.pat.kind {
             // look for multiple fields in this arm that contains at least one Wild pattern
diff --git a/clippy_lints/src/methods/bytecount.rs b/clippy_lints/src/methods/bytecount.rs
index 4a2124c74a8..687272e550b 100644
--- a/clippy_lints/src/methods/bytecount.rs
+++ b/clippy_lints/src/methods/bytecount.rs
@@ -62,5 +62,5 @@ pub(super) fn check<'tcx>(
             ),
             applicability,
         );
-    };
+    }
 }
diff --git a/clippy_lints/src/methods/bytes_count_to_len.rs b/clippy_lints/src/methods/bytes_count_to_len.rs
index 34159f2d150..a9f6a41c235 100644
--- a/clippy_lints/src/methods/bytes_count_to_len.rs
+++ b/clippy_lints/src/methods/bytes_count_to_len.rs
@@ -32,5 +32,5 @@ pub(super) fn check<'tcx>(
             ),
             applicability,
         );
-    };
+    }
 }
diff --git a/clippy_lints/src/methods/bytes_nth.rs b/clippy_lints/src/methods/bytes_nth.rs
index a82abc79f2a..de22514c37c 100644
--- a/clippy_lints/src/methods/bytes_nth.rs
+++ b/clippy_lints/src/methods/bytes_nth.rs
@@ -46,5 +46,5 @@ pub(super) fn check<'tcx>(cx: &LateContext<'tcx>, expr: &Expr<'_>, recv: &'tcx E
             format!("{receiver}.as_bytes().get({n}).copied()"),
             applicability,
         );
-    };
+    }
 }
diff --git a/clippy_lints/src/methods/cloned_instead_of_copied.rs b/clippy_lints/src/methods/cloned_instead_of_copied.rs
index 2a0a9d3710d..223a960b800 100644
--- a/clippy_lints/src/methods/cloned_instead_of_copied.rs
+++ b/clippy_lints/src/methods/cloned_instead_of_copied.rs
@@ -32,7 +32,7 @@ pub fn check(cx: &LateContext<'_>, expr: &Expr<'_>, recv: &Expr<'_>, span: Span,
         // &T where T: Copy
         ty::Ref(_, ty, _) if is_copy(cx, *ty) => {},
         _ => return,
-    };
+    }
     span_lint_and_sugg(
         cx,
         CLONED_INSTEAD_OF_COPIED,
diff --git a/clippy_lints/src/methods/drain_collect.rs b/clippy_lints/src/methods/drain_collect.rs
index 10360b4817b..cbf713a3b17 100644
--- a/clippy_lints/src/methods/drain_collect.rs
+++ b/clippy_lints/src/methods/drain_collect.rs
@@ -1,8 +1,8 @@
 use crate::methods::DRAIN_COLLECT;
 use clippy_utils::diagnostics::span_lint_and_sugg;
-use clippy_utils::is_range_full;
 use clippy_utils::source::snippet;
 use clippy_utils::ty::is_type_lang_item;
+use clippy_utils::{is_range_full, std_or_core};
 use rustc_errors::Applicability;
 use rustc_hir::{Expr, ExprKind, LangItem, Path, QPath};
 use rustc_lint::LateContext;
@@ -58,12 +58,13 @@ pub(super) fn check(cx: &LateContext<'_>, args: &[Expr<'_>], expr: &Expr<'_>, re
             .then_some("Vec")
             .or_else(|| check_string(cx, args, expr_ty, recv_ty_no_refs, recv_path).then_some("String"))
             .or_else(|| check_collections(cx, expr_ty, recv_ty_no_refs))
+        && let Some(exec_context) = std_or_core(cx)
     {
         let recv = snippet(cx, recv.span, "<expr>");
         let sugg = if let ty::Ref(..) = recv_ty.kind() {
-            format!("std::mem::take({recv})")
+            format!("{exec_context}::mem::take({recv})")
         } else {
-            format!("std::mem::take(&mut {recv})")
+            format!("{exec_context}::mem::take(&mut {recv})")
         };
 
         span_lint_and_sugg(
diff --git a/clippy_lints/src/methods/err_expect.rs b/clippy_lints/src/methods/err_expect.rs
index 44b55570eea..f2786efa44c 100644
--- a/clippy_lints/src/methods/err_expect.rs
+++ b/clippy_lints/src/methods/err_expect.rs
@@ -37,7 +37,7 @@ pub(super) fn check(
             "expect_err".to_string(),
             Applicability::MachineApplicable,
         );
-    };
+    }
 }
 
 /// Given a `Result<T, E>` type, return its data (`T`).
diff --git a/clippy_lints/src/methods/expect_fun_call.rs b/clippy_lints/src/methods/expect_fun_call.rs
index 6dc48c26ba9..daa6e0e7f94 100644
--- a/clippy_lints/src/methods/expect_fun_call.rs
+++ b/clippy_lints/src/methods/expect_fun_call.rs
@@ -58,7 +58,7 @@ pub(super) fn check<'tcx>(
             if ty.is_str() && can_be_static_str(cx, arg) {
                 return false;
             }
-        };
+        }
         true
     }
 
diff --git a/clippy_lints/src/methods/iter_with_drain.rs b/clippy_lints/src/methods/iter_with_drain.rs
index 16305871337..aa45969c898 100644
--- a/clippy_lints/src/methods/iter_with_drain.rs
+++ b/clippy_lints/src/methods/iter_with_drain.rs
@@ -25,5 +25,5 @@ pub(super) fn check(cx: &LateContext<'_>, expr: &Expr<'_>, recv: &Expr<'_>, span
             "into_iter()".to_string(),
             Applicability::MaybeIncorrect,
         );
-    };
+    }
 }
diff --git a/clippy_lints/src/methods/manual_repeat_n.rs b/clippy_lints/src/methods/manual_repeat_n.rs
new file mode 100644
index 00000000000..6e09bf132aa
--- /dev/null
+++ b/clippy_lints/src/methods/manual_repeat_n.rs
@@ -0,0 +1,43 @@
+use clippy_utils::diagnostics::span_lint_and_sugg;
+use clippy_utils::msrvs::{self, Msrv};
+use clippy_utils::source::{snippet, snippet_with_context};
+use clippy_utils::{expr_use_ctxt, fn_def_id, is_trait_method, std_or_core};
+use rustc_errors::Applicability;
+use rustc_hir::{Expr, ExprKind};
+use rustc_lint::LateContext;
+use rustc_span::sym;
+
+use super::MANUAL_REPEAT_N;
+
+pub(super) fn check<'tcx>(
+    cx: &LateContext<'tcx>,
+    expr: &'tcx Expr<'tcx>,
+    repeat_expr: &Expr<'_>,
+    take_arg: &Expr<'_>,
+    msrv: &Msrv,
+) {
+    if msrv.meets(msrvs::REPEAT_N)
+        && !expr.span.from_expansion()
+        && is_trait_method(cx, expr, sym::Iterator)
+        && let ExprKind::Call(_, [repeat_arg]) = repeat_expr.kind
+        && let Some(def_id) = fn_def_id(cx, repeat_expr)
+        && cx.tcx.is_diagnostic_item(sym::iter_repeat, def_id)
+        && !expr_use_ctxt(cx, expr).is_ty_unified
+        && let Some(std_or_core) = std_or_core(cx)
+    {
+        let mut app = Applicability::MachineApplicable;
+        span_lint_and_sugg(
+            cx,
+            MANUAL_REPEAT_N,
+            expr.span,
+            "this `repeat().take()` can be written more concisely",
+            "consider using `repeat_n()` instead",
+            format!(
+                "{std_or_core}::iter::repeat_n({}, {})",
+                snippet_with_context(cx, repeat_arg.span, expr.span.ctxt(), "..", &mut app).0,
+                snippet(cx, take_arg.span, "..")
+            ),
+            app,
+        );
+    }
+}
diff --git a/clippy_lints/src/methods/map_with_unused_argument_over_ranges.rs b/clippy_lints/src/methods/map_with_unused_argument_over_ranges.rs
index 1ebb71e251a..78656ace831 100644
--- a/clippy_lints/src/methods/map_with_unused_argument_over_ranges.rs
+++ b/clippy_lints/src/methods/map_with_unused_argument_over_ranges.rs
@@ -3,7 +3,7 @@ use clippy_utils::diagnostics::span_lint_and_then;
 use clippy_utils::msrvs::{self, Msrv};
 use clippy_utils::source::snippet_with_applicability;
 use clippy_utils::sugg::Sugg;
-use clippy_utils::{eager_or_lazy, higher, usage};
+use clippy_utils::{eager_or_lazy, higher, std_or_core, usage};
 use rustc_ast::LitKind;
 use rustc_ast::ast::RangeLimits;
 use rustc_data_structures::packed::Pu128;
@@ -75,6 +75,7 @@ pub(super) fn check(
         } = body_hir
         && !usage::BindingUsageFinder::are_params_used(cx, body_hir)
         && let Some(count) = extract_count_with_applicability(cx, range, &mut applicability)
+        && let Some(exec_context) = std_or_core(cx)
     {
         let method_to_use_name;
         let new_span;
@@ -105,7 +106,7 @@ pub(super) fn check(
         let mut parts = vec![
             (
                 receiver.span.to(method_call_span),
-                format!("std::iter::{method_to_use_name}"),
+                format!("{exec_context}::iter::{method_to_use_name}"),
             ),
             new_span,
         ];
diff --git a/clippy_lints/src/methods/mod.rs b/clippy_lints/src/methods/mod.rs
index 3965c4d4087..42418318fda 100644
--- a/clippy_lints/src/methods/mod.rs
+++ b/clippy_lints/src/methods/mod.rs
@@ -58,6 +58,7 @@ mod manual_inspect;
 mod manual_is_variant_and;
 mod manual_next_back;
 mod manual_ok_or;
+mod manual_repeat_n;
 mod manual_saturating_arithmetic;
 mod manual_str_repeat;
 mod manual_try_fold;
@@ -101,6 +102,7 @@ mod single_char_add_str;
 mod single_char_insert_string;
 mod single_char_push_string;
 mod skip_while_next;
+mod sliced_string_as_bytes;
 mod stable_sort_primitive;
 mod str_split;
 mod str_splitn;
@@ -130,6 +132,7 @@ mod unnecessary_to_owned;
 mod unused_enumerate_index;
 mod unwrap_expect_used;
 mod useless_asref;
+mod useless_nonzero_new_unchecked;
 mod utils;
 mod vec_resize_to_zero;
 mod verbose_file_reads;
@@ -2416,14 +2419,14 @@ declare_clippy_lint! {
 
 declare_clippy_lint! {
     /// ### What it does
-    /// Checks for usage of `.then_some(..).unwrap_or(..)`
+    /// Checks for unnecessary method chains that can be simplified into `if .. else ..`.
     ///
     /// ### Why is this bad?
     /// This can be written more clearly with `if .. else ..`
     ///
     /// ### Limitations
     /// This lint currently only looks for usages of
-    /// `.then_some(..).unwrap_or(..)`, but will be expanded
+    /// `.then_some(..).unwrap_or(..)` and `.then(..).unwrap_or(..)`, but will be expanded
     /// to account for similar patterns.
     ///
     /// ### Example
@@ -4311,6 +4314,84 @@ declare_clippy_lint! {
     "using `Iterator::last` on a `DoubleEndedIterator`"
 }
 
+declare_clippy_lint! {
+    /// ### What it does
+    ///
+    /// Checks for `NonZero*::new_unchecked()` being used in a `const` context.
+    ///
+    /// ### Why is this bad?
+    ///
+    /// Using `NonZero*::new_unchecked()` is an `unsafe` function and requires an `unsafe` context. When used in a
+    /// context evaluated at compilation time, `NonZero*::new().unwrap()` will provide the same result with identical
+    /// runtime performances while not requiring `unsafe`.
+    ///
+    /// ### Example
+    /// ```no_run
+    /// use std::num::NonZeroUsize;
+    /// const PLAYERS: NonZeroUsize = unsafe { NonZeroUsize::new_unchecked(3) };
+    /// ```
+    /// Use instead:
+    /// ```no_run
+    /// use std::num::NonZeroUsize;
+    /// const PLAYERS: NonZeroUsize = NonZeroUsize::new(3).unwrap();
+    /// ```
+    #[clippy::version = "1.86.0"]
+    pub USELESS_NONZERO_NEW_UNCHECKED,
+    complexity,
+    "using `NonZero::new_unchecked()` in a `const` context"
+}
+
+declare_clippy_lint! {
+    /// ### What it does
+    ///
+    /// Checks for `repeat().take()` that can be replaced with `repeat_n()`.
+    ///
+    /// ### Why is this bad?
+    ///
+    /// Using `repeat_n()` is more concise and clearer. Also, `repeat_n()` is sometimes faster than `repeat().take()` when the type of the element is non-trivial to clone because the original value can be reused for the last `.next()` call rather than always cloning.
+    ///
+    /// ### Example
+    /// ```no_run
+    /// let _ = std::iter::repeat(10).take(3);
+    /// ```
+    /// Use instead:
+    /// ```no_run
+    /// let _ = std::iter::repeat_n(10, 3);
+    /// ```
+    #[clippy::version = "1.86.0"]
+    pub MANUAL_REPEAT_N,
+    style,
+    "detect `repeat().take()` that can be replaced with `repeat_n()`"
+}
+
+declare_clippy_lint! {
+    /// ### What it does
+    /// Checks for string slices immediantly followed by `as_bytes`.
+    ///
+    /// ### Why is this bad?
+    /// It involves doing an unnecessary UTF-8 alignment check which is less efficient, and can cause a panic.
+    ///
+    /// ### Known problems
+    /// In some cases, the UTF-8 validation and potential panic from string slicing may be required for
+    /// the code's correctness. If you need to ensure the slice boundaries fall on valid UTF-8 character
+    /// boundaries, the original form (`s[1..5].as_bytes()`) should be preferred.
+    ///
+    /// ### Example
+    /// ```rust
+    /// let s = "Lorem ipsum";
+    /// s[1..5].as_bytes();
+    /// ```
+    /// Use instead:
+    /// ```rust
+    /// let s = "Lorem ipsum";
+    /// &s.as_bytes()[1..5];
+    /// ```
+     #[clippy::version = "1.86.0"]
+     pub SLICED_STRING_AS_BYTES,
+     perf,
+     "slicing a string and immediately calling as_bytes is less efficient and can lead to panics"
+}
+
 pub struct Methods {
     avoid_breaking_exported_api: bool,
     msrv: Msrv,
@@ -4477,6 +4558,9 @@ impl_lint_pass!(Methods => [
     MAP_WITH_UNUSED_ARGUMENT_OVER_RANGES,
     UNNECESSARY_MAP_OR,
     DOUBLE_ENDED_ITERATOR_LAST,
+    USELESS_NONZERO_NEW_UNCHECKED,
+    MANUAL_REPEAT_N,
+    SLICED_STRING_AS_BYTES,
 ]);
 
 /// Extracts a method call name, args, and `Span` of the method name.
@@ -4505,6 +4589,7 @@ impl<'tcx> LateLintPass<'tcx> for Methods {
                 from_iter_instead_of_collect::check(cx, expr, args, func);
                 unnecessary_fallible_conversions::check_function(cx, expr, func);
                 manual_c_str_literals::check(cx, expr, func, args, &self.msrv);
+                useless_nonzero_new_unchecked::check(cx, expr, func, args, &self.msrv);
             },
             ExprKind::MethodCall(method_call, receiver, args, _) => {
                 let method_span = method_call.ident.span;
@@ -4743,6 +4828,7 @@ impl Methods {
                     if let Some(("as_str", recv, [], as_str_span, _)) = method_call(recv) {
                         redundant_as_str::check(cx, expr, recv, as_str_span, span);
                     }
+                    sliced_string_as_bytes::check(cx, expr, recv);
                 },
                 ("as_mut", []) => useless_asref::check(cx, expr, "as_mut", recv),
                 ("as_ptr", []) => manual_c_str_literals::check_as_ptr(cx, expr, recv, &self.msrv),
@@ -4924,8 +5010,8 @@ impl Methods {
                 },
                 ("is_empty", []) => {
                     match method_call(recv) {
-                        Some(("as_bytes", prev_recv, [], _, _)) => {
-                            needless_as_bytes::check(cx, "is_empty", recv, prev_recv, expr.span);
+                        Some((prev_method @ ("as_bytes" | "bytes"), prev_recv, [], _, _)) => {
+                            needless_as_bytes::check(cx, prev_method, "is_empty", prev_recv, expr.span);
                         },
                         Some(("as_str", recv, [], as_str_span, _)) => {
                             redundant_as_str::check(cx, expr, recv, as_str_span, span);
@@ -4962,8 +5048,8 @@ impl Methods {
                     double_ended_iterator_last::check(cx, expr, recv, call_span);
                 },
                 ("len", []) => {
-                    if let Some(("as_bytes", prev_recv, [], _, _)) = method_call(recv) {
-                        needless_as_bytes::check(cx, "len", recv, prev_recv, expr.span);
+                    if let Some((prev_method @ ("as_bytes" | "bytes"), prev_recv, [], _, _)) = method_call(recv) {
+                        needless_as_bytes::check(cx, prev_method, "len", prev_recv, expr.span);
                     }
                 },
                 ("lock", []) => {
@@ -5015,7 +5101,7 @@ impl Methods {
                     option_map_or_none::check(cx, expr, recv, def, map);
                     manual_ok_or::check(cx, expr, recv, def, map);
                     option_map_or_err_ok::check(cx, expr, recv, def, map);
-                    unnecessary_map_or::check(cx, expr, recv, def, map, &self.msrv);
+                    unnecessary_map_or::check(cx, expr, recv, def, map, span, &self.msrv);
                 },
                 ("map_or_else", [def, map]) => {
                     result_map_or_else_none::check(cx, expr, recv, def, map);
@@ -5146,6 +5232,7 @@ impl Methods {
                 ("step_by", [arg]) => iterator_step_by_zero::check(cx, expr, arg),
                 ("take", [arg]) => {
                     iter_out_of_bounds::check_take(cx, expr, recv, arg);
+                    manual_repeat_n::check(cx, expr, recv, arg, &self.msrv);
                     if let Some(("cloned", recv2, [], _span2, _)) = method_call(recv) {
                         iter_overeager_cloned::check(
                             cx,
@@ -5220,8 +5307,8 @@ impl Methods {
                         Some(("map", m_recv, [m_arg], span, _)) => {
                             option_map_unwrap_or::check(cx, expr, m_recv, m_arg, recv, u_arg, span, &self.msrv);
                         },
-                        Some(("then_some", t_recv, [t_arg], _, _)) => {
-                            obfuscated_if_else::check(cx, expr, t_recv, t_arg, u_arg);
+                        Some((then_method @ ("then" | "then_some"), t_recv, [t_arg], _, _)) => {
+                            obfuscated_if_else::check(cx, expr, t_recv, t_arg, u_arg, then_method);
                         },
                         _ => {},
                     }
diff --git a/clippy_lints/src/methods/needless_as_bytes.rs b/clippy_lints/src/methods/needless_as_bytes.rs
index 75e9f317230..7c9f7bae990 100644
--- a/clippy_lints/src/methods/needless_as_bytes.rs
+++ b/clippy_lints/src/methods/needless_as_bytes.rs
@@ -8,18 +8,16 @@ use rustc_span::Span;
 
 use super::NEEDLESS_AS_BYTES;
 
-pub fn check(cx: &LateContext<'_>, method: &str, recv: &Expr<'_>, prev_recv: &Expr<'_>, span: Span) {
-    if cx.typeck_results().expr_ty_adjusted(recv).peel_refs().is_slice()
-        && let ty1 = cx.typeck_results().expr_ty_adjusted(prev_recv).peel_refs()
-        && (is_type_lang_item(cx, ty1, LangItem::String) || ty1.is_str())
-    {
+pub fn check(cx: &LateContext<'_>, prev_method: &str, method: &str, prev_recv: &Expr<'_>, span: Span) {
+    let ty1 = cx.typeck_results().expr_ty_adjusted(prev_recv).peel_refs();
+    if is_type_lang_item(cx, ty1, LangItem::String) || ty1.is_str() {
         let mut app = Applicability::MachineApplicable;
         let sugg = Sugg::hir_with_context(cx, prev_recv, span.ctxt(), "..", &mut app);
         span_lint_and_sugg(
             cx,
             NEEDLESS_AS_BYTES,
             span,
-            "needless call to `as_bytes()`",
+            format!("needless call to `{prev_method}`"),
             format!("`{method}()` can be called directly on strings"),
             format!("{sugg}.{method}()"),
             app,
diff --git a/clippy_lints/src/methods/obfuscated_if_else.rs b/clippy_lints/src/methods/obfuscated_if_else.rs
index 697eab32a33..b71f79f8482 100644
--- a/clippy_lints/src/methods/obfuscated_if_else.rs
+++ b/clippy_lints/src/methods/obfuscated_if_else.rs
@@ -1,8 +1,11 @@
 use super::OBFUSCATED_IF_ELSE;
 use clippy_utils::diagnostics::span_lint_and_sugg;
+use clippy_utils::eager_or_lazy::switch_to_eager_eval;
 use clippy_utils::source::snippet_with_applicability;
+use clippy_utils::sugg::Sugg;
 use rustc_errors::Applicability;
 use rustc_hir as hir;
+use rustc_hir::ExprKind;
 use rustc_lint::LateContext;
 
 pub(super) fn check<'tcx>(
@@ -11,19 +14,30 @@ pub(super) fn check<'tcx>(
     then_recv: &'tcx hir::Expr<'_>,
     then_arg: &'tcx hir::Expr<'_>,
     unwrap_arg: &'tcx hir::Expr<'_>,
+    then_method_name: &str,
 ) {
-    // something.then_some(blah).unwrap_or(blah)
-    // ^^^^^^^^^-then_recv ^^^^-then_arg   ^^^^- unwrap_arg
-    // ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^- expr
-
     let recv_ty = cx.typeck_results().expr_ty(then_recv);
 
     if recv_ty.is_bool() {
-        let mut applicability = Applicability::MachineApplicable;
+        let mut applicability = if switch_to_eager_eval(cx, then_arg) && switch_to_eager_eval(cx, unwrap_arg) {
+            Applicability::MachineApplicable
+        } else {
+            Applicability::MaybeIncorrect
+        };
+
+        let if_then = match then_method_name {
+            "then" if let ExprKind::Closure(closure) = then_arg.kind => {
+                let body = cx.tcx.hir().body(closure.body);
+                snippet_with_applicability(cx, body.value.span, "..", &mut applicability)
+            },
+            "then_some" => snippet_with_applicability(cx, then_arg.span, "..", &mut applicability),
+            _ => String::new().into(),
+        };
+
         let sugg = format!(
             "if {} {{ {} }} else {{ {} }}",
-            snippet_with_applicability(cx, then_recv.span, "..", &mut applicability),
-            snippet_with_applicability(cx, then_arg.span, "..", &mut applicability),
+            Sugg::hir_with_applicability(cx, then_recv, "..", &mut applicability),
+            if_then,
             snippet_with_applicability(cx, unwrap_arg.span, "..", &mut applicability)
         );
 
@@ -31,8 +45,7 @@ pub(super) fn check<'tcx>(
             cx,
             OBFUSCATED_IF_ELSE,
             expr.span,
-            "use of `.then_some(..).unwrap_or(..)` can be written \
-            more clearly with `if .. else ..`",
+            "this method chain can be written more clearly with `if .. else ..`",
             "try",
             sugg,
             applicability,
diff --git a/clippy_lints/src/methods/path_ends_with_ext.rs b/clippy_lints/src/methods/path_ends_with_ext.rs
index febd7fd5cf2..b3811a335e1 100644
--- a/clippy_lints/src/methods/path_ends_with_ext.rs
+++ b/clippy_lints/src/methods/path_ends_with_ext.rs
@@ -37,7 +37,7 @@ pub(super) fn check(
             let _ = write!(sugg, r#".extension().is_some_and(|ext| ext == "{path}")"#);
         } else {
             let _ = write!(sugg, r#".extension().map_or(false, |ext| ext == "{path}")"#);
-        };
+        }
 
         span_lint_and_sugg(
             cx,
diff --git a/clippy_lints/src/methods/sliced_string_as_bytes.rs b/clippy_lints/src/methods/sliced_string_as_bytes.rs
new file mode 100644
index 00000000000..6d4cfdb34f3
--- /dev/null
+++ b/clippy_lints/src/methods/sliced_string_as_bytes.rs
@@ -0,0 +1,29 @@
+use clippy_utils::diagnostics::span_lint_and_sugg;
+use clippy_utils::source::snippet_with_applicability;
+use clippy_utils::ty::is_type_lang_item;
+use rustc_errors::Applicability;
+use rustc_hir::{Expr, ExprKind, LangItem, is_range_literal};
+use rustc_lint::LateContext;
+
+use super::SLICED_STRING_AS_BYTES;
+
+pub(super) fn check(cx: &LateContext<'_>, expr: &Expr<'_>, recv: &Expr<'_>) {
+    if let ExprKind::Index(indexed, index, _) = recv.kind
+        && is_range_literal(index)
+        && let ty = cx.typeck_results().expr_ty(indexed).peel_refs()
+        && (ty.is_str() || is_type_lang_item(cx, ty, LangItem::String))
+    {
+        let mut applicability = Applicability::MaybeIncorrect;
+        let stringish = snippet_with_applicability(cx, indexed.span, "_", &mut applicability);
+        let range = snippet_with_applicability(cx, index.span, "_", &mut applicability);
+        span_lint_and_sugg(
+            cx,
+            SLICED_STRING_AS_BYTES,
+            expr.span,
+            "calling `as_bytes` after slicing a string",
+            "try",
+            format!("&{stringish}.as_bytes()[{range}]"),
+            applicability,
+        );
+    }
+}
diff --git a/clippy_lints/src/methods/unnecessary_iter_cloned.rs b/clippy_lints/src/methods/unnecessary_iter_cloned.rs
index 671c189a98e..c0e01568588 100644
--- a/clippy_lints/src/methods/unnecessary_iter_cloned.rs
+++ b/clippy_lints/src/methods/unnecessary_iter_cloned.rs
@@ -87,7 +87,7 @@ pub fn check_for_loop_iter(
                 // skip lint
                 return true;
             }
-        };
+        }
 
         // the lint should not be executed if no violation happens
         let snippet = if let ExprKind::MethodCall(maybe_iter_method_name, collection, [], _) = receiver.kind
diff --git a/clippy_lints/src/methods/unnecessary_map_or.rs b/clippy_lints/src/methods/unnecessary_map_or.rs
index b7dbebe60a4..6dea1506d0e 100644
--- a/clippy_lints/src/methods/unnecessary_map_or.rs
+++ b/clippy_lints/src/methods/unnecessary_map_or.rs
@@ -1,9 +1,8 @@
 use std::borrow::Cow;
 
-use clippy_utils::diagnostics::span_lint_and_sugg;
+use clippy_utils::diagnostics::span_lint_and_then;
 use clippy_utils::eager_or_lazy::switch_to_eager_eval;
 use clippy_utils::msrvs::{self, Msrv};
-use clippy_utils::source::snippet_opt;
 use clippy_utils::sugg::{Sugg, make_binop};
 use clippy_utils::ty::{get_type_diagnostic_name, implements_trait};
 use clippy_utils::visitors::is_local_used;
@@ -12,7 +11,7 @@ use rustc_ast::LitKind::Bool;
 use rustc_errors::Applicability;
 use rustc_hir::{BinOpKind, Expr, ExprKind, PatKind};
 use rustc_lint::LateContext;
-use rustc_span::sym;
+use rustc_span::{Span, sym};
 
 use super::UNNECESSARY_MAP_OR;
 
@@ -42,13 +41,14 @@ pub(super) fn check<'a>(
     recv: &Expr<'_>,
     def: &Expr<'_>,
     map: &Expr<'_>,
+    method_span: Span,
     msrv: &Msrv,
 ) {
     let ExprKind::Lit(def_kind) = def.kind else {
         return;
     };
 
-    let recv_ty = cx.typeck_results().expr_ty(recv);
+    let recv_ty = cx.typeck_results().expr_ty_adjusted(recv);
 
     let Bool(def_bool) = def_kind.node else {
         return;
@@ -60,6 +60,8 @@ pub(super) fn check<'a>(
         Some(_) | None => return,
     };
 
+    let ext_def_span = def.span.until(map.span);
+
     let (sugg, method, applicability) = if let ExprKind::Closure(map_closure) = map.kind
             && let closure_body = cx.tcx.hir().body(map_closure.body)
             && let closure_body_value = closure_body.value.peel_blocks()
@@ -114,26 +116,17 @@ pub(super) fn check<'a>(
         }
         .into_string();
 
-        (sugg, "a standard comparison", app)
-    } else if !def_bool
-        && msrv.meets(msrvs::OPTION_RESULT_IS_VARIANT_AND)
-        && let Some(recv_callsite) = snippet_opt(cx, recv.span.source_callsite())
-        && let Some(span_callsite) = snippet_opt(cx, map.span.source_callsite())
-    {
+        (vec![(expr.span, sugg)], "a standard comparison", app)
+    } else if !def_bool && msrv.meets(msrvs::OPTION_RESULT_IS_VARIANT_AND) {
         let suggested_name = variant.method_name();
         (
-            format!("{recv_callsite}.{suggested_name}({span_callsite})",),
+            vec![(method_span, suggested_name.into()), (ext_def_span, String::default())],
             suggested_name,
             Applicability::MachineApplicable,
         )
-    } else if def_bool
-        && matches!(variant, Variant::Some)
-        && msrv.meets(msrvs::IS_NONE_OR)
-        && let Some(recv_callsite) = snippet_opt(cx, recv.span.source_callsite())
-        && let Some(span_callsite) = snippet_opt(cx, map.span.source_callsite())
-    {
+    } else if def_bool && matches!(variant, Variant::Some) && msrv.meets(msrvs::IS_NONE_OR) {
         (
-            format!("{recv_callsite}.is_none_or({span_callsite})"),
+            vec![(method_span, "is_none_or".into()), (ext_def_span, String::default())],
             "is_none_or",
             Applicability::MachineApplicable,
         )
@@ -145,13 +138,13 @@ pub(super) fn check<'a>(
         return;
     }
 
-    span_lint_and_sugg(
+    span_lint_and_then(
         cx,
         UNNECESSARY_MAP_OR,
         expr.span,
         "this `map_or` can be simplified",
-        format!("use {method} instead"),
-        sugg,
-        applicability,
+        |diag| {
+            diag.multipart_suggestion_verbose(format!("use {method} instead"), sugg, applicability);
+        },
     );
 }
diff --git a/clippy_lints/src/methods/unnecessary_sort_by.rs b/clippy_lints/src/methods/unnecessary_sort_by.rs
index 9a45b04d1a6..ebc08503dec 100644
--- a/clippy_lints/src/methods/unnecessary_sort_by.rs
+++ b/clippy_lints/src/methods/unnecessary_sort_by.rs
@@ -5,7 +5,8 @@ use clippy_utils::{is_trait_method, std_or_core};
 use rustc_errors::Applicability;
 use rustc_hir::{Closure, Expr, ExprKind, Mutability, Param, Pat, PatKind, Path, PathSegment, QPath};
 use rustc_lint::LateContext;
-use rustc_middle::ty::{self, GenericArgKind};
+use rustc_middle::ty;
+use rustc_middle::ty::GenericArgKind;
 use rustc_span::sym;
 use rustc_span::symbol::Ident;
 use std::iter;
@@ -43,8 +44,7 @@ fn mirrored_exprs(a_expr: &Expr<'_>, a_ident: &Ident, b_expr: &Expr<'_>, b_ident
                 && iter::zip(*left_args, *right_args).all(|(left, right)| mirrored_exprs(left, a_ident, right, b_ident))
         },
         // The two exprs are method calls.
-        // Check to see that the function is the same and the arguments are mirrored
-        // This is enough because the receiver of the method is listed in the arguments
+        // Check to see that the function is the same and the arguments and receivers are mirrored
         (
             ExprKind::MethodCall(left_segment, left_receiver, left_args, _),
             ExprKind::MethodCall(right_segment, right_receiver, right_args, _),
diff --git a/clippy_lints/src/methods/unnecessary_to_owned.rs b/clippy_lints/src/methods/unnecessary_to_owned.rs
index 964f1603f0e..7d72310c1c4 100644
--- a/clippy_lints/src/methods/unnecessary_to_owned.rs
+++ b/clippy_lints/src/methods/unnecessary_to_owned.rs
@@ -217,10 +217,13 @@ fn check_into_iter_call_arg(
         && implements_trait(cx, parent_ty, iterator_trait_id, &[])
         && let Some(item_ty) = get_iterator_item_ty(cx, parent_ty)
         && let Some(receiver_snippet) = receiver.span.get_source_text(cx)
+        // If the receiver is a `Cow`, we can't remove the `into_owned` generally, see https://github.com/rust-lang/rust-clippy/issues/13624.
+        && !is_type_diagnostic_item(cx, cx.typeck_results().expr_ty(receiver), sym::Cow)
     {
         if unnecessary_iter_cloned::check_for_loop_iter(cx, parent, method_name, receiver, true) {
             return true;
         }
+
         let cloned_or_copied = if is_copy(cx, item_ty) && msrv.meets(msrvs::ITERATOR_COPIED) {
             "copied"
         } else {
diff --git a/clippy_lints/src/methods/useless_nonzero_new_unchecked.rs b/clippy_lints/src/methods/useless_nonzero_new_unchecked.rs
new file mode 100644
index 00000000000..0bd50429c09
--- /dev/null
+++ b/clippy_lints/src/methods/useless_nonzero_new_unchecked.rs
@@ -0,0 +1,59 @@
+use clippy_utils::diagnostics::{span_lint_and_sugg, span_lint_and_then};
+use clippy_utils::is_inside_always_const_context;
+use clippy_utils::msrvs::{self, Msrv};
+use clippy_utils::source::snippet_with_applicability;
+use clippy_utils::ty::is_type_diagnostic_item;
+use rustc_errors::Applicability;
+use rustc_hir::{Block, BlockCheckMode, Expr, ExprKind, Node, QPath, UnsafeSource};
+use rustc_lint::LateContext;
+use rustc_span::sym;
+
+use super::USELESS_NONZERO_NEW_UNCHECKED;
+
+pub(super) fn check<'tcx>(cx: &LateContext<'tcx>, expr: &Expr<'_>, func: &Expr<'tcx>, args: &[Expr<'_>], msrv: &Msrv) {
+    if msrv.meets(msrvs::CONST_UNWRAP)
+        && let ExprKind::Path(QPath::TypeRelative(ty, segment)) = func.kind
+        && segment.ident.name == sym::new_unchecked
+        && let [init_arg] = args
+        && is_inside_always_const_context(cx.tcx, expr.hir_id)
+        && is_type_diagnostic_item(cx, cx.typeck_results().node_type(ty.hir_id), sym::NonZero)
+    {
+        let mut app = Applicability::MachineApplicable;
+        let ty_str = snippet_with_applicability(cx, ty.span, "_", &mut app);
+        let msg = format!("`{ty_str}::new()` and `Option::unwrap()` can be safely used in a `const` context");
+        let sugg = format!(
+            "{ty_str}::new({}).unwrap()",
+            snippet_with_applicability(cx, init_arg.span, "_", &mut app)
+        );
+
+        if let Node::Block(Block {
+            stmts: [],
+            span: block_span,
+            rules: BlockCheckMode::UnsafeBlock(UnsafeSource::UserProvided),
+            ..
+        }) = cx.tcx.parent_hir_node(expr.hir_id)
+        {
+            if !block_span.from_expansion() {
+                // The expression is the only component of an `unsafe` block. Propose
+                // to replace the block altogether.
+                span_lint_and_sugg(
+                    cx,
+                    USELESS_NONZERO_NEW_UNCHECKED,
+                    *block_span,
+                    msg,
+                    "use instead",
+                    sugg,
+                    app,
+                );
+            }
+        } else {
+            // The expression is enclosed in a larger `unsafe` context. Indicate that
+            // this may no longer be needed for the fixed expression.
+            span_lint_and_then(cx, USELESS_NONZERO_NEW_UNCHECKED, expr.span, msg, |diagnostic| {
+                diagnostic
+                    .span_suggestion(expr.span, "use instead", sugg, app)
+                    .note("the fixed expression does not require an `unsafe` context");
+            });
+        }
+    }
+}
diff --git a/clippy_lints/src/misc.rs b/clippy_lints/src/misc.rs
index b856c929cf6..b511b1e46b3 100644
--- a/clippy_lints/src/misc.rs
+++ b/clippy_lints/src/misc.rs
@@ -214,11 +214,12 @@ impl<'tcx> LateLintPass<'tcx> for LintPass {
                     );
                 },
             );
-        };
+        }
         if let StmtKind::Semi(expr) = stmt.kind
-            && let ExprKind::Binary(ref binop, a, b) = expr.kind
-            && (binop.node == BinOpKind::And || binop.node == BinOpKind::Or)
-            && let Some(sugg) = Sugg::hir_opt(cx, a)
+            && let ExprKind::Binary(binop, a, b) = &expr.kind
+            && matches!(binop.node, BinOpKind::And | BinOpKind::Or)
+            && !stmt.span.from_expansion()
+            && expr.span.eq_ctxt(stmt.span)
         {
             span_lint_hir_and_then(
                 cx,
@@ -227,16 +228,14 @@ impl<'tcx> LateLintPass<'tcx> for LintPass {
                 stmt.span,
                 "boolean short circuit operator in statement may be clearer using an explicit test",
                 |diag| {
-                    let sugg = if binop.node == BinOpKind::Or { !sugg } else { sugg };
-                    diag.span_suggestion(
-                        stmt.span,
-                        "replace it with",
-                        format!("if {sugg} {{ {}; }}", &snippet(cx, b.span, ".."),),
-                        Applicability::MachineApplicable, // snippet
-                    );
+                    let mut app = Applicability::MachineApplicable;
+                    let test = Sugg::hir_with_context(cx, a, expr.span.ctxt(), "_", &mut app);
+                    let test = if binop.node == BinOpKind::Or { !test } else { test };
+                    let then = Sugg::hir_with_context(cx, b, expr.span.ctxt(), "_", &mut app);
+                    diag.span_suggestion(stmt.span, "replace it with", format!("if {test} {{ {then}; }}"), app);
                 },
             );
-        };
+        }
     }
 
     fn check_expr(&mut self, cx: &LateContext<'tcx>, expr: &'tcx Expr<'_>) {
diff --git a/clippy_lints/src/mismatching_type_param_order.rs b/clippy_lints/src/mismatching_type_param_order.rs
index 748289454be..d52fe7e7d5b 100644
--- a/clippy_lints/src/mismatching_type_param_order.rs
+++ b/clippy_lints/src/mismatching_type_param_order.rs
@@ -66,7 +66,7 @@ impl<'tcx> LateLintPass<'tcx> for TypeParamMismatch {
                     }) => impl_params.push((path.segments[0].ident.to_string(), path.span)),
                     GenericArg::Type(_) => return,
                     _ => (),
-                };
+                }
             }
 
             // find the type that the Impl is for
diff --git a/clippy_lints/src/missing_doc.rs b/clippy_lints/src/missing_doc.rs
index 29dcbaa9e62..06e92985e66 100644
--- a/clippy_lints/src/missing_doc.rs
+++ b/clippy_lints/src/missing_doc.rs
@@ -220,7 +220,7 @@ impl<'tcx> LateLintPass<'tcx> for MissingDoc {
             | hir::ItemKind::GlobalAsm(..)
             | hir::ItemKind::Impl { .. }
             | hir::ItemKind::Use(..) => note_prev_span_then_ret!(self.prev_span, it.span),
-        };
+        }
 
         let (article, desc) = cx.tcx.article_and_description(it.owner_id.to_def_id());
 
diff --git a/clippy_lints/src/missing_fields_in_debug.rs b/clippy_lints/src/missing_fields_in_debug.rs
index f28b431ab99..e9ec23b1efa 100644
--- a/clippy_lints/src/missing_fields_in_debug.rs
+++ b/clippy_lints/src/missing_fields_in_debug.rs
@@ -207,7 +207,7 @@ impl<'tcx> LateLintPass<'tcx> for MissingFieldsInDebug {
             // this prevents ICEs such as when self is a type parameter or a primitive type
             // (see #10887, #11063)
             && let Res::Def(DefKind::Struct | DefKind::Enum | DefKind::Union, self_path_did) = self_path.res
-            && cx.match_def_path(trait_def_id, &[sym::core, sym::fmt, sym::Debug])
+            && cx.tcx.is_diagnostic_item(sym::Debug, trait_def_id)
             // don't trigger if this impl was derived
             && !cx.tcx.has_attr(item.owner_id, sym::automatically_derived)
             && !item.span.from_expansion()
diff --git a/clippy_lints/src/missing_inline.rs b/clippy_lints/src/missing_inline.rs
index 05aa425de9e..bba1b63be27 100644
--- a/clippy_lints/src/missing_inline.rs
+++ b/clippy_lints/src/missing_inline.rs
@@ -135,7 +135,7 @@ impl<'tcx> LateLintPass<'tcx> for MissingInline {
             | hir::ItemKind::ForeignMod { .. }
             | hir::ItemKind::Impl { .. }
             | hir::ItemKind::Use(..) => {},
-        };
+        }
     }
 
     fn check_impl_item(&mut self, cx: &LateContext<'tcx>, impl_item: &'tcx hir::ImplItem<'_>) {
diff --git a/clippy_lints/src/multi_assignments.rs b/clippy_lints/src/multi_assignments.rs
index 9a6b1dfc52b..4383f28717d 100644
--- a/clippy_lints/src/multi_assignments.rs
+++ b/clippy_lints/src/multi_assignments.rs
@@ -56,10 +56,10 @@ impl EarlyLintPass for MultiAssignments {
         if let ExprKind::Assign(target, source, _) = &expr.kind {
             if let ExprKind::Assign(_target, _source, _) = &strip_paren_blocks(target).kind {
                 span_lint(cx, MULTI_ASSIGNMENTS, expr.span, "assignments don't nest intuitively");
-            };
+            }
             if let ExprKind::Assign(_target, _source, _) = &strip_paren_blocks(source).kind {
                 span_lint(cx, MULTI_ASSIGNMENTS, expr.span, "assignments don't nest intuitively");
             }
-        };
+        }
     }
 }
diff --git a/clippy_lints/src/multiple_unsafe_ops_per_block.rs b/clippy_lints/src/multiple_unsafe_ops_per_block.rs
index 79252bba74d..aad6ae52a6d 100644
--- a/clippy_lints/src/multiple_unsafe_ops_per_block.rs
+++ b/clippy_lints/src/multiple_unsafe_ops_per_block.rs
@@ -171,7 +171,7 @@ fn collect_unsafe_exprs<'tcx>(
             },
 
             _ => {},
-        };
+        }
 
         Continue::<(), _>(Descend::Yes)
     });
diff --git a/clippy_lints/src/mutable_debug_assertion.rs b/clippy_lints/src/mutable_debug_assertion.rs
index 152635a5c35..e589b3608b3 100644
--- a/clippy_lints/src/mutable_debug_assertion.rs
+++ b/clippy_lints/src/mutable_debug_assertion.rs
@@ -96,10 +96,6 @@ impl<'tcx> Visitor<'tcx> for MutArgVisitor<'_, 'tcx> {
                 self.found = true;
                 return;
             },
-            ExprKind::If(..) => {
-                self.found = true;
-                return;
-            },
             ExprKind::Path(_) => {
                 if let Some(adj) = self.cx.typeck_results().adjustments().get(expr.hir_id) {
                     if adj
diff --git a/clippy_lints/src/mutex_atomic.rs b/clippy_lints/src/mutex_atomic.rs
index 38841496458..86c084423b7 100644
--- a/clippy_lints/src/mutex_atomic.rs
+++ b/clippy_lints/src/mutex_atomic.rs
@@ -91,7 +91,7 @@ impl<'tcx> LateLintPass<'tcx> for Mutex {
                         ty::Uint(t) if t != UintTy::Usize => span_lint(cx, MUTEX_INTEGER, expr.span, msg),
                         ty::Int(t) if t != IntTy::Isize => span_lint(cx, MUTEX_INTEGER, expr.span, msg),
                         _ => span_lint(cx, MUTEX_ATOMIC, expr.span, msg),
-                    };
+                    }
                 }
             }
         }
diff --git a/clippy_lints/src/needless_late_init.rs b/clippy_lints/src/needless_late_init.rs
index a67addea948..4e19a2f409d 100644
--- a/clippy_lints/src/needless_late_init.rs
+++ b/clippy_lints/src/needless_late_init.rs
@@ -107,6 +107,10 @@ struct LocalAssign {
 
 impl LocalAssign {
     fn from_expr(expr: &Expr<'_>, span: Span) -> Option<Self> {
+        if expr.span.from_expansion() {
+            return None;
+        }
+
         if let ExprKind::Assign(lhs, rhs, _) = expr.kind {
             if lhs.span.from_expansion() {
                 return None;
@@ -336,7 +340,7 @@ fn check<'tcx>(
             );
         },
         _ => {},
-    };
+    }
 
     Some(())
 }
diff --git a/clippy_lints/src/no_mangle_with_rust_abi.rs b/clippy_lints/src/no_mangle_with_rust_abi.rs
index 9ee4e493277..2e2916c957d 100644
--- a/clippy_lints/src/no_mangle_with_rust_abi.rs
+++ b/clippy_lints/src/no_mangle_with_rust_abi.rs
@@ -37,7 +37,9 @@ declare_lint_pass!(NoMangleWithRustAbi => [NO_MANGLE_WITH_RUST_ABI]);
 
 impl<'tcx> LateLintPass<'tcx> for NoMangleWithRustAbi {
     fn check_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx Item<'tcx>) {
-        if let ItemKind::Fn { sig: fn_sig, .. } = &item.kind {
+        if let ItemKind::Fn { sig: fn_sig, .. } = &item.kind
+            && !item.span.from_expansion()
+        {
             let attrs = cx.tcx.hir().attrs(item.hir_id());
             let mut app = Applicability::MaybeIncorrect;
             let fn_snippet = snippet_with_applicability(cx, fn_sig.span.with_hi(item.ident.span.lo()), "..", &mut app);
diff --git a/clippy_lints/src/non_copy_const.rs b/clippy_lints/src/non_copy_const.rs
index 8409d179b0f..147654675ec 100644
--- a/clippy_lints/src/non_copy_const.rs
+++ b/clippy_lints/src/non_copy_const.rs
@@ -89,16 +89,6 @@ declare_clippy_lint! {
     ///
     /// The `const` value should be stored inside a `static` item.
     ///
-    /// ### Known problems
-    /// When an enum has variants with interior mutability, use of its non
-    /// interior mutable variants can generate false positives. See issue
-    /// [#3962](https://github.com/rust-lang/rust-clippy/issues/3962)
-    ///
-    /// Types that have underlying or potential interior mutability trigger the lint whether
-    /// the interior mutable field is used or not. See issues
-    /// [#5812](https://github.com/rust-lang/rust-clippy/issues/5812) and
-    /// [#3825](https://github.com/rust-lang/rust-clippy/issues/3825)
-    ///
     /// ### Example
     /// ```no_run
     /// use std::sync::atomic::{AtomicUsize, Ordering::SeqCst};
diff --git a/clippy_lints/src/non_octal_unix_permissions.rs b/clippy_lints/src/non_octal_unix_permissions.rs
index 0caa19cd844..852c3885f56 100644
--- a/clippy_lints/src/non_octal_unix_permissions.rs
+++ b/clippy_lints/src/non_octal_unix_permissions.rs
@@ -73,7 +73,7 @@ impl<'tcx> LateLintPass<'tcx> for NonOctalUnixPermissions {
                 }
             },
             _ => {},
-        };
+        }
     }
 }
 
diff --git a/clippy_lints/src/non_std_lazy_statics.rs b/clippy_lints/src/non_std_lazy_statics.rs
new file mode 100644
index 00000000000..312610db042
--- /dev/null
+++ b/clippy_lints/src/non_std_lazy_statics.rs
@@ -0,0 +1,306 @@
+use clippy_config::Conf;
+use clippy_utils::diagnostics::{span_lint, span_lint_and_then};
+use clippy_utils::msrvs::Msrv;
+use clippy_utils::visitors::for_each_expr;
+use clippy_utils::{def_path_def_ids, fn_def_id, path_def_id};
+use rustc_data_structures::fx::FxIndexMap;
+use rustc_errors::Applicability;
+use rustc_hir::def::{DefKind, Res};
+use rustc_hir::def_id::{CrateNum, DefId};
+use rustc_hir::{self as hir, BodyId, Expr, ExprKind, Item, ItemKind};
+use rustc_lint::{LateContext, LateLintPass, LintContext};
+use rustc_middle::lint::in_external_macro;
+use rustc_session::impl_lint_pass;
+use rustc_span::Span;
+
+declare_clippy_lint! {
+    /// ### What it does
+    /// Lints when `once_cell::sync::Lazy` or `lazy_static!` are used to define a static variable,
+    /// and suggests replacing such cases with `std::sync::LazyLock` instead.
+    ///
+    /// Note: This lint will not trigger in crate with `no_std` context, or with MSRV < 1.80.0. It
+    /// also will not trigger on `once_cell::sync::Lazy` usage in crates which use other types
+    /// from `once_cell`, such as `once_cell::race::OnceBox`.
+    ///
+    /// ### Why restrict this?
+    /// - Reduces the need for an extra dependency
+    /// - Enforce convention of using standard library types when possible
+    ///
+    /// ### Example
+    /// ```ignore
+    /// lazy_static! {
+    ///     static ref FOO: String = "foo".to_uppercase();
+    /// }
+    /// static BAR: once_cell::sync::Lazy<String> = once_cell::sync::Lazy::new(|| "BAR".to_lowercase());
+    /// ```
+    /// Use instead:
+    /// ```ignore
+    /// static FOO: std::sync::LazyLock<String> = std::sync::LazyLock::new(|| "FOO".to_lowercase());
+    /// static BAR: std::sync::LazyLock<String> = std::sync::LazyLock::new(|| "BAR".to_lowercase());
+    /// ```
+    #[clippy::version = "1.81.0"]
+    pub NON_STD_LAZY_STATICS,
+    pedantic,
+    "lazy static that could be replaced by `std::sync::LazyLock`"
+}
+
+/// A list containing functions with corresponding replacements in `LazyLock`.
+///
+/// Some functions could be replaced as well if we have replaced `Lazy` to `LazyLock`,
+/// therefore after suggesting replace the type, we need to make sure the function calls can be
+/// replaced, otherwise the suggestions cannot be applied thus the applicability should be
+/// `Unspecified` or `MaybeIncorret`.
+static FUNCTION_REPLACEMENTS: &[(&str, Option<&str>)] = &[
+    ("once_cell::sync::Lazy::force", Some("std::sync::LazyLock::force")),
+    ("once_cell::sync::Lazy::get", None), // `std::sync::LazyLock::get` is experimental
+    ("once_cell::sync::Lazy::new", Some("std::sync::LazyLock::new")),
+    // Note: `Lazy::{into_value, get_mut, force_mut}` are not in the list.
+    // Because the lint only checks for `static`s, and using these functions with statics
+    // will either be a hard error or triggers `static_mut_ref` that will be hard errors.
+    // But keep in mind that if somehow we decide to expand this lint to catch non-statics,
+    // add those functions into the list.
+];
+
+pub struct NonStdLazyStatic {
+    msrv: Msrv,
+    lazy_static_lazy_static: Vec<DefId>,
+    once_cell_crate: Vec<CrateNum>,
+    once_cell_sync_lazy: Vec<DefId>,
+    once_cell_sync_lazy_new: Vec<DefId>,
+    sugg_map: FxIndexMap<DefId, Option<String>>,
+    lazy_type_defs: FxIndexMap<DefId, LazyInfo>,
+    uses_other_once_cell_types: bool,
+}
+
+impl NonStdLazyStatic {
+    #[must_use]
+    pub fn new(conf: &'static Conf) -> Self {
+        Self {
+            msrv: conf.msrv.clone(),
+            lazy_static_lazy_static: Vec::new(),
+            once_cell_crate: Vec::new(),
+            once_cell_sync_lazy: Vec::new(),
+            once_cell_sync_lazy_new: Vec::new(),
+            sugg_map: FxIndexMap::default(),
+            lazy_type_defs: FxIndexMap::default(),
+            uses_other_once_cell_types: false,
+        }
+    }
+}
+
+impl_lint_pass!(NonStdLazyStatic => [NON_STD_LAZY_STATICS]);
+
+/// Return if current MSRV does not meet the requirement for `lazy_cell` feature,
+/// or current context has `no_std` attribute.
+macro_rules! ensure_prerequisite {
+    ($msrv:expr, $cx:ident) => {
+        if !$msrv.meets(clippy_utils::msrvs::LAZY_CELL) || clippy_utils::is_no_std_crate($cx) {
+            return;
+        }
+    };
+}
+
+impl<'hir> LateLintPass<'hir> for NonStdLazyStatic {
+    extract_msrv_attr!(LateContext);
+
+    fn check_crate(&mut self, cx: &LateContext<'hir>) {
+        // Do not lint if current crate does not support `LazyLock`.
+        ensure_prerequisite!(self.msrv, cx);
+
+        // Fetch def_ids for external paths
+        self.lazy_static_lazy_static = def_path_def_ids(cx.tcx, &["lazy_static", "lazy_static"]).collect();
+        self.once_cell_sync_lazy = def_path_def_ids(cx.tcx, &["once_cell", "sync", "Lazy"]).collect();
+        self.once_cell_sync_lazy_new = def_path_def_ids(cx.tcx, &["once_cell", "sync", "Lazy", "new"]).collect();
+        // And CrateNums for `once_cell` crate
+        self.once_cell_crate = self.once_cell_sync_lazy.iter().map(|d| d.krate).collect();
+
+        // Convert hardcoded fn replacement list into a map with def_id
+        for (path, sugg) in FUNCTION_REPLACEMENTS {
+            let path_vec: Vec<&str> = path.split("::").collect();
+            for did in def_path_def_ids(cx.tcx, &path_vec) {
+                self.sugg_map.insert(did, sugg.map(ToOwned::to_owned));
+            }
+        }
+    }
+
+    fn check_item(&mut self, cx: &LateContext<'hir>, item: &Item<'hir>) {
+        ensure_prerequisite!(self.msrv, cx);
+
+        if let ItemKind::Static(..) = item.kind
+            && let Some(macro_call) = clippy_utils::macros::root_macro_call(item.span)
+            && self.lazy_static_lazy_static.contains(&macro_call.def_id)
+        {
+            span_lint(
+                cx,
+                NON_STD_LAZY_STATICS,
+                macro_call.span,
+                "this macro has been superceded by `std::sync::LazyLock`",
+            );
+            return;
+        }
+
+        if in_external_macro(cx.sess(), item.span) {
+            return;
+        }
+
+        if let Some(lazy_info) = LazyInfo::from_item(self, cx, item) {
+            self.lazy_type_defs.insert(item.owner_id.to_def_id(), lazy_info);
+        }
+    }
+
+    fn check_expr(&mut self, cx: &LateContext<'hir>, expr: &Expr<'hir>) {
+        ensure_prerequisite!(self.msrv, cx);
+
+        // All functions in the `FUNCTION_REPLACEMENTS` have only one args
+        if let ExprKind::Call(callee, [arg]) = expr.kind
+            && let Some(call_def_id) = fn_def_id(cx, expr)
+            && self.sugg_map.contains_key(&call_def_id)
+            && let ExprKind::Path(qpath) = arg.peel_borrows().kind
+            && let Some(arg_def_id) = cx.typeck_results().qpath_res(&qpath, arg.hir_id).opt_def_id()
+            && let Some(lazy_info) = self.lazy_type_defs.get_mut(&arg_def_id)
+        {
+            lazy_info.calls_span_and_id.insert(callee.span, call_def_id);
+        }
+    }
+
+    fn check_ty(&mut self, cx: &LateContext<'hir>, ty: &'hir rustc_hir::Ty<'hir, rustc_hir::AmbigArg>) {
+        ensure_prerequisite!(self.msrv, cx);
+
+        // Record if types from `once_cell` besides `sync::Lazy` are used.
+        if let rustc_hir::TyKind::Path(qpath) = ty.peel_refs().kind
+            && let Some(ty_def_id) = cx.qpath_res(&qpath, ty.hir_id).opt_def_id()
+            // Is from `once_cell` crate
+            && self.once_cell_crate.contains(&ty_def_id.krate)
+            // And is NOT `once_cell::sync::Lazy`
+            && !self.once_cell_sync_lazy.contains(&ty_def_id)
+        {
+            self.uses_other_once_cell_types = true;
+        }
+    }
+
+    fn check_crate_post(&mut self, cx: &LateContext<'hir>) {
+        ensure_prerequisite!(self.msrv, cx);
+
+        if !self.uses_other_once_cell_types {
+            for (_, lazy_info) in &self.lazy_type_defs {
+                lazy_info.lint(cx, &self.sugg_map);
+            }
+        }
+    }
+}
+
+struct LazyInfo {
+    /// Span of the [`hir::Ty`] without including args.
+    /// i.e.:
+    /// ```ignore
+    /// static FOO: Lazy<String> = Lazy::new(...);
+    /// //          ^^^^
+    /// ```
+    ty_span_no_args: Span,
+    /// `Span` and `DefId` of calls on `Lazy` type.
+    /// i.e.:
+    /// ```ignore
+    /// static FOO: Lazy<String> = Lazy::new(...);
+    /// //                         ^^^^^^^^^
+    /// ```
+    calls_span_and_id: FxIndexMap<Span, DefId>,
+}
+
+impl LazyInfo {
+    fn from_item(state: &NonStdLazyStatic, cx: &LateContext<'_>, item: &Item<'_>) -> Option<Self> {
+        // Check if item is a `once_cell:sync::Lazy` static.
+        if let ItemKind::Static(ty, _, body_id) = item.kind
+            && let Some(path_def_id) = path_def_id(cx, ty)
+            && let hir::TyKind::Path(hir::QPath::Resolved(_, path)) = ty.kind
+            && state.once_cell_sync_lazy.contains(&path_def_id)
+        {
+            let ty_span_no_args = path_span_without_args(path);
+            let body = cx.tcx.hir().body(body_id);
+
+            // visit body to collect `Lazy::new` calls
+            let mut new_fn_calls = FxIndexMap::default();
+            for_each_expr::<(), ()>(cx, body, |ex| {
+                if let Some((fn_did, call_span)) = fn_def_id_and_span_from_body(cx, ex, body_id)
+                    && state.once_cell_sync_lazy_new.contains(&fn_did)
+                {
+                    new_fn_calls.insert(call_span, fn_did);
+                }
+                std::ops::ControlFlow::Continue(())
+            });
+
+            Some(LazyInfo {
+                ty_span_no_args,
+                calls_span_and_id: new_fn_calls,
+            })
+        } else {
+            None
+        }
+    }
+
+    fn lint(&self, cx: &LateContext<'_>, sugg_map: &FxIndexMap<DefId, Option<String>>) {
+        // Applicability might get adjusted to `Unspecified` later if any calls
+        // in `calls_span_and_id` are not replaceable judging by the `sugg_map`.
+        let mut appl = Applicability::MachineApplicable;
+        let mut suggs = vec![(self.ty_span_no_args, "std::sync::LazyLock".to_string())];
+
+        for (span, def_id) in &self.calls_span_and_id {
+            let maybe_sugg = sugg_map.get(def_id).cloned().flatten();
+            if let Some(sugg) = maybe_sugg {
+                suggs.push((*span, sugg));
+            } else {
+                // If NO suggested replacement, not machine applicable
+                appl = Applicability::Unspecified;
+            }
+        }
+
+        span_lint_and_then(
+            cx,
+            NON_STD_LAZY_STATICS,
+            self.ty_span_no_args,
+            "this type has been superceded by `LazyLock` in the standard library",
+            |diag| {
+                diag.multipart_suggestion("use `std::sync::LazyLock` instead", suggs, appl);
+            },
+        );
+    }
+}
+
+/// Return the span of a given `Path` without including any of its args.
+///
+/// NB: Re-write of a private function `rustc_lint::non_local_def::path_span_without_args`.
+fn path_span_without_args(path: &hir::Path<'_>) -> Span {
+    path.segments
+        .last()
+        .and_then(|seg| seg.args)
+        .map_or(path.span, |args| path.span.until(args.span_ext))
+}
+
+/// Returns the `DefId` and `Span` of the callee if the given expression is a function call.
+///
+/// NB: Modified from [`clippy_utils::fn_def_id`], to support calling in an static `Item`'s body.
+fn fn_def_id_and_span_from_body(cx: &LateContext<'_>, expr: &Expr<'_>, body_id: BodyId) -> Option<(DefId, Span)> {
+    // FIXME: find a way to cache the result.
+    let typeck = cx.tcx.typeck_body(body_id);
+    match &expr.kind {
+        ExprKind::Call(
+            Expr {
+                kind: ExprKind::Path(qpath),
+                hir_id: path_hir_id,
+                span,
+                ..
+            },
+            ..,
+        ) => {
+            // Only return Fn-like DefIds, not the DefIds of statics/consts/etc that contain or
+            // deref to fn pointers, dyn Fn, impl Fn - #8850
+            if let Res::Def(DefKind::Fn | DefKind::Ctor(..) | DefKind::AssocFn, id) =
+                typeck.qpath_res(qpath, *path_hir_id)
+            {
+                Some((id, *span))
+            } else {
+                None
+            }
+        },
+        _ => None,
+    }
+}
diff --git a/clippy_lints/src/operators/arithmetic_side_effects.rs b/clippy_lints/src/operators/arithmetic_side_effects.rs
index 0eca788c787..9d07a14718d 100644
--- a/clippy_lints/src/operators/arithmetic_side_effects.rs
+++ b/clippy_lints/src/operators/arithmetic_side_effects.rs
@@ -104,7 +104,7 @@ impl ArithmeticSideEffects {
 
             if !tcx.is_diagnostic_item(sym::NonZero, adt.did()) {
                 return false;
-            };
+            }
 
             let int_type = substs.type_at(0);
             let unsigned_int_types = [
@@ -214,13 +214,13 @@ impl ArithmeticSideEffects {
                 | hir::BinOpKind::Sub
         ) {
             return;
-        };
+        }
         let (mut actual_lhs, lhs_ref_counter) = peel_hir_expr_refs(lhs);
         let (mut actual_rhs, rhs_ref_counter) = peel_hir_expr_refs(rhs);
         actual_lhs = expr_or_init(cx, actual_lhs);
         actual_rhs = expr_or_init(cx, actual_rhs);
         let lhs_ty = cx.typeck_results().expr_ty(actual_lhs).peel_refs();
-        let rhs_ty = cx.typeck_results().expr_ty(actual_rhs).peel_refs();
+        let rhs_ty = cx.typeck_results().expr_ty_adjusted(actual_rhs).peel_refs();
         if self.has_allowed_binary(lhs_ty, rhs_ty) {
             return;
         }
@@ -283,7 +283,7 @@ impl ArithmeticSideEffects {
         if ConstEvalCtxt::new(cx).eval_simple(receiver).is_some() {
             return;
         }
-        let instance_ty = cx.typeck_results().expr_ty(receiver);
+        let instance_ty = cx.typeck_results().expr_ty_adjusted(receiver);
         if !Self::is_integral(instance_ty) {
             return;
         }
@@ -311,7 +311,7 @@ impl ArithmeticSideEffects {
         if ConstEvalCtxt::new(cx).eval(un_expr).is_some() {
             return;
         }
-        let ty = cx.typeck_results().expr_ty(expr).peel_refs();
+        let ty = cx.typeck_results().expr_ty_adjusted(expr).peel_refs();
         if self.has_allowed_unary(ty) {
             return;
         }
diff --git a/clippy_lints/src/operators/cmp_owned.rs b/clippy_lints/src/operators/cmp_owned.rs
index b0d872e98fd..cf6b8992973 100644
--- a/clippy_lints/src/operators/cmp_owned.rs
+++ b/clippy_lints/src/operators/cmp_owned.rs
@@ -104,7 +104,7 @@ fn check_op(cx: &LateContext<'_>, expr: &Expr<'_>, other: &Expr<'_>, left: bool)
             } else {
                 expr_snip = arg_snip.to_string();
                 eq_impl = without_deref;
-            };
+            }
 
             let span;
             let hint;
diff --git a/clippy_lints/src/operators/const_comparisons.rs b/clippy_lints/src/operators/const_comparisons.rs
index 1a0bfd8b997..10455d3b93a 100644
--- a/clippy_lints/src/operators/const_comparisons.rs
+++ b/clippy_lints/src/operators/const_comparisons.rs
@@ -127,7 +127,7 @@ pub(super) fn check<'tcx>(
                 None,
                 note,
             );
-        };
+        }
     }
 }
 
diff --git a/clippy_lints/src/operators/double_comparison.rs b/clippy_lints/src/operators/double_comparison.rs
index d72a2fc3b1a..54f50f11e03 100644
--- a/clippy_lints/src/operators/double_comparison.rs
+++ b/clippy_lints/src/operators/double_comparison.rs
@@ -49,5 +49,5 @@ pub(super) fn check<'tcx>(cx: &LateContext<'tcx>, op: BinOpKind, lhs: &'tcx Expr
             lint_double_comparison!(==);
         },
         _ => (),
-    };
+    }
 }
diff --git a/clippy_lints/src/operators/float_cmp.rs b/clippy_lints/src/operators/float_cmp.rs
index 8272d3643d4..01dc6a27c33 100644
--- a/clippy_lints/src/operators/float_cmp.rs
+++ b/clippy_lints/src/operators/float_cmp.rs
@@ -120,7 +120,7 @@ fn is_float(cx: &LateContext<'_>, expr: &Expr<'_>) -> bool {
 
     if let ty::Array(arr_ty, _) = value {
         return matches!(arr_ty.kind(), ty::Float(_));
-    };
+    }
 
     matches!(value, ty::Float(_))
 }
diff --git a/clippy_lints/src/operators/mod.rs b/clippy_lints/src/operators/mod.rs
index 9e8a821c3f4..d9845bc3b0f 100644
--- a/clippy_lints/src/operators/mod.rs
+++ b/clippy_lints/src/operators/mod.rs
@@ -262,7 +262,7 @@ declare_clippy_lint! {
     /// to `trailing_zeros`
     ///
     /// ### Why is this bad?
-    /// `x.trailing_zeros() > 4` is much clearer than `x & 15
+    /// `x.trailing_zeros() >= 4` is much clearer than `x & 15
     /// == 0`
     ///
     /// ### Known problems
@@ -278,7 +278,7 @@ declare_clippy_lint! {
     ///
     /// ```no_run
     /// # let x: i32 = 1;
-    /// if x.trailing_zeros() > 4 { }
+    /// if x.trailing_zeros() >= 4 { }
     /// ```
     #[clippy::version = "pre 1.29.0"]
     pub VERBOSE_BIT_MASK,
diff --git a/clippy_lints/src/operators/modulo_arithmetic.rs b/clippy_lints/src/operators/modulo_arithmetic.rs
index c83bdda347a..691d7b904ef 100644
--- a/clippy_lints/src/operators/modulo_arithmetic.rs
+++ b/clippy_lints/src/operators/modulo_arithmetic.rs
@@ -30,7 +30,7 @@ pub(super) fn check<'tcx>(
         } else {
             check_non_const_operands(cx, e, lhs);
         }
-    };
+    }
 }
 
 fn used_in_comparison_with_zero(cx: &LateContext<'_>, expr: &Expr<'_>) -> bool {
diff --git a/clippy_lints/src/operators/modulo_one.rs b/clippy_lints/src/operators/modulo_one.rs
index 54eea14833f..fc5565e821e 100644
--- a/clippy_lints/src/operators/modulo_one.rs
+++ b/clippy_lints/src/operators/modulo_one.rs
@@ -21,6 +21,6 @@ pub(crate) fn check(cx: &LateContext<'_>, expr: &Expr<'_>, op: BinOpKind, right:
                     "any number modulo -1 will panic/overflow or result in 0",
                 );
             }
-        };
+        }
     }
 }
diff --git a/clippy_lints/src/partialeq_ne_impl.rs b/clippy_lints/src/partialeq_ne_impl.rs
index 794bef7b321..55676522419 100644
--- a/clippy_lints/src/partialeq_ne_impl.rs
+++ b/clippy_lints/src/partialeq_ne_impl.rs
@@ -53,6 +53,6 @@ impl<'tcx> LateLintPass<'tcx> for PartialEqNeImpl {
                     );
                 }
             }
-        };
+        }
     }
 }
diff --git a/clippy_lints/src/precedence.rs b/clippy_lints/src/precedence.rs
index 031f0931059..421b2b74755 100644
--- a/clippy_lints/src/precedence.rs
+++ b/clippy_lints/src/precedence.rs
@@ -43,7 +43,7 @@ impl EarlyLintPass for Precedence {
                     cx,
                     PRECEDENCE,
                     expr.span,
-                    "operator precedence can trip the unwary",
+                    "operator precedence might not be obvious",
                     "consider parenthesizing your expression",
                     sugg,
                     appl,
diff --git a/clippy_lints/src/redundant_closure_call.rs b/clippy_lints/src/redundant_closure_call.rs
index 41a44de536b..b4dadef57a3 100644
--- a/clippy_lints/src/redundant_closure_call.rs
+++ b/clippy_lints/src/redundant_closure_call.rs
@@ -208,7 +208,7 @@ impl<'tcx> LateLintPass<'tcx> for RedundantClosureCall {
                         // avoid clippy::double_parens
                         if !is_in_fn_call_arg {
                             hint = hint.maybe_par();
-                        };
+                        }
 
                         diag.span_suggestion(full_expr.span, "try doing something like", hint, applicability);
                     }
diff --git a/clippy_lints/src/redundant_pub_crate.rs b/clippy_lints/src/redundant_pub_crate.rs
index 1b557730eca..8d6b1c7274d 100644
--- a/clippy_lints/src/redundant_pub_crate.rs
+++ b/clippy_lints/src/redundant_pub_crate.rs
@@ -1,8 +1,10 @@
 use clippy_utils::diagnostics::span_lint_and_then;
+use clippy_utils::source::HasSession;
 use rustc_errors::Applicability;
 use rustc_hir::def::{DefKind, Res};
 use rustc_hir::{Item, ItemKind};
 use rustc_lint::{LateContext, LateLintPass};
+use rustc_middle::lint::in_external_macro;
 use rustc_middle::ty;
 use rustc_session::impl_lint_pass;
 use rustc_span::def_id::CRATE_DEF_ID;
@@ -49,6 +51,7 @@ impl<'tcx> LateLintPass<'tcx> for RedundantPubCrate {
             && !cx.effective_visibilities.is_exported(item.owner_id.def_id)
             && self.is_exported.last() == Some(&false)
             && is_not_macro_export(item)
+            && !in_external_macro(cx.sess(), item.span)
         {
             let span = item.span.with_hi(item.ident.span.hi());
             let descr = cx.tcx.def_kind(item.owner_id).descr(item.owner_id.to_def_id());
diff --git a/clippy_lints/src/redundant_type_annotations.rs b/clippy_lints/src/redundant_type_annotations.rs
index 81556f39614..7bd4d6e993b 100644
--- a/clippy_lints/src/redundant_type_annotations.rs
+++ b/clippy_lints/src/redundant_type_annotations.rs
@@ -215,6 +215,6 @@ impl LateLintPass<'_> for RedundantTypeAnnotations {
                 },
                 _ => (),
             }
-        };
+        }
     }
 }
diff --git a/clippy_lints/src/repeat_vec_with_capacity.rs b/clippy_lints/src/repeat_vec_with_capacity.rs
index f54cafffb83..5dddf9263a3 100644
--- a/clippy_lints/src/repeat_vec_with_capacity.rs
+++ b/clippy_lints/src/repeat_vec_with_capacity.rs
@@ -3,7 +3,7 @@ use clippy_utils::diagnostics::span_lint_and_then;
 use clippy_utils::higher::VecArgs;
 use clippy_utils::macros::matching_root_macro_call;
 use clippy_utils::source::snippet;
-use clippy_utils::{expr_or_init, fn_def_id};
+use clippy_utils::{expr_or_init, fn_def_id, std_or_core};
 use rustc_errors::Applicability;
 use rustc_hir::{Expr, ExprKind};
 use rustc_lint::{LateContext, LateLintPass};
@@ -93,6 +93,7 @@ fn check_repeat_fn(cx: &LateContext<'_>, expr: &Expr<'_>) {
         && let ExprKind::Call(_, [repeat_expr]) = expr.kind
         && fn_def_id(cx, repeat_expr).is_some_and(|did| cx.tcx.is_diagnostic_item(sym::vec_with_capacity, did))
         && !repeat_expr.span.from_expansion()
+        && let Some(exec_context) = std_or_core(cx)
     {
         emit_lint(
             cx,
@@ -100,7 +101,10 @@ fn check_repeat_fn(cx: &LateContext<'_>, expr: &Expr<'_>) {
             "iter::repeat",
             "none of the yielded `Vec`s will have the requested capacity",
             "if you intended to create an iterator that yields `Vec`s with an initial capacity, try",
-            format!("std::iter::repeat_with(|| {})", snippet(cx, repeat_expr.span, "..")),
+            format!(
+                "{exec_context}::iter::repeat_with(|| {})",
+                snippet(cx, repeat_expr.span, "..")
+            ),
         );
     }
 }
diff --git a/clippy_lints/src/returns.rs b/clippy_lints/src/returns.rs
index dfaee8cc305..664e984fece 100644
--- a/clippy_lints/src/returns.rs
+++ b/clippy_lints/src/returns.rs
@@ -1,10 +1,11 @@
 use clippy_utils::diagnostics::{span_lint_and_sugg, span_lint_hir_and_then};
 use clippy_utils::source::{SpanRangeExt, snippet_with_context};
 use clippy_utils::sugg::has_enclosing_paren;
-use clippy_utils::visitors::{Descend, for_each_expr, for_each_unconsumed_temporary};
+use clippy_utils::visitors::{Descend, for_each_expr};
 use clippy_utils::{
-    binary_expr_needs_parentheses, fn_def_id, is_from_proc_macro, is_inside_let_else, is_res_lang_ctor, path_res,
-    path_to_local_id, span_contains_cfg, span_find_starting_semi,
+    binary_expr_needs_parentheses, fn_def_id, is_from_proc_macro, is_inside_let_else, is_res_lang_ctor,
+    leaks_droppable_temporary_with_limited_lifetime, path_res, path_to_local_id, span_contains_cfg,
+    span_find_starting_semi,
 };
 use core::ops::ControlFlow;
 use rustc_ast::MetaItemInner;
@@ -389,22 +390,8 @@ fn check_final_expr<'tcx>(
                 }
             };
 
-            if let Some(inner) = inner {
-                if for_each_unconsumed_temporary(cx, inner, |temporary_ty| {
-                    if temporary_ty.has_significant_drop(cx.tcx, cx.typing_env())
-                        && temporary_ty
-                            .walk()
-                            .any(|arg| matches!(arg.unpack(), GenericArgKind::Lifetime(re) if !re.is_static()))
-                    {
-                        ControlFlow::Break(())
-                    } else {
-                        ControlFlow::Continue(())
-                    }
-                })
-                .is_break()
-                {
-                    return;
-                }
+            if inner.is_some_and(|inner| leaks_droppable_temporary_with_limited_lifetime(cx, inner)) {
+                return;
             }
 
             if ret_span.from_expansion() || is_from_proc_macro(cx, expr) {
diff --git a/clippy_lints/src/single_range_in_vec_init.rs b/clippy_lints/src/single_range_in_vec_init.rs
index 9737b84cdb9..2d989b1cf0b 100644
--- a/clippy_lints/src/single_range_in_vec_init.rs
+++ b/clippy_lints/src/single_range_in_vec_init.rs
@@ -1,9 +1,9 @@
 use clippy_utils::diagnostics::span_lint_and_then;
-use clippy_utils::get_trait_def_id;
 use clippy_utils::higher::VecArgs;
 use clippy_utils::macros::root_macro_call_first_node;
 use clippy_utils::source::SpanRangeExt;
 use clippy_utils::ty::implements_trait;
+use clippy_utils::{get_trait_def_id, is_no_std_crate};
 use rustc_ast::{LitIntType, LitKind, UintTy};
 use rustc_errors::Applicability;
 use rustc_hir::{Expr, ExprKind, LangItem, QPath, StructTailExpr};
@@ -125,7 +125,7 @@ impl LateLintPass<'_> for SingleRangeInVecInit {
                     span,
                     format!("{suggested_type} of `Range` that is only one element"),
                     |diag| {
-                        if should_emit_every_value {
+                        if should_emit_every_value && !is_no_std_crate(cx) {
                             diag.span_suggestion(
                                 span,
                                 "if you wanted a `Vec` that contains the entire range, try",
diff --git a/clippy_lints/src/size_of_in_element_count.rs b/clippy_lints/src/size_of_in_element_count.rs
index db1c75fc3de..f72ff10dd43 100644
--- a/clippy_lints/src/size_of_in_element_count.rs
+++ b/clippy_lints/src/size_of_in_element_count.rs
@@ -97,7 +97,7 @@ fn get_pointee_ty_and_count_expr<'tcx>(
         && let Some(pointee_ty) = cx.typeck_results().node_args(func.hir_id).types().next()
     {
         return Some((pointee_ty, count));
-    };
+    }
     if let ExprKind::MethodCall(method_path, ptr_self, [.., count], _) = expr.kind
         // Find calls to copy_{from,to}{,_nonoverlapping} and write_bytes methods
         && let method_ident = method_path.ident.as_str()
@@ -108,7 +108,7 @@ fn get_pointee_ty_and_count_expr<'tcx>(
             cx.typeck_results().expr_ty(ptr_self).kind()
     {
         return Some((*pointee_ty, count));
-    };
+    }
     None
 }
 
@@ -130,6 +130,6 @@ impl<'tcx> LateLintPass<'tcx> for SizeOfInElementCount {
             && pointee_ty == ty_used_for_size_of
         {
             span_lint_and_help(cx, SIZE_OF_IN_ELEMENT_COUNT, count_expr.span, LINT_MSG, None, HELP_MSG);
-        };
+        }
     }
 }
diff --git a/clippy_lints/src/slow_vector_initialization.rs b/clippy_lints/src/slow_vector_initialization.rs
index d2d693eaa1f..d26288adb39 100644
--- a/clippy_lints/src/slow_vector_initialization.rs
+++ b/clippy_lints/src/slow_vector_initialization.rs
@@ -3,6 +3,7 @@ use clippy_utils::macros::matching_root_macro_call;
 use clippy_utils::sugg::Sugg;
 use clippy_utils::{
     SpanlessEq, get_enclosing_block, is_integer_literal, is_path_diagnostic_item, path_to_local, path_to_local_id,
+    span_contains_comment,
 };
 use rustc_errors::Applicability;
 use rustc_hir::intravisit::{Visitor, walk_block, walk_expr, walk_stmt};
@@ -190,7 +191,7 @@ impl SlowVectorInit {
             InitializationType::Extend(e) | InitializationType::Resize(e) => {
                 Self::emit_lint(cx, e, vec_alloc, "slow zero-filling initialization");
             },
-        };
+        }
     }
 
     fn emit_lint(cx: &LateContext<'_>, slow_fill: &Expr<'_>, vec_alloc: &VecAllocation<'_>, msg: &'static str) {
@@ -206,6 +207,14 @@ impl SlowVectorInit {
         let span_to_replace = slow_fill
             .span
             .with_lo(vec_alloc.allocation_expr.span.source_callsite().lo());
+
+        // If there is no comment in `span_to_replace`, Clippy can automatically fix the code.
+        let app = if span_contains_comment(cx.tcx.sess.source_map(), span_to_replace) {
+            Applicability::Unspecified
+        } else {
+            Applicability::MachineApplicable
+        };
+
         span_lint_and_sugg(
             cx,
             SLOW_VECTOR_INITIALIZATION,
@@ -213,7 +222,7 @@ impl SlowVectorInit {
             msg,
             "consider replacing this with",
             format!("vec![0; {len_expr}]"),
-            Applicability::Unspecified,
+            app,
         );
     }
 }
diff --git a/clippy_lints/src/swap.rs b/clippy_lints/src/swap.rs
index ff116800512..9b4c3d275ae 100644
--- a/clippy_lints/src/swap.rs
+++ b/clippy_lints/src/swap.rs
@@ -296,7 +296,7 @@ fn check_xor_swap<'tcx>(cx: &LateContext<'tcx>, block: &'tcx Block<'tcx>) {
         {
             let span = s1.span.to(s3.span);
             generate_swap_warning(block, cx, lhs0, rhs0, rhs1, rhs2, span, true);
-        };
+        }
     }
 }
 
diff --git a/clippy_lints/src/transmute/missing_transmute_annotations.rs b/clippy_lints/src/transmute/missing_transmute_annotations.rs
index 531422798a6..bed4e60ba62 100644
--- a/clippy_lints/src/transmute/missing_transmute_annotations.rs
+++ b/clippy_lints/src/transmute/missing_transmute_annotations.rs
@@ -50,10 +50,7 @@ pub(super) fn check<'tcx>(
     }
     let args = last.args;
     let missing_generic = match args {
-        Some(args) if !args.args.is_empty() => args.args.iter().any(|arg| match arg {
-            GenericArg::Infer(_) => true,
-            _ => false,
-        }),
+        Some(args) if !args.args.is_empty() => args.args.iter().any(|arg| matches!(arg, GenericArg::Infer(_))),
         _ => true,
     };
     if !missing_generic {
diff --git a/clippy_lints/src/transmute/transmute_int_to_non_zero.rs b/clippy_lints/src/transmute/transmute_int_to_non_zero.rs
index 3729dfd3e86..f27aaa2fa77 100644
--- a/clippy_lints/src/transmute/transmute_int_to_non_zero.rs
+++ b/clippy_lints/src/transmute/transmute_int_to_non_zero.rs
@@ -24,7 +24,7 @@ pub(super) fn check<'tcx>(
 
     if !tcx.is_diagnostic_item(sym::NonZero, adt.did()) {
         return false;
-    };
+    }
 
     let int_ty = substs.type_at(0);
     if from_ty != int_ty {
diff --git a/clippy_lints/src/tuple_array_conversions.rs b/clippy_lints/src/tuple_array_conversions.rs
index 99a55f9fc35..008e09dd8bd 100644
--- a/clippy_lints/src/tuple_array_conversions.rs
+++ b/clippy_lints/src/tuple_array_conversions.rs
@@ -119,7 +119,7 @@ fn check_tuple<'tcx>(cx: &LateContext<'tcx>, expr: &'tcx Expr<'tcx>, elements: &
                         && let LitKind::Int(val, _) = lit.node
                     {
                         return (val == i as u128).then_some(lhs);
-                    };
+                    }
 
                     None
                 })
diff --git a/clippy_lints/src/types/borrowed_box.rs b/clippy_lints/src/types/borrowed_box.rs
index 1a5fdf0cd64..2e97772407f 100644
--- a/clippy_lints/src/types/borrowed_box.rs
+++ b/clippy_lints/src/types/borrowed_box.rs
@@ -71,7 +71,7 @@ pub(super) fn check(cx: &LateContext<'_>, hir_ty: &hir::Ty<'_>, lt: &Lifetime, m
                     Applicability::Unspecified,
                 );
                 return true;
-            };
+            }
             false
         },
         _ => false,
diff --git a/clippy_lints/src/unnecessary_semicolon.rs b/clippy_lints/src/unnecessary_semicolon.rs
new file mode 100644
index 00000000000..efbc536dcb4
--- /dev/null
+++ b/clippy_lints/src/unnecessary_semicolon.rs
@@ -0,0 +1,109 @@
+use clippy_utils::diagnostics::span_lint_and_sugg;
+use clippy_utils::leaks_droppable_temporary_with_limited_lifetime;
+use rustc_errors::Applicability;
+use rustc_hir::{Block, ExprKind, HirId, MatchSource, Stmt, StmtKind};
+use rustc_lint::{LateContext, LateLintPass};
+use rustc_session::impl_lint_pass;
+use rustc_span::edition::Edition::Edition2021;
+
+declare_clippy_lint! {
+    /// ### What it does
+    /// Checks for the presence of a semicolon at the end of
+    /// a `match` or `if` statement evaluating to `()`.
+    ///
+    /// ### Why is this bad?
+    /// The semicolon is not needed, and may be removed to
+    /// avoid confusion and visual clutter.
+    ///
+    /// ### Example
+    /// ```no_run
+    /// # let a: u32 = 42;
+    /// if a > 10 {
+    ///     println!("a is greater than 10");
+    /// };
+    /// ```
+    /// Use instead:
+    /// ```no_run
+    /// # let a: u32 = 42;
+    /// if a > 10 {
+    ///    println!("a is greater than 10");
+    /// }
+    /// ```
+    #[clippy::version = "1.86.0"]
+    pub UNNECESSARY_SEMICOLON,
+    pedantic,
+    "unnecessary semicolon after expression returning `()`"
+}
+
+#[derive(Default)]
+pub struct UnnecessarySemicolon {
+    last_statements: Vec<HirId>,
+}
+
+impl_lint_pass!(UnnecessarySemicolon => [UNNECESSARY_SEMICOLON]);
+
+impl UnnecessarySemicolon {
+    /// Enter or leave a block, remembering the last statement of the block.
+    fn handle_block(&mut self, cx: &LateContext<'_>, block: &Block<'_>, enter: bool) {
+        // Up to edition 2021, removing the semicolon of the last statement of a block
+        // may result in the scrutinee temporary values to live longer than the block
+        // variables. To avoid this problem, we do not lint the last statement of an
+        // expressionless block.
+        if cx.tcx.sess.edition() <= Edition2021
+            && block.expr.is_none()
+            && let Some(last_stmt) = block.stmts.last()
+        {
+            if enter {
+                self.last_statements.push(last_stmt.hir_id);
+            } else {
+                self.last_statements.pop();
+            }
+        }
+    }
+
+    /// Checks if `stmt` is the last statement in an expressionless block for edition ≤ 2021.
+    fn is_last_in_block(&self, stmt: &Stmt<'_>) -> bool {
+        self.last_statements
+            .last()
+            .is_some_and(|last_stmt_id| last_stmt_id == &stmt.hir_id)
+    }
+}
+
+impl<'tcx> LateLintPass<'tcx> for UnnecessarySemicolon {
+    fn check_block(&mut self, cx: &LateContext<'_>, block: &Block<'_>) {
+        self.handle_block(cx, block, true);
+    }
+
+    fn check_block_post(&mut self, cx: &LateContext<'_>, block: &Block<'_>) {
+        self.handle_block(cx, block, false);
+    }
+
+    fn check_stmt(&mut self, cx: &LateContext<'tcx>, stmt: &Stmt<'tcx>) {
+        // rustfmt already takes care of removing semicolons at the end
+        // of loops.
+        if let StmtKind::Semi(expr) = stmt.kind
+            && !stmt.span.from_expansion()
+            && !expr.span.from_expansion()
+            && matches!(
+                expr.kind,
+                ExprKind::If(..) | ExprKind::Match(_, _, MatchSource::Normal | MatchSource::Postfix)
+            )
+            && cx.typeck_results().expr_ty(expr) == cx.tcx.types.unit
+        {
+            if self.is_last_in_block(stmt) && leaks_droppable_temporary_with_limited_lifetime(cx, expr) {
+                return;
+            }
+
+            let semi_span = expr.span.shrink_to_hi().to(stmt.span.shrink_to_hi());
+            span_lint_and_sugg(
+                cx,
+                UNNECESSARY_SEMICOLON,
+                semi_span,
+                "unnecessary semicolon",
+                "remove",
+                String::new(),
+                Applicability::MachineApplicable,
+            );
+        }
+    }
+}
diff --git a/clippy_lints/src/unneeded_struct_pattern.rs b/clippy_lints/src/unneeded_struct_pattern.rs
new file mode 100644
index 00000000000..40ba70d451d
--- /dev/null
+++ b/clippy_lints/src/unneeded_struct_pattern.rs
@@ -0,0 +1,76 @@
+use clippy_utils::diagnostics::span_lint_and_sugg;
+use clippy_utils::is_from_proc_macro;
+use rustc_errors::Applicability;
+use rustc_hir::def::{DefKind, Res};
+use rustc_hir::{Pat, PatKind, QPath};
+use rustc_lint::{LateContext, LateLintPass};
+use rustc_session::declare_lint_pass;
+
+declare_clippy_lint! {
+    /// ### What it does
+    /// Checks for struct patterns that match against unit variant.
+    ///
+    /// ### Why is this bad?
+    /// Struct pattern `{ }` or `{ .. }` is not needed for unit variant.
+    ///
+    /// ### Example
+    /// ```no_run
+    /// match Some(42) {
+    ///     Some(v) => v,
+    ///     None { .. } => 0,
+    /// };
+    /// // Or
+    /// match Some(42) {
+    ///     Some(v) => v,
+    ///     None { } => 0,
+    /// };
+    /// ```
+    /// Use instead:
+    /// ```no_run
+    /// match Some(42) {
+    ///     Some(v) => v,
+    ///     None => 0,
+    /// };
+    /// ```
+    #[clippy::version = "1.83.0"]
+    pub UNNEEDED_STRUCT_PATTERN,
+    style,
+    "using struct pattern to match against unit variant"
+}
+
+declare_lint_pass!(UnneededStructPattern => [UNNEEDED_STRUCT_PATTERN]);
+
+impl LateLintPass<'_> for UnneededStructPattern {
+    fn check_pat(&mut self, cx: &LateContext<'_>, pat: &Pat<'_>) {
+        if !pat.span.from_expansion()
+            && let PatKind::Struct(path, [], _) = &pat.kind
+            && let QPath::Resolved(_, path) = path
+            && let Res::Def(DefKind::Variant, did) = path.res
+        {
+            let enum_did = cx.tcx.parent(did);
+            let variant = cx.tcx.adt_def(enum_did).variant_with_id(did);
+
+            let has_only_fields_brackets = variant.ctor.is_some() && variant.fields.is_empty();
+            let non_exhaustive_activated = !variant.def_id.is_local() && variant.is_field_list_non_exhaustive();
+            if !has_only_fields_brackets || non_exhaustive_activated {
+                return;
+            }
+
+            if is_from_proc_macro(cx, *path) {
+                return;
+            }
+
+            if let Some(brackets_span) = pat.span.trim_start(path.span) {
+                span_lint_and_sugg(
+                    cx,
+                    UNNEEDED_STRUCT_PATTERN,
+                    brackets_span,
+                    "struct pattern is not needed for a unit variant",
+                    "remove the struct pattern",
+                    String::new(),
+                    Applicability::MachineApplicable,
+                );
+            }
+        }
+    }
+}
diff --git a/clippy_lints/src/unused_io_amount.rs b/clippy_lints/src/unused_io_amount.rs
index 7c9455bf8ab..e65123b8a94 100644
--- a/clippy_lints/src/unused_io_amount.rs
+++ b/clippy_lints/src/unused_io_amount.rs
@@ -182,7 +182,7 @@ fn check_expr<'a>(cx: &LateContext<'a>, expr: &'a hir::Expr<'a>) {
             emit_lint(cx, expr.span, expr.hir_id, op, &[]);
         },
         _ => {},
-    };
+    }
 }
 
 fn should_lint<'a>(cx: &LateContext<'a>, mut inner: &'a hir::Expr<'a>) -> Option<IoOp> {
diff --git a/clippy_lints/src/useless_conversion.rs b/clippy_lints/src/useless_conversion.rs
index 7ffab81a544..5e452c6d2ac 100644
--- a/clippy_lints/src/useless_conversion.rs
+++ b/clippy_lints/src/useless_conversion.rs
@@ -1,5 +1,5 @@
 use clippy_utils::diagnostics::{span_lint_and_help, span_lint_and_sugg, span_lint_and_then};
-use clippy_utils::source::{snippet, snippet_with_applicability, snippet_with_context};
+use clippy_utils::source::{snippet, snippet_with_context};
 use clippy_utils::sugg::{DiagExt as _, Sugg};
 use clippy_utils::ty::{is_copy, is_type_diagnostic_item, same_type_and_consts};
 use clippy_utils::{
@@ -12,6 +12,7 @@ use rustc_infer::infer::TyCtxtInferExt;
 use rustc_infer::traits::Obligation;
 use rustc_lint::{LateContext, LateLintPass};
 use rustc_middle::traits::ObligationCause;
+use rustc_middle::ty::adjustment::{Adjust, AutoBorrow, AutoBorrowMutability};
 use rustc_middle::ty::{self, AdtDef, EarlyBinder, GenericArg, GenericArgsRef, Ty, TypeVisitableExt};
 use rustc_session::impl_lint_pass;
 use rustc_span::{Span, sym};
@@ -251,26 +252,25 @@ impl<'tcx> LateLintPass<'tcx> for UselessConversion {
                             //  ^^^
                             let (into_iter_recv, depth) = into_iter_deep_call(cx, into_iter_recv);
 
-                            let plural = if depth == 0 { "" } else { "s" };
-                            let mut applicability = Applicability::MachineApplicable;
-                            let sugg = snippet_with_applicability(
-                                cx,
-                                into_iter_recv.span.source_callsite(),
-                                "<expr>",
-                                &mut applicability,
-                            )
-                            .into_owned();
                             span_lint_and_then(
                                 cx,
                                 USELESS_CONVERSION,
                                 e.span,
                                 "explicit call to `.into_iter()` in function argument accepting `IntoIterator`",
                                 |diag| {
-                                    diag.span_suggestion(
-                                        e.span,
+                                    let receiver_span = into_iter_recv.span.source_callsite();
+                                    let adjustments = adjustments(cx, into_iter_recv);
+                                    let mut sugg = if adjustments.is_empty() {
+                                        vec![]
+                                    } else {
+                                        vec![(receiver_span.shrink_to_lo(), adjustments)]
+                                    };
+                                    let plural = if depth == 0 { "" } else { "s" };
+                                    sugg.push((e.span.with_lo(receiver_span.hi()), String::new()));
+                                    diag.multipart_suggestion(
                                         format!("consider removing the `.into_iter()`{plural}"),
                                         sugg,
-                                        applicability,
+                                        Applicability::MachineApplicable,
                                     );
                                     diag.span_note(span, "this parameter accepts any `IntoIterator`, so you don't need to call `.into_iter()`");
                                 },
@@ -431,3 +431,16 @@ fn has_eligible_receiver(cx: &LateContext<'_>, recv: &Expr<'_>, expr: &Expr<'_>)
     }
     false
 }
+
+fn adjustments(cx: &LateContext<'_>, expr: &Expr<'_>) -> String {
+    let mut prefix = String::new();
+    for adj in cx.typeck_results().expr_adjustments(expr) {
+        match adj.kind {
+            Adjust::Deref(_) => prefix = format!("*{prefix}"),
+            Adjust::Borrow(AutoBorrow::Ref(AutoBorrowMutability::Mut { .. })) => prefix = format!("&mut {prefix}"),
+            Adjust::Borrow(AutoBorrow::Ref(AutoBorrowMutability::Not)) => prefix = format!("&{prefix}"),
+            _ => {},
+        }
+    }
+    prefix
+}
diff --git a/clippy_lints/src/utils/internal_lints/slow_symbol_comparisons.rs b/clippy_lints/src/utils/internal_lints/slow_symbol_comparisons.rs
index 49aad881994..b8bcb9b3756 100644
--- a/clippy_lints/src/utils/internal_lints/slow_symbol_comparisons.rs
+++ b/clippy_lints/src/utils/internal_lints/slow_symbol_comparisons.rs
@@ -69,6 +69,6 @@ impl<'tcx> LateLintPass<'tcx> for SlowSymbolComparisons {
                 ),
                 applicability,
             );
-        };
+        }
     }
 }
diff --git a/clippy_lints/src/vec.rs b/clippy_lints/src/vec.rs
index 0730b561bc2..03c667846b6 100644
--- a/clippy_lints/src/vec.rs
+++ b/clippy_lints/src/vec.rs
@@ -69,7 +69,7 @@ impl<'tcx> LateLintPass<'tcx> for UselessVec {
         };
         if self.allow_in_test && is_in_test(cx.tcx, expr.hir_id) {
             return;
-        };
+        }
         // the parent callsite of this `vec!` expression, or span to the borrowed one such as `&vec!`
         let callsite = expr.span.parent_callsite().unwrap_or(expr.span);