summaryrefslogtreecommitdiff
path: root/dhall/src/core/value.rs
diff options
context:
space:
mode:
authorNadrieril2019-08-19 23:00:49 +0200
committerNadrieril2019-08-19 23:00:49 +0200
commit730f2ebb146792994c7492b6c05f7d09d42cbccf (patch)
tree9685812388937fdd6c51165804fddf7a1bbf5e6a /dhall/src/core/value.rs
parent07a276c1d6ee892b93abbd7a73c78c96d56f4fe7 (diff)
Merge TypedValue and Value
Diffstat (limited to 'dhall/src/core/value.rs')
-rw-r--r--dhall/src/core/value.rs192
1 files changed, 63 insertions, 129 deletions
diff --git a/dhall/src/core/value.rs b/dhall/src/core/value.rs
index c4e3831..8573d11 100644
--- a/dhall/src/core/value.rs
+++ b/dhall/src/core/value.rs
@@ -35,7 +35,7 @@ use Form::{Unevaled, NF, WHNF};
struct ValueInternal {
form: Form,
value: ValueF,
- ty: Option<TypedValue>,
+ ty: Option<Value>,
}
/// Stores a possibly unevaluated value. Gets (partially) normalized on-demand,
@@ -45,11 +45,6 @@ struct ValueInternal {
#[derive(Clone)]
pub struct Value(Rc<RefCell<ValueInternal>>);
-/// A value that needs to carry a type for typechecking to work.
-/// TODO: actually enforce this.
-#[derive(Debug, Clone)]
-pub struct TypedValue(Value);
-
impl ValueInternal {
fn into_value(self) -> Value {
Value(Rc::new(RefCell::new(self)))
@@ -96,7 +91,7 @@ impl ValueInternal {
}
}
- fn get_type(&self) -> Result<&TypedValue, TypeError> {
+ fn get_type(&self) -> Result<&Value, TypeError> {
match &self.ty {
Some(t) => Ok(t),
None => Err(TypeError::new(
@@ -116,7 +111,7 @@ impl Value {
}
.into_value()
}
- pub(crate) fn from_valuef_and_type(v: ValueF, t: TypedValue) -> Value {
+ pub(crate) fn from_valuef_and_type(v: ValueF, t: Value) -> Value {
ValueInternal {
form: Unevaled,
value: v,
@@ -125,7 +120,57 @@ impl Value {
.into_value()
}
pub(crate) fn from_valuef_simple_type(v: ValueF) -> Value {
- Value::from_valuef_and_type(v, TypedValue::from_const(Const::Type))
+ Value::from_valuef_and_type(v, Value::from_const(Const::Type))
+ }
+ pub(crate) fn from_const(c: Const) -> Self {
+ match type_of_const(c) {
+ Ok(t) => Value::from_valuef_and_type(ValueF::Const(c), t),
+ Err(_) => Value::from_valuef_untyped(ValueF::Const(c)),
+ }
+ }
+ pub fn const_type() -> Self {
+ Value::from_const(Const::Type)
+ }
+
+ pub(crate) fn as_const(&self) -> Option<Const> {
+ match &*self.as_whnf() {
+ ValueF::Const(c) => Some(*c),
+ _ => None,
+ }
+ }
+
+ fn as_internal(&self) -> Ref<ValueInternal> {
+ self.0.borrow()
+ }
+ fn as_internal_mut(&self) -> RefMut<ValueInternal> {
+ self.0.borrow_mut()
+ }
+ /// This is what you want if you want to pattern-match on the value.
+ /// WARNING: drop this ref before normalizing the same value or you will run into BorrowMut
+ /// panics.
+ pub(crate) fn as_whnf(&self) -> Ref<ValueF> {
+ self.do_normalize_whnf();
+ Ref::map(self.as_internal(), ValueInternal::as_whnf)
+ }
+
+ // TODO: rename `normalize_to_expr`
+ pub(crate) fn to_expr(&self) -> NormalizedSubExpr {
+ self.as_whnf().normalize_to_expr()
+ }
+ // TODO: rename `normalize_to_expr_maybe_alpha`
+ pub(crate) fn to_expr_alpha(&self) -> NormalizedSubExpr {
+ self.as_whnf().normalize_to_expr_maybe_alpha(true)
+ }
+ // TODO: deprecated
+ pub(crate) fn to_value(&self) -> Value {
+ self.clone()
+ }
+ /// TODO: cloning a valuef can often be avoided
+ pub(crate) fn to_whnf(&self) -> ValueF {
+ self.as_whnf().clone()
+ }
+ pub(crate) fn into_typed(self) -> Typed {
+ Typed::from_value(self)
}
/// Mutates the contents. If no one else shares this thunk,
@@ -138,20 +183,12 @@ impl Value {
None => f(&mut self.as_internal_mut()),
}
}
-
/// Normalizes contents to normal form; faster than `normalize_nf` if
/// no one else shares this thunk.
pub(crate) fn normalize_mut(&mut self) {
self.mutate_internal(|vint| vint.normalize_nf())
}
- fn as_internal(&self) -> Ref<ValueInternal> {
- self.0.borrow()
- }
- fn as_internal_mut(&self) -> RefMut<ValueInternal> {
- self.0.borrow_mut()
- }
-
fn do_normalize_whnf(&self) {
let borrow = self.as_internal();
match borrow.form {
@@ -163,7 +200,6 @@ impl Value {
WHNF | NF => {}
}
}
-
fn do_normalize_nf(&self) {
let borrow = self.as_internal();
match borrow.form {
@@ -176,26 +212,14 @@ impl Value {
}
}
- // WARNING: avoid normalizing any thunk while holding on to this ref
- // or you could run into BorrowMut panics
+ /// WARNING: avoid normalizing any thunk while holding on to this ref
+ /// or you could run into BorrowMut panics
+ // TODO: rename to `as_nf`
pub(crate) fn normalize_nf(&self) -> Ref<ValueF> {
self.do_normalize_nf();
Ref::map(self.as_internal(), ValueInternal::as_nf)
}
- /// This is what you want if you want to pattern-match on the value.
- /// WARNING: drop this ref before normalizing the same value or you will run into BorrowMut
- /// panics.
- pub(crate) fn as_whnf(&self) -> Ref<ValueF> {
- self.do_normalize_whnf();
- Ref::map(self.as_internal(), ValueInternal::as_whnf)
- }
-
- /// TODO: cloning a valuef can often be avoided
- pub(crate) fn to_whnf(&self) -> ValueF {
- self.as_whnf().clone()
- }
-
pub(crate) fn normalize_to_expr_maybe_alpha(
&self,
alpha: bool,
@@ -211,83 +235,11 @@ impl Value {
apply_any(self.clone(), th)
}
- pub(crate) fn get_type(&self) -> Result<Cow<'_, TypedValue>, TypeError> {
+ pub(crate) fn get_type(&self) -> Result<Cow<'_, Value>, TypeError> {
Ok(Cow::Owned(self.as_internal().get_type()?.clone()))
}
}
-impl TypedValue {
- pub fn from_value(th: Value) -> Self {
- TypedValue(th)
- }
- pub(crate) fn from_valuef_untyped(v: ValueF) -> TypedValue {
- TypedValue::from_value(Value::from_valuef_untyped(v))
- }
- pub(crate) fn from_valuef_and_type(v: ValueF, t: TypedValue) -> Self {
- TypedValue(Value::from_valuef_and_type(v, t))
- }
- // TODO: do something with the info that the type is Type. Maybe check
- // is a type is present ?
- pub(crate) fn from_value_simple_type(th: Value) -> Self {
- TypedValue::from_value(th)
- }
- pub(crate) fn from_const(c: Const) -> Self {
- match type_of_const(c) {
- Ok(t) => TypedValue::from_valuef_and_type(ValueF::Const(c), t),
- Err(_) => TypedValue::from_valuef_untyped(ValueF::Const(c)),
- }
- }
- pub fn const_type() -> Self {
- TypedValue::from_const(Const::Type)
- }
-
- pub(crate) fn normalize_nf(&self) -> ValueF {
- self.0.normalize_nf().clone()
- }
-
- pub(crate) fn normalize_to_expr_maybe_alpha(
- &self,
- alpha: bool,
- ) -> OutputSubExpr {
- self.normalize_nf().normalize_to_expr_maybe_alpha(alpha)
- }
-
- /// WARNING: drop this ref before normalizing the same value or you will run into BorrowMut
- /// panics.
- pub(crate) fn as_whnf(&self) -> Ref<ValueF> {
- self.0.as_whnf()
- }
- pub(crate) fn to_whnf(&self) -> ValueF {
- self.0.to_whnf()
- }
- pub(crate) fn to_expr(&self) -> NormalizedSubExpr {
- self.as_whnf().normalize_to_expr()
- }
- pub(crate) fn to_expr_alpha(&self) -> NormalizedSubExpr {
- self.as_whnf().normalize_to_expr_maybe_alpha(true)
- }
- pub(crate) fn to_value(&self) -> Value {
- self.0.clone()
- }
- pub(crate) fn into_typed(self) -> Typed {
- Typed::from_typedvalue(self)
- }
- pub(crate) fn as_const(&self) -> Option<Const> {
- match &*self.as_whnf() {
- ValueF::Const(c) => Some(*c),
- _ => None,
- }
- }
-
- pub(crate) fn normalize_mut(&mut self) {
- self.0.normalize_mut()
- }
-
- pub(crate) fn get_type(&self) -> Result<Cow<'_, TypedValue>, TypeError> {
- self.0.get_type()
- }
-}
-
impl Shift for Value {
fn shift(&self, delta: isize, var: &AlphaVar) -> Option<Self> {
Some(Value(self.0.shift(delta, var)?))
@@ -304,20 +256,14 @@ impl Shift for ValueInternal {
}
}
-impl Shift for TypedValue {
- fn shift(&self, delta: isize, var: &AlphaVar) -> Option<Self> {
- Some(TypedValue(self.0.shift(delta, var)?))
- }
-}
-
-impl Subst<TypedValue> for Value {
- fn subst_shift(&self, var: &AlphaVar, val: &TypedValue) -> Self {
+impl Subst<Value> for Value {
+ fn subst_shift(&self, var: &AlphaVar, val: &Value) -> Self {
Value(self.0.subst_shift(var, val))
}
}
-impl Subst<TypedValue> for ValueInternal {
- fn subst_shift(&self, var: &AlphaVar, val: &TypedValue) -> Self {
+impl Subst<Value> for ValueInternal {
+ fn subst_shift(&self, var: &AlphaVar, val: &Value) -> Self {
ValueInternal {
// The resulting value may not stay in wnhf after substitution
form: Unevaled,
@@ -327,12 +273,7 @@ impl Subst<TypedValue> for ValueInternal {
}
}
-impl Subst<TypedValue> for TypedValue {
- fn subst_shift(&self, var: &AlphaVar, val: &TypedValue) -> Self {
- TypedValue(self.0.subst_shift(var, val))
- }
-}
-
+// TODO: use Rc comparison to shortcut on identical pointers
impl std::cmp::PartialEq for Value {
fn eq(&self, other: &Self) -> bool {
*self.as_whnf() == *other.as_whnf()
@@ -340,13 +281,6 @@ impl std::cmp::PartialEq for Value {
}
impl std::cmp::Eq for Value {}
-impl std::cmp::PartialEq for TypedValue {
- fn eq(&self, other: &Self) -> bool {
- &*self.as_whnf() == &*other.as_whnf()
- }
-}
-impl std::cmp::Eq for TypedValue {}
-
impl std::fmt::Debug for Value {
fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
let vint: &ValueInternal = &self.as_internal();