diff options
-rw-r--r-- | Tasks.org | 4 | ||||
-rw-r--r-- | src/crates/library/src/btreemap.rs | 26 | ||||
-rw-r--r-- | src/crates/library/src/hashmap.rs | 36 | ||||
-rw-r--r-- | src/crates/library/src/list.rs | 12 | ||||
-rw-r--r-- | src/crates/library/src/vector.rs | 12 | ||||
-rw-r--r-- | src/crates/primrose/src/bounded_ops.rs | 109 | ||||
-rw-r--r-- | src/crates/primrose/src/parser.rs | 14 | ||||
-rw-r--r-- | src/tests/aoc-2021-09/src/types.pr.rs | 4 | ||||
-rw-r--r-- | src/tests/example_stack/src/types.pr.rs | 2 | ||||
-rw-r--r-- | src/tests/prime_sieve/src/types.pr.rs | 2 | ||||
-rw-r--r-- | thesis/parts/design.tex | 2 |
11 files changed, 163 insertions, 60 deletions
@@ -233,6 +233,10 @@ Ideas: **** TODO Resiliency, etc +require_cdr fuckery +renaming of op- stuff +boolean literals + *** TODO Integration w/ Cargo **** TODO Metadata fetching diff --git a/src/crates/library/src/btreemap.rs b/src/crates/library/src/btreemap.rs index 3943eee..5e6891b 100644 --- a/src/crates/library/src/btreemap.rs +++ b/src/crates/library/src/btreemap.rs @@ -12,10 +12,10 @@ Mapping impl<K: Ord + Hash, V> Mapping<K, V> for BTreeMap<K, V> { /*LIBSPEC* /*OPNAME* - len len pre-len post-len + len op-len pre-len post-len *ENDOPNAME*/ (define (pre-len xs) (is-map? xs)) - (define (len xs) (cons xs (length xs))) + (define (op-len xs) (cons xs (length xs))) (define (post-len xs r) (equal? r (len xs))) *ENDLIBSPEC*/ fn len(&self) -> usize { @@ -24,10 +24,10 @@ impl<K: Ord + Hash, V> Mapping<K, V> for BTreeMap<K, V> { /*LIBSPEC* /*OPNAME* - contains contains pre-contains post-contains + contains op-contains pre-contains post-contains *ENDOPNAME*/ (define (pre-contains xs) (is-map? xs)) - (define (contains xs k) (assoc k xs)) + (define (op-contains xs k) (assoc k xs)) (define (post-contains xs k r) (equal? r (contains xs k))) *ENDLIBSPEC*/ fn contains(&mut self, x: &K) -> bool { @@ -36,14 +36,14 @@ impl<K: Ord + Hash, V> Mapping<K, V> for BTreeMap<K, V> { /*LIBSPEC* /*OPNAME* - insert insert pre-insert post-insert + insert op-insert pre-insert post-insert *ENDOPNAME*/ (define (pre-insert xs) (is-map? xs)) - (define (insert xs k v) + (define (op-insert xs k v) (let ([idx (index-where xs (lambda (p) (equal? k (car p))))]) (cond [idx (list-set xs idx (cons k v))] [else (list* (cons k v) xs)]))) - (define (post-insert xs k v r) (equal? r (insert xs k v))) + (define (post-insert xs k v r) (equal? r (op-insert xs k v))) *ENDLIBSPEC*/ fn insert(&mut self, key: K, val: V) -> Option<V> { BTreeMap::insert(self, key, val) @@ -54,8 +54,8 @@ impl<K: Ord + Hash, V> Mapping<K, V> for BTreeMap<K, V> { get get pre-get post-get *ENDOPNAME*/ (define (pre-get xs) (is-map? xs)) - (define (get xs k) (cdr (assoc k xs))) - (define (post-get xs k r) (equal? r (get xs k))) + (define (op-get xs k) (cdr (assoc k xs))) + (define (post-get xs k r) (equal? r (op-get xs k))) *ENDLIBSPEC*/ fn get(&self, key: &K) -> Option<&V> { BTreeMap::get(self, key) @@ -66,8 +66,8 @@ impl<K: Ord + Hash, V> Mapping<K, V> for BTreeMap<K, V> { remove remove pre-remove post-remove *ENDOPNAME*/ (define (pre-remove xs) (is-map? xs)) - (define (remove xs k) (cdr (assoc k xs))) - (define (post-remove xs k r) (equal? r (remove xs k))) + (define (op-remove xs k) (cdr (assoc k xs))) + (define (post-remove xs k r) (equal? r (op-remove xs k))) *ENDLIBSPEC*/ fn remove(&mut self, key: &K) -> Option<V> { BTreeMap::remove(self, key) @@ -78,8 +78,8 @@ impl<K: Ord + Hash, V> Mapping<K, V> for BTreeMap<K, V> { clear clear pre-clear post-clear *ENDOPNAME*/ (define (pre-clear xs) (is-map? xs)) - (define (clear xs) null) - (define (post-clear xs r) (equal? r (clear xs))) + (define (op-clear xs) null) + (define (post-clear xs r) (equal? r (op-clear xs))) *ENDLIBSPEC*/ fn clear(&mut self) { BTreeMap::clear(self) diff --git a/src/crates/library/src/hashmap.rs b/src/crates/library/src/hashmap.rs index b26c5b0..a841297 100644 --- a/src/crates/library/src/hashmap.rs +++ b/src/crates/library/src/hashmap.rs @@ -12,11 +12,11 @@ Mapping impl<K: Ord + Hash, V> Mapping<K, V> for HashMap<K, V> { /*LIBSPEC* /*OPNAME* - len len pre-len post-len + len op-len pre-len post-len *ENDOPNAME*/ (define (pre-len xs) (is-map? xs)) - (define (len xs) (cons xs (length xs))) - (define (post-len xs r) (equal? r (len xs))) + (define (op-len xs) (cons xs (length xs))) + (define (post-len xs r) (equal? r (op-len xs))) *ENDLIBSPEC*/ fn len(&self) -> usize { HashMap::len(self) @@ -24,11 +24,11 @@ impl<K: Ord + Hash, V> Mapping<K, V> for HashMap<K, V> { /*LIBSPEC* /*OPNAME* - contains contains pre-contains post-contains + contains op-contains pre-contains post-contains *ENDOPNAME*/ (define (pre-contains xs) (is-map? xs)) - (define (contains xs k) (assoc k xs)) - (define (post-contains xs k r) (equal? r (contains xs k))) + (define (op-contains xs k) (assoc k xs)) + (define (post-contains xs k r) (equal? r (op-contains xs k))) *ENDLIBSPEC*/ fn contains(&mut self, x: &K) -> bool { HashMap::contains_key(self, x) @@ -36,14 +36,14 @@ impl<K: Ord + Hash, V> Mapping<K, V> for HashMap<K, V> { /*LIBSPEC* /*OPNAME* - insert insert pre-insert post-insert + insert op-insert pre-insert post-insert *ENDOPNAME*/ (define (pre-insert xs) (is-map? xs)) - (define (insert xs k v) + (define (op-insert xs k v) (let ([idx (index-where xs (lambda (p) (equal? k (car p))))]) (cond [idx (list-set xs idx (cons k v))] [else (list* (cons k v) xs)]))) - (define (post-insert xs k v r) (equal? r (insert xs k v))) + (define (post-insert xs k v r) (equal? r (op-insert xs k v))) *ENDLIBSPEC*/ fn insert(&mut self, key: K, val: V) -> Option<V> { HashMap::insert(self, key, val) @@ -51,11 +51,11 @@ impl<K: Ord + Hash, V> Mapping<K, V> for HashMap<K, V> { /*LIBSPEC* /*OPNAME* - get get pre-get post-get + get op-get pre-get post-get *ENDOPNAME*/ (define (pre-get xs) (is-map? xs)) - (define (get xs k) (cdr (assoc k xs))) - (define (post-get xs k r) (equal? r (get xs k))) + (define (op-get xs k) (cdr (assoc k xs))) + (define (post-get xs k r) (equal? r (op-get xs k))) *ENDLIBSPEC*/ fn get(&self, key: &K) -> Option<&V> { HashMap::get(self, key) @@ -63,11 +63,11 @@ impl<K: Ord + Hash, V> Mapping<K, V> for HashMap<K, V> { /*LIBSPEC* /*OPNAME* - remove remove pre-remove post-remove + remove op-remove pre-remove post-remove *ENDOPNAME*/ (define (pre-remove xs) (is-map? xs)) - (define (remove xs k) (cdr (assoc k xs))) - (define (post-remove xs k r) (equal? r (remove xs k))) + (define (op-remove xs k) (cdr (assoc k xs))) + (define (post-remove xs k r) (equal? r (op-remove xs k))) *ENDLIBSPEC*/ fn remove(&mut self, key: &K) -> Option<V> { HashMap::remove(self, key) @@ -75,11 +75,11 @@ impl<K: Ord + Hash, V> Mapping<K, V> for HashMap<K, V> { /*LIBSPEC* /*OPNAME* - clear clear pre-clear post-clear + clear op-clear pre-clear post-clear *ENDOPNAME*/ (define (pre-clear xs) (is-map? xs)) - (define (clear xs) null) - (define (post-clear xs r) (equal? r (clear xs))) + (define (op-clear xs) null) + (define (post-clear xs r) (equal? r (op-clear xs))) *ENDLIBSPEC*/ fn clear(&mut self) { HashMap::clear(self) diff --git a/src/crates/library/src/list.rs b/src/crates/library/src/list.rs index ae72b54..8ccb146 100644 --- a/src/crates/library/src/list.rs +++ b/src/crates/library/src/list.rs @@ -108,11 +108,11 @@ Stack impl<T> Stack<T> for LinkedList<T> { /*LIBSPEC* /*OPNAME* - push push pre-push post-push + push op-push pre-push post-push *ENDOPNAME*/ - (define (push xs x) (append xs (list x))) + (define (op-push xs x) (append xs (list x))) (define (pre-push xs) #t) - (define (post-push xs x ys) (equal? ys (push xs x))) + (define (post-push xs x ys) (equal? ys (op-push xs x))) *ENDLIBSPEC*/ fn push(&mut self, elt: T) { LinkedList::push_back(self, elt); @@ -120,14 +120,14 @@ impl<T> Stack<T> for LinkedList<T> { /*LIBSPEC* /*OPNAME* - pop pop pre-pop post-pop + pop op-pop pre-pop post-pop *ENDOPNAME*/ - (define (pop xs) + (define (op-pop xs) (cond [(null? xs) (cons xs null)] [else (cons (take xs (- (length xs) 1)) (last xs))])) (define (pre-pop xs) #t) - (define (post-pop xs r) (equal? r (pop xs))) + (define (post-pop xs r) (equal? r (op-pop xs))) *ENDLIBSPEC*/ fn pop(&mut self) -> Option<T> { LinkedList::pop_back(self) diff --git a/src/crates/library/src/vector.rs b/src/crates/library/src/vector.rs index f508f65..3555f6c 100644 --- a/src/crates/library/src/vector.rs +++ b/src/crates/library/src/vector.rs @@ -96,11 +96,11 @@ Stack impl<T> Stack<T> for Vec<T> { /*LIBSPEC* /*OPNAME* - push push pre-push post-push + push op-push pre-push post-push *ENDOPNAME*/ - (define (push xs x) (append xs (list x))) + (define (op-push xs x) (append xs (list x))) (define (pre-push xs) #t) - (define (post-push xs x ys) (equal? ys (push xs x))) + (define (post-push xs x ys) (equal? ys (op-push xs x))) *ENDLIBSPEC*/ fn push(&mut self, elt: T) { Vec::push(self, elt); @@ -108,14 +108,14 @@ impl<T> Stack<T> for Vec<T> { /*LIBSPEC* /*OPNAME* - pop pop pre-pop post-pop + pop op-pop pre-pop post-pop *ENDOPNAME*/ - (define (pop xs) + (define (op-pop xs) (cond [(null? xs) (cons xs null)] [else (cons (take xs (- (length xs) 1)) (last xs))])) (define (pre-pop xs) #t) - (define (post-pop xs r) (equal? r (pop xs))) + (define (post-pop xs r) (equal? r (op-pop xs))) *ENDLIBSPEC*/ fn pop(&mut self) -> Option<T> { Vec::pop(self) diff --git a/src/crates/primrose/src/bounded_ops.rs b/src/crates/primrose/src/bounded_ops.rs index 6496c78..6e91eeb 100644 --- a/src/crates/primrose/src/bounded_ops.rs +++ b/src/crates/primrose/src/bounded_ops.rs @@ -10,7 +10,7 @@ pub type BoundedOps = HashMap<BoundName, Vec<OpInfo>>; pub fn generate_bounded_ops() -> BoundedOps { let mut ops = BoundedOps::new(); let push = ( - "push".to_string(), + "op-push".to_string(), Type::Fun( Box::new(Type::Con( "Con".to_string(), @@ -28,7 +28,7 @@ pub fn generate_bounded_ops() -> BoundedOps { ), ); let pop = ( - "pop".to_string(), + "op-pop".to_string(), Type::Fun( Box::new(Type::Con( "Con".to_string(), @@ -50,15 +50,15 @@ pub fn generate_bounded_ops() -> BoundedOps { "Mapping".to_string(), vec![ ( - "len".to_string(), + "op-len".to_string(), Type::Fun(Box::new(mapping_ty.clone()), Box::new(Type::Int)), ), ( - "is_empty".to_string(), + "op-is_empty".to_string(), Type::Fun(Box::new(mapping_ty.clone()), Box::new(Type::Bool())), ), ( - "contains".to_string(), + "op-contains".to_string(), Type::Fun( Box::new(mapping_ty.clone()), Box::new(Type::Fun( @@ -68,7 +68,7 @@ pub fn generate_bounded_ops() -> BoundedOps { ), ), ( - "insert".to_string(), + "op-insert".to_string(), Type::Fun( Box::new(mapping_ty.clone()), Box::new(Type::Fun( @@ -81,7 +81,7 @@ pub fn generate_bounded_ops() -> BoundedOps { ), ), ( - "get".to_string(), + "op-get".to_string(), Type::Fun( Box::new(mapping_ty.clone()), Box::new(Type::Fun( @@ -91,7 +91,7 @@ pub fn generate_bounded_ops() -> BoundedOps { ), ), ( - "remove".to_string(), + "op-remove".to_string(), Type::Fun( Box::new(mapping_ty.clone()), Box::new(Type::Fun( @@ -107,7 +107,98 @@ pub fn generate_bounded_ops() -> BoundedOps { ], ); - // TODO: Shouldn't this have container operations? + let indexable_ty = Type::Con( + "Con".to_string(), + vec![TypeVar::new("T").into()], + Bounds::from(["Indexable".to_string()]), + ); + + ops.insert( + "Indexable".to_string(), + vec![ + ( + "op-last".to_string(), + Type::Fun( + Box::new(indexable_ty.clone()), + Box::new(TypeVar::new("T").into()), + ), + ), + ( + "op-first".to_string(), + Type::Fun( + Box::new(indexable_ty.clone()), + Box::new(TypeVar::new("T").into()), + ), + ), + ( + "op-nth".to_string(), + Type::Fun( + Box::new(indexable_ty.clone()), + Box::new(Type::Fun( + Box::new(Type::Int), + Box::new(TypeVar::new("T").into()), + )), + ), + ), + ], + ); + + // TODO: Container operations + let container_ty = Type::Con( + "Con".to_string(), + vec![TypeVar::new("T").into()], + Bounds::from(["Container".to_string()]), + ); + ops.insert( + "Container".to_string(), + vec![ + ( + "op-len".to_string(), + Type::Fun(Box::new(container_ty.clone()), Box::new(Type::Int)), + ), + ( + "op-is_empty".to_string(), + Type::Fun(Box::new(container_ty.clone()), Box::new(Type::Bool())), + ), + ( + "op-contains".to_string(), + Type::Fun( + Box::new(container_ty.clone()), + Box::new(Type::Fun( + Box::new(TypeVar::new("T").into()), + Box::new(Type::Bool()), + )), + ), + ), + ( + "op-insert".to_string(), + Type::Fun( + Box::new(container_ty.clone()), + Box::new(Type::Fun( + Box::new(TypeVar::new("T").into()), + Box::new(container_ty.clone()), + )), + ), + ), + ( + "op-remove".to_string(), + Type::Fun( + Box::new(container_ty.clone()), + Box::new(Type::Fun( + Box::new(TypeVar::new("T").into()), + Box::new(container_ty.clone()), + )), + ), + ), + ( + "op-clear".to_string(), + Type::Fun( + Box::new(container_ty.clone()), + Box::new(container_ty.clone()), + ), + ), + ], + ); ops } diff --git a/src/crates/primrose/src/parser.rs b/src/crates/primrose/src/parser.rs index d8b269c..96720c5 100644 --- a/src/crates/primrose/src/parser.rs +++ b/src/crates/primrose/src/parser.rs @@ -34,7 +34,19 @@ impl Term { pub fn require_cdr(&self) -> bool { match self { - Term::Var(id) => id.to_string().eq("pop"), + Term::Var(id) + if id == "op-pop" + || id == "op-len" + || id == "op-contains" + || id == "op-is-empty" + || id == "op-remove" + || id == "op-first" + || id == "op-last" + || id == "op-nth" + || id == "op-get" => + { + true + } _ => false, } } diff --git a/src/tests/aoc-2021-09/src/types.pr.rs b/src/tests/aoc-2021-09/src/types.pr.rs index 067e89e..8441695 100644 --- a/src/tests/aoc-2021-09/src/types.pr.rs +++ b/src/tests/aoc-2021-09/src/types.pr.rs @@ -1,8 +1,4 @@ /*SPEC* -property fifo<T> { - \c <: (Stack) -> (forall \x -> (forall \j -> ((equal? (pop ((push ((push c) x)) j))) x))) -} - property unique<T> { \c <: (Container) -> ((for-all-elems c) \a -> ((unique-count? a) c)) } diff --git a/src/tests/example_stack/src/types.pr.rs b/src/tests/example_stack/src/types.pr.rs index 525fdee..c45bb34 100644 --- a/src/tests/example_stack/src/types.pr.rs +++ b/src/tests/example_stack/src/types.pr.rs @@ -1,6 +1,6 @@ /*SPEC* property lifo<T> { - \c <: (Stack) -> (forall \x -> ((equal? (pop ((push c) x))) x)) + \c <: (Stack) -> (forall \x -> ((equal? (op-pop ((op-push c) x))) x)) } type StackCon<S> = {c impl (Container, Stack) | (lifo c)} diff --git a/src/tests/prime_sieve/src/types.pr.rs b/src/tests/prime_sieve/src/types.pr.rs index a7f04bf..daa9a82 100644 --- a/src/tests/prime_sieve/src/types.pr.rs +++ b/src/tests/prime_sieve/src/types.pr.rs @@ -1,6 +1,6 @@ /*SPEC* property lifo<T> { - \c <: (Stack) -> (forall \x -> ((equal? (pop ((push c) x))) x)) + \c <: (Stack) -> (forall \x -> ((equal? (op-pop ((op-push c) x))) x)) } property ascending<T> { diff --git a/thesis/parts/design.tex b/thesis/parts/design.tex index 80c208c..6886c9c 100644 --- a/thesis/parts/design.tex +++ b/thesis/parts/design.tex @@ -26,7 +26,7 @@ This property requires that at any point, for all consecutive \code{x, y} pairs \begin{lstlisting}[caption=Container type definitions for prime\_sieve,label={lst:selection_example}] /*SPEC* property lifo<T> { - \c <: (Stack) -> (forall \x -> ((equal? (pop ((push c) x))) x)) + \c <: (Stack) -> (forall \x -> ((equal? (pop ((op-push c) x))) x)) } property ascending<T> { |