Skip to content

Commit 3c3caae

Browse files
authored
Merge pull request #129 from leodasvacas/split-off-context-ops
Split off ContextOps from Context
2 parents 92f0203 + c8a74b2 commit 3c3caae

File tree

5 files changed

+42
-34
lines changed

5 files changed

+42
-34
lines changed

chalk-engine/src/context.rs

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,9 @@ use std::hash::Hash;
77
crate mod prelude;
88

99
/// The "context" in which the SLG solver operates.
10-
pub trait Context: Sized + Clone + Debug + ContextOps<Self> + AggregateOps<Self> {
10+
// FIXME(leodasvacas): Clone and Debug bounds are just for easy derive,
11+
// they are not actually necessary.
12+
pub trait Context: Clone + Debug {
1113
type CanonicalExClause: Debug;
1214

1315
/// A map between universes. These are produced when
@@ -125,7 +127,7 @@ pub trait InferenceContext<C: Context>: ExClauseContext<C> {
125127
) -> Self::Environment;
126128
}
127129

128-
pub trait ContextOps<C: Context> {
130+
pub trait ContextOps<C: Context>: Sized + Clone + Debug + AggregateOps<C> {
129131
/// True if this is a coinductive goal -- e.g., proving an auto trait.
130132
fn is_coinductive(&self, goal: &C::UCanonicalGoalInEnvironment) -> bool;
131133

chalk-engine/src/context/prelude.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
crate use super::Context;
44
crate use super::ContextOps;
5+
crate use super::AggregateOps;
56
crate use super::ResolventOps;
67
crate use super::TruncateOps;
78
crate use super::InferenceTable;

chalk-engine/src/forest.rs

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -6,17 +6,17 @@ use crate::stack::{Stack, StackIndex};
66
use crate::tables::Tables;
77
use crate::table::{Answer, AnswerIndex};
88

9-
pub struct Forest<C: Context> {
9+
pub struct Forest<C: Context, CO: ContextOps<C>> {
1010
#[allow(dead_code)]
11-
crate context: C,
11+
crate context: CO,
1212
crate tables: Tables<C>,
1313
crate stack: Stack,
1414

1515
dfn: DepthFirstNumber,
1616
}
1717

18-
impl<C: Context> Forest<C> {
19-
pub fn new(context: C) -> Self {
18+
impl<C: Context, CO: ContextOps<C>> Forest<C, CO> {
19+
pub fn new(context: CO) -> Self {
2020
Forest {
2121
context,
2222
tables: Tables::new(),
@@ -79,7 +79,7 @@ impl<C: Context> Forest<C> {
7979
/// as much work towards `goal` as it has to (and that works is
8080
/// cached for future attempts).
8181
pub fn solve(&mut self, goal: &C::UCanonicalGoalInEnvironment) -> Option<C::Solution> {
82-
self.context.clone().make_solution(C::canonical(&goal), self.iter_answers(goal))
82+
self.context.clone().make_solution(CO::canonical(&goal), self.iter_answers(goal))
8383
}
8484

8585
/// True if all the tables on the stack starting from `depth` and
@@ -122,13 +122,13 @@ impl<C: Context> Forest<C> {
122122
}
123123
}
124124

125-
struct ForestSolver<'forest, C: Context + 'forest> {
126-
forest: &'forest mut Forest<C>,
125+
struct ForestSolver<'forest, C: Context + 'forest, CO: ContextOps<C> + 'forest> {
126+
forest: &'forest mut Forest<C, CO>,
127127
table: TableIndex,
128128
answer: AnswerIndex,
129129
}
130130

131-
impl<'forest, C> AnswerStream<C> for ForestSolver<'forest, C>
131+
impl<'forest, C, CO: ContextOps<C>> AnswerStream<C> for ForestSolver<'forest, C, CO>
132132
where
133133
C: Context,
134134
{

chalk-engine/src/logic.rs

Lines changed: 28 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ use crate::stack::StackIndex;
88
use crate::strand::{CanonicalStrand, SelectedSubgoal, Strand};
99
use crate::table::{Answer, AnswerIndex};
1010
use fxhash::FxHashSet;
11+
use std::marker::PhantomData;
1112
use std::mem;
1213

1314
type RootSearchResult<T> = Result<T, RootSearchFail>;
@@ -78,7 +79,7 @@ enum EnsureSuccess {
7879
Coinductive,
7980
}
8081

81-
impl<C: Context> Forest<C> {
82+
impl<C: Context, CO: ContextOps<C>> Forest<C, CO> {
8283
/// Ensures that answer with the given index is available from the
8384
/// given table. This may require activating a strand. Returns
8485
/// `Ok(())` if the answer is available and otherwise a
@@ -111,11 +112,11 @@ impl<C: Context> Forest<C> {
111112
) -> bool {
112113
if let Some(answer) = self.tables[table].answer(answer) {
113114
info!("answer cached = {:?}", answer);
114-
return test(C::inference_normalized_subst_from_subst(&answer.subst));
115+
return test(CO::inference_normalized_subst_from_subst(&answer.subst));
115116
}
116117

117118
self.tables[table].strands_mut().any(|strand| {
118-
test(C::inference_normalized_subst_from_ex_clause(&strand.canonical_ex_clause))
119+
test(CO::inference_normalized_subst_from_ex_clause(&strand.canonical_ex_clause))
119120
})
120121
}
121122

@@ -205,7 +206,7 @@ impl<C: Context> Forest<C> {
205206
loop {
206207
match self.tables[table].pop_next_strand() {
207208
Some(canonical_strand) => {
208-
let num_universes = C::num_universes(&self.tables[table].table_goal);
209+
let num_universes = CO::num_universes(&self.tables[table].table_goal);
209210
let result = Self::with_instantiated_strand(
210211
self.context.clone(),
211212
num_universes,
@@ -263,10 +264,10 @@ impl<C: Context> Forest<C> {
263264
}
264265

265266
fn with_instantiated_strand<R>(
266-
context: C,
267+
context: CO,
267268
num_universes: usize,
268269
canonical_strand: &CanonicalStrand<C>,
269-
op: impl WithInstantiatedStrand<C, Output = R>,
270+
op: impl WithInstantiatedStrand<C, CO, Output = R>,
270271
) -> R {
271272
let CanonicalStrand {
272273
canonical_ex_clause,
@@ -278,15 +279,18 @@ impl<C: Context> Forest<C> {
278279
With {
279280
op,
280281
selected_subgoal: selected_subgoal.clone(),
282+
ops: PhantomData,
281283
},
282284
);
283285

284-
struct With<C: Context, OP: WithInstantiatedStrand<C>> {
286+
struct With<C: Context, CO: ContextOps<C>, OP: WithInstantiatedStrand<C, CO>> {
285287
op: OP,
286288
selected_subgoal: Option<SelectedSubgoal<C>>,
289+
ops: PhantomData<CO>,
287290
}
288291

289-
impl<C: Context, OP: WithInstantiatedStrand<C>> WithInstantiatedExClause<C> for With<C, OP> {
292+
impl<C: Context, CO: ContextOps<C>, OP: WithInstantiatedStrand<C, CO>>
293+
WithInstantiatedExClause<C> for With<C, CO, OP> {
290294
type Output = OP::Output;
291295

292296
fn with<I: InferenceContext<C>>(
@@ -399,7 +403,7 @@ impl<C: Context> Forest<C> {
399403
fn delay_strands_after_cycle(&mut self, table: TableIndex, visited: &mut FxHashSet<TableIndex>) {
400404
let mut tables = vec![];
401405

402-
let num_universes = C::num_universes(&self.tables[table].table_goal);
406+
let num_universes = CO::num_universes(&self.tables[table].table_goal);
403407
for canonical_strand in self.tables[table].strands_mut() {
404408
// FIXME if CanonicalExClause were not held abstract, we
405409
// could do this in place like we used to (and
@@ -627,8 +631,8 @@ impl<C: Context> Forest<C> {
627631
// must be backed by an impl *eventually*).
628632
let is_trivial_answer = {
629633
answer.delayed_literals.is_empty()
630-
&& C::is_trivial_substitution(&self.tables[table].table_goal, &answer.subst)
631-
&& C::empty_constraints(&answer.subst)
634+
&& CO::is_trivial_substitution(&self.tables[table].table_goal, &answer.subst)
635+
&& CO::empty_constraints(&answer.subst)
632636
};
633637

634638
if self.tables[table].push_answer(answer) {
@@ -726,12 +730,13 @@ impl<C: Context> Forest<C> {
726730
PushInitialStrandsInstantiated { table, this: self },
727731
);
728732

729-
struct PushInitialStrandsInstantiated<'a, C: Context + 'a> {
733+
struct PushInitialStrandsInstantiated<'a, C: Context + 'a, CO: ContextOps<C> + 'a> {
730734
table: TableIndex,
731-
this: &'a mut Forest<C>,
735+
this: &'a mut Forest<C, CO>,
732736
}
733737

734-
impl<C: Context> WithInstantiatedUCanonicalGoal<C> for PushInitialStrandsInstantiated<'a, C> {
738+
impl<C: Context, CO: ContextOps<C>> WithInstantiatedUCanonicalGoal<C>
739+
for PushInitialStrandsInstantiated<'a, C, CO> {
735740
type Output = ();
736741

737742
fn with<I: InferenceContext<C>>(
@@ -1044,10 +1049,10 @@ impl<C: Context> Forest<C> {
10441049
),
10451050
};
10461051

1047-
let table_goal = &C::map_goal_from_canonical(&universe_map,
1048-
&C::canonical(&self.tables[subgoal_table].table_goal));
1052+
let table_goal = &CO::map_goal_from_canonical(&universe_map,
1053+
&CO::canonical(&self.tables[subgoal_table].table_goal));
10491054
let answer_subst =
1050-
&C::map_subst_from_canonical(&universe_map, &self.answer(subgoal_table, answer_index).subst);
1055+
&CO::map_subst_from_canonical(&universe_map, &self.answer(subgoal_table, answer_index).subst);
10511056
match infer.apply_answer_subst(ex_clause, &subgoal, table_goal, answer_subst) {
10521057
Ok(mut ex_clause) => {
10531058
// If the answer had delayed literals, we have to
@@ -1301,18 +1306,18 @@ impl<C: Context> Forest<C> {
13011306
}
13021307
}
13031308

1304-
trait WithInstantiatedStrand<C: Context> {
1309+
trait WithInstantiatedStrand<C: Context, CO: AggregateOps<C>> {
13051310
type Output;
13061311

13071312
fn with(self, strand: Strand<'_, C, impl InferenceContext<C>>) -> Self::Output;
13081313
}
13091314

1310-
struct PursueStrand<'a, C: Context + 'a> {
1311-
forest: &'a mut Forest<C>,
1315+
struct PursueStrand<'a, C: Context + 'a, CO: ContextOps<C> + 'a> {
1316+
forest: &'a mut Forest<C, CO>,
13121317
depth: StackIndex,
13131318
}
13141319

1315-
impl<C: Context> WithInstantiatedStrand<C> for PursueStrand<'a, C> {
1320+
impl<C: Context, CO: ContextOps<C>> WithInstantiatedStrand<C, CO> for PursueStrand<'a, C, CO> {
13161321
type Output = StrandResult<C, ()>;
13171322

13181323
fn with(self, strand: Strand<'_, C, impl InferenceContext<C>>) -> Self::Output {
@@ -1324,10 +1329,10 @@ struct DelayStrandAfterCycle {
13241329
table: TableIndex,
13251330
}
13261331

1327-
impl<C: Context> WithInstantiatedStrand<C> for DelayStrandAfterCycle {
1332+
impl<C: Context, CO: ContextOps<C>> WithInstantiatedStrand<C, CO> for DelayStrandAfterCycle {
13281333
type Output = (CanonicalStrand<C>, TableIndex);
13291334

13301335
fn with(self, strand: Strand<'_, C, impl InferenceContext<C>>) -> Self::Output {
1331-
<Forest<C>>::delay_strand_after_cycle(self.table, strand)
1336+
<Forest<C, CO>>::delay_strand_after_cycle(self.table, strand)
13321337
}
13331338
}

chalk-engine/src/simplify.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ use crate::forest::Forest;
44
use crate::hh::HhGoal;
55
use crate::context::prelude::*;
66

7-
impl<C: Context> Forest<C> {
7+
impl<C: Context, CO: ContextOps<C>> Forest<C, CO> {
88
/// Simplifies an HH goal into a series of positive domain goals
99
/// and negative HH goals. This operation may fail if the HH goal
1010
/// includes unifications that cannot be completed.

0 commit comments

Comments
 (0)