diff --git a/abscond/env.rkt b/abscond/env.rkt new file mode 100644 index 0000000..5c2ab01 --- /dev/null +++ b/abscond/env.rkt @@ -0,0 +1,16 @@ +#lang racket +(provide lookup ext) + +;; Env Variable -> Answer +(define (lookup env x) + (match env + ['() 'err] + [(cons (list y i) env) + (match (symbol=? x y) + [#t i] + [#f (lookup env x)])])) + +;; Env Variable Value -> Value +(define (ext r x i) + (cons (list x i) r)) + diff --git a/blackmail/env.rkt b/blackmail/env.rkt new file mode 100644 index 0000000..5c2ab01 --- /dev/null +++ b/blackmail/env.rkt @@ -0,0 +1,16 @@ +#lang racket +(provide lookup ext) + +;; Env Variable -> Answer +(define (lookup env x) + (match env + ['() 'err] + [(cons (list y i) env) + (match (symbol=? x y) + [#t i] + [#f (lookup env x)])])) + +;; Env Variable Value -> Value +(define (ext r x i) + (cons (list x i) r)) + diff --git a/con/env.rkt b/con/env.rkt new file mode 100644 index 0000000..5c2ab01 --- /dev/null +++ b/con/env.rkt @@ -0,0 +1,16 @@ +#lang racket +(provide lookup ext) + +;; Env Variable -> Answer +(define (lookup env x) + (match env + ['() 'err] + [(cons (list y i) env) + (match (symbol=? x y) + [#t i] + [#f (lookup env x)])])) + +;; Env Variable Value -> Value +(define (ext r x i) + (cons (list x i) r)) + diff --git a/dodger/env.rkt b/dodger/env.rkt new file mode 100644 index 0000000..5c2ab01 --- /dev/null +++ b/dodger/env.rkt @@ -0,0 +1,16 @@ +#lang racket +(provide lookup ext) + +;; Env Variable -> Answer +(define (lookup env x) + (match env + ['() 'err] + [(cons (list y i) env) + (match (symbol=? x y) + [#t i] + [#f (lookup env x)])])) + +;; Env Variable Value -> Value +(define (ext r x i) + (cons (list x i) r)) + diff --git a/dupe/env.rkt b/dupe/env.rkt new file mode 100644 index 0000000..5c2ab01 --- /dev/null +++ b/dupe/env.rkt @@ -0,0 +1,16 @@ +#lang racket +(provide lookup ext) + +;; Env Variable -> Answer +(define (lookup env x) + (match env + ['() 'err] + [(cons (list y i) env) + (match (symbol=? x y) + [#t i] + [#f (lookup env x)])])) + +;; Env Variable Value -> Value +(define (ext r x i) + (cons (list x i) r)) + diff --git a/evildoer/env.rkt b/evildoer/env.rkt new file mode 100644 index 0000000..5c2ab01 --- /dev/null +++ b/evildoer/env.rkt @@ -0,0 +1,16 @@ +#lang racket +(provide lookup ext) + +;; Env Variable -> Answer +(define (lookup env x) + (match env + ['() 'err] + [(cons (list y i) env) + (match (symbol=? x y) + [#t i] + [#f (lookup env x)])])) + +;; Env Variable Value -> Value +(define (ext r x i) + (cons (list x i) r)) + diff --git a/extort/env.rkt b/extort/env.rkt new file mode 100644 index 0000000..5c2ab01 --- /dev/null +++ b/extort/env.rkt @@ -0,0 +1,16 @@ +#lang racket +(provide lookup ext) + +;; Env Variable -> Answer +(define (lookup env x) + (match env + ['() 'err] + [(cons (list y i) env) + (match (symbol=? x y) + [#t i] + [#f (lookup env x)])])) + +;; Env Variable Value -> Value +(define (ext r x i) + (cons (list x i) r)) + diff --git a/fraud/env.rkt b/fraud/env.rkt new file mode 100644 index 0000000..5c2ab01 --- /dev/null +++ b/fraud/env.rkt @@ -0,0 +1,16 @@ +#lang racket +(provide lookup ext) + +;; Env Variable -> Answer +(define (lookup env x) + (match env + ['() 'err] + [(cons (list y i) env) + (match (symbol=? x y) + [#t i] + [#f (lookup env x)])])) + +;; Env Variable Value -> Value +(define (ext r x i) + (cons (list x i) r)) + diff --git a/fraud/interp.rkt b/fraud/interp.rkt index 7a8bce0..aaf3834 100644 --- a/fraud/interp.rkt +++ b/fraud/interp.rkt @@ -3,6 +3,7 @@ (provide interp-env) (require "ast.rkt") (require "interp-prim.rkt") +(require "env.rkt") ;; type Value = ;; | Integer @@ -51,15 +52,3 @@ ['err 'err] [v (interp-env e2 (ext r x v))])])) -;; Env Id -> Value -(define (lookup r x) - (match r - [(cons (list y val) r) - (if (symbol=? x y) - val - (lookup r x))])) - -;; Env Id Value -> Env -(define (ext r x v) - (cons (list x v) r)) - diff --git a/hoax/env.rkt b/hoax/env.rkt index c43be9c..5c2ab01 100644 --- a/hoax/env.rkt +++ b/hoax/env.rkt @@ -12,4 +12,5 @@ ;; Env Variable Value -> Value (define (ext r x i) - (cons (list x i) r)) \ No newline at end of file + (cons (list x i) r)) + diff --git a/hoax/heap-bits.rkt b/hoax/heap-bits.rkt new file mode 100644 index 0000000..961044e --- /dev/null +++ b/hoax/heap-bits.rkt @@ -0,0 +1,69 @@ +#lang racket +(require "types.rkt") +(provide (struct-out heap) heap-ref heap-set! + alloc-box alloc-cons + alloc-vect alloc-str) + +(struct heap ([n #:mutable] bytes)) + +;; Value* Heap -> Value* +(define (alloc-box v h) + (match h + [(heap n bs) + (heap-set! h n v) + (set-heap-n! h (+ n 8)) + (bitwise-xor n type-box)])) + +;; Value* Value* Heap -> Value* +(define (alloc-cons v1 v2 h) + (match h + [(heap n bs) + (heap-set! h (+ n 0) v1) + (heap-set! h (+ n 8) v2) + (set-heap-n! h (+ n 16)) + (bitwise-xor n type-cons)])) + +;; [Listof Value*] Heap -> Value* +(define (alloc-vect vs h) + (match h + [(heap n bs) + (heap-set! h n (arithmetic-shift (length vs) int-shift)) + (write-values! h vs (+ n 8)) + (set-heap-n! h (+ n (* 8 (add1 (length vs))))) + (bitwise-xor n type-vect)])) + +;; [Listof CharBits] Heap -> Value* +(define (alloc-str cs h) + (match h + [(heap n bs) + (heap-set! h n (arithmetic-shift (length cs) int-shift)) + (write-values! h cs (+ n 8)) + (set-heap-n! h (+ n (* 8 (add1 (length cs))))) + (bitwise-xor n type-str)])) + + +;; Heap [Listof Value*] Natural -> Void +(define (write-values! h vs i) + (match vs + ['() (void)] + [(cons v vs) + (heap-set! h i v) + (write-values! h vs (+ i 8))])) + +;; Heap Address -> Value* +(define (heap-ref h a) + (integer-bytes->integer (heap-bytes h) #t #f a (+ a 8))) + +;; Heap Address Natural -> [Listof Value*] +(define (heap-ref/n h a n) + (define (loop n vs) + (match n + [0 vs] + [_ (loop (sub1 n) + (cons (heap-ref h (+ a n)) vs))])) + (loop n '())) + +;; Heap Address Value* -> Void +(define (heap-set! h i v) + (integer->integer-bytes v 8 (negative? v) #f (heap-bytes h) i)) + diff --git a/hoax/heap.rkt b/hoax/heap.rkt new file mode 100644 index 0000000..1b6e57b --- /dev/null +++ b/hoax/heap.rkt @@ -0,0 +1,50 @@ +#lang racket +(provide alloc-box alloc-cons heap-ref heap-set + (struct-out box-ptr) + (struct-out cons-ptr) + heap-ref/n + alloc-vect alloc-str + (struct-out vect-ptr) + (struct-out str-ptr)) + +(struct box-ptr (i)) +(struct cons-ptr (i)) +(struct vect-ptr (i)) +(struct str-ptr (i)) + +;; Value* Heap -> Answer* +(define (alloc-box v h) + (cons (cons v h) + (box-ptr (length h)))) + +;; Value* Value* Heap -> Answer* +(define (alloc-cons v1 v2 h) + (cons (cons v2 (cons v1 h)) + (cons-ptr (length h)))) + +;; [Listof Value*] Heap -> Answer* +(define (alloc-vect vs h) + (cons (append (reverse (cons (length vs) vs)) h) + (vect-ptr (length h)))) + +;; [Listof Char] Heap -> Answer* +(define (alloc-str cs h) + (cons (append (reverse (cons (length cs) cs)) h) + (str-ptr (length h)))) + +;; Heap Address -> Value* +(define (heap-ref h a) + (list-ref h (- (length h) (add1 a)))) + +;; Heap Address Value* -> Heap +(define (heap-set h i v) + (list-set h (- (length h) i 1) v)) + +;; Heap Address Natural -> [Listof Value*] +(define (heap-ref/n h a n) + (define (loop n vs) + (match n + [0 vs] + [_ (loop (sub1 n) + (cons (heap-ref h (+ a n)) vs))])) + (loop n '())) diff --git a/hoax/interp-heap-bits.rkt b/hoax/interp-heap-bits.rkt new file mode 100644 index 0000000..60991ae --- /dev/null +++ b/hoax/interp-heap-bits.rkt @@ -0,0 +1,85 @@ +#lang racket +(provide interp) +(require "ast.rkt") +(require "types.rkt") +(require "env.rkt") +(require "heap-bits.rkt") +(require "interp-prims-heap-bits.rkt") +(require "unload-bits.rkt") + +(define *heap-size* 100000) ; # words in heap + +;; type Answer* = +;; | Value* +;; | 'err + +;; type Value* = +;; | (value->bits Integer) +;; | (value->bits Boolean) +;; | (value->bits Character) +;; | (value->bits Eof) +;; | (value->bits Void) +;; | (value->bits '()) +;; | (bitwise-xor Address type-box) +;; | (bitwise-xor Address type-cons) + +;; type Address = Natural divisible by 8 + +;; type Heap = (heap Address Bytes) + +;; type REnv = (Listof (List Id Value*)) + +;; Expr -> Value +(define (interp e) + (define h (heap 0 (make-bytes (* 8 *heap-size*) 0))) + (unload h (interp-env-heap-bits e '() h))) + +;; Expr REnv Heap -> Answer* +(define (interp-env-heap-bits e r h) + (match e + [(Lit (? string? s)) (alloc-str (map value->bits (string->list s)) h)] + [(Lit d) (value->bits d)] + [(Eof) (value->bits eof)] + [(Var x) (lookup r x)] + [(Prim0 p) (interp-prim0 p h)] + [(Prim1 p e) + (match (interp-env-heap-bits e r h) + ['err 'err] + [v + (interp-prim1 p v h)])] + [(Prim2 p e1 e2) + (match (interp-env-heap-bits e1 r h) + ['err 'err] + [v1 + (match (interp-env-heap-bits e2 r h) + ['err 'err] + [v2 + (interp-prim2 p v1 v2 h)])])] + [(Prim3 p e1 e2 e3) + (match (interp-env-heap-bits e1 r h) + ['err 'err] + [v1 + (match (interp-env-heap-bits e2 r h) + ['err 'err] + [v2 + (match (interp-env-heap-bits e3 r h) + ['err 'err] + [v3 + (interp-prim3 p v1 v2 v3 h)])])])] + [(If p e1 e2) + (match (interp-env-heap-bits p r h) + ['err 'err] + [v + (if (= v (value->bits #f)) + (interp-env-heap-bits e2 r h) + (interp-env-heap-bits e1 r h))])] + [(Begin e1 e2) + (match (interp-env-heap-bits e1 r h) + ['err 'err] + [_ (interp-env-heap-bits e2 r h)])] + [(Let x e1 e2) + (match (interp-env-heap-bits e1 r h) + ['err 'err] + [v + (interp-env-heap-bits e2 (ext r x v) h)])])) + diff --git a/hoax/interp-heap.rkt b/hoax/interp-heap.rkt new file mode 100644 index 0000000..9244824 --- /dev/null +++ b/hoax/interp-heap.rkt @@ -0,0 +1,81 @@ +#lang racket +(provide interp interp-env-heap) +(require "env.rkt") +(require "unload.rkt") +(require "interp-prims-heap.rkt") +(require "ast.rkt") +(require "heap.rkt") + +;; type Answer* = +;; | (cons Heap Value*) +;; | 'err + +;; type Value* = +;; | Integer +;; | Boolean +;; | Character +;; | Eof +;; | Void +;; | '() +;; | (box-ptr Address) +;; | (cons-ptr Address) +;; | (vect-ptr Address) +;; | (str-ptr Address) + +;; type Address = Natural + +;; type Heap = (Listof Value*) +;; type REnv = (Listof (List Id Value*)) + +;; Expr -> Answer +(define (interp e) + (unload (interp-env-heap e '() '()))) + +;; Expr REnv Heap -> Answer* +(define (interp-env-heap e r h) + (match e + [(Lit (? string? s)) (alloc-str (string->list s) h)] + [(Lit d) (cons h d)] + [(Eof) (cons h eof)] + [(Var x) (cons h (lookup r x))] + [(Prim0 p) (interp-prim0 p h)] + [(Prim1 p e) + (match (interp-env-heap e r h) + ['err 'err] + [(cons h v) + (interp-prim1 p v h)])] + [(Prim2 p e1 e2) + (match (interp-env-heap e1 r h) + ['err 'err] + [(cons h v1) + (match (interp-env-heap e2 r h) + ['err 'err] + [(cons h v2) + (interp-prim2 p v1 v2 h)])])] + [(Prim3 p e1 e2 e3) + (match (interp-env-heap e1 r h) + ['err 'err] + [(cons h v1) + (match (interp-env-heap e2 r h) + ['err 'err] + [(cons h v2) + (match (interp-env-heap e3 r h) + [(cons h v3) + (interp-prim3 p v1 v2 v3 h)])])])] + [(If p e1 e2) + (match (interp-env-heap p r h) + ['err 'err] + [(cons h v) + (if v + (interp-env-heap e1 r h) + (interp-env-heap e2 r h))])] + [(Begin e1 e2) + (match (interp-env-heap e1 r h) + ['err 'err] + [(cons h _) (interp-env-heap e2 r h)])] + [(Let x e1 e2) + (match (interp-env-heap e1 r h) + ['err 'err] + [(cons h v) + (interp-env-heap e2 (ext r x v) h)])])) + diff --git a/hoax/interp-prims-heap-bits.rkt b/hoax/interp-prims-heap-bits.rkt new file mode 100644 index 0000000..c8dab81 --- /dev/null +++ b/hoax/interp-prims-heap-bits.rkt @@ -0,0 +1,103 @@ +#lang racket +(provide interp-prim0 interp-prim1 interp-prim2 interp-prim3) +(require "heap-bits.rkt") +(require "types.rkt") + +;; Op0 Heap -> Answer* +(define (interp-prim0 op h) + (match op + ['read-byte (value->bits (read-byte))] + ['peek-byte (value->bits (peek-byte))] + ['void (value->bits (void))])) + +;; Op1 Value* Heap -> Answer* +(define (interp-prim1 p v h) + (match (list p v) + [(list 'add1 (? int-bits? i)) + (+ i (value->bits 1))] + [(list 'sub1 (? int-bits? i)) + (- i (value->bits 1))] + [(list 'zero? (? int-bits? i)) + (value->bits (zero? i))] + [(list 'char? v) + (value->bits (char-bits? v))] + [(list 'char->integer (? char-bits?)) + (arithmetic-shift (bitwise-xor v type-char) (- int-shift char-shift))] + [(list 'integer->char (? codepoint-bits?)) + (bitwise-xor (arithmetic-shift v (- char-shift int-shift)) type-char)] + [(list 'eof-object? v) + (value->bits (= (value->bits eof) v))] + [(list 'write-byte (? byte-bits?)) + (begin (write-byte (arithmetic-shift v (- int-shift))) + (value->bits (void)))] + [(list 'box v) (alloc-box v h)] + [(list 'unbox (? box-bits? i)) + (heap-ref h (bitwise-xor i type-box))] + [(list 'car (? cons-bits? i)) + (heap-ref h (bitwise-xor i type-cons))] + [(list 'cdr (? cons-bits? i)) + (heap-ref h (bitwise-xor (+ i 8) type-cons))] + [(list 'empty? v) + (value->bits (= (value->bits '()) v))] + [(list 'vector? v) + (value->bits (vect-bits? v))] + [(list 'string? v) + (value->bits (str-bits? v))] + [(list 'vector-length (? vect-bits?)) + (define p (bitwise-xor v type-vect)) + (heap-ref h p)] + [(list 'string-length (? str-bits?)) + (define p (bitwise-xor v type-str)) + (heap-ref h p)] + [_ 'err])) + +;; Op2 Value* Value* Heap -> Answer* +(define (interp-prim2 p v1 v2 h) + (match (list p v1 v2) + [(list '+ (? int-bits? i1) (? int-bits? i2)) (+ i1 i2)] + [(list '- (? int-bits? i1) (? int-bits? i2)) (- i1 i2)] + [(list '< (? int-bits? i1) (? int-bits? i2)) (value->bits (< i1 i2))] + [(list '= (? int-bits? i1) (? int-bits? i2)) (value->bits (= i1 i2))] + [(list 'eq? v1 v2) (value->bits (= v1 v2))] + [(list 'cons v1 v2) (alloc-cons v1 v2 h)] + [(list 'make-vector (? int-bits? i) v) + (if (< i 0) + 'err + (alloc-vect (make-list (arithmetic-shift i (- int-shift)) v) h))] + [(list 'vector-ref (? vect-bits? a) (? int-bits? i)) + (define p (bitwise-xor a type-vect)) + (if (<= 0 i (sub1 (heap-ref h p))) + (heap-ref h (+ p 8 (arithmetic-shift i (- 3 int-shift)))) + 'err)] + [(list 'make-string (? int-bits? i) (? char-bits? c)) + (if (< i 0) + 'err + (alloc-str (make-list (arithmetic-shift i (- int-shift)) c) h))] + [(list 'string-ref (? str-bits? a) (? int-bits? i)) + (define p (bitwise-xor a type-str)) + (if (<= 0 i (sub1 (heap-ref h p))) + (heap-ref h (+ p 8 (arithmetic-shift i (- 3 int-shift)))) + 'err)] + [_ 'err])) + +;; Op3 Value* Value* Value* Heap -> Answer* +(define (interp-prim3 p v1 v2 v3 h) + (match (list p v1 v2 v3) + [(list 'vector-set! (? vect-bits?) (? int-bits?) _) + (define p (bitwise-xor v1 type-vect)) + (if (<= 0 v2 (sub1 (heap-ref h p))) + (heap-set! h (+ p 8 (arithmetic-shift v2 (- 3 int-shift))) v3) + 'err)] + [_ 'err])) + +;; Int64 -> Boolean +(define (byte-bits? v) + (and (int-bits? v) + (<= 0 v (value->bits 255)))) + +;; Int64 -> Boolean +(define (codepoint-bits? v) + (and (int-bits? v) + (or (<= 0 v (value->bits 55295)) + (<= (value->bits 57344) v (value->bits 1114111))))) + diff --git a/hoax/interp-prims-heap.rkt b/hoax/interp-prims-heap.rkt new file mode 100644 index 0000000..df7dbaa --- /dev/null +++ b/hoax/interp-prims-heap.rkt @@ -0,0 +1,80 @@ +#lang racket +(provide interp-prim0 interp-prim1 interp-prim2 interp-prim3) +(require "heap.rkt") + +;; Op0 Heap -> Answer* +(define (interp-prim0 op h) + (match op + ['read-byte (cons h (read-byte))] + ['peek-byte (cons h (peek-byte))] + ['void (cons h (void))])) + +;; Op1 Value* Heap -> Answer* +(define (interp-prim1 p v h) + (match (list p v) + [(list 'add1 (? integer? i)) (cons h (add1 i))] + [(list 'sub1 (? integer? i)) (cons h (sub1 i))] + [(list 'zero? (? integer? i)) (cons h (zero? i))] + [(list 'char? v) (cons h (char? v))] + [(list 'char->integer (? char?)) (cons h (char->integer v))] + [(list 'integer->char (? codepoint?)) (cons h (integer->char v))] + [(list 'eof-object? v) (cons h (eof-object? v))] + [(list 'write-byte (? byte?)) (cons h (write-byte v))] + [(list 'box v) (alloc-box v h)] + [(list 'unbox (box-ptr i)) (cons h (heap-ref h i))] + [(list 'car (cons-ptr i)) (cons h (heap-ref h i))] + [(list 'cdr (cons-ptr i)) (cons h (heap-ref h (add1 i)))] + [(list 'empty? v) (cons h (empty? v))] + [(list 'vector? v) (cons h (vect-ptr? v))] + [(list 'string? v) (cons h (str-ptr? v))] + [(list 'vector-length (vect-ptr a)) (cons h (heap-ref h a))] + [(list 'string-length (str-ptr a)) (cons h (heap-ref h a))] + [_ 'err])) + +;; Op2 Value* Value* Heap -> Answer* +(define (interp-prim2 p v1 v2 h) + (match (list p v1 v2) + [(list '+ (? integer? i1) (? integer? i2)) (cons h (+ i1 i2))] + [(list '- (? integer? i1) (? integer? i2)) (cons h (- i1 i2))] + [(list '< (? integer? i1) (? integer? i2)) (cons h (< i1 i2))] + [(list '= (? integer? i1) (? integer? i2)) (cons h (= i1 i2))] + [(list 'eq? v1 v2) + (match (list v1 v2) + [(list (cons-ptr a1) (cons-ptr a2)) (cons h (= a1 a2))] + [(list (box-ptr a1) (box-ptr a2)) (cons h (= a1 a2))] + [_ (cons h (eqv? v1 v2))])] + [(list 'cons v1 v2) (alloc-cons v1 v2 h)] + [(list 'make-vector (? integer? i) v) + (if (< i 0) + 'err + (alloc-vect (make-list i v) h))] + [(list 'vector-ref (vect-ptr a) (? integer? i)) + (if (<= 0 i (sub1 (heap-ref h a))) + (cons h (heap-ref h (+ a i 1))) + 'err)] + [(list 'make-string (? integer? i) (? char? c)) + (if (< i 0) + 'err + (alloc-str (make-list i c) h))] + [(list 'string-ref (str-ptr a) (? integer? i)) + (if (<= 0 i (sub1 (heap-ref h a))) + (cons h (heap-ref h (+ a i 1))) + 'err)] + [_ 'err])) + +;; Op3 Value* Value* Value* Heap -> Answer* +(define (interp-prim3 p v1 v2 v3 h) + (match (list p v1 v2 v3) + [(list 'vector-set! (vect-ptr a) (? integer? i) v) + (if (<= 0 i (sub1 (heap-ref h a))) + (cons (heap-set h (+ a i 1) v) + (void)) + 'err)] + [_ 'err])) + +;; Any -> Boolean +(define (codepoint? v) + (and (integer? v) + (or (<= 0 v 55295) + (<= 57344 v 1114111)))) + diff --git a/hoax/interp.rkt b/hoax/interp.rkt index 7224079..230714c 100644 --- a/hoax/interp.rkt +++ b/hoax/interp.rkt @@ -3,6 +3,7 @@ (provide interp-env) (require "ast.rkt") (require "interp-prim.rkt") +(require "env.rkt") ;; type Value = ;; | Integer @@ -64,15 +65,3 @@ ['err 'err] [v (interp-env e2 (ext r x v))])])) -;; Env Id -> Value -(define (lookup r x) - (match r - [(cons (list y val) r) - (if (symbol=? x y) - val - (lookup r x))])) - -;; Env Id Value -> Env -(define (ext r x v) - (cons (list x v) r)) - diff --git a/hoax/test/interp-heap-bits.rkt b/hoax/test/interp-heap-bits.rkt new file mode 100644 index 0000000..be21e60 --- /dev/null +++ b/hoax/test/interp-heap-bits.rkt @@ -0,0 +1,11 @@ +#lang racket +(require "test-runner.rkt") +(require "../parse.rkt") +(require "../interp-heap-bits.rkt") +(require "../interp-io.rkt") + +(test (λ (e) (interp (parse e)))) + +;; FIXME: this is not running a heap-based interpreter! +(test/io (λ (s e) (interp/io (parse e) s))) + diff --git a/hoax/test/interp-heap.rkt b/hoax/test/interp-heap.rkt new file mode 100644 index 0000000..6ad0cb9 --- /dev/null +++ b/hoax/test/interp-heap.rkt @@ -0,0 +1,11 @@ +#lang racket +(require "test-runner.rkt") +(require "../parse.rkt") +(require "../interp-heap.rkt") +(require "../interp-io.rkt") + +(test (λ (e) (interp (parse e)))) + +;; FIXME: this is not running a heap-based interpreter! +(test/io (λ (s e) (interp/io (parse e) s))) + diff --git a/hoax/types.rkt b/hoax/types.rkt index e0da50d..c18ec17 100644 --- a/hoax/types.rkt +++ b/hoax/types.rkt @@ -27,20 +27,20 @@ [(char-bits? b) (integer->char (arithmetic-shift b (- char-shift)))] [(box-bits? b) - (box (bits->value (heap-ref b)))] + (box (bits->value (mem-ref b)))] [(cons-bits? b) - (cons (bits->value (heap-ref (+ b 8))) - (bits->value (heap-ref b)))] + (cons (bits->value (mem-ref (+ b 8))) + (bits->value (mem-ref b)))] [(vect-bits? b) (if (zero? (untag b)) (vector) - (build-vector (heap-ref b) + (build-vector (mem-ref b) (lambda (j) - (bits->value (heap-ref (+ b (* 8 (add1 j))))))))] + (bits->value (mem-ref (+ b (* 8 (add1 j))))))))] [(str-bits? b) (if (zero? (untag b)) (string) - (build-string (heap-ref b) + (build-string (mem-ref b) (lambda (j) (char-ref (+ b 8) j))))] [else (error "invalid bits")])) @@ -82,7 +82,7 @@ (arithmetic-shift (arithmetic-shift i (- (integer-length ptr-mask))) (integer-length ptr-mask))) -(define (heap-ref i) +(define (mem-ref i) (ptr-ref (cast (untag i) _int64 _pointer) _int64)) (define (char-ref i j) diff --git a/hoax/unload-bits.rkt b/hoax/unload-bits.rkt new file mode 100644 index 0000000..eb70337 --- /dev/null +++ b/hoax/unload-bits.rkt @@ -0,0 +1,33 @@ +#lang racket +(provide unload unload-value) +(require "heap-bits.rkt") +(require "types.rkt") + +;; Heap Answer* -> Answer +(define (unload h a) + (match a + ['err 'err] + [v (unload-value v h)])) + +;; Value* Heap -> Value +(define (unload-value v h) + (match v + [(? box-bits?) + (define p (bitwise-xor v type-box)) + (box (unload-value (heap-ref h p) h))] + [(? cons-bits?) + (define p (bitwise-xor v type-cons)) + (cons (unload-value (heap-ref h (+ p 0)) h) + (unload-value (heap-ref h (+ p 8)) h))] + [(? vect-bits?) + (define p (bitwise-xor v type-vect)) + (build-vector (arithmetic-shift (heap-ref h p) (- int-shift)) + (λ (i) + (bits->value (heap-ref h (+ p (* 8 (add1 i)))))))] + [(? str-bits?) + (define p (bitwise-xor v type-str)) + (build-string (arithmetic-shift (heap-ref h p) (- int-shift)) + (λ (i) + (bits->value (heap-ref h (+ p (* 8 (add1 i)))))))] + [_ (bits->value v)])) + diff --git a/hoax/unload.rkt b/hoax/unload.rkt new file mode 100644 index 0000000..443ac00 --- /dev/null +++ b/hoax/unload.rkt @@ -0,0 +1,29 @@ +#lang racket +(provide unload unload-value) +(require "heap.rkt") + +;; Answer* -> Answer +(define (unload a) + (match a + ['err 'err] + [(cons h v) (unload-value v h)])) + +;; Value* Heap -> Value +(define (unload-value v h) + (match v + [(? integer?) v] + [(? boolean?) v] + [(? char?) v] + [(? eof-object?) v] + [(? void?) v] + ['() '()] + [(box-ptr a) + (box (unload-value (heap-ref h a) h))] + [(cons-ptr a) + (cons (unload-value (heap-ref h a) h) + (unload-value (heap-ref h (add1 a)) h))] + [(vect-ptr a) + (apply vector (heap-ref/n h a (heap-ref h a)))] + [(str-ptr a) + (apply string (heap-ref/n h a (heap-ref h a)))])) + diff --git a/hustle/heap-bits.rkt b/hustle/heap-bits.rkt index 4b8f704..43cd566 100644 --- a/hustle/heap-bits.rkt +++ b/hustle/heap-bits.rkt @@ -1,25 +1,32 @@ #lang racket -(provide alloc-box alloc-cons heap-ref heap-set) (require "types.rkt") +(provide (struct-out heap) heap-ref + alloc-box alloc-cons) -;; Value* Heap -> Answer +(struct heap ([n #:mutable] bytes)) + +;; Value* Heap -> Value* (define (alloc-box v h) - (cons (cons v h) - (bitwise-ior (arithmetic-shift (length h) imm-shift) - type-box))) + (match h + [(heap n bs) + (heap-set! h n v) + (set-heap-n! h (+ n 8)) + (bitwise-xor n type-box)])) -;; Value* Value* Heap -> Answer +;; Value* Value* Heap -> Value* (define (alloc-cons v1 v2 h) - (cons (cons v2 (cons v1 h)) - (bitwise-ior (arithmetic-shift (length h) imm-shift) - type-cons))) + (match h + [(heap n bs) + (heap-set! h (+ n 0) v1) + (heap-set! h (+ n 8) v2) + (set-heap-n! h (+ n 16)) + (bitwise-xor n type-cons)])) ;; Heap Address -> Value* (define (heap-ref h a) - (let ((a (arithmetic-shift a (- imm-shift)))) - (list-ref h (- (length h) (add1 a))))) + (integer-bytes->integer (heap-bytes h) #t #f a (+ a 8))) + +;; Heap Address Value* -> Void +(define (heap-set! h i v) + (integer->integer-bytes v 8 (negative? v) #f (heap-bytes h) i)) -;; Heap Address Value* -> Heap -(define (heap-set h a v) - (let ((a (arithmetic-shift a (- imm-shift)))) - (list-set h (- (length h) a 1) v))) diff --git a/hustle/heap.rkt b/hustle/heap.rkt index 5eae8cb..d06911a 100644 --- a/hustle/heap.rkt +++ b/hustle/heap.rkt @@ -1,5 +1,7 @@ #lang racket -(provide alloc-box alloc-cons heap-ref heap-set box-ptr cons-ptr) +(provide alloc-box alloc-cons heap-ref heap-set + (struct-out box-ptr) + (struct-out cons-ptr)) (struct box-ptr (i)) (struct cons-ptr (i)) @@ -22,3 +24,11 @@ (define (heap-set h i v) (list-set h (- (length h) i 1) v)) +;; Heap Address Natural -> [Listof Value*] +(define (heap-ref/n h a n) + (define (loop n vs) + (match n + [0 vs] + [_ (loop (sub1 n) + (cons (heap-ref h (+ a n)) vs))])) + (loop n '())) diff --git a/hustle/interp-heap-bits.rkt b/hustle/interp-heap-bits.rkt index d1d4777..6d2ef99 100644 --- a/hustle/interp-heap-bits.rkt +++ b/hustle/interp-heap-bits.rkt @@ -1,56 +1,73 @@ #lang racket -(provide interp interp-env-heap) -(require (except-in "types.rkt" heap-ref) - "env.rkt" - "heap-bits.rkt" - "interp-prims-heap-bits.rkt" - "unload-bits.rkt" - "ast.rkt") +(provide interp) +(require "ast.rkt") +(require "types.rkt") +(require "env.rkt") +(require "heap-bits.rkt") +(require "interp-prims-heap-bits.rkt") +(require "unload-bits.rkt") + +(define *heap-size* 100000) ; # words in heap ;; type Answer* = -;; | (cons Heap ValueBits*) +;; | Value* ;; | 'err -;; Expr -> Answer -(define (interp e) - (unload (interp-env-heap e '() '()))) - -;; Expr REnv Heap -> Answer -(define (interp-env-heap e r h) - (match e - [(Lit d) (cons h (value->bits d))] - [(Eof) (cons h (value->bits eof))] - [(Var x) (cons h (lookup r x))] - [(Prim0 'void) (cons h (value->bits (void)))] - [(Prim0 'read-byte) (cons h (value->bits (read-byte)))] - [(Prim0 'peek-byte) (cons h (value->bits (peek-byte)))] +;; type Value* = +;; | (value->bits Integer) +;; | (value->bits Boolean) +;; | (value->bits Character) +;; | (value->bits Eof) +;; | (value->bits Void) +;; | (value->bits '()) +;; | (bitwise-xor Address type-box) +;; | (bitwise-xor Address type-cons) + +;; type Address = Natural divisible by 8 + +;; type Heap = (heap Address Bytes) + +;; type REnv = (Listof (List Id Value*)) + +;; Expr -> Value +(define (interp e) + (define h (heap 0 (make-bytes (* 8 *heap-size*) 0))) + (unload h (interp-env-heap-bits e '() h))) + +;; Expr REnv Heap -> Answer* +(define (interp-env-heap-bits e r h) + (match e + [(Lit d) (value->bits d)] + [(Eof) (value->bits eof)] + [(Var x) (lookup r x)] + [(Prim0 p) (interp-prim0 p h)] [(Prim1 p e) - (match (interp-env-heap e r h) + (match (interp-env-heap-bits e r h) ['err 'err] - [(cons h a) - (interp-prim1 p a h)])] + [v + (interp-prim1 p v h)])] [(Prim2 p e1 e2) - (match (interp-env-heap e1 r h) + (match (interp-env-heap-bits e1 r h) ['err 'err] - [(cons h a1) - (match (interp-env-heap e2 r h) + [v1 + (match (interp-env-heap-bits e2 r h) ['err 'err] - [(cons h a2) - (interp-prim2 p a1 a2 h)])])] + [v2 + (interp-prim2 p v1 v2 h)])])] [(If p e1 e2) - (match (interp-env-heap p r h) + (match (interp-env-heap-bits p r h) ['err 'err] - [(cons h v) + [v (if (= v (value->bits #f)) - (interp-env-heap e2 r h) - (interp-env-heap e1 r h))])] - [(Begin e1 e2) - (match (interp-env-heap e1 r h) + (interp-env-heap-bits e2 r h) + (interp-env-heap-bits e1 r h))])] + [(Begin e1 e2) + (match (interp-env-heap-bits e1 r h) ['err 'err] - [(cons h _) (interp-env-heap e2 r h)])] + [_ (interp-env-heap-bits e2 r h)])] [(Let x e1 e2) - (match (interp-env-heap e1 r h) + (match (interp-env-heap-bits e1 r h) ['err 'err] - [(cons h v) - (interp-env-heap e2 (ext r x v) h)])])) + [v + (interp-env-heap-bits e2 (ext r x v) h)])])) diff --git a/hustle/interp-heap.rkt b/hustle/interp-heap.rkt index e10840f..9d9c198 100644 --- a/hustle/interp-heap.rkt +++ b/hustle/interp-heap.rkt @@ -19,6 +19,7 @@ ;; | (box-ptr Address) ;; | (cons-ptr Address) + ;; type Address = Natural ;; type Heap = (Listof Value*) diff --git a/hustle/interp-prims-heap-bits.rkt b/hustle/interp-prims-heap-bits.rkt index a9f26ad..393eeac 100644 --- a/hustle/interp-prims-heap-bits.rkt +++ b/hustle/interp-prims-heap-bits.rkt @@ -1,44 +1,65 @@ #lang racket -(provide interp-prim1 interp-prim2) -(require (except-in "types.rkt" heap-ref) - "heap-bits.rkt") +(provide interp-prim0 interp-prim1 interp-prim2) +(require "heap-bits.rkt") +(require "types.rkt") + +;; Op0 Heap -> Answer* +(define (interp-prim0 op h) + (match op + ['read-byte (value->bits (read-byte))] + ['peek-byte (value->bits (peek-byte))] + ['void (value->bits (void))])) ;; Op1 Value* Heap -> Answer* (define (interp-prim1 p v h) (match (list p v) - [(list 'add1 (? int-bits? i)) (cons h (+ i (value->bits 1)))] - [(list 'sub1 (? int-bits? i)) (cons h (- i (value->bits 1)))] - [(list 'zero? (? int-bits? i)) (cons h (value->bits (zero? i)))] - [(list 'char? v) (cons h (value->bits (char-bits? v)))] - [(list 'char->integer (? char-bits?)) (cons h (value->bits (char->integer (bits->value v))))] - [(list 'integer->char (? cp-bits?)) (cons h (value->bits (integer->char (bits->value v))))] - [(list 'eof-object? v) (cons h (value->bits (= v (value->bits eof))))] - [(list 'write-byte (? byte-bits?)) (cons h (begin (write-byte (bits->value v)) (value->bits (void))))] - [(list 'box v) (alloc-box v h)] - [(list 'unbox (? box-bits? i)) (cons h (heap-ref h i))] - [(list 'car (? cons-bits? i)) (cons h (heap-ref h i))] - [(list 'cdr (? cons-bits? i)) (cons h (heap-ref h (+ i (arithmetic-shift 1 imm-shift))))] - [(list 'empty? v) (cons h (value->bits (= (value->bits '()) v)))] - [_ 'err])) + [(list 'add1 (? int-bits? i)) + (+ i (value->bits 1))] + [(list 'sub1 (? int-bits? i)) + (- i (value->bits 1))] + [(list 'zero? (? int-bits? i)) + (value->bits (zero? i))] + [(list 'char? v) + (value->bits (char-bits? v))] + [(list 'char->integer (? char-bits?)) + (arithmetic-shift (bitwise-xor v type-char) (- int-shift char-shift))] + [(list 'integer->char (? codepoint-bits?)) + (bitwise-xor (arithmetic-shift v (- char-shift int-shift)) type-char)] + [(list 'eof-object? v) + (value->bits (= (value->bits eof) v))] + [(list 'write-byte (? byte-bits?)) + (begin (write-byte (arithmetic-shift v (- int-shift))) + (value->bits (void)))] + [(list 'box v) (alloc-box v h)] + [(list 'unbox (? box-bits? i)) + (heap-ref h (bitwise-xor i type-box))] + [(list 'car (? cons-bits? i)) + (heap-ref h (bitwise-xor i type-cons))] + [(list 'cdr (? cons-bits? i)) + (heap-ref h (bitwise-xor (+ i 8) type-cons))] + [(list 'empty? v) + (value->bits (= (value->bits '()) v))] + [_ 'err])) ;; Op2 Value* Value* Heap -> Answer* (define (interp-prim2 p v1 v2 h) (match (list p v1 v2) - [(list '+ (? int-bits? i1) (? int-bits? i2)) (cons h (+ i1 i2))] - [(list '- (? int-bits? i1) (? int-bits? i2)) (cons h (- i1 i2))] - [(list '< (? int-bits? i1) (? int-bits? i2)) (cons h (value->bits (< i1 i2)))] - [(list '= (? int-bits? i1) (? int-bits? i2)) (cons h (value->bits (= i1 i2)))] - [(list 'eq? v1 v2) (cons h (value->bits (= v1 v2)))] - [(list 'cons v1 v2) (alloc-cons v1 v2 h)] - [_ 'err])) + [(list '+ (? int-bits? i1) (? int-bits? i2)) (+ i1 i2)] + [(list '- (? int-bits? i1) (? int-bits? i2)) (- i1 i2)] + [(list '< (? int-bits? i1) (? int-bits? i2)) (value->bits (< i1 i2))] + [(list '= (? int-bits? i1) (? int-bits? i2)) (value->bits (= i1 i2))] + [(list 'eq? v1 v2) (value->bits (= v1 v2))] + [(list 'cons v1 v2) (alloc-cons v1 v2 h)] + [_ 'err])) -;; Bits -> Boolean -(define (byte-bits? i) - (and (int-bits? i) - (<= (value->bits 0) i (value->bits 255)))) +;; Int64 -> Boolean +(define (byte-bits? v) + (and (int-bits? v) + (<= 0 v (value->bits 255)))) -;; Bits -> Boolean -(define (cp-bits? v) +;; Int64 -> Boolean +(define (codepoint-bits? v) (and (int-bits? v) - (or (<= (value->bits 0) v (value->bits 55295)) + (or (<= 0 v (value->bits 55295)) (<= (value->bits 57344) v (value->bits 1114111))))) + diff --git a/hustle/interp.rkt b/hustle/interp.rkt index 1fd0606..7f04a3e 100644 --- a/hustle/interp.rkt +++ b/hustle/interp.rkt @@ -3,6 +3,7 @@ (provide interp-env) (require "ast.rkt") (require "interp-prim.rkt") +(require "env.rkt") ;; type Value = ;; | Integer @@ -54,15 +55,3 @@ ['err 'err] [v (interp-env e2 (ext r x v))])])) -;; Env Id -> Value -(define (lookup r x) - (match r - [(cons (list y val) r) - (if (symbol=? x y) - val - (lookup r x))])) - -;; Env Id Value -> Env -(define (ext r x v) - (cons (list x v) r)) - diff --git a/hustle/test/interp-heap-bits.rkt b/hustle/test/interp-heap-bits.rkt index dc52744..be21e60 100644 --- a/hustle/test/interp-heap-bits.rkt +++ b/hustle/test/interp-heap-bits.rkt @@ -1,9 +1,11 @@ #lang racket -(require "test-runner.rkt" - "../parse.rkt" - "../interp-heap-bits.rkt" - "../interp-io.rkt") +(require "test-runner.rkt") +(require "../parse.rkt") +(require "../interp-heap-bits.rkt") +(require "../interp-io.rkt") (test (λ (e) (interp (parse e)))) +;; FIXME: this is not running a heap-based interpreter! (test/io (λ (s e) (interp/io (parse e) s))) + diff --git a/hustle/types.rkt b/hustle/types.rkt index 6323bc0..d1c081a 100644 --- a/hustle/types.rkt +++ b/hustle/types.rkt @@ -25,10 +25,10 @@ [(char-bits? b) (integer->char (arithmetic-shift b (- char-shift)))] [(box-bits? b) - (box (bits->value (heap-ref b)))] + (box (bits->value (mem-ref b)))] [(cons-bits? b) - (cons (bits->value (heap-ref (+ b 8))) - (bits->value (heap-ref b)))] + (cons (bits->value (mem-ref (+ b 8))) + (bits->value (mem-ref b)))] [else (error "invalid bits")])) (define (value->bits v) @@ -62,6 +62,6 @@ (arithmetic-shift (arithmetic-shift i (- (integer-length ptr-mask))) (integer-length ptr-mask))) -(define (heap-ref i) +(define (mem-ref i) (ptr-ref (cast (untag i) _int64 _pointer) _int64)) diff --git a/hustle/unload-bits.rkt b/hustle/unload-bits.rkt index 21d084b..d9b0a73 100644 --- a/hustle/unload-bits.rkt +++ b/hustle/unload-bits.rkt @@ -1,20 +1,23 @@ #lang racket (provide unload unload-value) -(require (except-in "types.rkt" heap-ref) - "heap-bits.rkt") +(require "heap-bits.rkt") +(require "types.rkt") -;; Answer* -> Answer -(define (unload a) +;; Heap Answer* -> Answer +(define (unload h a) (match a ['err 'err] - [(cons h v) (unload-value v h)])) + [v (unload-value v h)])) ;; Value* Heap -> Value (define (unload-value v h) (match v - [(? imm-bits?) (bits->value v)] - [(? box-bits? i) - (box (unload-value (heap-ref h i) h))] - [(? cons-bits? i) - (cons (unload-value (heap-ref h i) h) - (unload-value (heap-ref h (+ i (arithmetic-shift 1 imm-shift))) h))])) + [(? box-bits?) + (define p (bitwise-xor v type-box)) + (box (unload-value (heap-ref h p) h))] + [(? cons-bits?) + (define p (bitwise-xor v type-cons)) + (cons (unload-value (heap-ref h (+ p 0)) h) + (unload-value (heap-ref h (+ p 8)) h))] + [_ (bits->value v)])) + diff --git a/iniquity/env.rkt b/iniquity/env.rkt index c43be9c..5c2ab01 100644 --- a/iniquity/env.rkt +++ b/iniquity/env.rkt @@ -12,4 +12,5 @@ ;; Env Variable Value -> Value (define (ext r x i) - (cons (list x i) r)) \ No newline at end of file + (cons (list x i) r)) + diff --git a/iniquity/interp.rkt b/iniquity/interp.rkt index 2b15b67..2f14bff 100644 --- a/iniquity/interp.rkt +++ b/iniquity/interp.rkt @@ -3,6 +3,7 @@ (provide interp-env) (require "ast.rkt") (require "interp-prim.rkt") +(require "env.rkt") ;; type Value = ;; | Integer @@ -98,15 +99,3 @@ (cons (list x y) (zip xs ys))])) -;; Env Id -> Value -(define (lookup r x) - (match r - [(cons (list y val) r) - (if (symbol=? x y) - val - (lookup r x))])) - -;; Env Id Value -> Env -(define (ext r x v) - (cons (list x v) r)) - diff --git a/iniquity/types.rkt b/iniquity/types.rkt index e0da50d..c18ec17 100644 --- a/iniquity/types.rkt +++ b/iniquity/types.rkt @@ -27,20 +27,20 @@ [(char-bits? b) (integer->char (arithmetic-shift b (- char-shift)))] [(box-bits? b) - (box (bits->value (heap-ref b)))] + (box (bits->value (mem-ref b)))] [(cons-bits? b) - (cons (bits->value (heap-ref (+ b 8))) - (bits->value (heap-ref b)))] + (cons (bits->value (mem-ref (+ b 8))) + (bits->value (mem-ref b)))] [(vect-bits? b) (if (zero? (untag b)) (vector) - (build-vector (heap-ref b) + (build-vector (mem-ref b) (lambda (j) - (bits->value (heap-ref (+ b (* 8 (add1 j))))))))] + (bits->value (mem-ref (+ b (* 8 (add1 j))))))))] [(str-bits? b) (if (zero? (untag b)) (string) - (build-string (heap-ref b) + (build-string (mem-ref b) (lambda (j) (char-ref (+ b 8) j))))] [else (error "invalid bits")])) @@ -82,7 +82,7 @@ (arithmetic-shift (arithmetic-shift i (- (integer-length ptr-mask))) (integer-length ptr-mask))) -(define (heap-ref i) +(define (mem-ref i) (ptr-ref (cast (untag i) _int64 _pointer) _int64)) (define (char-ref i j) diff --git a/jig/env.rkt b/jig/env.rkt index c43be9c..5c2ab01 100644 --- a/jig/env.rkt +++ b/jig/env.rkt @@ -12,4 +12,5 @@ ;; Env Variable Value -> Value (define (ext r x i) - (cons (list x i) r)) \ No newline at end of file + (cons (list x i) r)) + diff --git a/jig/interp.rkt b/jig/interp.rkt index 2b15b67..2f14bff 100644 --- a/jig/interp.rkt +++ b/jig/interp.rkt @@ -3,6 +3,7 @@ (provide interp-env) (require "ast.rkt") (require "interp-prim.rkt") +(require "env.rkt") ;; type Value = ;; | Integer @@ -98,15 +99,3 @@ (cons (list x y) (zip xs ys))])) -;; Env Id -> Value -(define (lookup r x) - (match r - [(cons (list y val) r) - (if (symbol=? x y) - val - (lookup r x))])) - -;; Env Id Value -> Env -(define (ext r x v) - (cons (list x v) r)) - diff --git a/jig/types.rkt b/jig/types.rkt index e0da50d..c18ec17 100644 --- a/jig/types.rkt +++ b/jig/types.rkt @@ -27,20 +27,20 @@ [(char-bits? b) (integer->char (arithmetic-shift b (- char-shift)))] [(box-bits? b) - (box (bits->value (heap-ref b)))] + (box (bits->value (mem-ref b)))] [(cons-bits? b) - (cons (bits->value (heap-ref (+ b 8))) - (bits->value (heap-ref b)))] + (cons (bits->value (mem-ref (+ b 8))) + (bits->value (mem-ref b)))] [(vect-bits? b) (if (zero? (untag b)) (vector) - (build-vector (heap-ref b) + (build-vector (mem-ref b) (lambda (j) - (bits->value (heap-ref (+ b (* 8 (add1 j))))))))] + (bits->value (mem-ref (+ b (* 8 (add1 j))))))))] [(str-bits? b) (if (zero? (untag b)) (string) - (build-string (heap-ref b) + (build-string (mem-ref b) (lambda (j) (char-ref (+ b 8) j))))] [else (error "invalid bits")])) @@ -82,7 +82,7 @@ (arithmetic-shift (arithmetic-shift i (- (integer-length ptr-mask))) (integer-length ptr-mask))) -(define (heap-ref i) +(define (mem-ref i) (ptr-ref (cast (untag i) _int64 _pointer) _int64)) (define (char-ref i j) diff --git a/knock/env.rkt b/knock/env.rkt index c43be9c..5c2ab01 100644 --- a/knock/env.rkt +++ b/knock/env.rkt @@ -12,4 +12,5 @@ ;; Env Variable Value -> Value (define (ext r x i) - (cons (list x i) r)) \ No newline at end of file + (cons (list x i) r)) + diff --git a/knock/interp.rkt b/knock/interp.rkt index 1a1baae..9f666a6 100644 --- a/knock/interp.rkt +++ b/knock/interp.rkt @@ -4,6 +4,7 @@ (provide interp-match-pat) (require "ast.rkt") (require "interp-prim.rkt") +(require "env.rkt") ;; type Value = ;; | Integer @@ -136,15 +137,3 @@ (cons (list x y) (zip xs ys))])) -;; Env Id -> Value -(define (lookup r x) - (match r - [(cons (list y val) r) - (if (symbol=? x y) - val - (lookup r x))])) - -;; Env Id Value -> Env -(define (ext r x v) - (cons (list x v) r)) - diff --git a/knock/types.rkt b/knock/types.rkt index e0da50d..c18ec17 100644 --- a/knock/types.rkt +++ b/knock/types.rkt @@ -27,20 +27,20 @@ [(char-bits? b) (integer->char (arithmetic-shift b (- char-shift)))] [(box-bits? b) - (box (bits->value (heap-ref b)))] + (box (bits->value (mem-ref b)))] [(cons-bits? b) - (cons (bits->value (heap-ref (+ b 8))) - (bits->value (heap-ref b)))] + (cons (bits->value (mem-ref (+ b 8))) + (bits->value (mem-ref b)))] [(vect-bits? b) (if (zero? (untag b)) (vector) - (build-vector (heap-ref b) + (build-vector (mem-ref b) (lambda (j) - (bits->value (heap-ref (+ b (* 8 (add1 j))))))))] + (bits->value (mem-ref (+ b (* 8 (add1 j))))))))] [(str-bits? b) (if (zero? (untag b)) (string) - (build-string (heap-ref b) + (build-string (mem-ref b) (lambda (j) (char-ref (+ b 8) j))))] [else (error "invalid bits")])) @@ -82,7 +82,7 @@ (arithmetic-shift (arithmetic-shift i (- (integer-length ptr-mask))) (integer-length ptr-mask))) -(define (heap-ref i) +(define (mem-ref i) (ptr-ref (cast (untag i) _int64 _pointer) _int64)) (define (char-ref i j) diff --git a/loot/env.rkt b/loot/env.rkt index c43be9c..5c2ab01 100644 --- a/loot/env.rkt +++ b/loot/env.rkt @@ -12,4 +12,5 @@ ;; Env Variable Value -> Value (define (ext r x i) - (cons (list x i) r)) \ No newline at end of file + (cons (list x i) r)) + diff --git a/loot/interp.rkt b/loot/interp.rkt index 573a32b..0643bfc 100644 --- a/loot/interp.rkt +++ b/loot/interp.rkt @@ -4,6 +4,7 @@ (provide interp-match-pat) (require "ast.rkt") (require "interp-prim.rkt") +(require "env.rkt") ;; type Value = ;; | Integer @@ -150,16 +151,3 @@ (cons (list x y) (zip xs ys))])) -;; Env Id -> Answer -(define (lookup env x) - (match env - ['() 'err] - [(cons (list y i) env) - (match (symbol=? x y) - [#t i] - [#f (lookup env x)])])) - -;; Env Id Value -> Env -(define (ext r x v) - (cons (list x v) r)) - diff --git a/loot/types.rkt b/loot/types.rkt index 190d8a3..a45cbf3 100644 --- a/loot/types.rkt +++ b/loot/types.rkt @@ -28,20 +28,20 @@ [(char-bits? b) (integer->char (arithmetic-shift b (- char-shift)))] [(box-bits? b) - (box (bits->value (heap-ref b)))] + (box (bits->value (mem-ref b)))] [(cons-bits? b) - (cons (bits->value (heap-ref (+ b 8))) - (bits->value (heap-ref b)))] + (cons (bits->value (mem-ref (+ b 8))) + (bits->value (mem-ref b)))] [(vect-bits? b) (if (zero? (untag b)) (vector) - (build-vector (heap-ref b) + (build-vector (mem-ref b) (lambda (j) - (bits->value (heap-ref (+ b (* 8 (add1 j))))))))] + (bits->value (mem-ref (+ b (* 8 (add1 j))))))))] [(str-bits? b) (if (zero? (untag b)) (string) - (build-string (heap-ref b) + (build-string (mem-ref b) (lambda (j) (char-ref (+ b 8) j))))] [(proc-bits? b) @@ -86,7 +86,7 @@ (arithmetic-shift (arithmetic-shift i (- (integer-length ptr-mask))) (integer-length ptr-mask))) -(define (heap-ref i) +(define (mem-ref i) (ptr-ref (cast (untag i) _int64 _pointer) _int64)) (define (char-ref i j)