about summary refs log tree commit diff
path: root/compiler
diff options
context:
space:
mode:
authorGuillaume Gomez <guillaume1.gomez@gmail.com>2023-06-09 16:29:02 +0200
committerGitHub <noreply@github.com>2023-06-09 16:29:02 +0200
commit4ef72570189401dee5b148fd423b36cfd37fa3f7 (patch)
treefaf1c9d11e60fd3df5941ae1679293cd7d0e8d87 /compiler
parentf83c8e43170da30341d4d4cfcdf7039dc7f987d3 (diff)
parentd5e25d40c969009d0f40cbf6280339f2839e19c4 (diff)
downloadrust-4ef72570189401dee5b148fd423b36cfd37fa3f7.tar.gz
rust-4ef72570189401dee5b148fd423b36cfd37fa3f7.zip
Rollup merge of #112442 - compiler-errors:next-solver-deduplicate-region-constraints, r=lcnr
Deduplicate identical region constraints in new solver

the new solver doesn't track whether we've already proven a goal like the fulfillment context's obligation forest does, so we may be instantiating a canonical response (and specifically, its nested region obligations) quite a few times.

This may lead to exponentially gathering up identical region constraints for things like auto traits, so let's deduplicate region constraints when in `compute_external_query_constraints`.

r? ``@lcnr``
Diffstat (limited to 'compiler')
-rw-r--r--compiler/rustc_trait_selection/src/solve/eval_ctxt/canonical.rs6
1 files changed, 5 insertions, 1 deletions
diff --git a/compiler/rustc_trait_selection/src/solve/eval_ctxt/canonical.rs b/compiler/rustc_trait_selection/src/solve/eval_ctxt/canonical.rs
index bca2343e424..72b3c3d0180 100644
--- a/compiler/rustc_trait_selection/src/solve/eval_ctxt/canonical.rs
+++ b/compiler/rustc_trait_selection/src/solve/eval_ctxt/canonical.rs
@@ -11,6 +11,7 @@
 use super::{CanonicalInput, Certainty, EvalCtxt, Goal};
 use crate::solve::canonicalize::{CanonicalizeMode, Canonicalizer};
 use crate::solve::{CanonicalResponse, QueryResult, Response};
+use rustc_data_structures::fx::FxHashSet;
 use rustc_index::IndexVec;
 use rustc_infer::infer::canonical::query_response::make_query_region_constraints;
 use rustc_infer::infer::canonical::CanonicalVarValues;
@@ -147,7 +148,7 @@ impl<'tcx> EvalCtxt<'_, 'tcx> {
         // Cannot use `take_registered_region_obligations` as we may compute the response
         // inside of a `probe` whenever we have multiple choices inside of the solver.
         let region_obligations = self.infcx.inner.borrow().region_obligations().to_owned();
-        let region_constraints = self.infcx.with_region_constraints(|region_constraints| {
+        let mut region_constraints = self.infcx.with_region_constraints(|region_constraints| {
             make_query_region_constraints(
                 self.tcx(),
                 region_obligations
@@ -157,6 +158,9 @@ impl<'tcx> EvalCtxt<'_, 'tcx> {
             )
         });
 
+        let mut seen = FxHashSet::default();
+        region_constraints.outlives.retain(|outlives| seen.insert(*outlives));
+
         let mut opaque_types = self.infcx.clone_opaque_types_for_query_response();
         // Only return opaque type keys for newly-defined opaques
         opaque_types.retain(|(a, _)| {