]> git.lizzy.rs Git - rust.git/blobdiff - src/tools/clippy/clippy_utils/src/ty.rs
Merge commit 'd7b5cbf065b88830ca519adcb73fad4c0d24b1c7' into clippyup
[rust.git] / src / tools / clippy / clippy_utils / src / ty.rs
index 75d27d3b594822ff342ab4c1bde86804e16a4dfd..227e97d37ecc3bbcc0eac4d284ceace56057c88b 100644 (file)
@@ -13,7 +13,8 @@
 use rustc_middle::mir::interpret::{ConstValue, Scalar};
 use rustc_middle::ty::subst::{GenericArg, GenericArgKind, Subst};
 use rustc_middle::ty::{
-    self, AdtDef, Binder, FnSig, IntTy, Predicate, PredicateKind, Ty, TyCtxt, TypeFoldable, UintTy, VariantDiscr,
+    self, AdtDef, Binder, FnSig, IntTy, ParamEnv, Predicate, PredicateKind, Ty, TyCtxt, TypeFoldable, UintTy,
+    VariantDiscr,
 };
 use rustc_span::symbol::Ident;
 use rustc_span::{sym, Span, Symbol, DUMMY_SP};
@@ -77,9 +78,9 @@ pub fn get_associated_type<'tcx>(
     cx.tcx
         .associated_items(trait_id)
         .find_by_name_and_kind(cx.tcx, Ident::from_str(name), ty::AssocKind::Type, trait_id)
-        .map(|assoc| {
+        .and_then(|assoc| {
             let proj = cx.tcx.mk_projection(assoc.def_id, cx.tcx.mk_substs_trait(ty, &[]));
-            cx.tcx.normalize_erasing_regions(cx.param_env, proj)
+            cx.tcx.try_normalize_erasing_regions(cx.param_env, proj).ok()
         })
 }
 
@@ -151,18 +152,29 @@ pub fn implements_trait<'tcx>(
     ty: Ty<'tcx>,
     trait_id: DefId,
     ty_params: &[GenericArg<'tcx>],
+) -> bool {
+    implements_trait_with_env(cx.tcx, cx.param_env, ty, trait_id, ty_params)
+}
+
+/// Same as `implements_trait` but allows using a `ParamEnv` different from the lint context.
+pub fn implements_trait_with_env<'tcx>(
+    tcx: TyCtxt<'tcx>,
+    param_env: ParamEnv<'tcx>,
+    ty: Ty<'tcx>,
+    trait_id: DefId,
+    ty_params: &[GenericArg<'tcx>],
 ) -> bool {
     // Clippy shouldn't have infer types
     assert!(!ty.needs_infer());
 
-    let ty = cx.tcx.erase_regions(ty);
+    let ty = tcx.erase_regions(ty);
     if ty.has_escaping_bound_vars() {
         return false;
     }
-    let ty_params = cx.tcx.mk_substs(ty_params.iter());
-    cx.tcx.infer_ctxt().enter(|infcx| {
+    let ty_params = tcx.mk_substs(ty_params.iter());
+    tcx.infer_ctxt().enter(|infcx| {
         infcx
-            .type_implements_trait(trait_id, ty, ty_params, cx.param_env)
+            .type_implements_trait(trait_id, ty, ty_params, param_env)
             .must_apply_modulo_regions()
     })
 }