Skip to content

Commit

Permalink
Merge pull request #140 from sunjay/implallowed
Browse files Browse the repository at this point in the history
Rename IsLocal to ImplAllowed
  • Loading branch information
nikomatsakis authored May 28, 2018
2 parents 1b9140c + 6658d35 commit 733f12f
Show file tree
Hide file tree
Showing 9 changed files with 31 additions and 23 deletions.
2 changes: 1 addition & 1 deletion chalk-parse/src/ast.rs
Original file line number Diff line number Diff line change
Expand Up @@ -218,7 +218,7 @@ pub enum WhereClause {
UnifyLifetimes { a: Lifetime, b: Lifetime },
TraitInScope { trait_name: Identifier },
Derefs { source: Ty, target: Ty },
TyIsLocal { ty: Ty },
IsLocal { ty: Ty },
}

pub struct QuantifiedWhereClause {
Expand Down
2 changes: 1 addition & 1 deletion chalk-parse/src/parser.lalrpop
Original file line number Diff line number Diff line change
Expand Up @@ -273,7 +273,7 @@ WhereClause: WhereClause = {
"InScope" "(" <t:Id> ")" => WhereClause::TraitInScope { trait_name: t },
"Derefs" "(" <source:Ty> "," <target:Ty> ")" => WhereClause::Derefs { source, target },

"IsLocal" "(" <ty:Ty> ")" => WhereClause::TyIsLocal { ty },
"IsLocal" "(" <ty:Ty> ")" => WhereClause::IsLocal { ty },
};

QuantifiedWhereClause: QuantifiedWhereClause = {
Expand Down
2 changes: 1 addition & 1 deletion src/fold.rs
Original file line number Diff line number Diff line change
Expand Up @@ -425,7 +425,7 @@ enum_fold!(PolarizedTraitRef[] { Positive(a), Negative(a) });
enum_fold!(ParameterKind[T,L] { Ty(a), Lifetime(a) } where T: Fold, L: Fold);
enum_fold!(WhereClauseAtom[] { Implemented(a), ProjectionEq(a) });
enum_fold!(DomainGoal[] { Holds(a), WellFormed(a), FromEnv(a), Normalize(a), UnselectedNormalize(a),
WellFormedTy(a), FromEnvTy(a), InScope(a), Derefs(a), IsLocalTy(a), IsLocalTraitRef(a) });
WellFormedTy(a), FromEnvTy(a), InScope(a), Derefs(a), IsLocal(a), LocalImplAllowed(a) });
enum_fold!(LeafGoal[] { EqGoal(a), DomainGoal(a) });
enum_fold!(Constraint[] { LifetimeEq(a, b) });
enum_fold!(Goal[] { Quantified(qkind, subgoal), Implies(wc, subgoal), And(g1, g2), Not(g),
Expand Down
14 changes: 11 additions & 3 deletions src/ir.rs
Original file line number Diff line number Diff line change
Expand Up @@ -269,7 +269,7 @@ pub enum InlineBound {

impl InlineBound {
/// Applies the `InlineBound` to `self_ty` and lowers to a [`DomainGoal`].
///
///
/// Because an `InlineBound` does not know anything about what it's binding,
/// you must provide that type as `self_ty`.
crate fn lower_with_self(&self, self_ty: Ty) -> Vec<DomainGoal> {
Expand Down Expand Up @@ -691,8 +691,16 @@ pub enum DomainGoal {
/// True if a type is considered to have been "defined" by the current crate. This is true for
/// a `struct Foo { }` but false for a `extern struct Foo { }`. However, for fundamental types
/// like `Box<T>`, it is true if `T` is local.
IsLocalTy(Ty),
IsLocalTraitRef(TraitRef),
IsLocal(Ty),

/// Used to dictate when trait impls are allowed in the current (local) crate based on the
/// orphan rules.
///
/// `LocalImplAllowed(T: Trait)` is true if the type T is allowed to impl trait Trait in
/// the current crate. Under the current rules, this is unconditionally true for all types if
/// the Trait is considered to be "defined" in the current crate. If that is not the case, then
/// `LocalImplAllowed(T: Trait)` can still be true if `IsLocal(T)` is true.
LocalImplAllowed(TraitRef),
}

pub type QuantifiedDomainGoal = Binders<DomainGoal>;
Expand Down
4 changes: 2 additions & 2 deletions src/ir/debug.rs
Original file line number Diff line number Diff line change
Expand Up @@ -206,8 +206,8 @@ impl Debug for DomainGoal {
DomainGoal::FromEnvTy(t) => write!(fmt, "FromEnv({:?})", t),
DomainGoal::InScope(n) => write!(fmt, "InScope({:?})", n),
DomainGoal::Derefs(n) => write!(fmt, "Derefs({:?})", n),
DomainGoal::IsLocalTy(n) => write!(fmt, "IsLocalTy({:?})", n),
DomainGoal::IsLocalTraitRef(n) => write!(fmt, "IsLocalTraitRef({:?})", n),
DomainGoal::IsLocal(n) => write!(fmt, "IsLocal({:?})", n),
DomainGoal::LocalImplAllowed(n) => write!(fmt, "LocalImplAllowed({:?})", n),
}
}
}
Expand Down
6 changes: 3 additions & 3 deletions src/ir/lowering.rs
Original file line number Diff line number Diff line change
Expand Up @@ -494,8 +494,8 @@ impl LowerWhereClause<ir::DomainGoal> for WhereClause {
target: target.lower(env)?
})
],
WhereClause::TyIsLocal { ty } => vec![
ir::DomainGoal::IsLocalTy(ty.lower(env)?)
WhereClause::IsLocal { ty } => vec![
ir::DomainGoal::IsLocal(ty.lower(env)?)
],
};
Ok(goals)
Expand Down Expand Up @@ -527,7 +527,7 @@ impl LowerWhereClause<ir::LeafGoal> for WhereClause {
| WhereClause::TyFromEnv { .. }
| WhereClause::TraitRefFromEnv { .. }
| WhereClause::Derefs { .. }
| WhereClause::TyIsLocal { .. } => {
| WhereClause::IsLocal { .. } => {
let goals: Vec<ir::DomainGoal> = self.lower(env)?;
goals.into_iter().casted().collect()
}
Expand Down
16 changes: 8 additions & 8 deletions src/rules.rs
Original file line number Diff line number Diff line change
Expand Up @@ -294,7 +294,7 @@ impl ir::StructDatum {
//
// If the type Foo is not marked `extern`, we also generate:
//
// forall<T> { IsLocalTy(Foo<T>) }
// forall<T> { IsLocal(Foo<T>) }
//
// Given an `extern` type that is also fundamental:
//
Expand All @@ -303,7 +303,7 @@ impl ir::StructDatum {
//
// We generate the following clause:
//
// forall<T> { IsLocalTy(Box<T>) :- IsLocalTy(T) }
// forall<T> { IsLocal(Box<T>) :- IsLocal(T) }

let wf = self.binders.map_ref(|bound_datum| {
ir::ProgramClauseImplication {
Expand All @@ -323,16 +323,16 @@ impl ir::StructDatum {

// Types that are not marked `extern` satisfy IsLocal(TypeName)
if !self.binders.value.flags.external {
// `IsLocalTy(Ty)` depends *only* on whether the type is marked extern and nothing else
// `IsLocal(Ty)` depends *only* on whether the type is marked extern and nothing else
let is_local = self.binders.map_ref(|bound_datum| ir::ProgramClauseImplication {
consequence: ir::DomainGoal::IsLocalTy(bound_datum.self_ty.clone().cast()),
consequence: ir::DomainGoal::IsLocal(bound_datum.self_ty.clone().cast()),
conditions: Vec::new(),
}).cast();

clauses.push(is_local);
} else if self.binders.value.flags.fundamental {
// If a type is `extern`, but is also `#[fundamental]`, it satisfies IsLocalTy
// if and only if its parameters satisfy IsLocalTy
// If a type is `extern`, but is also `#[fundamental]`, it satisfies IsLocal
// if and only if its parameters satisfy IsLocal

// Fundamental types must always have at least one type parameter for this rule to
// make any sense. We currently do not have have any fundamental types with more than
Expand All @@ -343,9 +343,9 @@ impl ir::StructDatum {
"Only fundamental types with a single parameter are supported");

let local_fundamental = self.binders.map_ref(|bound_datum| ir::ProgramClauseImplication {
consequence: ir::DomainGoal::IsLocalTy(bound_datum.self_ty.clone().cast()),
consequence: ir::DomainGoal::IsLocal(bound_datum.self_ty.clone().cast()),
conditions: vec![
ir::DomainGoal::IsLocalTy(
ir::DomainGoal::IsLocal(
// This unwrap is safe because we asserted above for the presence of a type
// parameter
bound_datum.self_ty.first_type_parameter().unwrap()
Expand Down
4 changes: 2 additions & 2 deletions src/rules/wf.rs
Original file line number Diff line number Diff line change
Expand Up @@ -143,8 +143,8 @@ impl FoldInputTypes for DomainGoal {
DomainGoal::FromEnv(..) |
DomainGoal::WellFormedTy(..) |
DomainGoal::FromEnvTy(..) |
DomainGoal::IsLocalTy(..) |
DomainGoal::IsLocalTraitRef(..) |
DomainGoal::IsLocal(..) |
DomainGoal::LocalImplAllowed(..) |
DomainGoal::Derefs(..) => panic!("unexpected where clause"),

DomainGoal::InScope(..) => (),
Expand Down
4 changes: 2 additions & 2 deletions src/zip.rs
Original file line number Diff line number Diff line change
Expand Up @@ -227,8 +227,8 @@ enum_zip!(DomainGoal {
FromEnvTy,
InScope,
Derefs,
IsLocalTy,
IsLocalTraitRef
IsLocal,
LocalImplAllowed
});
enum_zip!(LeafGoal { DomainGoal, EqGoal });
enum_zip!(ProgramClause { Implies, ForAll });
Expand Down

0 comments on commit 733f12f

Please sign in to comment.