tricu

A lazy functional language based on Tree Calculus
Log | Files | Refs | README | LICENSE

binding-substitution.tri (4841B)


      1 -- Isolated resolved-core substitution and Boolean-binding rewrite prototype.
      2 -- Trusted well-formed core only. Not wired into the accepted compiler.
      3 !import analysis as A
      4 !import native_math as N
      5 !import kernels as K
      6 !export *
      7 head = K.head
      8 tail = K.tail
      9 kind = A.kind
     10 payload = A.payload
     11 lazy = K.lazy
     12 choose = K.choose
     13 rebuild original value = t (kind original) (t value (tail (tail original)))
     14 withSpan original value = t (kind value) (t (payload value) (tail (tail original)))
     15 -- Positive de Bruijn shift. Local variables below cutoff are unchanged.
     16 shift amount cutoff node = lazy (_ : node)
     17   (_ : case kind node of
     18     2 = lazy (_ : rebuild node (N.add amount (payload node))) (_ : node) (N.gte (payload node) cutoff)
     19     3 = let ab = payload node in rebuild node
     20       (t (shift amount cutoff (head ab)) (shift amount cutoff (tail ab)))
     21     4 = rebuild node (shift amount (N.successor cutoff) (payload node))
     22     8 = rebuild node (K.map (child : shift amount cutoff child) (payload node))
     23     _ = node) (N.zero amount)
     24 -- Remove one surrounding binder. RHS is in the outer scope, not that binder's.
     25 substitute rhs depth node = case kind node of
     26   2 = lazy (_ : shift depth 0 rhs)
     27     (_ : lazy (_ : rebuild node (N.predecessor (payload node))) (_ : node)
     28       (N.gt (payload node) depth)) (N.equal (payload node) depth)
     29   3 = let ab = payload node in rebuild node
     30     (t (substitute rhs depth (head ab)) (substitute rhs depth (tail ab)))
     31   4 = rebuild node (substitute rhs (N.successor depth) (payload node))
     32   8 = rebuild node (K.map (child : substitute rhs depth child) (payload node))
     33   _ = node
     34 containsLambda node = case kind node of
     35   4 = t t
     36   3 = let ab = payload node in K.either (containsLambda (head ab)) (containsLambda (tail ab))
     37   8 = (let rec walk xs = K.triage t (_ : t t)
     38         (a b : K.either (containsLambda a) (walk b)) xs in walk (payload node))
     39   _ = t
     40 boolTree value = K.triage (t t) (child : N.zero child) (_ _ : t) value
     41 leafLiteral node = lazy (_ : t t)
     42   (_ : lazy (_ : N.zero (payload node)) (_ : t) (N.equal (kind node) 5)) (N.equal (kind node) 1)
     43 -- Literal Boolean trees, including the core constructor spelling `t t`.
     44 boolLiteral node = case kind node of
     45   1 = t t
     46   5 = boolTree (payload node)
     47   6 = boolTree (payload node)
     48   3 = let ab = payload node in K.both (leafLiteral (head ab)) (leafLiteral (tail ab))
     49   _ = t
     50 -- The literal identity is matched only when saturated with one argument.
     51 -- The harness authenticates the certificate's Boolean-result contract.
     52 booleanRhs negation node = lazy (_ : t t)
     53   (_ : lazy
     54     (_ : let ab = payload node in let fun = head ab in let arg = tail ab in
     55       K.both (K.either (N.equal (kind arg) 2) (boolLiteral arg))
     56         (K.both (N.equal (kind fun) 5) (A.equal (payload fun) negation)))
     57     (_ : t) (N.equal (kind node) 3)) (boolLiteral node)
     58 -- Input node must be Apply (Lambda body) rhs. The screening certificate is
     59 -- still experimental, not a general proof for arbitrary reflective contexts.
     60 -- 0..6: analysis decisions; 7: uncertified RHS; 8: any nested body lambda;
     61 -- 9: not an immediate binding. Only decision 1 performs substitution.
     62 rewrite selector negation node = lazy
     63   (_ : let ab = payload node in let fun = head ab in
     64     lazy
     65       (_ : let body = payload fun in let rhs = tail ab in
     66         let decision = A.classify (A.analyze selector body) in
     67         lazy
     68           (_ : lazy (_ : t 7 node)
     69             (_ : lazy (_ : t 8 node)
     70               (_ : t 1 (withSpan node (substitute rhs 0 body))) (containsLambda body))
     71             (K.not (booleanRhs negation rhs)))
     72           (_ : t decision node) (N.equal decision 1))
     73       (_ : t 9 node) (N.equal (kind fun) 4))
     74   (_ : t 9 node) (N.equal (kind node) 3)
     75 -- Batch transport helpers for independent host oracles.
     76 shiftBatch inputs = K.map (x : let rest = tail x in shift (head x) (head rest) (tail rest)) inputs
     77 substituteBatch inputs = K.map (x : substitute (head x) 0 (tail x)) inputs
     78 rewriteBatch certificates nodes = K.map (node : rewrite (head certificates) (tail certificates) node) nodes
     79 -- Conservative whole-core traversal: an immediate binding is a decision unit.
     80 -- Rejected bindings are returned exactly, without rewriting their descendants.
     81 -- Accepted bindings are substituted once; no fixed-point rewrite loop.
     82 transform selector negation node = case kind node of
     83   3 = let ab = payload node in
     84     lazy (_ : tail (rewrite selector negation node))
     85       (_ : rebuild node (t (transform selector negation (head ab))
     86         (transform selector negation (tail ab)))) (N.equal (kind (head ab)) 4)
     87   4 = rebuild node (transform selector negation (payload node))
     88   8 = rebuild node (K.map (child : transform selector negation child) (payload node))
     89   _ = node
     90 transformBatch certificates nodes = K.map (node : transform (head certificates) (tail certificates) node) nodes