]> git.proxmox.com Git - rustc.git/blobdiff - src/tools/clippy/clippy_utils/src/hir_utils.rs
New upstream version 1.62.1+dfsg1
[rustc.git] / src / tools / clippy / clippy_utils / src / hir_utils.rs
index 00594f4d42addb594875349a2e6e2e031e24423a..f4da625f1e306a0e083716316ede4a5f07ced8d7 100644 (file)
@@ -1,4 +1,4 @@
-use crate::consts::{constant_context, constant_simple};
+use crate::consts::constant_simple;
 use crate::source::snippet_opt;
 use rustc_ast::ast::InlineAsmTemplatePiece;
 use rustc_data_structures::fx::FxHasher;
@@ -16,15 +16,14 @@ use rustc_span::Symbol;
 use std::hash::{Hash, Hasher};
 
 /// Type used to check whether two ast are the same. This is different from the
-/// operator
-/// `==` on ast types as this operator would compare true equality with ID and
-/// span.
+/// operator `==` on ast types as this operator would compare true equality with
+/// ID and span.
 ///
 /// Note that some expressions kinds are not considered but could be added.
 pub struct SpanlessEq<'a, 'tcx> {
     /// Context used to evaluate constant expressions.
     cx: &'a LateContext<'tcx>,
-    maybe_typeck_results: Option<&'tcx TypeckResults<'tcx>>,
+    maybe_typeck_results: Option<(&'tcx TypeckResults<'tcx>, &'tcx TypeckResults<'tcx>)>,
     allow_side_effects: bool,
     expr_fallback: Option<Box<dyn FnMut(&Expr<'_>, &Expr<'_>) -> bool + 'a>>,
 }
@@ -33,7 +32,7 @@ impl<'a, 'tcx> SpanlessEq<'a, 'tcx> {
     pub fn new(cx: &'a LateContext<'tcx>) -> Self {
         Self {
             cx,
-            maybe_typeck_results: cx.maybe_typeck_results(),
+            maybe_typeck_results: cx.maybe_typeck_results().map(|x| (x, x)),
             allow_side_effects: true,
             expr_fallback: None,
         }
@@ -102,9 +101,9 @@ impl HirEqInterExpr<'_, '_, '_> {
             (&StmtKind::Local(l), &StmtKind::Local(r)) => {
                 // This additional check ensures that the type of the locals are equivalent even if the init
                 // expression or type have some inferred parts.
-                if let Some(typeck) = self.inner.maybe_typeck_results {
-                    let l_ty = typeck.pat_ty(l.pat);
-                    let r_ty = typeck.pat_ty(r.pat);
+                if let Some((typeck_lhs, typeck_rhs)) = self.inner.maybe_typeck_results {
+                    let l_ty = typeck_lhs.pat_ty(l.pat);
+                    let r_ty = typeck_rhs.pat_ty(r.pat);
                     if l_ty != r_ty {
                         return false;
                     }
@@ -182,9 +181,17 @@ impl HirEqInterExpr<'_, '_, '_> {
     }
 
     pub fn eq_body(&mut self, left: BodyId, right: BodyId) -> bool {
-        let cx = self.inner.cx;
-        let eval_const = |body| constant_context(cx, cx.tcx.typeck_body(body)).expr(&cx.tcx.hir().body(body).value);
-        eval_const(left) == eval_const(right)
+        // swap out TypeckResults when hashing a body
+        let old_maybe_typeck_results = self.inner.maybe_typeck_results.replace((
+            self.inner.cx.tcx.typeck_body(left),
+            self.inner.cx.tcx.typeck_body(right),
+        ));
+        let res = self.eq_expr(
+            &self.inner.cx.tcx.hir().body(left).value,
+            &self.inner.cx.tcx.hir().body(right).value,
+        );
+        self.inner.maybe_typeck_results = old_maybe_typeck_results;
+        res
     }
 
     #[allow(clippy::similar_names)]
@@ -193,10 +200,10 @@ impl HirEqInterExpr<'_, '_, '_> {
             return false;
         }
 
-        if let Some(typeck_results) = self.inner.maybe_typeck_results {
+        if let Some((typeck_lhs, typeck_rhs)) = self.inner.maybe_typeck_results {
             if let (Some(l), Some(r)) = (
-                constant_simple(self.inner.cx, typeck_results, left),
-                constant_simple(self.inner.cx, typeck_results, right),
+                constant_simple(self.inner.cx, typeck_lhs, left),
+                constant_simple(self.inner.cx, typeck_rhs, right),
             ) {
                 if l == r {
                     return true;
@@ -674,8 +681,10 @@ impl<'a, 'tcx> SpanlessHash<'a, 'tcx> {
                                 self.hash_expr(out_expr);
                             }
                         },
-                        InlineAsmOperand::Const { anon_const } => self.hash_body(anon_const.body),
-                        InlineAsmOperand::Sym { expr } => self.hash_expr(expr),
+                        InlineAsmOperand::Const { anon_const } | InlineAsmOperand::SymFn { anon_const } => {
+                            self.hash_body(anon_const.body);
+                        },
+                        InlineAsmOperand::SymStatic { path, def_id: _ } => self.hash_qpath(path),
                     }
                 }
             },