about summary refs log tree commit diff
diff options
context:
space:
mode:
authorChayim Refael Friedman <chayimfr@gmail.com>2025-09-04 22:36:31 +0300
committerChayim Refael Friedman <chayimfr@gmail.com>2025-09-04 22:36:31 +0300
commit7ff5a3d277939c9a3648f2dc270ff2e9166bcf70 (patch)
treee1a002f4cddcd08863daaff5079a399edc4af891
parent2127c2df5d669bbed19f7a184ad90c8e2cb671d3 (diff)
downloadrust-7ff5a3d277939c9a3648f2dc270ff2e9166bcf70.tar.gz
rust-7ff5a3d277939c9a3648f2dc270ff2e9166bcf70.zip
Upgrade rustc crates
The main changes are (there are some other small changes):

 - Using a specific type for trait IDs in the new solver, allowing us to simplify a lot of code.
 - Add `BoundConst` similar to `BoundTy` and `BoundRegion` (previously consts used `BoundVar` directly), due to a new trait requirement.
-rw-r--r--src/tools/rust-analyzer/Cargo.lock77
-rw-r--r--src/tools/rust-analyzer/Cargo.toml16
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/display.rs12
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/dyn_compatibility.rs72
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/lower_nextsolver.rs64
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/lower_nextsolver/path.rs5
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/method_resolution.rs6
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/consts.rs29
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/def_id.rs57
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/fold.rs8
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/fulfill.rs2
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/generic_arg.rs2
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/canonical/instantiate.rs3
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/mod.rs6
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/relate/higher_ranked.rs8
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/interner.rs511
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/ir_print.rs10
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/mapping.rs32
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/predicate.rs8
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/solver.rs8
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/ty.rs27
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/next_solver/util.rs28
-rw-r--r--src/tools/rust-analyzer/crates/hir-ty/src/utils.rs5
-rw-r--r--src/tools/rust-analyzer/crates/hir/src/lib.rs29
24 files changed, 446 insertions, 579 deletions
diff --git a/src/tools/rust-analyzer/Cargo.lock b/src/tools/rust-analyzer/Cargo.lock
index b008aa1c50f..344e6d101fe 100644
--- a/src/tools/rust-analyzer/Cargo.lock
+++ b/src/tools/rust-analyzer/Cargo.lock
@@ -1360,7 +1360,7 @@ dependencies = [
  "expect-test",
  "intern",
  "parser",
- "ra-ap-rustc_lexer 0.123.0",
+ "ra-ap-rustc_lexer",
  "rustc-hash 2.1.1",
  "smallvec",
  "span",
@@ -1596,8 +1596,8 @@ dependencies = [
  "drop_bomb",
  "edition",
  "expect-test",
- "ra-ap-rustc_lexer 0.123.0",
- "rustc-literal-escaper",
+ "ra-ap-rustc_lexer",
+ "rustc-literal-escaper 0.0.4",
  "stdx",
  "tracing",
 ]
@@ -1717,7 +1717,7 @@ dependencies = [
  "object",
  "paths",
  "proc-macro-test",
- "ra-ap-rustc_lexer 0.123.0",
+ "ra-ap-rustc_lexer",
  "span",
  "syntax-bridge",
  "temp-dir",
@@ -1863,9 +1863,9 @@ dependencies = [
 
 [[package]]
 name = "ra-ap-rustc_abi"
-version = "0.123.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "f18c877575c259d127072e9bfc41d985202262fb4d6bfdae3d1252147c2562c2"
+checksum = "0c6789d94fb3e6e30d62f55e99a321ba63484a8bb3b4ead338687c9ddc282d28"
 dependencies = [
  "bitflags 2.9.1",
  "ra-ap-rustc_hashes",
@@ -1875,24 +1875,24 @@ dependencies = [
 
 [[package]]
 name = "ra-ap-rustc_ast_ir"
-version = "0.123.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "87cc17e8ce797f2a8d03b838fbf166749b876164432ce81e37d283bf69e3cf80"
+checksum = "aaab80bda0f05e9842e3afb7779b0bad0a4b54e0f7ba6deb5705dcf86482811d"
 
 [[package]]
 name = "ra-ap-rustc_hashes"
-version = "0.123.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "2439ed1df3472443133b66949f81080dff88089b42f825761455463709ee1cad"
+checksum = "64bd405e538102b5f699241794b2eefee39d5414c0e4bc72435e91430c51f905"
 dependencies = [
  "rustc-stable-hash",
 ]
 
 [[package]]
 name = "ra-ap-rustc_index"
-version = "0.123.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "57a24fe0be21be1f8ebc21dcb40129214fb4cefb0f2753f3d46b6dbe656a1a45"
+checksum = "521621e271aa03b8433dad5981838278d6cfd7d2d8c9f4eb6d427f1d671f90fc"
 dependencies = [
  "ra-ap-rustc_index_macros",
  "smallvec",
@@ -1900,9 +1900,9 @@ dependencies = [
 
 [[package]]
 name = "ra-ap-rustc_index_macros"
-version = "0.123.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "844a27ddcad0116facae2df8e741fd788662cf93dc13029cd864f2b8013b81f9"
+checksum = "245e30f2e1fef258913cc548b36f575549c8af31cbc4649929d21deda96ceeb7"
 dependencies = [
  "proc-macro2",
  "quote",
@@ -1911,20 +1911,9 @@ dependencies = [
 
 [[package]]
 name = "ra-ap-rustc_lexer"
-version = "0.121.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "22944e31fb91e9b3e75bcbc91e37d958b8c0825a6160927f2856831d2ce83b36"
-dependencies = [
- "memchr",
- "unicode-properties",
- "unicode-xid",
-]
-
-[[package]]
-name = "ra-ap-rustc_lexer"
-version = "0.123.0"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "2b734cfcb577d09877799a22742f1bd398be6c00bc428d9de56d48d11ece5771"
+checksum = "a82681f924500e888c860e60ed99e9bf702a219a69374f59116c4261525a2157"
 dependencies = [
  "memchr",
  "unicode-properties",
@@ -1933,9 +1922,9 @@ dependencies = [
 
 [[package]]
 name = "ra-ap-rustc_next_trait_solver"
-version = "0.123.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "14f7dfbdf1d045ff4e385e1efdfc3799379895e9c3f3b9b379a0bef4cb238441"
+checksum = "0c9ce51f2431fbdc7fabd2d957522b6e27f41f68ec2af74b52a6f4116352ce1a"
 dependencies = [
  "derive-where",
  "ra-ap-rustc_index",
@@ -1946,19 +1935,19 @@ dependencies = [
 
 [[package]]
 name = "ra-ap-rustc_parse_format"
-version = "0.121.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "81057891bc2063ad9e353f29462fbc47a0f5072560af34428ae9313aaa5e9d97"
+checksum = "adc85ef3fdb6c084bde84857d8948dc66b752129dc8417a8614ce490e99a143f"
 dependencies = [
- "ra-ap-rustc_lexer 0.121.0",
- "rustc-literal-escaper",
+ "ra-ap-rustc_lexer",
+ "rustc-literal-escaper 0.0.5",
 ]
 
 [[package]]
 name = "ra-ap-rustc_pattern_analysis"
-version = "0.123.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "75b0ee1f059b9dea0818c6c7267478926eee95ba4c7dcf89c8db32fa165d3904"
+checksum = "3cd81eccf33d9528905d4e5abaa254b3129a6405d6c5f123fed9b73a3d217f35"
 dependencies = [
  "ra-ap-rustc_index",
  "rustc-hash 2.1.1",
@@ -1969,9 +1958,9 @@ dependencies = [
 
 [[package]]
 name = "ra-ap-rustc_type_ir"
-version = "0.123.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "0bc59fb10a922c38a24cb8a1494f799b0af30bd041acbea689378d3bf330534b"
+checksum = "11cb0da02853698d9c89e1d1c01657b9969752befd56365e8899d4310e52b373"
 dependencies = [
  "bitflags 2.9.1",
  "derive-where",
@@ -1988,9 +1977,9 @@ dependencies = [
 
 [[package]]
 name = "ra-ap-rustc_type_ir_macros"
-version = "0.123.0"
+version = "0.126.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "58878914b6dac7499baeecc8dbb4b9d9dda88030e4ab90cd3b4e87523fbedafe"
+checksum = "ffc93adeb52c483ede13bee6680466458218243ab479c04fb71bb53925a6e0ff"
 dependencies = [
  "proc-macro2",
  "quote",
@@ -2141,6 +2130,12 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "ab03008eb631b703dd16978282ae36c73282e7922fe101a4bd072a40ecea7b8b"
 
 [[package]]
+name = "rustc-literal-escaper"
+version = "0.0.5"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "e4ee29da77c5a54f42697493cd4c9b9f31b74df666a6c04dfc4fde77abe0438b"
+
+[[package]]
 name = "rustc-stable-hash"
 version = "0.1.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -2445,7 +2440,7 @@ dependencies = [
  "rayon",
  "rowan",
  "rustc-hash 2.1.1",
- "rustc-literal-escaper",
+ "rustc-literal-escaper 0.0.4",
  "rustc_apfloat",
  "smol_str",
  "stdx",
@@ -2773,7 +2768,7 @@ version = "0.0.0"
 dependencies = [
  "arrayvec",
  "intern",
- "ra-ap-rustc_lexer 0.123.0",
+ "ra-ap-rustc_lexer",
  "stdx",
  "text-size",
 ]
diff --git a/src/tools/rust-analyzer/Cargo.toml b/src/tools/rust-analyzer/Cargo.toml
index 05ee190480c..f325027ee58 100644
--- a/src/tools/rust-analyzer/Cargo.toml
+++ b/src/tools/rust-analyzer/Cargo.toml
@@ -89,14 +89,14 @@ vfs-notify = { path = "./crates/vfs-notify", version = "0.0.0" }
 vfs = { path = "./crates/vfs", version = "0.0.0" }
 edition = { path = "./crates/edition", version = "0.0.0" }
 
-ra-ap-rustc_lexer = { version = "0.123", default-features = false }
-ra-ap-rustc_parse_format = { version = "0.121", default-features = false }
-ra-ap-rustc_index = { version = "0.123", default-features = false }
-ra-ap-rustc_abi = { version = "0.123", default-features = false }
-ra-ap-rustc_pattern_analysis = { version = "0.123", default-features = false }
-ra-ap-rustc_ast_ir = { version = "0.123", default-features = false }
-ra-ap-rustc_type_ir = { version = "0.123", default-features = false }
-ra-ap-rustc_next_trait_solver = { version = "0.123", default-features = false }
+ra-ap-rustc_lexer = { version = "0.126", default-features = false }
+ra-ap-rustc_parse_format = { version = "0.126", default-features = false }
+ra-ap-rustc_index = { version = "0.126", default-features = false }
+ra-ap-rustc_abi = { version = "0.126", default-features = false }
+ra-ap-rustc_pattern_analysis = { version = "0.126", default-features = false }
+ra-ap-rustc_ast_ir = { version = "0.126", default-features = false }
+ra-ap-rustc_type_ir = { version = "0.126", default-features = false }
+ra-ap-rustc_next_trait_solver = { version = "0.126", default-features = false }
 
 # local crates that aren't published to crates.io. These should not have versions.
 
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/display.rs b/src/tools/rust-analyzer/crates/hir-ty/src/display.rs
index 5b8093f6b72..fcb79e9ffb5 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/display.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/display.rs
@@ -737,7 +737,7 @@ impl<'db> HirDisplay for crate::next_solver::Const<'db> {
         match self.kind() {
             rustc_type_ir::ConstKind::Placeholder(_) => write!(f, "<placeholder>"),
             rustc_type_ir::ConstKind::Bound(db, bound_const) => {
-                write!(f, "?{}.{}", db.as_u32(), bound_const.as_u32())
+                write!(f, "?{}.{}", db.as_u32(), bound_const.var.as_u32())
             }
             rustc_type_ir::ConstKind::Infer(..) => write!(f, "#c#"),
             rustc_type_ir::ConstKind::Param(param) => {
@@ -1208,10 +1208,7 @@ impl<'db> HirDisplay for crate::next_solver::Ty<'db> {
                 let contains_impl_fn_ns = |bounds: &[BoundExistentialPredicate<'_>]| {
                     bounds.iter().any(|bound| match bound.skip_binder() {
                         rustc_type_ir::ExistentialPredicate::Trait(trait_ref) => {
-                            let trait_ = match trait_ref.def_id {
-                                SolverDefId::TraitId(id) => id,
-                                _ => unreachable!(),
-                            };
+                            let trait_ = trait_ref.def_id.0;
                             fn_traits(db, trait_).any(|it| it == trait_)
                         }
                         _ => false,
@@ -2217,10 +2214,7 @@ impl HirDisplay for TraitRef {
 
 impl<'db> HirDisplay for crate::next_solver::TraitRef<'db> {
     fn hir_fmt(&self, f: &mut HirFormatter<'_>) -> Result<(), HirDisplayError> {
-        let trait_ = match self.def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => unreachable!(),
-        };
+        let trait_ = self.def_id.0;
         f.start_location_link(trait_.into());
         write!(f, "{}", f.db.trait_signature(trait_).name.display(f.db, f.edition()))?;
         f.end_location_link();
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/dyn_compatibility.rs b/src/tools/rust-analyzer/crates/hir-ty/src/dyn_compatibility.rs
index 23280b1f3b4..d4b3751cf56 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/dyn_compatibility.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/dyn_compatibility.rs
@@ -2,12 +2,11 @@
 
 use std::ops::ControlFlow;
 
-use hir_def::hir::generics::LocalTypeOrConstParamId;
 use hir_def::{
     AssocItemId, ConstId, CrateRootModuleId, FunctionId, GenericDefId, HasModule, TraitId,
-    TypeAliasId, lang_item::LangItem, signatures::TraitFlags,
+    TypeAliasId, TypeOrConstParamId, TypeParamId, hir::generics::LocalTypeOrConstParamId,
+    lang_item::LangItem, signatures::TraitFlags,
 };
-use hir_def::{TypeOrConstParamId, TypeParamId};
 use intern::Symbol;
 use rustc_hash::FxHashSet;
 use rustc_type_ir::{
@@ -22,7 +21,7 @@ use crate::{
     db::{HirDatabase, InternedOpaqueTyId},
     lower_nextsolver::associated_ty_item_bounds,
     next_solver::{
-        Clause, Clauses, DbInterner, GenericArgs, ParamEnv, SolverDefId, TraitPredicate,
+        Clause, Clauses, DbInterner, GenericArgs, ParamEnv, SolverDefId, TraitPredicate, TraitRef,
         TypingMode, infer::DbInternerInferExt, mk_param,
     },
     traits::next_trait_solve_in_ctxt,
@@ -56,16 +55,12 @@ pub fn dyn_compatibility(
     trait_: TraitId,
 ) -> Option<DynCompatibilityViolation> {
     let interner = DbInterner::new_with(db, Some(trait_.krate(db)), None);
-    for super_trait in elaborate::supertrait_def_ids(interner, SolverDefId::TraitId(trait_)) {
-        let super_trait = match super_trait {
-            SolverDefId::TraitId(id) => id,
-            _ => unreachable!(),
-        };
-        if let Some(v) = db.dyn_compatibility_of_trait(super_trait) {
-            return if super_trait == trait_ {
+    for super_trait in elaborate::supertrait_def_ids(interner, trait_.into()) {
+        if let Some(v) = db.dyn_compatibility_of_trait(super_trait.0) {
+            return if super_trait.0 == trait_ {
                 Some(v)
             } else {
-                Some(DynCompatibilityViolation::HasNonCompatibleSuperTrait(super_trait))
+                Some(DynCompatibilityViolation::HasNonCompatibleSuperTrait(super_trait.0))
             };
         }
     }
@@ -82,13 +77,8 @@ where
     F: FnMut(DynCompatibilityViolation) -> ControlFlow<()>,
 {
     let interner = DbInterner::new_with(db, Some(trait_.krate(db)), None);
-    for super_trait in elaborate::supertrait_def_ids(interner, SolverDefId::TraitId(trait_)).skip(1)
-    {
-        let super_trait = match super_trait {
-            SolverDefId::TraitId(id) => id,
-            _ => unreachable!(),
-        };
-        if db.dyn_compatibility_of_trait(super_trait).is_some() {
+    for super_trait in elaborate::supertrait_def_ids(interner, trait_.into()).skip(1) {
+        if db.dyn_compatibility_of_trait(super_trait.0).is_some() {
             cb(DynCompatibilityViolation::HasNonCompatibleSuperTrait(trait_))?;
         }
     }
@@ -151,7 +141,7 @@ pub fn generics_require_sized_self(db: &dyn HirDatabase, def: GenericDefId) -> b
     elaborate::elaborate(interner, predicates.iter().copied()).any(|pred| {
         match pred.kind().skip_binder() {
             ClauseKind::Trait(trait_pred) => {
-                if SolverDefId::TraitId(sized) == trait_pred.def_id()
+                if sized == trait_pred.def_id().0
                     && let rustc_type_ir::TyKind::Param(param_ty) =
                         trait_pred.trait_ref.self_ty().kind()
                     && param_ty.index == 0
@@ -257,15 +247,9 @@ fn contains_illegal_self_type_reference<'db, T: rustc_type_ir::TypeVisitable<DbI
                         };
                         if self.super_traits.is_none() {
                             self.super_traits = Some(
-                                elaborate::supertrait_def_ids(
-                                    interner,
-                                    SolverDefId::TraitId(self.trait_),
-                                )
-                                .map(|super_trait| match super_trait {
-                                    SolverDefId::TraitId(id) => id,
-                                    _ => unreachable!(),
-                                })
-                                .collect(),
+                                elaborate::supertrait_def_ids(interner, self.trait_.into())
+                                    .map(|super_trait| super_trait.0)
+                                    .collect(),
                             )
                         }
                         if self.super_traits.as_ref().is_some_and(|s| s.contains(&trait_)) {
@@ -390,8 +374,7 @@ where
             trait_ref: pred_trait_ref,
             polarity: PredicatePolarity::Positive,
         }) = pred
-            && let SolverDefId::TraitId(trait_id) = pred_trait_ref.def_id
-            && let trait_data = db.trait_signature(trait_id)
+            && let trait_data = db.trait_signature(pred_trait_ref.def_id.0)
             && trait_data.flags.contains(TraitFlags::AUTO)
             && let rustc_type_ir::TyKind::Param(crate::next_solver::ParamTy { index: 0, .. }) =
                 pred_trait_ref.self_ty().kind()
@@ -464,25 +447,17 @@ fn receiver_is_dispatchable<'db>(
         let generic_predicates = &*db.generic_predicates_ns(func.into());
 
         // Self: Unsize<U>
-        let unsize_predicate = crate::next_solver::TraitRef::new(
-            interner,
-            SolverDefId::TraitId(unsize_did),
-            [self_param_ty, unsized_self_ty],
-        );
+        let unsize_predicate =
+            TraitRef::new(interner, unsize_did.into(), [self_param_ty, unsized_self_ty]);
 
         // U: Trait<Arg1, ..., ArgN>
-        let trait_def_id = SolverDefId::TraitId(trait_);
-        let args = GenericArgs::for_item(interner, trait_def_id, |name, index, kind, _| {
+        let args = GenericArgs::for_item(interner, trait_.into(), |name, index, kind, _| {
             if index == 0 { unsized_self_ty.into() } else { mk_param(interner, index, name, kind) }
         });
-        let trait_predicate =
-            crate::next_solver::TraitRef::new_from_args(interner, trait_def_id, args);
+        let trait_predicate = TraitRef::new_from_args(interner, trait_.into(), args);
 
-        let meta_sized_predicate = crate::next_solver::TraitRef::new(
-            interner,
-            SolverDefId::TraitId(meta_sized_did),
-            [unsized_self_ty],
-        );
+        let meta_sized_predicate =
+            TraitRef::new(interner, meta_sized_did.into(), [unsized_self_ty]);
 
         ParamEnv {
             clauses: Clauses::new_from_iter(
@@ -497,11 +472,8 @@ fn receiver_is_dispatchable<'db>(
     };
 
     // Receiver: DispatchFromDyn<Receiver[Self => U]>
-    let predicate = crate::next_solver::TraitRef::new(
-        interner,
-        SolverDefId::TraitId(dispatch_from_dyn_did),
-        [receiver_ty, unsized_receiver_ty],
-    );
+    let predicate =
+        TraitRef::new(interner, dispatch_from_dyn_did.into(), [receiver_ty, unsized_receiver_ty]);
     let goal = crate::next_solver::Goal::new(interner, param_env, predicate);
 
     let infcx = interner.infer_ctxt().build(TypingMode::non_body_analysis());
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/lower_nextsolver.rs b/src/tools/rust-analyzer/crates/hir-ty/src/lower_nextsolver.rs
index 4578922ce32..c6a8fa81edf 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/lower_nextsolver.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/lower_nextsolver.rs
@@ -590,11 +590,9 @@ impl<'db, 'a> TyLoweringContext<'db, 'a> {
                         .resolve_trait(ctx.ty_ctx().db, ctx.ty_ctx().resolver.krate());
                     let pointee_sized = LangItem::PointeeSized
                         .resolve_trait(ctx.ty_ctx().db, ctx.ty_ctx().resolver.krate());
-                    if meta_sized.is_some_and(|it| SolverDefId::TraitId(it) == trait_ref.def_id) {
+                    if meta_sized.is_some_and(|it| it == trait_ref.def_id.0) {
                         // Ignore this bound
-                    } else if pointee_sized
-                        .is_some_and(|it| SolverDefId::TraitId(it) == trait_ref.def_id)
-                    {
+                    } else if pointee_sized.is_some_and(|it| it == trait_ref.def_id.0) {
                         // Regard this as `?Sized` bound
                         ctx.ty_ctx().unsized_types.insert(self_ty);
                     } else {
@@ -618,13 +616,9 @@ impl<'db, 'a> TyLoweringContext<'db, 'a> {
                 // Don't lower associated type bindings as the only possible relaxed trait bound
                 // `?Sized` has no of them.
                 // If we got another trait here ignore the bound completely.
-                let trait_id =
-                    self.lower_trait_ref_from_path(path, self_ty).map(|(trait_ref, _)| {
-                        match trait_ref.def_id {
-                            SolverDefId::TraitId(id) => id,
-                            _ => unreachable!(),
-                        }
-                    });
+                let trait_id = self
+                    .lower_trait_ref_from_path(path, self_ty)
+                    .map(|(trait_ref, _)| trait_ref.def_id.0);
                 if trait_id == sized_trait {
                     self.unsized_types.insert(self_ty);
                 }
@@ -668,12 +662,8 @@ impl<'db, 'a> TyLoweringContext<'db, 'a> {
                         .map_bound(|c| match c {
                             rustc_type_ir::ClauseKind::Trait(t) => {
                                 let id = t.def_id();
-                                let id = match id {
-                                    SolverDefId::TraitId(id) => id,
-                                    _ => unreachable!(),
-                                };
                                 let is_auto =
-                                    db.trait_signature(id).flags.contains(TraitFlags::AUTO);
+                                    db.trait_signature(id.0).flags.contains(TraitFlags::AUTO);
                                 if is_auto {
                                     Some(ExistentialPredicate::AutoTrait(t.def_id()))
                                 } else {
@@ -733,17 +723,7 @@ impl<'db, 'a> TyLoweringContext<'db, 'a> {
                     (
                         ExistentialPredicate::AutoTrait(lhs_id),
                         ExistentialPredicate::AutoTrait(rhs_id),
-                    ) => {
-                        let lhs_id = match lhs_id {
-                            SolverDefId::TraitId(id) => id,
-                            _ => unreachable!(),
-                        };
-                        let rhs_id = match rhs_id {
-                            SolverDefId::TraitId(id) => id,
-                            _ => unreachable!(),
-                        };
-                        lhs_id.cmp(&rhs_id)
-                    }
+                    ) => lhs_id.0.cmp(&rhs_id.0),
                     (ExistentialPredicate::Trait(_), _) => Ordering::Less,
                     (_, ExistentialPredicate::Trait(_)) => Ordering::Greater,
                     (ExistentialPredicate::AutoTrait(_), _) => Ordering::Less,
@@ -1195,11 +1175,7 @@ pub(crate) fn generic_predicates_for_param_query<'db>(
                     };
 
                     rustc_type_ir::elaborate::supertrait_def_ids(interner, tr.into()).any(|tr| {
-                        let tr = match tr {
-                            SolverDefId::TraitId(id) => id,
-                            _ => unreachable!(),
-                        };
-                        tr.trait_items(db).items.iter().any(|(name, item)| {
+                        tr.0.trait_items(db).items.iter().any(|(name, item)| {
                             matches!(item, AssocItemId::TypeAliasId(_)) && name == assoc_name
                         })
                     })
@@ -1629,11 +1605,7 @@ pub(crate) fn associated_ty_item_bounds<'db>(
                 .map_bound(|c| match c {
                     rustc_type_ir::ClauseKind::Trait(t) => {
                         let id = t.def_id();
-                        let id = match id {
-                            SolverDefId::TraitId(id) => id,
-                            _ => unreachable!(),
-                        };
-                        let is_auto = db.trait_signature(id).flags.contains(TraitFlags::AUTO);
+                        let is_auto = db.trait_signature(id.0).flags.contains(TraitFlags::AUTO);
                         if is_auto {
                             Some(ExistentialPredicate::AutoTrait(t.def_id()))
                         } else {
@@ -1677,7 +1649,7 @@ pub(crate) fn associated_ty_item_bounds<'db>(
         let sized_trait = LangItem::Sized.resolve_trait(db, resolver.krate());
         let sized_clause = Binder::dummy(ExistentialPredicate::Trait(ExistentialTraitRef::new(
             interner,
-            SolverDefId::TraitId(trait_),
+            trait_.into(),
             [] as [crate::next_solver::GenericArg<'_>; 0],
         )));
         bounds.push(sized_clause);
@@ -1694,10 +1666,7 @@ pub(crate) fn associated_type_by_name_including_super_traits<'db>(
 ) -> Option<(TraitRef<'db>, TypeAliasId)> {
     let interner = DbInterner::new_with(db, None, None);
     rustc_type_ir::elaborate::supertraits(interner, Binder::dummy(trait_ref)).find_map(|t| {
-        let trait_id = match t.as_ref().skip_binder().def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => unreachable!(),
-        };
+        let trait_id = t.as_ref().skip_binder().def_id.0;
         let assoc_type = trait_id.trait_items(db).associated_type_by_name(name)?;
         Some((t.skip_binder(), assoc_type))
     })
@@ -1727,10 +1696,7 @@ fn named_associated_type_shorthand_candidates<'db, R>(
 ) -> Option<R> {
     let db = interner.db;
     let mut search = |t: TraitRef<'db>| -> Option<R> {
-        let trait_id = match t.def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => unreachable!(),
-        };
+        let trait_id = t.def_id.0;
         let mut checked_traits = FxHashSet::default();
         let mut check_trait = |trait_id: TraitId| {
             let name = &db.trait_signature(trait_id).name;
@@ -1773,11 +1739,7 @@ fn named_associated_type_shorthand_candidates<'db, R>(
                     rustc_type_ir::ClauseKind::Trait(pred) => pred.def_id(),
                     _ => continue,
                 };
-                let trait_id = match trait_id {
-                    SolverDefId::TraitId(trait_id) => trait_id,
-                    _ => continue,
-                };
-                stack.push(trait_id);
+                stack.push(trait_id.0);
             }
             tracing::debug!(?stack);
         }
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/lower_nextsolver/path.rs b/src/tools/rust-analyzer/crates/hir-ty/src/lower_nextsolver/path.rs
index ccdb5a0bdb4..7d6734303c4 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/lower_nextsolver/path.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/lower_nextsolver/path.rs
@@ -208,10 +208,7 @@ impl<'a, 'b, 'db> PathLoweringContext<'a, 'b, 'db> {
                         tracing::debug!(?trait_ref);
                         self.skip_resolved_segment();
                         let segment = self.current_or_prev_segment;
-                        let trait_id = match trait_ref.def_id {
-                            SolverDefId::TraitId(id) => id,
-                            _ => unreachable!(),
-                        };
+                        let trait_id = trait_ref.def_id.0;
                         let found =
                             trait_id.trait_items(self.ctx.db).associated_type_by_name(segment.name);
 
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/method_resolution.rs b/src/tools/rust-analyzer/crates/hir-ty/src/method_resolution.rs
index 8bd71df7c19..f0be352fdd1 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/method_resolution.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/method_resolution.rs
@@ -168,11 +168,7 @@ impl TyFingerprint {
                         _ => None,
                     })
                     .next()?;
-                let trait_id = match trait_ref {
-                    SolverDefId::TraitId(id) => id,
-                    _ => panic!("Bad GenericDefId in trait ref"),
-                };
-                TyFingerprint::Dyn(trait_id)
+                TyFingerprint::Dyn(trait_ref.0)
             }
             TyKind::Ref(_, _, mutability) => match mutability {
                 rustc_ast_ir::Mutability::Mut => TyFingerprint::Ref(Mutability::Mut),
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/consts.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/consts.rs
index cfafc65d184..23789b06e82 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/consts.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/consts.rs
@@ -81,7 +81,7 @@ impl<'db> std::fmt::Debug for InternedWrapperNoDebug<WithCachedTypeInfo<ConstKin
     }
 }
 
-pub type PlaceholderConst = Placeholder<rustc_type_ir::BoundVar>;
+pub type PlaceholderConst = Placeholder<BoundConst>;
 
 #[derive(Copy, Clone, Hash, Eq, PartialEq)]
 pub struct ParamConst {
@@ -304,7 +304,7 @@ impl<'db> rustc_type_ir::inherent::Const<DbInterner<'db>> for Const<'db> {
     fn new_bound(
         interner: DbInterner<'db>,
         debruijn: rustc_type_ir::DebruijnIndex,
-        var: BoundVar,
+        var: BoundConst,
     ) -> Self {
         Const::new(interner, ConstKind::Bound(debruijn, var))
     }
@@ -314,7 +314,7 @@ impl<'db> rustc_type_ir::inherent::Const<DbInterner<'db>> for Const<'db> {
         debruijn: rustc_type_ir::DebruijnIndex,
         var: rustc_type_ir::BoundVar,
     ) -> Self {
-        Const::new(interner, ConstKind::Bound(debruijn, var))
+        Const::new(interner, ConstKind::Bound(debruijn, BoundConst { var }))
     }
 
     fn new_unevaluated(
@@ -340,26 +340,41 @@ impl<'db> rustc_type_ir::inherent::Const<DbInterner<'db>> for Const<'db> {
     }
 }
 
+#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
+pub struct BoundConst {
+    pub var: BoundVar,
+}
+
+impl<'db> rustc_type_ir::inherent::BoundVarLike<DbInterner<'db>> for BoundConst {
+    fn var(self) -> BoundVar {
+        self.var
+    }
+
+    fn assert_eq(self, var: BoundVarKind) {
+        var.expect_const()
+    }
+}
+
 impl<'db> PlaceholderLike<DbInterner<'db>> for PlaceholderConst {
-    type Bound = rustc_type_ir::BoundVar;
+    type Bound = BoundConst;
 
     fn universe(self) -> rustc_type_ir::UniverseIndex {
         self.universe
     }
 
     fn var(self) -> rustc_type_ir::BoundVar {
-        self.bound
+        self.bound.var
     }
 
     fn with_updated_universe(self, ui: rustc_type_ir::UniverseIndex) -> Self {
         Placeholder { universe: ui, bound: self.bound }
     }
 
-    fn new(ui: rustc_type_ir::UniverseIndex, var: rustc_type_ir::BoundVar) -> Self {
+    fn new(ui: rustc_type_ir::UniverseIndex, var: BoundConst) -> Self {
         Placeholder { universe: ui, bound: var }
     }
     fn new_anon(ui: rustc_type_ir::UniverseIndex, var: rustc_type_ir::BoundVar) -> Self {
-        Placeholder { universe: ui, bound: var }
+        Placeholder { universe: ui, bound: BoundConst { var } }
     }
 }
 
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/def_id.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/def_id.rs
index c9632ddcd4b..8bbc6e33703 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/def_id.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/def_id.rs
@@ -88,3 +88,60 @@ impl<'db> inherent::DefId<DbInterner<'db>> for SolverDefId {
         true
     }
 }
+
+macro_rules! declare_id_wrapper {
+    ($name:ident, $wraps:ident) => {
+        #[derive(Clone, Copy, PartialEq, Eq, Hash)]
+        pub struct $name(pub $wraps);
+
+        impl std::fmt::Debug for $name {
+            fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
+                std::fmt::Debug::fmt(&self.0, f)
+            }
+        }
+
+        impl From<$name> for $wraps {
+            #[inline]
+            fn from(value: $name) -> $wraps {
+                value.0
+            }
+        }
+
+        impl From<$wraps> for $name {
+            #[inline]
+            fn from(value: $wraps) -> $name {
+                Self(value)
+            }
+        }
+
+        impl From<$name> for SolverDefId {
+            #[inline]
+            fn from(value: $name) -> SolverDefId {
+                value.0.into()
+            }
+        }
+
+        impl TryFrom<SolverDefId> for $name {
+            type Error = ();
+
+            #[inline]
+            fn try_from(value: SolverDefId) -> Result<Self, Self::Error> {
+                match value {
+                    SolverDefId::$wraps(it) => Ok(Self(it)),
+                    _ => Err(()),
+                }
+            }
+        }
+
+        impl<'db> inherent::DefId<DbInterner<'db>> for $name {
+            fn as_local(self) -> Option<SolverDefId> {
+                Some(self.into())
+            }
+            fn is_local(self) -> bool {
+                true
+            }
+        }
+    };
+}
+
+declare_id_wrapper!(TraitIdWrapper, TraitId);
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/fold.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/fold.rs
index 3cc1e64b6ad..405a57d9e89 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/fold.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/fold.rs
@@ -6,6 +6,8 @@ use rustc_type_ir::{
     inherent::{IntoKind, Region as _},
 };
 
+use crate::next_solver::BoundConst;
+
 use super::{
     Binder, BoundRegion, BoundTy, Const, ConstKind, DbInterner, Predicate, Region, Ty, TyKind,
 };
@@ -18,7 +20,7 @@ use super::{
 pub trait BoundVarReplacerDelegate<'db> {
     fn replace_region(&mut self, br: BoundRegion) -> Region<'db>;
     fn replace_ty(&mut self, bt: BoundTy) -> Ty<'db>;
-    fn replace_const(&mut self, bv: BoundVar) -> Const<'db>;
+    fn replace_const(&mut self, bv: BoundConst) -> Const<'db>;
 }
 
 /// A simple delegate taking 3 mutable functions. The used functions must
@@ -27,7 +29,7 @@ pub trait BoundVarReplacerDelegate<'db> {
 pub struct FnMutDelegate<'db, 'a> {
     pub regions: &'a mut (dyn FnMut(BoundRegion) -> Region<'db> + 'a),
     pub types: &'a mut (dyn FnMut(BoundTy) -> Ty<'db> + 'a),
-    pub consts: &'a mut (dyn FnMut(BoundVar) -> Const<'db> + 'a),
+    pub consts: &'a mut (dyn FnMut(BoundConst) -> Const<'db> + 'a),
 }
 
 impl<'db, 'a> BoundVarReplacerDelegate<'db> for FnMutDelegate<'db, 'a> {
@@ -37,7 +39,7 @@ impl<'db, 'a> BoundVarReplacerDelegate<'db> for FnMutDelegate<'db, 'a> {
     fn replace_ty(&mut self, bt: BoundTy) -> Ty<'db> {
         (self.types)(bt)
     }
-    fn replace_const(&mut self, bv: BoundVar) -> Const<'db> {
+    fn replace_const(&mut self, bv: BoundConst) -> Const<'db> {
         (self.consts)(bv)
     }
 }
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/fulfill.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/fulfill.rs
index 007a674ad39..4258f4c7ac6 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/fulfill.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/fulfill.rs
@@ -167,7 +167,7 @@ impl<'db> FulfillmentCtxt<'db> {
                 }
 
                 let result = delegate.evaluate_root_goal(goal, Span::dummy(), stalled_on);
-                let GoalEvaluation { certainty, has_changed, stalled_on } = match result {
+                let GoalEvaluation { goal: _, certainty, has_changed, stalled_on } = match result {
                     Ok(result) => result,
                     Err(NoSolution) => {
                         errors.push(NextSolverError::TrueError(obligation));
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/generic_arg.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/generic_arg.rs
index d284eb9c6b4..4e124d07d2b 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/generic_arg.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/generic_arg.rs
@@ -384,7 +384,6 @@ impl<'db> rustc_type_ir::inherent::GenericArgs<DbInterner<'db>> for GenericArgs<
                 signature_parts_ty: signature_parts_ty.expect_ty(),
                 tupled_upvars_ty: tupled_upvars_ty.expect_ty(),
                 coroutine_captures_by_ref_ty: coroutine_captures_by_ref_ty.expect_ty(),
-                coroutine_witness_ty: coroutine_witness_ty.expect_ty(),
             },
             _ => panic!("GenericArgs were likely not for a CoroutineClosure."),
         }
@@ -400,7 +399,6 @@ impl<'db> rustc_type_ir::inherent::GenericArgs<DbInterner<'db>> for GenericArgs<
                     resume_ty: resume_ty.expect_ty(),
                     yield_ty: yield_ty.expect_ty(),
                     return_ty: return_ty.expect_ty(),
-                    witness: Ty::new_unit(interner),
                     tupled_upvars_ty: Ty::new_unit(interner),
                 }
             }
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/canonical/instantiate.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/canonical/instantiate.rs
index 0448f03463e..6c7a87ef524 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/canonical/instantiate.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/canonical/instantiate.rs
@@ -6,6 +6,7 @@
 //!
 //! [c]: https://rust-lang.github.io/chalk/book/canonical_queries/canonicalization.html
 
+use crate::next_solver::BoundConst;
 use crate::next_solver::{
     AliasTy, Binder, BoundRegion, BoundTy, Canonical, CanonicalVarValues, Const, DbInterner, Goal,
     ParamEnv, Predicate, PredicateKind, Region, Ty, TyKind,
@@ -95,7 +96,7 @@ where
                 GenericArgKind::Type(ty) => ty,
                 r => panic!("{bound_ty:?} is a type but value is {r:?}"),
             },
-            consts: &mut |bound_ct: BoundVar| match var_values[bound_ct].kind() {
+            consts: &mut |bound_ct: BoundConst| match var_values[bound_ct.var].kind() {
                 GenericArgKind::Const(ct) => ct,
                 c => panic!("{bound_ct:?} is a const but value is {c:?}"),
             },
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/mod.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/mod.rs
index 58832aef895..585719144ef 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/mod.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/mod.rs
@@ -37,7 +37,7 @@ use unify_key::{ConstVariableOrigin, ConstVariableValue, ConstVidKey};
 
 use crate::next_solver::fold::BoundVarReplacerDelegate;
 use crate::next_solver::infer::opaque_types::table::OpaqueTypeStorageEntries;
-use crate::next_solver::{BoundRegion, BoundTy, BoundVarKind};
+use crate::next_solver::{BoundConst, BoundRegion, BoundTy, BoundVarKind};
 
 use super::generics::GenericParamDef;
 use super::{
@@ -864,8 +864,8 @@ impl<'db> InferCtxt<'db> {
             fn replace_ty(&mut self, bt: BoundTy) -> Ty<'db> {
                 self.args[bt.var.index()].expect_ty()
             }
-            fn replace_const(&mut self, bv: BoundVar) -> Const<'db> {
-                self.args[bv.index()].expect_const()
+            fn replace_const(&mut self, bv: BoundConst) -> Const<'db> {
+                self.args[bv.var.index()].expect_const()
             }
         }
         let delegate = ToFreshVars { args };
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/relate/higher_ranked.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/relate/higher_ranked.rs
index bb80c515710..62028e0e703 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/relate/higher_ranked.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/infer/relate/higher_ranked.rs
@@ -10,8 +10,8 @@ use crate::next_solver::fold::FnMutDelegate;
 use crate::next_solver::infer::InferCtxt;
 use crate::next_solver::infer::snapshot::CombinedSnapshot;
 use crate::next_solver::{
-    Binder, BoundRegion, BoundTy, Const, DbInterner, PlaceholderConst, PlaceholderRegion,
-    PlaceholderTy, Region, Ty,
+    Binder, BoundConst, BoundRegion, BoundTy, Const, DbInterner, PlaceholderConst,
+    PlaceholderRegion, PlaceholderTy, Region, Ty,
 };
 
 impl<'db> InferCtxt<'db> {
@@ -50,10 +50,10 @@ impl<'db> InferCtxt<'db> {
                     PlaceholderTy { universe: next_universe, bound: bound_ty },
                 )
             },
-            consts: &mut |bound_var: BoundVar| {
+            consts: &mut |bound: BoundConst| {
                 Const::new_placeholder(
                     self.interner,
-                    PlaceholderConst { universe: next_universe, bound: bound_var },
+                    PlaceholderConst { universe: next_universe, bound },
                 )
             },
         };
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/interner.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/interner.rs
index 6e1a5e96455..5709beaefc2 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/interner.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/interner.rs
@@ -19,7 +19,7 @@ use rustc_type_ir::error::TypeError;
 use rustc_type_ir::inherent::{
     AdtDef as _, GenericArgs as _, GenericsOf, IntoKind, SliceLike as _, Span as _,
 };
-use rustc_type_ir::lang_items::TraitSolverLangItem;
+use rustc_type_ir::lang_items::{SolverLangItem, SolverTraitLangItem};
 use rustc_type_ir::solve::SizedTraitKind;
 use rustc_type_ir::{
     AliasTerm, AliasTermKind, AliasTy, AliasTyKind, EarlyBinder, FlagComputation, Flags,
@@ -44,9 +44,11 @@ use rustc_type_ir::{
 
 use crate::lower_nextsolver::{self, TyLoweringContext};
 use crate::method_resolution::{ALL_FLOAT_FPS, ALL_INT_FPS, TyFingerprint};
+use crate::next_solver::infer::InferCtxt;
 use crate::next_solver::util::{ContainsTypeErrors, explicit_item_bounds, for_trait_impls};
 use crate::next_solver::{
-    CanonicalVarKind, FxIndexMap, InternedWrapperNoDebug, RegionAssumptions, SolverDefIds,
+    BoundConst, CanonicalVarKind, FxIndexMap, InternedWrapperNoDebug, RegionAssumptions,
+    SolverContext, SolverDefIds, TraitIdWrapper,
 };
 use crate::{ConstScalar, FnAbi, Interner, db::HirDatabase};
 
@@ -858,10 +860,35 @@ impl<'db> rustc_type_ir::relate::Relate<DbInterner<'db>> for Pattern<'db> {
 
 interned_vec_db!(PatList, Pattern);
 
+macro_rules! as_lang_item {
+    (
+        $solver_enum:ident, $var:ident;
+
+        ignore = {
+            $( $ignore:ident ),* $(,)?
+        }
+
+        $( $variant:ident ),* $(,)?
+    ) => {{
+        // Ensure exhaustiveness.
+        if let Some(it) = None::<$solver_enum> {
+            match it {
+                $( $solver_enum::$variant => {} )*
+                $( $solver_enum::$ignore => {} )*
+            }
+        }
+        match $var {
+            $( LangItem::$variant => Some($solver_enum::$variant), )*
+            _ => None
+        }
+    }};
+}
+
 impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
     type DefId = SolverDefId;
     type LocalDefId = SolverDefId;
     type LocalDefIds = SolverDefIds;
+    type TraitId = TraitIdWrapper;
     type Span = Span;
 
     type GenericArgs = GenericArgs<'db>;
@@ -923,7 +950,7 @@ impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
     type Const = Const<'db>;
     type PlaceholderConst = PlaceholderConst;
     type ParamConst = ParamConst;
-    type BoundConst = rustc_type_ir::BoundVar;
+    type BoundConst = BoundConst;
     type ValueConst = ValueConst<'db>;
     type ValTree = Valtree<'db>;
     type ExprConst = ExprConst;
@@ -1117,7 +1144,7 @@ impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
         );
         let alias_args =
             GenericArgs::new_from_iter(self, args.iter().skip(trait_generics.own_params.len()));
-        (TraitRef::new_from_args(self, trait_def_id, trait_args), alias_args)
+        (TraitRef::new_from_args(self, trait_def_id.try_into().unwrap(), trait_args), alias_args)
     }
 
     fn check_args_compatible(self, def_id: Self::DefId, args: Self::GenericArgs) -> bool {
@@ -1305,11 +1332,11 @@ impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
     #[tracing::instrument(skip(self), ret)]
     fn explicit_super_predicates_of(
         self,
-        def_id: Self::DefId,
+        def_id: Self::TraitId,
     ) -> EarlyBinder<Self, impl IntoIterator<Item = (Self::Clause, Self::Span)>> {
         let predicates: Vec<(Clause<'db>, Span)> = self
             .db()
-            .generic_predicates_ns(def_id.try_into().unwrap())
+            .generic_predicates_ns(def_id.0.into())
             .iter()
             .cloned()
             .map(|p| (p, Span::dummy()))
@@ -1369,65 +1396,19 @@ impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
         false
     }
 
-    fn require_lang_item(
-        self,
-        lang_item: rustc_type_ir::lang_items::TraitSolverLangItem,
-    ) -> Self::DefId {
+    fn require_lang_item(self, lang_item: SolverLangItem) -> Self::DefId {
         let lang_item = match lang_item {
-            rustc_type_ir::lang_items::TraitSolverLangItem::AsyncFn => LangItem::AsyncFn,
-            rustc_type_ir::lang_items::TraitSolverLangItem::AsyncFnKindHelper => unimplemented!(),
-            rustc_type_ir::lang_items::TraitSolverLangItem::AsyncFnKindUpvars => unimplemented!(),
-            rustc_type_ir::lang_items::TraitSolverLangItem::AsyncFnMut => LangItem::AsyncFnMut,
-            rustc_type_ir::lang_items::TraitSolverLangItem::AsyncFnOnce => LangItem::AsyncFnOnce,
-            rustc_type_ir::lang_items::TraitSolverLangItem::AsyncFnOnceOutput => {
-                LangItem::AsyncFnOnceOutput
-            }
-            rustc_type_ir::lang_items::TraitSolverLangItem::AsyncIterator => unimplemented!(),
-            rustc_type_ir::lang_items::TraitSolverLangItem::CallOnceFuture => {
-                LangItem::CallOnceFuture
-            }
-            rustc_type_ir::lang_items::TraitSolverLangItem::CallRefFuture => {
-                LangItem::CallRefFuture
-            }
-            rustc_type_ir::lang_items::TraitSolverLangItem::Clone => LangItem::Clone,
-            rustc_type_ir::lang_items::TraitSolverLangItem::Copy => LangItem::Copy,
-            rustc_type_ir::lang_items::TraitSolverLangItem::Coroutine => LangItem::Coroutine,
-            rustc_type_ir::lang_items::TraitSolverLangItem::CoroutineReturn => {
-                LangItem::CoroutineReturn
-            }
-            rustc_type_ir::lang_items::TraitSolverLangItem::CoroutineYield => {
-                LangItem::CoroutineYield
-            }
-            rustc_type_ir::lang_items::TraitSolverLangItem::Destruct => LangItem::Destruct,
-            rustc_type_ir::lang_items::TraitSolverLangItem::DiscriminantKind => {
-                LangItem::DiscriminantKind
-            }
-            rustc_type_ir::lang_items::TraitSolverLangItem::Drop => LangItem::Drop,
-            rustc_type_ir::lang_items::TraitSolverLangItem::DynMetadata => LangItem::DynMetadata,
-            rustc_type_ir::lang_items::TraitSolverLangItem::Fn => LangItem::Fn,
-            rustc_type_ir::lang_items::TraitSolverLangItem::FnMut => LangItem::FnMut,
-            rustc_type_ir::lang_items::TraitSolverLangItem::FnOnce => LangItem::FnOnce,
-            rustc_type_ir::lang_items::TraitSolverLangItem::FnPtrTrait => LangItem::FnPtrTrait,
-            rustc_type_ir::lang_items::TraitSolverLangItem::FusedIterator => unimplemented!(),
-            rustc_type_ir::lang_items::TraitSolverLangItem::Future => LangItem::Future,
-            rustc_type_ir::lang_items::TraitSolverLangItem::FutureOutput => LangItem::FutureOutput,
-            rustc_type_ir::lang_items::TraitSolverLangItem::Iterator => LangItem::Iterator,
-            rustc_type_ir::lang_items::TraitSolverLangItem::Metadata => LangItem::Metadata,
-            rustc_type_ir::lang_items::TraitSolverLangItem::Option => LangItem::Option,
-            rustc_type_ir::lang_items::TraitSolverLangItem::PointeeTrait => LangItem::PointeeTrait,
-            rustc_type_ir::lang_items::TraitSolverLangItem::Poll => LangItem::Poll,
-            rustc_type_ir::lang_items::TraitSolverLangItem::Sized => LangItem::Sized,
-            rustc_type_ir::lang_items::TraitSolverLangItem::MetaSized => LangItem::MetaSized,
-            rustc_type_ir::lang_items::TraitSolverLangItem::PointeeSized => LangItem::PointeeSized,
-            rustc_type_ir::lang_items::TraitSolverLangItem::TransmuteTrait => {
-                LangItem::TransmuteTrait
-            }
-            rustc_type_ir::lang_items::TraitSolverLangItem::Tuple => LangItem::Tuple,
-            rustc_type_ir::lang_items::TraitSolverLangItem::Unpin => LangItem::Unpin,
-            rustc_type_ir::lang_items::TraitSolverLangItem::Unsize => LangItem::Unsize,
-            rustc_type_ir::lang_items::TraitSolverLangItem::BikeshedGuaranteedNoDrop => {
-                unimplemented!()
-            }
+            SolverLangItem::AsyncFnKindUpvars => unimplemented!(),
+            SolverLangItem::AsyncFnOnceOutput => LangItem::AsyncFnOnceOutput,
+            SolverLangItem::CallOnceFuture => LangItem::CallOnceFuture,
+            SolverLangItem::CallRefFuture => LangItem::CallRefFuture,
+            SolverLangItem::CoroutineReturn => LangItem::CoroutineReturn,
+            SolverLangItem::CoroutineYield => LangItem::CoroutineYield,
+            SolverLangItem::DynMetadata => LangItem::DynMetadata,
+            SolverLangItem::FutureOutput => LangItem::FutureOutput,
+            SolverLangItem::Metadata => LangItem::Metadata,
+            SolverLangItem::Option => LangItem::Option,
+            SolverLangItem::Poll => LangItem::Poll,
         };
         let target = hir_def::lang_item::lang_item(
             self.db(),
@@ -1448,216 +1429,131 @@ impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
         }
     }
 
+    fn require_trait_lang_item(self, lang_item: SolverTraitLangItem) -> TraitIdWrapper {
+        let lang_item = match lang_item {
+            SolverTraitLangItem::AsyncFn => LangItem::AsyncFn,
+            SolverTraitLangItem::AsyncFnKindHelper => unimplemented!(),
+            SolverTraitLangItem::AsyncFnMut => LangItem::AsyncFnMut,
+            SolverTraitLangItem::AsyncFnOnce => LangItem::AsyncFnOnce,
+            SolverTraitLangItem::AsyncFnOnceOutput => LangItem::AsyncFnOnceOutput,
+            SolverTraitLangItem::AsyncIterator => unimplemented!(),
+            SolverTraitLangItem::Clone => LangItem::Clone,
+            SolverTraitLangItem::Copy => LangItem::Copy,
+            SolverTraitLangItem::Coroutine => LangItem::Coroutine,
+            SolverTraitLangItem::Destruct => LangItem::Destruct,
+            SolverTraitLangItem::DiscriminantKind => LangItem::DiscriminantKind,
+            SolverTraitLangItem::Drop => LangItem::Drop,
+            SolverTraitLangItem::Fn => LangItem::Fn,
+            SolverTraitLangItem::FnMut => LangItem::FnMut,
+            SolverTraitLangItem::FnOnce => LangItem::FnOnce,
+            SolverTraitLangItem::FnPtrTrait => LangItem::FnPtrTrait,
+            SolverTraitLangItem::FusedIterator => unimplemented!(),
+            SolverTraitLangItem::Future => LangItem::Future,
+            SolverTraitLangItem::Iterator => LangItem::Iterator,
+            SolverTraitLangItem::PointeeTrait => LangItem::PointeeTrait,
+            SolverTraitLangItem::Sized => LangItem::Sized,
+            SolverTraitLangItem::MetaSized => LangItem::MetaSized,
+            SolverTraitLangItem::PointeeSized => LangItem::PointeeSized,
+            SolverTraitLangItem::TransmuteTrait => LangItem::TransmuteTrait,
+            SolverTraitLangItem::Tuple => LangItem::Tuple,
+            SolverTraitLangItem::Unpin => LangItem::Unpin,
+            SolverTraitLangItem::Unsize => LangItem::Unsize,
+            SolverTraitLangItem::BikeshedGuaranteedNoDrop => {
+                unimplemented!()
+            }
+        };
+        lang_item
+            .resolve_trait(self.db(), self.krate.expect("Must have self.krate"))
+            .unwrap_or_else(|| panic!("Lang item {lang_item:?} required but not found."))
+            .into()
+    }
+
     #[allow(clippy::match_like_matches_macro)]
-    fn is_lang_item(
-        self,
-        def_id: Self::DefId,
-        lang_item: rustc_type_ir::lang_items::TraitSolverLangItem,
-    ) -> bool {
-        use rustc_type_ir::lang_items::TraitSolverLangItem::*;
-
-        // FIXME: derive PartialEq on TraitSolverLangItem
-        self.as_lang_item(def_id).map_or(false, |l| match (l, lang_item) {
-            (AsyncFn, AsyncFn) => true,
-            (AsyncFnKindHelper, AsyncFnKindHelper) => true,
-            (AsyncFnKindUpvars, AsyncFnKindUpvars) => true,
-            (AsyncFnMut, AsyncFnMut) => true,
-            (AsyncFnOnce, AsyncFnOnce) => true,
-            (AsyncFnOnceOutput, AsyncFnOnceOutput) => true,
-            (AsyncIterator, AsyncIterator) => true,
-            (CallOnceFuture, CallOnceFuture) => true,
-            (CallRefFuture, CallRefFuture) => true,
-            (Clone, Clone) => true,
-            (Copy, Copy) => true,
-            (Coroutine, Coroutine) => true,
-            (CoroutineReturn, CoroutineReturn) => true,
-            (CoroutineYield, CoroutineYield) => true,
-            (Destruct, Destruct) => true,
-            (DiscriminantKind, DiscriminantKind) => true,
-            (Drop, Drop) => true,
-            (DynMetadata, DynMetadata) => true,
-            (Fn, Fn) => true,
-            (FnMut, FnMut) => true,
-            (FnOnce, FnOnce) => true,
-            (FnPtrTrait, FnPtrTrait) => true,
-            (FusedIterator, FusedIterator) => true,
-            (Future, Future) => true,
-            (FutureOutput, FutureOutput) => true,
-            (Iterator, Iterator) => true,
-            (Metadata, Metadata) => true,
-            (Option, Option) => true,
-            (PointeeTrait, PointeeTrait) => true,
-            (Poll, Poll) => true,
-            (Sized, Sized) => true,
-            (TransmuteTrait, TransmuteTrait) => true,
-            (Tuple, Tuple) => true,
-            (Unpin, Unpin) => true,
-            (Unsize, Unsize) => true,
-            _ => false,
-        })
+    fn is_lang_item(self, def_id: Self::DefId, lang_item: SolverLangItem) -> bool {
+        use SolverLangItem::*;
+
+        // FIXME: derive PartialEq on SolverLangItem
+        self.as_lang_item(def_id)
+            .map_or(false, |l| std::mem::discriminant(&l) == std::mem::discriminant(&lang_item))
     }
 
-    fn as_lang_item(
-        self,
-        def_id: Self::DefId,
-    ) -> Option<rustc_type_ir::lang_items::TraitSolverLangItem> {
-        use rustc_type_ir::lang_items::TraitSolverLangItem;
+    #[allow(clippy::match_like_matches_macro)]
+    fn is_trait_lang_item(self, def_id: Self::TraitId, lang_item: SolverTraitLangItem) -> bool {
+        use SolverTraitLangItem::*;
+
+        // FIXME: derive PartialEq on SolverTraitLangItem
+        self.as_trait_lang_item(def_id)
+            .map_or(false, |l| std::mem::discriminant(&l) == std::mem::discriminant(&lang_item))
+    }
 
+    fn as_lang_item(self, def_id: Self::DefId) -> Option<SolverLangItem> {
         let def_id: AttrDefId = match def_id {
             SolverDefId::TraitId(id) => id.into(),
             SolverDefId::TypeAliasId(id) => id.into(),
+            SolverDefId::AdtId(id) => id.into(),
             _ => panic!("Unexpected SolverDefId in as_lang_item"),
         };
         let lang_item = self.db().lang_attr(def_id)?;
-        Some(match lang_item {
-            LangItem::Sized => TraitSolverLangItem::Sized,
-            LangItem::MetaSized => TraitSolverLangItem::MetaSized,
-            LangItem::PointeeSized => TraitSolverLangItem::PointeeSized,
-            LangItem::Unsize => TraitSolverLangItem::Unsize,
-            LangItem::StructuralPeq => return None,
-            LangItem::StructuralTeq => return None,
-            LangItem::Copy => TraitSolverLangItem::Copy,
-            LangItem::Clone => TraitSolverLangItem::Clone,
-            LangItem::Sync => return None,
-            LangItem::DiscriminantKind => TraitSolverLangItem::DiscriminantKind,
-            LangItem::Discriminant => return None,
-            LangItem::PointeeTrait => TraitSolverLangItem::PointeeTrait,
-            LangItem::Metadata => TraitSolverLangItem::Metadata,
-            LangItem::DynMetadata => TraitSolverLangItem::DynMetadata,
-            LangItem::Freeze => return None,
-            LangItem::FnPtrTrait => TraitSolverLangItem::FnPtrTrait,
-            LangItem::FnPtrAddr => return None,
-            LangItem::Drop => TraitSolverLangItem::Drop,
-            LangItem::Destruct => TraitSolverLangItem::Destruct,
-            LangItem::CoerceUnsized => return None,
-            LangItem::DispatchFromDyn => return None,
-            LangItem::TransmuteOpts => return None,
-            LangItem::TransmuteTrait => TraitSolverLangItem::TransmuteTrait,
-            LangItem::Add => return None,
-            LangItem::Sub => return None,
-            LangItem::Mul => return None,
-            LangItem::Div => return None,
-            LangItem::Rem => return None,
-            LangItem::Neg => return None,
-            LangItem::Not => return None,
-            LangItem::BitXor => return None,
-            LangItem::BitAnd => return None,
-            LangItem::BitOr => return None,
-            LangItem::Shl => return None,
-            LangItem::Shr => return None,
-            LangItem::AddAssign => return None,
-            LangItem::SubAssign => return None,
-            LangItem::MulAssign => return None,
-            LangItem::DivAssign => return None,
-            LangItem::RemAssign => return None,
-            LangItem::BitXorAssign => return None,
-            LangItem::BitAndAssign => return None,
-            LangItem::BitOrAssign => return None,
-            LangItem::ShlAssign => return None,
-            LangItem::ShrAssign => return None,
-            LangItem::Index => return None,
-            LangItem::IndexMut => return None,
-            LangItem::UnsafeCell => return None,
-            LangItem::VaList => return None,
-            LangItem::Deref => return None,
-            LangItem::DerefMut => return None,
-            LangItem::DerefTarget => return None,
-            LangItem::Receiver => return None,
-            LangItem::Fn => TraitSolverLangItem::Fn,
-            LangItem::FnMut => TraitSolverLangItem::FnMut,
-            LangItem::FnOnce => TraitSolverLangItem::FnOnce,
-            LangItem::FnOnceOutput => return None,
-            LangItem::Future => TraitSolverLangItem::Future,
-            LangItem::CoroutineState => return None,
-            LangItem::Coroutine => TraitSolverLangItem::Coroutine,
-            LangItem::CoroutineReturn => TraitSolverLangItem::CoroutineReturn,
-            LangItem::CoroutineYield => TraitSolverLangItem::CoroutineYield,
-            LangItem::Unpin => TraitSolverLangItem::Unpin,
-            LangItem::Pin => return None,
-            LangItem::PartialEq => return None,
-            LangItem::PartialOrd => return None,
-            LangItem::CVoid => return None,
-            LangItem::Panic => return None,
-            LangItem::PanicNounwind => return None,
-            LangItem::PanicFmt => return None,
-            LangItem::PanicDisplay => return None,
-            LangItem::ConstPanicFmt => return None,
-            LangItem::PanicBoundsCheck => return None,
-            LangItem::PanicMisalignedPointerDereference => return None,
-            LangItem::PanicInfo => return None,
-            LangItem::PanicLocation => return None,
-            LangItem::PanicImpl => return None,
-            LangItem::PanicCannotUnwind => return None,
-            LangItem::BeginPanic => return None,
-            LangItem::FormatAlignment => return None,
-            LangItem::FormatArgument => return None,
-            LangItem::FormatArguments => return None,
-            LangItem::FormatCount => return None,
-            LangItem::FormatPlaceholder => return None,
-            LangItem::FormatUnsafeArg => return None,
-            LangItem::ExchangeMalloc => return None,
-            LangItem::BoxFree => return None,
-            LangItem::DropInPlace => return None,
-            LangItem::AllocLayout => return None,
-            LangItem::Start => return None,
-            LangItem::EhPersonality => return None,
-            LangItem::EhCatchTypeinfo => return None,
-            LangItem::OwnedBox => return None,
-            LangItem::PhantomData => return None,
-            LangItem::ManuallyDrop => return None,
-            LangItem::MaybeUninit => return None,
-            LangItem::AlignOffset => return None,
-            LangItem::Termination => return None,
-            LangItem::Try => return None,
-            LangItem::Tuple => TraitSolverLangItem::Tuple,
-            LangItem::SliceLen => return None,
-            LangItem::TryTraitFromResidual => return None,
-            LangItem::TryTraitFromOutput => return None,
-            LangItem::TryTraitBranch => return None,
-            LangItem::TryTraitFromYeet => return None,
-            LangItem::PointerLike => return None,
-            LangItem::ConstParamTy => return None,
-            LangItem::Poll => TraitSolverLangItem::Poll,
-            LangItem::PollReady => return None,
-            LangItem::PollPending => return None,
-            LangItem::ResumeTy => return None,
-            LangItem::GetContext => return None,
-            LangItem::Context => return None,
-            LangItem::FuturePoll => return None,
-            LangItem::FutureOutput => TraitSolverLangItem::FutureOutput,
-            LangItem::Option => TraitSolverLangItem::Option,
-            LangItem::OptionSome => return None,
-            LangItem::OptionNone => return None,
-            LangItem::ResultOk => return None,
-            LangItem::ResultErr => return None,
-            LangItem::ControlFlowContinue => return None,
-            LangItem::ControlFlowBreak => return None,
-            LangItem::IntoFutureIntoFuture => return None,
-            LangItem::IntoIterIntoIter => return None,
-            LangItem::IteratorNext => return None,
-            LangItem::Iterator => TraitSolverLangItem::Iterator,
-            LangItem::PinNewUnchecked => return None,
-            LangItem::RangeFrom => return None,
-            LangItem::RangeFull => return None,
-            LangItem::RangeInclusiveStruct => return None,
-            LangItem::RangeInclusiveNew => return None,
-            LangItem::Range => return None,
-            LangItem::RangeToInclusive => return None,
-            LangItem::RangeTo => return None,
-            LangItem::String => return None,
-            LangItem::CStr => return None,
-            LangItem::AsyncFn => TraitSolverLangItem::AsyncFn,
-            LangItem::AsyncFnMut => TraitSolverLangItem::AsyncFnMut,
-            LangItem::AsyncFnOnce => TraitSolverLangItem::AsyncFnOnce,
-            LangItem::AsyncFnOnceOutput => TraitSolverLangItem::AsyncFnOnceOutput,
-            LangItem::CallRefFuture => TraitSolverLangItem::CallRefFuture,
-            LangItem::CallOnceFuture => TraitSolverLangItem::CallOnceFuture,
-            LangItem::Ordering => return None,
-            LangItem::PanicNullPointerDereference => return None,
-            LangItem::ReceiverTarget => return None,
-            LangItem::UnsafePinned => return None,
-            LangItem::AsyncFnOnceOutput => TraitSolverLangItem::AsyncFnOnceOutput,
-        })
+        as_lang_item!(
+            SolverLangItem, lang_item;
+
+            ignore = {
+                AsyncFnKindUpvars,
+            }
+
+            Metadata,
+            DynMetadata,
+            CoroutineReturn,
+            CoroutineYield,
+            Poll,
+            FutureOutput,
+            Option,
+            AsyncFnOnceOutput,
+            CallRefFuture,
+            CallOnceFuture,
+            AsyncFnOnceOutput,
+        )
+    }
+
+    fn as_trait_lang_item(self, def_id: Self::TraitId) -> Option<SolverTraitLangItem> {
+        let def_id: AttrDefId = def_id.0.into();
+        let lang_item = self.db().lang_attr(def_id)?;
+        as_lang_item!(
+            SolverTraitLangItem, lang_item;
+
+            ignore = {
+                AsyncFnKindHelper,
+                AsyncIterator,
+                BikeshedGuaranteedNoDrop,
+                FusedIterator,
+            }
+
+            Sized,
+            MetaSized,
+            PointeeSized,
+            Unsize,
+            Copy,
+            Clone,
+            DiscriminantKind,
+            PointeeTrait,
+            FnPtrTrait,
+            Drop,
+            Destruct,
+            TransmuteTrait,
+            Fn,
+            FnMut,
+            FnOnce,
+            Future,
+            Coroutine,
+            Unpin,
+            Tuple,
+            Iterator,
+            AsyncFn,
+            AsyncFnMut,
+            AsyncFnOnce,
+            AsyncFnOnceOutput,
+            AsyncFnOnceOutput,
+        )
     }
 
     fn associated_type_def_ids(self, def_id: Self::DefId) -> impl IntoIterator<Item = Self::DefId> {
@@ -1670,15 +1566,11 @@ impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
 
     fn for_each_relevant_impl(
         self,
-        trait_def_id: Self::DefId,
+        trait_: Self::TraitId,
         self_ty: Self::Ty,
         mut f: impl FnMut(Self::DefId),
     ) {
-        let trait_ = match trait_def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => panic!("for_each_relevant_impl called for non-trait"),
-        };
-
+        let trait_ = trait_.0;
         let self_ty_fp = TyFingerprint::for_trait_impl_ns(&self_ty);
         let fps: &[TyFingerprint] = match self_ty.kind() {
             TyKind::Infer(InferTy::IntVar(..)) => &ALL_INT_FPS,
@@ -1775,42 +1667,26 @@ impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
         }
     }
 
-    fn trait_is_auto(self, trait_def_id: Self::DefId) -> bool {
-        let trait_ = match trait_def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => panic!("Unexpected SolverDefId in trait_is_auto"),
-        };
-        let trait_data = self.db().trait_signature(trait_);
+    fn trait_is_auto(self, trait_: Self::TraitId) -> bool {
+        let trait_data = self.db().trait_signature(trait_.0);
         trait_data.flags.contains(TraitFlags::AUTO)
     }
 
-    fn trait_is_alias(self, trait_def_id: Self::DefId) -> bool {
-        let trait_ = match trait_def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => panic!("Unexpected SolverDefId in trait_is_alias"),
-        };
-        let trait_data = self.db().trait_signature(trait_);
+    fn trait_is_alias(self, trait_: Self::TraitId) -> bool {
+        let trait_data = self.db().trait_signature(trait_.0);
         trait_data.flags.contains(TraitFlags::ALIAS)
     }
 
-    fn trait_is_dyn_compatible(self, trait_def_id: Self::DefId) -> bool {
-        let trait_ = match trait_def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => unreachable!(),
-        };
-        crate::dyn_compatibility::dyn_compatibility(self.db(), trait_).is_none()
+    fn trait_is_dyn_compatible(self, trait_: Self::TraitId) -> bool {
+        crate::dyn_compatibility::dyn_compatibility(self.db(), trait_.0).is_none()
     }
 
-    fn trait_is_fundamental(self, def_id: Self::DefId) -> bool {
-        let trait_ = match def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => panic!("Unexpected SolverDefId in trait_is_fundamental"),
-        };
-        let trait_data = self.db().trait_signature(trait_);
+    fn trait_is_fundamental(self, trait_: Self::TraitId) -> bool {
+        let trait_data = self.db().trait_signature(trait_.0);
         trait_data.flags.contains(TraitFlags::FUNDAMENTAL)
     }
 
-    fn trait_may_be_implemented_via_object(self, trait_def_id: Self::DefId) -> bool {
+    fn trait_may_be_implemented_via_object(self, trait_def_id: Self::TraitId) -> bool {
         // FIXME(next-solver): should check the `TraitFlags` for
         // the `#[rustc_do_not_implement_via_object]` flag
         true
@@ -1920,12 +1796,12 @@ impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
                     (*entry.or_insert_with(|| BoundVarKind::Ty(BoundTyKind::Anon))).expect_ty();
                 Ty::new_bound(self.interner, DebruijnIndex::ZERO, BoundTy { var, kind })
             }
-            fn replace_const(&mut self, bv: BoundVar) -> Const<'db> {
-                let entry = self.map.entry(bv);
+            fn replace_const(&mut self, bv: BoundConst) -> Const<'db> {
+                let entry = self.map.entry(bv.var);
                 let index = entry.index();
                 let var = BoundVar::from_usize(index);
                 let () = (*entry.or_insert_with(|| BoundVarKind::Const)).expect_const();
-                Const::new_bound(self.interner, DebruijnIndex::ZERO, var)
+                Const::new_bound(self.interner, DebruijnIndex::ZERO, BoundConst { var })
             }
         }
 
@@ -2008,24 +1884,16 @@ impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
         unimplemented!()
     }
 
-    fn is_default_trait(self, def_id: Self::DefId) -> bool {
-        self.as_lang_item(def_id).map_or(false, |l| matches!(l, TraitSolverLangItem::Sized))
+    fn is_default_trait(self, def_id: Self::TraitId) -> bool {
+        self.as_trait_lang_item(def_id).map_or(false, |l| matches!(l, SolverTraitLangItem::Sized))
     }
 
-    fn trait_is_coinductive(self, trait_def_id: Self::DefId) -> bool {
-        let id = match trait_def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => unreachable!(),
-        };
-        self.db().trait_signature(id).flags.contains(TraitFlags::COINDUCTIVE)
+    fn trait_is_coinductive(self, trait_: Self::TraitId) -> bool {
+        self.db().trait_signature(trait_.0).flags.contains(TraitFlags::COINDUCTIVE)
     }
 
-    fn trait_is_unsafe(self, trait_def_id: Self::DefId) -> bool {
-        let id = match trait_def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => unreachable!(),
-        };
-        self.db().trait_signature(id).flags.contains(TraitFlags::UNSAFE)
+    fn trait_is_unsafe(self, trait_: Self::TraitId) -> bool {
+        self.db().trait_signature(trait_.0).flags.contains(TraitFlags::UNSAFE)
     }
 
     fn impl_self_is_guaranteed_unsized(self, def_id: Self::DefId) -> bool {
@@ -2047,6 +1915,20 @@ impl<'db> rustc_type_ir::Interner for DbInterner<'db> {
         // FIXME(next-solver)
         unimplemented!()
     }
+
+    type Probe = rustc_type_ir::solve::inspect::Probe<DbInterner<'db>>;
+    fn mk_probe(self, probe: rustc_type_ir::solve::inspect::Probe<Self>) -> Self::Probe {
+        probe
+    }
+    fn evaluate_root_goal_for_proof_tree_raw(
+        self,
+        canonical_goal: rustc_type_ir::solve::CanonicalInput<Self>,
+    ) -> (rustc_type_ir::solve::QueryResult<Self>, Self::Probe) {
+        rustc_next_trait_solver::solve::evaluate_root_goal_for_proof_tree_raw_provider::<
+            SolverContext<'db>,
+            Self,
+        >(self, canonical_goal)
+    }
 }
 
 impl<'db> DbInterner<'db> {
@@ -2072,7 +1954,9 @@ impl<'db> DbInterner<'db> {
                         BoundTy { var: shift_bv(t.var), kind: t.kind },
                     )
                 },
-                consts: &mut |c| Const::new_bound(self, DebruijnIndex::ZERO, shift_bv(c)),
+                consts: &mut |c| {
+                    Const::new_bound(self, DebruijnIndex::ZERO, BoundConst { var: shift_bv(c.var) })
+                },
             },
         )
     }
@@ -2135,6 +2019,7 @@ macro_rules! TrivialTypeTraversalImpls {
 
 TrivialTypeTraversalImpls! {
     SolverDefId,
+    TraitIdWrapper,
     Pattern<'db>,
     Safety,
     FnAbi,
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/ir_print.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/ir_print.rs
index 4d32b271323..407e1575643 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/ir_print.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/ir_print.rs
@@ -58,10 +58,7 @@ impl<'db> IrPrint<ty::TraitRef<Self>> for DbInterner<'db> {
 
     fn print_debug(t: &ty::TraitRef<Self>, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
         salsa::with_attached_database(|db| {
-            let trait_ = match t.def_id {
-                SolverDefId::TraitId(id) => id,
-                _ => panic!("Expected trait."),
-            };
+            let trait_ = t.def_id.0;
             let self_ty = &t.args.as_slice()[0];
             let trait_args = &t.args.as_slice()[1..];
             if trait_args.is_empty() {
@@ -122,10 +119,7 @@ impl<'db> IrPrint<ty::ExistentialTraitRef<Self>> for DbInterner<'db> {
         fmt: &mut std::fmt::Formatter<'_>,
     ) -> std::fmt::Result {
         salsa::with_attached_database(|db| {
-            let trait_ = match t.def_id {
-                SolverDefId::TraitId(id) => id,
-                _ => panic!("Expected trait."),
-            };
+            let trait_ = t.def_id.0;
             fmt.write_str(&format!(
                 "ExistentialTraitRef({:?}[{:?}])",
                 db.as_view::<dyn HirDatabase>().trait_signature(trait_).name.as_str(),
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/mapping.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/mapping.rs
index 6755d065e10..dc54ee7d587 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/mapping.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/mapping.rs
@@ -22,6 +22,7 @@ use rustc_type_ir::{
 use salsa::plumbing::FromId;
 use salsa::{Id, plumbing::AsId};
 
+use crate::next_solver::BoundConst;
 use crate::{
     ConcreteConst, ConstScalar, ImplTraitId, Interner, MemoryMap,
     db::{
@@ -125,12 +126,12 @@ impl<'db> rustc_type_ir::TypeFolder<DbInterner<'db>> for BinderToEarlyBinder<'db
     fn fold_const(&mut self, c: Const<'db>) -> Const<'db> {
         match c.kind() {
             rustc_type_ir::ConstKind::Bound(debruijn, var) if self.debruijn == debruijn => {
-                let GenericParamId::ConstParamId(id) = self.params[var.as_usize()] else {
+                let GenericParamId::ConstParamId(id) = self.params[var.var.as_usize()] else {
                     unreachable!()
                 };
                 Const::new(
                     self.cx(),
-                    rustc_type_ir::ConstKind::Param(ParamConst { index: var.as_u32(), id }),
+                    rustc_type_ir::ConstKind::Param(ParamConst { index: var.var.as_u32(), id }),
                 )
             }
             _ => c.super_fold_with(self),
@@ -286,11 +287,8 @@ impl<'db> ChalkToNextSolver<'db, Ty<'db>> for chalk_ir::Ty<Interner> {
                                         .flags
                                         .contains(TraitFlags::AUTO)
                                     {
-                                        ExistentialPredicate::AutoTrait(SolverDefId::TraitId(
-                                            trait_id,
-                                        ))
+                                        ExistentialPredicate::AutoTrait(trait_id.into())
                                     } else {
-                                        let def_id = SolverDefId::TraitId(trait_id);
                                         let args = GenericArgs::new_from_iter(
                                             interner,
                                             trait_ref
@@ -301,7 +299,7 @@ impl<'db> ChalkToNextSolver<'db, Ty<'db>> for chalk_ir::Ty<Interner> {
                                                 .map(|a| a.to_nextsolver(interner)),
                                         );
                                         let trait_ref = ExistentialTraitRef::new_from_args(
-                                            interner, def_id, args,
+                                            interner, trait_id.into(), args,
                                         );
                                         ExistentialPredicate::Trait(trait_ref)
                                     }
@@ -473,7 +471,7 @@ impl<'db> ChalkToNextSolver<'db, Const<'db>> for chalk_ir::Const<Interner> {
             match &data.value {
                 chalk_ir::ConstValue::BoundVar(bound_var) => rustc_type_ir::ConstKind::Bound(
                     bound_var.debruijn.to_nextsolver(interner),
-                    rustc_type_ir::BoundVar::from_usize(bound_var.index),
+                    BoundConst { var: rustc_type_ir::BoundVar::from_usize(bound_var.index) },
                 ),
                 chalk_ir::ConstValue::InferenceVar(inference_var) => {
                     rustc_type_ir::ConstKind::Infer(rustc_type_ir::InferConst::Var(
@@ -871,11 +869,7 @@ impl<'db> ChalkToNextSolver<'db, PredicateKind<'db>> for chalk_ir::DomainGoal<In
 impl<'db> ChalkToNextSolver<'db, TraitRef<'db>> for chalk_ir::TraitRef<Interner> {
     fn to_nextsolver(&self, interner: DbInterner<'db>) -> TraitRef<'db> {
         let args = self.substitution.to_nextsolver(interner);
-        TraitRef::new_from_args(
-            interner,
-            SolverDefId::TraitId(from_chalk_trait_id(self.trait_id)),
-            args,
-        )
+        TraitRef::new_from_args(interner, from_chalk_trait_id(self.trait_id).into(), args)
     }
 }
 
@@ -1207,20 +1201,14 @@ pub(crate) fn convert_ty_for_result<'db>(interner: DbInterner<'db>, ty: Ty<'db>)
                                 trait_ref.def_id,
                                 [self_ty.into()].into_iter().chain(trait_ref.args.iter()),
                             );
-                            let trait_id = match trait_ref.def_id {
-                                SolverDefId::TraitId(id) => to_chalk_trait_id(id),
-                                _ => unreachable!(),
-                            };
+                            let trait_id = to_chalk_trait_id(trait_ref.def_id.0);
                             let substitution =
                                 convert_args_for_result(interner, trait_ref.args.as_slice());
                             let trait_ref = chalk_ir::TraitRef { trait_id, substitution };
                             chalk_ir::WhereClause::Implemented(trait_ref)
                         }
                         rustc_type_ir::ExistentialPredicate::AutoTrait(trait_) => {
-                            let trait_id = match trait_ {
-                                SolverDefId::TraitId(id) => to_chalk_trait_id(id),
-                                _ => unreachable!(),
-                            };
+                            let trait_id = to_chalk_trait_id(trait_.0);
                             let substitution = chalk_ir::Substitution::from1(
                                 Interner,
                                 convert_ty_for_result(interner, self_ty),
@@ -1354,7 +1342,7 @@ pub fn convert_const_for_result<'db>(
         rustc_type_ir::ConstKind::Bound(debruijn_index, var) => {
             chalk_ir::ConstValue::BoundVar(chalk_ir::BoundVar::new(
                 chalk_ir::DebruijnIndex::new(debruijn_index.as_u32()),
-                var.index(),
+                var.var.index(),
             ))
         }
         rustc_type_ir::ConstKind::Placeholder(placeholder_const) => {
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/predicate.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/predicate.rs
index 50261bb5e38..c86d3a4aadb 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/predicate.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/predicate.rs
@@ -15,6 +15,8 @@ use rustc_type_ir::{
 };
 use smallvec::{SmallVec, smallvec};
 
+use crate::next_solver::TraitIdWrapper;
+
 use super::{Binder, BoundVarKinds, DbInterner, Region, Ty, interned_vec_db};
 
 pub type BoundExistentialPredicate<'db> = Binder<'db, ExistentialPredicate<'db>>;
@@ -72,7 +74,7 @@ interned_vec_db!(BoundExistentialPredicates, BoundExistentialPredicate);
 impl<'db> rustc_type_ir::inherent::BoundExistentialPredicates<DbInterner<'db>>
     for BoundExistentialPredicates<'db>
 {
-    fn principal_def_id(self) -> Option<<DbInterner<'db> as rustc_type_ir::Interner>::DefId> {
+    fn principal_def_id(self) -> Option<TraitIdWrapper> {
         self.principal().map(|trait_ref| trait_ref.skip_binder().def_id)
     }
 
@@ -89,9 +91,7 @@ impl<'db> rustc_type_ir::inherent::BoundExistentialPredicates<DbInterner<'db>>
             .transpose()
     }
 
-    fn auto_traits(
-        self,
-    ) -> impl IntoIterator<Item = <DbInterner<'db> as rustc_type_ir::Interner>::DefId> {
+    fn auto_traits(self) -> impl IntoIterator<Item = TraitIdWrapper> {
         self.iter().filter_map(|predicate| match predicate.skip_binder() {
             ExistentialPredicate::AutoTrait(did) => Some(did),
             _ => None,
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/solver.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/solver.rs
index 45888ac4d23..1d0ee0e488d 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/solver.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/solver.rs
@@ -2,10 +2,10 @@
 
 use hir_def::{AssocItemId, GeneralConstId, TypeAliasId};
 use rustc_next_trait_solver::delegate::SolverDelegate;
+use rustc_type_ir::lang_items::SolverTraitLangItem;
 use rustc_type_ir::{
     InferCtxtLike, Interner, PredicatePolarity, TypeFlags, TypeVisitableExt, UniverseIndex,
     inherent::{IntoKind, SliceLike, Span as _, Term as _, Ty as _},
-    lang_items::TraitSolverLangItem,
     solve::{Certainty, NoSolution},
 };
 
@@ -225,14 +225,14 @@ impl<'db> SolverDelegate for SolverContext<'db> {
             }
 
             if trait_pred.polarity() == PredicatePolarity::Positive {
-                match self.0.cx().as_lang_item(trait_pred.def_id()) {
-                    Some(TraitSolverLangItem::Sized) | Some(TraitSolverLangItem::MetaSized) => {
+                match self.0.cx().as_trait_lang_item(trait_pred.def_id()) {
+                    Some(SolverTraitLangItem::Sized) | Some(SolverTraitLangItem::MetaSized) => {
                         let predicate = self.resolve_vars_if_possible(goal.predicate);
                         if sizedness_fast_path(self.cx(), predicate, goal.param_env) {
                             return Some(Certainty::Yes);
                         }
                     }
-                    Some(TraitSolverLangItem::Copy | TraitSolverLangItem::Clone) => {
+                    Some(SolverTraitLangItem::Copy | SolverTraitLangItem::Clone) => {
                         let self_ty =
                             self.resolve_vars_if_possible(trait_pred.self_ty().skip_binder());
                         // Unlike `Sized` traits, which always prefer the built-in impl,
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/ty.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/ty.rs
index 92f1076e75e..4794e2d6045 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/ty.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/ty.rs
@@ -4,6 +4,7 @@ use hir_def::{GenericDefId, TypeOrConstParamId, TypeParamId};
 use intern::{Interned, Symbol, sym};
 use rustc_abi::{Float, Integer, Size};
 use rustc_ast_ir::{Mutability, try_visit, visit::VisitorResult};
+use rustc_type_ir::Interner;
 use rustc_type_ir::{
     BoundVar, ClosureKind, FlagComputation, Flags, FloatTy, FloatVid, InferTy, IntTy, IntVid,
     TypeFoldable, TypeSuperFoldable, TypeSuperVisitable, TypeVisitable, TypeVisitableExt, UintTy,
@@ -19,6 +20,7 @@ use rustc_type_ir::{
 use salsa::plumbing::{AsId, FromId};
 use smallvec::SmallVec;
 
+use crate::next_solver::GenericArg;
 use crate::{
     db::HirDatabase,
     interner::InternedWrapperNoDebug,
@@ -645,6 +647,31 @@ impl<'db> rustc_type_ir::inherent::Ty<DbInterner<'db>> for Ty<'db> {
         Ty::new(interner, TyKind::CoroutineWitness(def_id, args))
     }
 
+    fn new_coroutine_witness_for_coroutine(
+        interner: DbInterner<'db>,
+        def_id: <DbInterner<'db> as rustc_type_ir::Interner>::DefId,
+        coroutine_args: <DbInterner<'db> as rustc_type_ir::Interner>::GenericArgs,
+    ) -> Self {
+        // HACK: Coroutine witness types are lifetime erased, so they
+        // never reference any lifetime args from the coroutine. We erase
+        // the regions here since we may get into situations where a
+        // coroutine is recursively contained within itself, leading to
+        // witness types that differ by region args. This means that
+        // cycle detection in fulfillment will not kick in, which leads
+        // to unnecessary overflows in async code. See the issue:
+        // <https://github.com/rust-lang/rust/issues/145151>.
+        let coroutine_args = interner.mk_args_from_iter(coroutine_args.iter().map(|arg| {
+            match arg {
+                GenericArg::Ty(_) | GenericArg::Const(_) => arg,
+                GenericArg::Lifetime(_) => {
+                    crate::next_solver::Region::new(interner, rustc_type_ir::RegionKind::ReErased)
+                        .into()
+                }
+            }
+        }));
+        Ty::new_coroutine_witness(interner, def_id, coroutine_args)
+    }
+
     fn new_ptr(interner: DbInterner<'db>, ty: Self, mutbl: rustc_ast_ir::Mutability) -> Self {
         Ty::new(interner, TyKind::RawPtr(ty, mutbl))
     }
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/util.rs b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/util.rs
index 1db02e9eb61..50b96a160ed 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/util.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/next_solver/util.rs
@@ -14,7 +14,7 @@ use rustc_type_ir::inherent::{
     AdtDef, Const as _, GenericArg as _, GenericArgs as _, ParamEnv as _, Region as _, SliceLike,
     Ty as _,
 };
-use rustc_type_ir::lang_items::TraitSolverLangItem;
+use rustc_type_ir::lang_items::SolverTraitLangItem;
 use rustc_type_ir::solve::SizedTraitKind;
 use rustc_type_ir::{
     BoundVar, Canonical, DebruijnIndex, GenericArgKind, INNERMOST, Interner, PredicatePolarity,
@@ -29,8 +29,8 @@ use rustc_type_ir::{InferCtxtLike, TypeFoldable};
 use crate::lower_nextsolver::{LifetimeElisionKind, TyLoweringContext};
 use crate::next_solver::infer::InferCtxt;
 use crate::next_solver::{
-    CanonicalVarKind, FxIndexMap, ParamEnv, Placeholder, PlaceholderConst, PlaceholderRegion,
-    TypingMode,
+    BoundConst, CanonicalVarKind, FxIndexMap, ParamEnv, Placeholder, PlaceholderConst,
+    PlaceholderRegion, TypingMode,
 };
 use crate::{
     db::HirDatabase,
@@ -511,7 +511,7 @@ pub fn apply_args_to_binder<'db, T: TypeFoldable<DbInterner<'db>>>(
 ) -> T {
     let types = &mut |ty: BoundTy| args.as_slice()[ty.var.index()].expect_ty();
     let regions = &mut |region: BoundRegion| args.as_slice()[region.var.index()].expect_region();
-    let consts = &mut |const_: BoundVar| args.as_slice()[const_.index()].expect_const();
+    let consts = &mut |const_: BoundConst| args.as_slice()[const_.var.index()].expect_const();
     let mut instantiate = BoundVarReplacer::new(interner, FnMutDelegate { types, regions, consts });
     b.skip_binder().fold_with(&mut instantiate)
 }
@@ -654,7 +654,10 @@ impl<'db> TypeFolder<DbInterner<'db>> for MiniCanonicalizer<'_, 'db> {
             ConstKind::Infer(infer) => {
                 let len = self.vars.len();
                 let var = *self.vars.entry(c.into()).or_insert(len);
-                Const::new(self.cx(), ConstKind::Bound(self.db, BoundVar::from_usize(var)))
+                Const::new(
+                    self.cx(),
+                    ConstKind::Bound(self.db, BoundConst { var: BoundVar::from_usize(var) }),
+                )
             }
             _ => c.super_fold_with(self),
         }
@@ -852,7 +855,7 @@ pub struct PlaceholderReplacer<'a, 'db> {
     infcx: &'a InferCtxt<'db>,
     mapped_regions: FxIndexMap<PlaceholderRegion, BoundRegion>,
     mapped_types: FxIndexMap<Placeholder<BoundTy>, BoundTy>,
-    mapped_consts: FxIndexMap<PlaceholderConst, BoundVar>,
+    mapped_consts: FxIndexMap<PlaceholderConst, BoundConst>,
     universe_indices: &'a [Option<UniverseIndex>],
     current_index: DebruijnIndex,
 }
@@ -862,7 +865,7 @@ impl<'a, 'db> PlaceholderReplacer<'a, 'db> {
         infcx: &'a InferCtxt<'db>,
         mapped_regions: FxIndexMap<PlaceholderRegion, BoundRegion>,
         mapped_types: FxIndexMap<Placeholder<BoundTy>, BoundTy>,
-        mapped_consts: FxIndexMap<PlaceholderConst, BoundVar>,
+        mapped_consts: FxIndexMap<PlaceholderConst, BoundConst>,
         universe_indices: &'a [Option<UniverseIndex>],
         value: T,
     ) -> T {
@@ -1026,9 +1029,9 @@ pub fn sizedness_fast_path<'db>(
     if let PredicateKind::Clause(ClauseKind::Trait(trait_pred)) = predicate.kind().skip_binder()
         && trait_pred.polarity == PredicatePolarity::Positive
     {
-        let sizedness = match tcx.as_lang_item(trait_pred.def_id()) {
-            Some(TraitSolverLangItem::Sized) => SizedTraitKind::Sized,
-            Some(TraitSolverLangItem::MetaSized) => SizedTraitKind::MetaSized,
+        let sizedness = match tcx.as_trait_lang_item(trait_pred.def_id()) {
+            Some(SolverTraitLangItem::Sized) => SizedTraitKind::Sized,
+            Some(SolverTraitLangItem::MetaSized) => SizedTraitKind::MetaSized,
             _ => return false,
         };
 
@@ -1051,7 +1054,10 @@ pub fn sizedness_fast_path<'db>(
                     && clause_pred.self_ty() == trait_pred.self_ty()
                     && (clause_pred.def_id() == trait_pred.def_id()
                         || (sizedness == SizedTraitKind::MetaSized
-                            && tcx.is_lang_item(clause_pred.def_id(), TraitSolverLangItem::Sized)))
+                            && tcx.is_trait_lang_item(
+                                clause_pred.def_id(),
+                                SolverTraitLangItem::Sized,
+                            )))
                 {
                     return true;
                 }
diff --git a/src/tools/rust-analyzer/crates/hir-ty/src/utils.rs b/src/tools/rust-analyzer/crates/hir-ty/src/utils.rs
index 092d4e3a8d9..881b1c1a9db 100644
--- a/src/tools/rust-analyzer/crates/hir-ty/src/utils.rs
+++ b/src/tools/rust-analyzer/crates/hir-ty/src/utils.rs
@@ -212,10 +212,7 @@ fn direct_super_trait_refs(db: &dyn HirDatabase, trait_ref: &TraitRef, cb: impl
                 rustc_type_ir::ClauseKind::Trait(t) => {
                     let t =
                         rustc_type_ir::EarlyBinder::bind(t).instantiate(interner, trait_ref_args);
-                    let trait_id = match t.def_id() {
-                        crate::next_solver::SolverDefId::TraitId(id) => to_chalk_trait_id(id),
-                        _ => unreachable!(),
-                    };
+                    let trait_id = to_chalk_trait_id(t.def_id().0);
 
                     let substitution =
                         convert_args_for_result(interner, t.trait_ref.args.as_slice());
diff --git a/src/tools/rust-analyzer/crates/hir/src/lib.rs b/src/tools/rust-analyzer/crates/hir/src/lib.rs
index 46d3a2bcd67..6610375451d 100644
--- a/src/tools/rust-analyzer/crates/hir/src/lib.rs
+++ b/src/tools/rust-analyzer/crates/hir/src/lib.rs
@@ -86,8 +86,7 @@ use hir_ty::{
     method_resolution,
     mir::{MutBorrowKind, interpret_mir},
     next_solver::{
-        ClauseKind, DbInterner, GenericArgs, SolverDefId, infer::InferCtxt,
-        mapping::ChalkToNextSolver,
+        ClauseKind, DbInterner, GenericArgs, infer::InferCtxt, mapping::ChalkToNextSolver,
     },
     primitive::UintTy,
     traits::FnTrait,
@@ -4251,13 +4250,7 @@ impl TypeParam {
         db.generic_predicates_for_param_ns(self.id.parent(), self.id.into(), None)
             .iter()
             .filter_map(|pred| match &pred.kind().skip_binder() {
-                ClauseKind::Trait(trait_ref) => {
-                    let trait_ = match trait_ref.def_id() {
-                        SolverDefId::TraitId(t) => t,
-                        _ => unreachable!(),
-                    };
-                    Some(Trait::from(trait_))
-                }
+                ClauseKind::Trait(trait_ref) => Some(Trait::from(trait_ref.def_id().0)),
                 _ => None,
             })
             .collect()
@@ -4515,11 +4508,7 @@ impl Impl {
     pub fn trait_(self, db: &dyn HirDatabase) -> Option<Trait> {
         let trait_ref = db.impl_trait_ns(self.id)?;
         let id = trait_ref.skip_binder().def_id;
-        let id = match id {
-            SolverDefId::TraitId(id) => id,
-            _ => unreachable!(),
-        };
-        Some(Trait { id })
+        Some(Trait { id: id.0 })
     }
 
     pub fn trait_ref(self, db: &dyn HirDatabase) -> Option<TraitRef<'_>> {
@@ -4609,11 +4598,7 @@ impl<'db> TraitRef<'db> {
     }
 
     pub fn trait_(&self) -> Trait {
-        let id = match self.trait_ref.def_id {
-            SolverDefId::TraitId(id) => id,
-            _ => unreachable!(),
-        };
-        Trait { id }
+        Trait { id: self.trait_ref.def_id.0 }
     }
 
     pub fn self_ty(&self) -> TypeNs<'_> {
@@ -5984,11 +5969,7 @@ impl<'db> TypeNs<'db> {
             infcx.interner,
             [self.ty].into_iter().chain(args.iter().map(|t| t.ty)).map(|t| t.into()),
         );
-        let trait_ref = hir_ty::next_solver::TraitRef::new(
-            infcx.interner,
-            SolverDefId::TraitId(trait_.id),
-            args,
-        );
+        let trait_ref = hir_ty::next_solver::TraitRef::new(infcx.interner, trait_.id.into(), args);
 
         let pred_kind = rustc_type_ir::Binder::dummy(rustc_type_ir::PredicateKind::Clause(
             rustc_type_ir::ClauseKind::Trait(rustc_type_ir::TraitPredicate {