diff --git a/IBAF-cbs/Funcons-beta b/IBAF-cbs/Funcons-beta
deleted file mode 120000
index 02b90f3..0000000
--- a/IBAF-cbs/Funcons-beta
+++ /dev/null
@@ -1 +0,0 @@
-/home/peter/cbs-all/CBS-beta/Funcons-beta
\ No newline at end of file
diff --git a/IBAF-cbs/Funcons-beta/.gitignore b/IBAF-cbs/Funcons-beta/.gitignore
new file mode 100644
index 0000000..292720e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/.gitignore
@@ -0,0 +1,5 @@
+/.cache
+/target
+
+/.project
+/.settings
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/Abrupting.cbs b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/Abrupting.cbs
new file mode 100644
index 0000000..fc166c0
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/Abrupting.cbs
@@ -0,0 +1,91 @@
+### Abruptly terminating
+
+[
+ Funcon stuck
+ Entity abrupted
+ Funcon finalise-abrupting
+ Funcon abrupt
+ Funcon handle-abrupt
+ Funcon finally
+]
+
+
+Meta-variables
+ T, T', T'' <: values
+
+
+Funcon
+ stuck : =>empty-type
+/*
+ `stuck` does not have any computation. It is used to represent the result of
+ a transition that causes the computation to terminate abruptly.
+*/
+
+
+Entity
+ _ --abrupted(_:values?)-> _
+/*
+ `abrupted(V)` in a label on a tranistion indicates abrupt termination for
+ reason `V`. `abrupted( )` indicates the absence of abrupt termination.
+*/
+
+
+Funcon
+ finalise-abrupting(X:=>T) : =>T|null-type
+ ~> handle-abrupt(X, null-value)
+/*
+ `finalise-abrupting(X)` handles abrupt termination of `X` for any reason.
+*/
+
+
+Funcon
+ abrupt(_:values) :=>empty-type
+/*
+ `abrupt(V)` terminates abruptly for reason `V`.
+*/
+Rule
+ abrupt(V:values) --abrupted(V)-> stuck
+
+
+Funcon
+ handle-abrupt(_:T'=>T, _:T''=>T) : T'=>T
+/*
+ `handle-abrupt(X, Y)` first evaluates `X`. If `X` terminates normally with
+ value `V`, then `V` is returned and `Y` is ignored. If `X` terminates abruptly
+ for reason `V`, then `Y` is executed with `V` as `given` value.
+
+ `handle-abrupt(X, Y)` is associative, with `abrupt(given)` as left and right
+ unit. `handle-abrupt(X, else(Y, abrupt(given)))` ensures propagation of
+ abrupt termination for the given reason if `Y` fails
+*/
+Rule
+ X --abrupted( )-> X'
+ --------------------------------------------------------
+ handle-abrupt(X, Y) --abrupted( )-> handle-abrupt(X', Y)
+Rule
+ X --abrupted(V:T'')-> X'
+ ----------------------------------------------
+ handle-abrupt(X, Y) --abrupted( )-> give(V, Y)
+Rule
+ handle-abrupt(V:T, Y) ~> V
+
+
+Funcon
+ finally(_:=>T, _:=>null-type) : =>T
+/*
+ `finally(X, Y)` first executes `X`. If `X` terminates normally with
+ value `V`, then `Y` is executed before terminating normally with value `V`.
+ If `X` terminates abruptly for reason `V`, then `Y` is executed before
+ terminating abruptly with the same reason `V`.
+*/
+Rule
+ X --abrupted( )-> X'
+ --------------------------------------------
+ finally(X, Y) --abrupted( )-> finally(X', Y)
+Rule
+ X --abrupted(V:values)-> X'
+ -----------------------------------------------------
+ finally(X, Y) --abrupted()-> sequential(Y, abrupt(V))
+Rule
+ finally(V:T, Y) ~> sequential(Y,V)
+
\ No newline at end of file
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/index.md b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/index.md
new file mode 100644
index 0000000..bf645d2
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/index.md
@@ -0,0 +1,131 @@
+---
+layout: default
+title: "Abrupting"
+parent: Abnormal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Abrupting.cbs]
+-----------------------------
+
+### Abruptly terminating
+
+
+
+
+
+Meta-variables
+ T, T′, T′′ <: values
+
+
+
+
+
+ stuck does not have any computation. It is used to represent the result of
+ a transition that causes the computation to terminate abruptly.
+
+
+
+Entity
+ _ --abrupted(_:values?)-> _
+
+
+ abrupted(V) in a label on a tranistion indicates abrupt termination for
+ reason V. abrupted( ) indicates the absence of abrupt termination.
+
+
+
+
+
+
+ finalise-abrupting(X) handles abrupt termination of X for any reason.
+
+
+
+
+
+ abrupt(V) terminates abruptly for reason V.
+
+
+
+
+
+Funcon
+ handle-abrupt(_:T′=>T, _:T′′=>T) : T′=>T
+
+ handle-abrupt(X, Y) first evaluates X. If X terminates normally with
+ value V, then V is returned and Y is ignored. If X terminates abruptly
+ for reason V, then Y is executed with V as given value.
+
+ handle-abrupt(X, Y) is associative, with abrupt(given) as left and right
+ unit. handle-abrupt(X, else(Y, abrupt(given))) ensures propagation of
+ abrupt termination for the given reason if Y fails
+
+
+
+
+
+
+
+ finally(X, Y) first executes X. If X terminates normally with
+ value V, then Y is executed before terminating normally with value V.
+ If X terminates abruptly for reason V, then Y is executed before
+ terminating abruptly with the same reason V.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Abrupting.cbs]: Abrupting.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Abnormal/Abrupting/Abrupting.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/tests/finally.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/tests/finally.config
new file mode 100644
index 0000000..c308c3f
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/tests/finally.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ finalise-abrupting
+ sequential(
+ print finally(2, print 1),
+ finally(print 3, print 4),
+ else(finally(fail, print 5), print 6)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4, 5, 6];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/tests/handle-abrupt.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/tests/handle-abrupt.config
new file mode 100644
index 0000000..6b8c9cd
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Abrupting/tests/handle-abrupt.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ finalise-abrupting
+ sequential(
+ print handle-abrupt(1, fail),
+ handle-abrupt(print 2, fail),
+ handle-abrupt(
+ sequential(print 3, abrupt(sequential(print 4, 5))),
+ print given)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4, 5];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Breaking/Breaking.cbs b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Breaking/Breaking.cbs
new file mode 100644
index 0000000..12318ea
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Breaking/Breaking.cbs
@@ -0,0 +1,59 @@
+### Breaking
+
+[
+ Datatype breaking
+ Funcon broken
+ Funcon finalise-breaking
+ Funcon break
+ Funcon handle-break
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ breaking ::= broken
+/*
+ `broken` is a reason for abrupt termination.
+*/
+
+
+Funcon
+ finalise-breaking(X:=>T) : =>T|null-type
+ ~> finalise-abrupting(X)
+/*
+ `finalise-breaking(X)` handles abrupt termination of `X` due to executing
+ `break`.
+*/
+
+
+Funcon
+ break : =>empty-type
+ ~> abrupt(broken)
+/*
+ `break` abruptly terminates all enclosing computations until it is handled.
+*/
+
+
+Funcon
+ handle-break(_:=>null-type) : =>null-type
+/*
+ `handle-break(X)` terminates normally when `X` terminates abruptly for the
+ reason `broken`.
+*/
+Rule
+ X --abrupted( )-> X'
+ ------------------------------------------------
+ handle-break(X) --abrupted( )-> handle-break(X')
+Rule
+ X --abrupted(broken)-> _
+ ---------------------------------------
+ handle-break(X) --abrupted( )-> null-value
+Rule
+ X --abrupted(V:~breaking)-> X'
+ ------------------------------------------------
+ handle-break(X) --abrupted(V)-> handle-break(X')
+Rule
+ handle-break(null-value) ~> null-value
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Breaking/index.md b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Breaking/index.md
new file mode 100644
index 0000000..18a1219
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Breaking/index.md
@@ -0,0 +1,98 @@
+---
+layout: default
+title: "Breaking"
+parent: Abnormal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Breaking.cbs]
+-----------------------------
+
+### Breaking
+
+
+
+
+
+
+
+
+
+Datatype
+ breaking ::= broken
+
+ broken is a reason for abrupt termination.
+
+
+
+
+
+
+ finalise-breaking(X) handles abrupt termination of X due to executing
+ break.
+
+
+
+
+
+
+ break abruptly terminates all enclosing computations until it is handled.
+
+
+
+
+
+ handle-break(X) terminates normally when X terminates abruptly for the
+ reason broken.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Breaking.cbs]: Breaking.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Abnormal/Breaking/Breaking.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Breaking/tests/handle-break.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Breaking/tests/handle-break.config
new file mode 100644
index 0000000..272d7b5
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Breaking/tests/handle-break.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ finalise-breaking
+ sequential(
+ print sequential(handle-break(null-value),0),
+ handle-break(print 1),
+ print sequential(handle-break(
+ sequential(print 2, break, fail)),3)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [0, 1, 2, 3];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Continuing/Continuing.cbs b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Continuing/Continuing.cbs
new file mode 100644
index 0000000..2827cbe
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Continuing/Continuing.cbs
@@ -0,0 +1,59 @@
+### Continuing
+
+[
+ Datatype continuing
+ Funcon continued
+ Funcon finalise-continuing
+ Funcon continue
+ Funcon handle-continue
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ continuing ::= continued
+/*
+ `continued` is a reason for abrupt termination.
+*/
+
+
+Funcon
+ finalise-continuing(X:=>T) : =>T|null-type
+ ~> finalise-abrupting(X)
+/*
+ `finalise-continuing(X)` handles abrupt termination of `X` due to executing
+ `continue`.
+*/
+
+
+Funcon
+ continue : =>empty-type
+ ~> abrupt(continued)
+/*
+ `continue` abruptly terminates all enclosing computations until it is handled.
+*/
+
+
+Funcon
+ handle-continue(_:=>null-type) : =>null-type
+/*
+ `handle-continue(X)` terminates normally when `X` terminates abruptly for the
+ reason `continued`.
+*/
+Rule
+ X --abrupted( )-> X'
+ ------------------------------------------------------
+ handle-continue(X) --abrupted( )-> handle-continue(X')
+Rule
+ X --abrupted(continued)-> _
+ --------------------------------------------
+ handle-continue(X) --abrupted( )-> null-value
+Rule
+ X --abrupted(V:~continuing)-> X'
+ ------------------------------------------------------
+ handle-continue(X) --abrupted(V)-> handle-continue(X')
+Rule
+ handle-continue(null-value) ~> null-value
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Continuing/index.md b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Continuing/index.md
new file mode 100644
index 0000000..42b1e6c
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Continuing/index.md
@@ -0,0 +1,98 @@
+---
+layout: default
+title: "Continuing"
+parent: Abnormal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Continuing.cbs]
+-----------------------------
+
+### Continuing
+
+
+
+
+
+
+
+
+
+Datatype
+ continuing ::= continued
+
+ continued is a reason for abrupt termination.
+
+
+
+
+
+
+ finalise-continuing(X) handles abrupt termination of X due to executing
+ continue.
+
+
+
+
+
+
+ continue abruptly terminates all enclosing computations until it is handled.
+
+
+
+
+
+ handle-continue(X) terminates normally when X terminates abruptly for the
+ reason continued.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Continuing.cbs]: Continuing.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Abnormal/Continuing/Continuing.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Continuing/tests/handle-continue.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Continuing/tests/handle-continue.config
new file mode 100644
index 0000000..c0d5cde
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Continuing/tests/handle-continue.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ finalise-continuing
+ sequential(
+ print sequential(handle-continue(null-value),0),
+ handle-continue(print 1),
+ print sequential(handle-continue(
+ sequential(print 2, continue, fail)),3)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [0, 1, 2, 3];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Controlling/Controlling.cbs b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Controlling/Controlling.cbs
new file mode 100644
index 0000000..2dd69c6
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Controlling/Controlling.cbs
@@ -0,0 +1,89 @@
+### Controlling
+
+[
+ Datatype continuations
+ Funcon continuation
+ Entity plug-signal
+ Funcon hole
+ Funcon resume-continuation
+ Entity control-signal
+ Funcon control
+ Funcon delimit-current-continuation Alias delimit-cc
+]
+
+Meta-variables
+ T, T1, T2 <: values
+
+Datatype
+ continuations(T1,T2) ::= continuation(_:abstractions(()=>T2))
+/*
+ `continuations(T1, T2)` consists of abstractions whose bodies contain a `hole`,
+ and which will normally compute a value of type `T2` when the `hole` is plugged
+ with a value of type `T1`.
+*/
+
+Entity
+ _ --plug-signal(V?:values?)-> _
+/*
+ A plug-signal contains the value to be filled into a `hole` in a continuation,
+ thereby allowing a continuation to resume.
+*/
+
+ Funcon
+ hole : =>values
+/*
+ A `hole` in a term cannot proceed until it receives a plug-signal
+ containing a value to plug the hole.
+*/
+Rule
+ hole --plug-signal(V)-> V
+
+Funcon
+ resume-continuation(K:continuations(T1, T2), V:T1) : =>T2
+/*
+ `resume-continuation(K, V)` resumes a continuation `K` by plugging the value
+ `V` into the `hole` in the continuation.
+*/
+Rule
+ X --plug-signal(V)-> X'
+ ---------------------------------------------------------------------------
+ resume-continuation(continuation(abstraction(X)), V:T) --plug-signal()-> X'
+
+
+Entity
+ _ --control-signal(F?:(functions(continuations(T1, T2), T2))?)-> _
+/*
+ A control-signal contains the function to which control is about to be passed
+ by the enclosing `delimit-current-continuation(X)`.
+*/
+
+Funcon
+ control(F:functions(continuations(T1, T2), T2)) : =>T1
+/*
+ `control(F)` emits a control-signal that, when handled by an enclosing
+ `delimit-current-continuation(X)`, will apply `F` to the current continuation of
+ `control(F)`, (rather than proceeding with that current continuation).
+*/
+Rule
+ control(F:functions(_,_)) --control-signal(F)-> hole
+
+
+Funcon
+ delimit-current-continuation(X:=>T) : =>T
+Alias
+ delimit-cc = delimit-current-continuation
+/*
+ `delimit-current-continuation(X)` delimits the scope of captured continuations.
+*/
+Rule
+ delimit-current-continuation(V:T) ~> V
+Rule
+ X --control-signal( )-> X'
+ -----------------------------------------------------
+ delimit-current-continuation(X) --control-signal( )->
+ delimit-current-continuation(X')
+Rule
+ X --control-signal(F)-> X'
+ ------------------------------------------------------------------
+ delimit-current-continuation(X) --control-signal( )->
+ delimit-current-continuation(apply(F, continuation closure(X')))
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Controlling/index.md b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Controlling/index.md
new file mode 100644
index 0000000..fc2185e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Controlling/index.md
@@ -0,0 +1,131 @@
+---
+layout: default
+title: "Controlling"
+parent: Abnormal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Controlling.cbs]
+-----------------------------
+
+### Controlling
+
+
+
+
+Meta-variables
+ T, T1, T2 <: values
+
+
+Datatype
+ continuations(T1,T2) ::= continuation(_:abstractions(()=>T2))
+
+
+ continuations(T1, T2) consists of abstractions whose bodies contain a hole,
+ and which will normally compute a value of type T2 when the hole is plugged
+ with a value of type T1.
+
+
+Entity
+ _ --plug-signal(V?:values?)-> _
+
+
+ A plug-signal contains the value to be filled into a hole in a continuation,
+ thereby allowing a continuation to resume.
+
+
+
+
+ A hole in a term cannot proceed until it receives a plug-signal
+ containing a value to plug the hole.
+
+
+
+
+Funcon
+ resume-continuation(K:continuations(T1, T2), V:T1) : =>T2
+
+ resume-continuation(K, V) resumes a continuation K by plugging the value
+ V into the hole in the continuation.
+
+
+
+
+
+
+
+
+ A control-signal contains the function to which control is about to be passed
+ by the enclosing delimit-current-continuation(X).
+
+
+
+
+ control(F) emits a control-signal that, when handled by an enclosing
+ delimit-current-continuation(X), will apply F to the current continuation of
+ control(F), (rather than proceeding with that current continuation).
+
+
+
+
+
+
+ delimit-current-continuation(X) delimits the scope of captured continuations.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Controlling.cbs]: Controlling.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Abnormal/Controlling/Controlling.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/Failing.cbs b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/Failing.cbs
new file mode 100644
index 0000000..12fe3da
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/Failing.cbs
@@ -0,0 +1,108 @@
+### Failing
+
+[
+ Datatype failing
+ Funcon failed
+ Funcon finalise-failing
+ Funcon fail
+ Funcon else
+ Funcon else-choice
+ Funcon checked
+ Funcon check-true
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ failing ::= failed
+/*
+ `failed` is a reason for abrupt termination.
+*/
+
+
+Funcon
+ finalise-failing(X:=>T) : =>T|null-type
+ ~> finalise-abrupting(X)
+/*
+ `finalise-failing(X)` handles abrupt termination of `X` due to executing `fail`.
+*/
+
+
+Funcon
+ fail : =>empty-type
+ ~> abrupt(failed)
+/*
+ `fail` abruptly terminates all enclosing computations until it is handled.
+*/
+
+
+Funcon
+ else(_:=>T, _:(=>T)+) : =>T
+/*
+ `else(X1, X2, ...)` executes the arguments in turn until either some
+ `Xi` does *not* fail, or all arguments `Xi` have been executed.
+ The last argument executed determines the result.
+ `else(X, Y)` is associative, with unit `fail`.
+*/
+Rule
+ X --abrupted( )-> X'
+ --------------------------------------
+ else(X, Y) --abrupted( )-> else(X', Y)
+Rule
+ X --abrupted(failed)-> _
+ ---------------------------------
+ else(X, Y) --abrupted( )-> Y
+Rule
+ X --abrupted(V:~failing)-> X'
+ --------------------------------------
+ else(X, Y) --abrupted(V)-> else(X', Y)
+Rule
+ else(V:T, Y) ~> V
+Rule
+ else(X, Y, Z+) ~> else(X, else(Y, Z+))
+
+
+Funcon
+ else-choice(_:(=>T)+) : =>T
+/*
+ `else-choice(X,...)` executes the arguments in any order until either some
+ `Xi` does *not* fail, or all arguments `Xi` have been executed.
+ The last argument executed determines the result.
+ `else(X, Y)` is associative and commutative, with unit `fail`.
+*/
+Rule
+ else-choice(W*, X, Y, Z*)
+ ~> choice(else(X, else-choice(W*, Y, Z*),
+ else(Y, else-choice(W*, X, Z*))))
+Rule
+ else-choice(X) ~> X
+
+
+Funcon
+ check-true(_:booleans) : =>null-type
+Alias
+ check = check-true
+/*
+ `check-true(X)` terminates normally if the value computed by `X` is `true`,
+ and fails if it is `false`.
+*/
+Rule
+ check-true(true) ~> null-value
+Rule
+ check-true(false) ~> fail
+
+
+Funcon
+ checked(_:(T)?) : =>T
+/*
+ `checked(X)` fails when `X` gives the empty sequence of values `( )`,
+ representing that an optional value has not been computed. It otherwise
+ computes the same as `X`.
+*/
+Rule
+ checked(V:T) ~> V
+Rule
+ checked( ) ~> fail
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/index.md b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/index.md
new file mode 100644
index 0000000..c9ecbd1
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/index.md
@@ -0,0 +1,149 @@
+---
+layout: default
+title: "Failing"
+parent: Abnormal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Failing.cbs]
+-----------------------------
+
+### Failing
+
+
+
+
+
+
+
+
+
+Datatype
+ failing ::= failed
+
+ failed is a reason for abrupt termination.
+
+
+
+
+
+
+ finalise-failing(X) handles abrupt termination of X due to executing fail.
+
+
+
+
+
+
+ fail abruptly terminates all enclosing computations until it is handled.
+
+
+
+Funcon
+ else(_:=>T, _:(=>T)+) : =>T
+
+ else(X1, X2, ...) executes the arguments in turn until either some
+ Xi does *not* fail, or all arguments Xi have been executed.
+ The last argument executed determines the result.
+ else(X, Y) is associative, with unit fail.
+
+Rule
+ X --abrupted( )-> X′
+ --------------------------------------
+ else(X, Y) --abrupted( )-> else(X′, Y)
+Rule
+ X --abrupted(failed)-> _
+ ---------------------------------
+ else(X, Y) --abrupted( )-> Y
+Rule
+ X --abrupted(V:~failing)-> X′
+ --------------------------------------
+ else(X, Y) --abrupted(V)-> else(X′, Y)
+Rule
+ else(V:T, Y) ~> V
+Rule
+ else(X, Y, Z+) ~> else(X, else(Y, Z+))
+
+
+
+Funcon
+ else-choice(_:(=>T)+) : =>T
+
+ else-choice(X,...) executes the arguments in any order until either some
+ Xi does *not* fail, or all arguments Xi have been executed.
+ The last argument executed determines the result.
+ else(X, Y) is associative and commutative, with unit fail.
+
+Rule
+ else-choice(W*, X, Y, Z*)
+ ~> choice(else(X, else-choice(W*, Y, Z*),
+ else(Y, else-choice(W*, X, Z*))))
+Rule
+ else-choice(X) ~> X
+
+
+
+
+ check-true(X) terminates normally if the value computed by X is true,
+ and fails if it is false.
+
+
+
+
+
+Funcon
+ checked(_:(T)?) : =>T
+
+ checked(X) fails when X gives the empty sequence of values ( ),
+ representing that an optional value has not been computed. It otherwise
+ computes the same as X.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Failing.cbs]: Failing.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Abnormal/Failing/Failing.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/check-true.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/check-true.config
new file mode 100644
index 0000000..9644185
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/check-true.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ finalise-failing
+ sequential(
+ check-true(true), print 1,
+ else(check-true(false), print 2),
+ check-true(not false), print 3,
+ print sequential(check-true(true),4)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/checked.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/checked.config
new file mode 100644
index 0000000..27819bc
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/checked.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ finalise-failing
+ sequential(
+ effect(checked(true)), print 1,
+ else(effect(checked()), print 2),
+ else(effect(checked(map-lookup(map(),1))), print 3),
+ print(checked(map-lookup(map(tuple(0,1),tuple(1,4)),1)))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/defined.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/defined.config
new file mode 100644
index 0000000..fdc1584
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/defined.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term:
+ finalise-failing
+ sequential(
+ effect(checked(42)), print 1,
+ else(checked(sequential(print(2),lookup(map-empty,"x"))), print 3)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/else-choice.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/else-choice.config
new file mode 100644
index 0000000..1d3c541
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/else-choice.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ finalise-failing finalise-abrupting
+ sequential(
+ else-choice(print 1),
+ else-choice(fail, fail, fail, print 2, fail, print 3)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2];
+// Also possible:
+// standard-out: [1, 3];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/else.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/else.config
new file mode 100644
index 0000000..0407a80
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Failing/tests/else.config
@@ -0,0 +1,19 @@
+general {
+ funcon-term:
+ finalise-failing finalise-abrupting
+ sequential(
+ else(fail, print 1),
+ print else(2, fail),
+ else(print 3, fail),
+ handle-abrupt(
+ else(abrupt(true), print 99),
+ print 4),
+ else(fail, fail, print 5)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4, 5];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Returning/Returning.cbs b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Returning/Returning.cbs
new file mode 100644
index 0000000..7835b90
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Returning/Returning.cbs
@@ -0,0 +1,60 @@
+### Returning
+
+[
+ Datatype returning
+ Funcon returned
+ Funcon finalise-returning
+ Funcon return
+ Funcon handle-return
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ returning ::= returned(_:values)
+/*
+ `returned(V?)` is a reason for abrupt termination.
+*/
+
+
+Funcon
+ finalise-returning(X:=>T) : =>T|null-type
+ ~> finalise-abrupting(X)
+/*
+ `finalise-returning(X)` handles abrupt termination of `X` due to
+ executing `return(V)`.
+*/
+
+
+Funcon
+ return(V:T) : =>empty-type
+ ~> abrupt(returned(V))
+/*
+ `return(V)` abruptly terminates all enclosing computations until it is
+ handled, then giving `V`. Note that `V` may be `null-value`.
+*/
+
+
+Funcon
+ handle-return(_:=>T) : =>T
+/*
+ `handle-return(X)` first evaluates `X`. If `X` either terminates abruptly for
+ reason `returned(V)`, or terminates normally with value `V`, it gives `V`.
+*/
+Rule
+ X --abrupted( )-> X'
+ --------------------------------------------------
+ handle-return(X) --abrupted( )-> handle-return(X')
+Rule
+ X --abrupted(returned(V:values))-> X'
+ ----------------------------------------------
+ handle-return(X) --abrupted( )-> V
+Rule
+ X --abrupted(V':~returning)-> X'
+ ---------------------------------------------------
+ handle-return(X) --abrupted(V')-> handle-return(X')
+Rule
+ handle-return(V:T) ~> V
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Returning/index.md b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Returning/index.md
new file mode 100644
index 0000000..b1dd016
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Returning/index.md
@@ -0,0 +1,100 @@
+---
+layout: default
+title: "Returning"
+parent: Abnormal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Returning.cbs]
+-----------------------------
+
+### Returning
+
+
+
+
+
+
+
+
+
+Datatype
+ returning ::= returned(_:values)
+
+
+ returned(V?) is a reason for abrupt termination.
+
+
+
+
+
+
+ finalise-returning(X) handles abrupt termination of X due to
+ executing return(V).
+
+
+
+
+
+
+ return(V) abruptly terminates all enclosing computations until it is
+ handled, then giving V. Note that V may be null-value.
+
+
+
+Funcon
+ handle-return(_:=>T) : =>T
+
+ handle-return(X) first evaluates X. If X either terminates abruptly for
+ reason returned(V), or terminates normally with value V, it gives V.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Returning.cbs]: Returning.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Abnormal/Returning/Returning.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Returning/tests/handle-return.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Returning/tests/handle-return.config
new file mode 100644
index 0000000..309767d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Returning/tests/handle-return.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ finalise-returning
+ sequential(
+ print handle-return(1),
+ handle-return(print 2),
+ print handle-return(
+ sequential(print 3, return(sequential(print 4, 5))))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4, 5];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/Throwing.cbs b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/Throwing.cbs
new file mode 100644
index 0000000..40bbb01
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/Throwing.cbs
@@ -0,0 +1,86 @@
+### Throwing
+
+[
+ Datatype throwing
+ Funcon thrown
+ Funcon finalise-throwing
+ Funcon throw
+ Funcon handle-thrown
+ Funcon handle-recursively
+ Funcon catch-else-throw
+]
+
+
+Meta-variables
+ R, S, T, T', T'' <: values
+
+
+Datatype
+ throwing ::= thrown(_:values)
+/*
+ `thrown(V)` is a reason for abrupt termination.
+*/
+
+
+Funcon
+ finalise-throwing(X:=>T) : =>T|null-type
+ ~> finalise-abrupting(X)
+/*
+ `finalise-throwing(X)` handles abrupt termination of `X` due to
+ executing `throw(V)`.
+*/
+
+
+Funcon
+ throw(V:T) : =>empty-type
+ ~> abrupt(thrown(V))
+/*
+ `throw(V)` abruptly terminates all enclosing computations uTil it is handled.
+*/
+
+
+Funcon
+ handle-thrown(_:T'=>T, _:T''=>T) : T'=>T
+/*
+ `handle-thrown(X, Y)` first evaluates `X`. If `X` terminates normally with
+ value `V`, then `V` is returned and `Y` is ignored. If `X` terminates abruptly
+ with a thrown eTity having value `V`, then `Y` is executed with `V` as
+ `given` value.
+
+ `handle-thrown(X, Y)` is associative, with `throw(given)` as unit.
+ `handle-thrown(X, else(Y, throw(given)))` ensures that if `Y` fails, the
+ thrown value is re-thrown.
+*/
+Rule
+ X --abrupted( )-> X'
+ --------------------------------------------------------
+ handle-thrown(X, Y) --abrupted( )-> handle-thrown(X', Y)
+Rule
+ X --abrupted(thrown(V'':values))-> X'
+ ----------------------------------------------
+ handle-thrown(X, Y) --abrupted( )-> give(V'', Y)
+Rule
+ X --abrupted(V':~throwing)-> X'
+ ---------------------------------------------------------
+ handle-thrown(X, Y) --abrupted(V')-> handle-thrown(X', Y)
+Rule
+ handle-thrown(V:T, Y) ~> V
+
+
+Funcon
+ handle-recursively(X:S=>T, Y:R=>T) : S=>T
+ ~> handle-thrown(X, else(handle-recursively(Y, Y), throw(given)))
+/*
+ `handle-recursively(X, Y)` behaves similarly to `handle-thrown(X, Y)`, except
+ that another copy of the handler attempts to handle any values thrown by `Y`.
+ Thus, many thrown values may get handled by the same handler.
+*/
+
+
+Funcon
+ catch-else-throw(P:values, Y:=>T) : =>T
+ ~> else(case-match(P, Y), throw(given))
+ /*
+ `handle-thrown(X, catch-else-throw(P, Y))` handles those values thrown by `X`
+ that match pattern `P`. Other thrown values are re-thrown.
+ */
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/index.md b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/index.md
new file mode 100644
index 0000000..2603cb0
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/index.md
@@ -0,0 +1,128 @@
+---
+layout: default
+title: "Throwing"
+parent: Abnormal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Throwing.cbs]
+-----------------------------
+
+### Throwing
+
+
+
+
+
+Meta-variables
+ R, S, T, T′, T′′ <: values
+
+
+
+Datatype
+ throwing ::= thrown(_:values)
+
+
+ thrown(V) is a reason for abrupt termination.
+
+
+
+
+
+
+ finalise-throwing(X) handles abrupt termination of X due to
+ executing throw(V).
+
+
+
+
+
+
+ throw(V) abruptly terminates all enclosing computations uTil it is handled.
+
+
+
+Funcon
+ handle-thrown(_:T′=>T, _:T′′=>T) : T′=>T
+
+ handle-thrown(X, Y) first evaluates X. If X terminates normally with
+ value V, then V is returned and Y is ignored. If X terminates abruptly
+ with a thrown eTity having value V, then Y is executed with V as
+ given value.
+
+ handle-thrown(X, Y) is associative, with throw(given) as unit.
+ handle-thrown(X, else(Y, throw(given))) ensures that if Y fails, the
+ thrown value is re-thrown.
+
+
+
+
+
+
+
+
+ handle-recursively(X, Y) behaves similarly to handle-thrown(X, Y), except
+ that another copy of the handler attempts to handle any values thrown by Y.
+ Thus, many thrown values may get handled by the same handler.
+
+
+
+
+
+
+ handle-thrown(X, catch-else-throw(P, Y)) handles those values thrown by X
+ that match pattern P. Other thrown values are re-thrown.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Throwing.cbs]: Throwing.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Abnormal/Throwing/Throwing.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/tests/catch-else-throw.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/tests/catch-else-throw.config
new file mode 100644
index 0000000..0a77e42
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/tests/catch-else-throw.config
@@ -0,0 +1,19 @@
+general {
+ funcon-term:
+ initialise-binding
+ finalise-throwing
+ sequential(
+ handle-thrown(
+ throw 1,
+ catch-else-throw(1, print 1)),
+ handle-thrown(
+ handle-thrown(throw 2,
+ catch-else-throw(1, fail)),
+ catch-else-throw(2, print 2)))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/tests/handle-recursively.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/tests/handle-recursively.config
new file mode 100644
index 0000000..71bd0dd
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/tests/handle-recursively.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ finalise-throwing
+ handle-recursively(
+ throw 1,
+ if-true-else(
+ is-less(given,4),
+ sequential(print given, throw integer-add(1,given)),
+ print"OK")
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, "OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/tests/handle-thrown.config b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/tests/handle-thrown.config
new file mode 100644
index 0000000..547d41e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Abnormal/Throwing/tests/handle-thrown.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ finalise-throwing
+ sequential(
+ print handle-thrown(1, fail),
+ handle-thrown(print 2, fail),
+ handle-thrown(
+ sequential(print 3, throw(sequential(print 4, 5))),
+ print given)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4, 5];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Computation-Types/Computation-Types.cbs b/IBAF-cbs/Funcons-beta/Computations/Computation-Types/Computation-Types.cbs
new file mode 100644
index 0000000..1f6ef95
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Computation-Types/Computation-Types.cbs
@@ -0,0 +1,13 @@
+## Computation Types
+
+Built-in Funcon
+ computation-types : types
+/*
+ For any value type `T`, the term `=>T` is the type of computations that
+ compute values of type `T` whenever they terminate normally.
+
+ For any subtypes `S`, `T` of `values`, `S=>T` is the type of computations
+ that compute values of type `T` whenever they terminate normally, and
+ either do not refer at all to the `given` entity, or require the `given`
+ entity to have type `S`.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Computations/Computation-Types/index.md b/IBAF-cbs/Funcons-beta/Computations/Computation-Types/index.md
new file mode 100644
index 0000000..7531018
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Computation-Types/index.md
@@ -0,0 +1,47 @@
+---
+layout: default
+title: "Computation-Types"
+parent: Computations
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Computation-Types.cbs]
+-----------------------------
+
+## Computation Types
+
+Built-in Funcon
+ computation-types : types
+
+ For any value type T, the term =>T is the type of computations that
+ compute values of type T whenever they terminate normally.
+
+ For any subtypes S, T of values, S=>T is the type of computations
+ that compute values of type T whenever they terminate normally, and
+ either do not refer at all to the given entity, or require the given
+ entity to have type S.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Computation-Types.cbs]: Computation-Types.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Computation-Types/Computation-Types.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/Binding.cbs b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/Binding.cbs
new file mode 100644
index 0000000..967d5cb
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/Binding.cbs
@@ -0,0 +1,269 @@
+### Binding
+
+[
+ Type environments Alias envs
+ Datatype identifiers Alias ids
+ Funcon identifier-tagged Alias id-tagged
+ Funcon fresh-identifier
+ Entity environment Alias env
+ Funcon initialise-binding
+ Funcon bind-value Alias bind
+ Funcon unbind
+ Funcon bound-directly
+ Funcon bound-value Alias bound
+ Funcon closed
+ Funcon scope
+ Funcon accumulate
+ Funcon collateral
+ Funcon bind-recursively
+ Funcon recursive
+]
+
+
+Meta-variables
+ T <: values
+
+
+#### Environments
+
+Type
+ environments ~> maps(identifiers, values?)
+Alias
+ envs = environments
+/*
+ An environment represents bindings of identifiers to values.
+ Mapping an identifier to `( )` represents that its binding is hidden.
+
+ Circularity in environments (due to recursive bindings) is represented using
+ bindings to cut-points called `links`. Funcons are provided for making
+ declarations recursive and for referring to bound values without explicit
+ mention of links, so their existence can generally be ignored.
+*/
+
+
+Datatype
+ identifiers ::= {_:strings} | identifier-tagged(_:identifiers, _:values)
+Alias
+ ids = identifiers
+Alias
+ id-tagged = identifier-tagged
+/*
+ An identifier is either a string of characters, or an identifier tagged with
+ some value (e.g., with the identifier of a namespace).
+*/
+
+
+Funcon
+ fresh-identifier : =>identifiers
+/*
+ `fresh-identifier` computes an identifier distinct from all previously
+ computed identifiers.
+*/
+Rule
+ fresh-identifier ~> identifier-tagged("generated", fresh-atom)
+
+
+#### Current bindings
+
+Entity
+ environment(_:environments) |- _ ---> _
+Alias
+ env = environment
+/*
+ The environment entity allows a computation to refer to the current bindings
+ of identifiers to values.
+*/
+
+
+Funcon
+ initialise-binding(X:=>T) : =>T
+ ~> initialise-linking(initialise-generating(closed(X)))
+/*
+ `initialise-binding(X)` ensures that `X` does not depend on non-local bindings.
+ It also ensures that the linking entity (used to represent potentially cyclic
+ bindings) and the generating entity (for creating fresh identifiers) are
+ initialised.
+*/
+
+
+Funcon
+ bind-value(I:identifiers, V:values) : =>environments
+ ~> { I |-> V }
+Alias
+ bind = bind-value
+/*
+ `bind-value(I, X)` computes the environment that binds only `I` to the value
+ computed by `X`.
+*/
+
+
+Funcon
+ unbind(I:identifiers) : =>environments
+ ~> { I |-> ( ) }
+/*
+ `unbind(I)` computes the environment that hides the binding of `I`.
+*/
+
+
+Funcon
+ bound-directly(_:identifiers) : =>values
+/*
+ `bound-directly(I)` returns the value to which `I` is currently bound, if any,
+ and otherwise fails.
+
+ `bound-directly(I)` does *not* follow links. It is used only in connection with
+ recursively-bound values when references are not encapsulated in abstractions.
+*/
+Rule
+ lookup(Rho, I) ~> (V:values)
+ --------------------------------------------------------
+ environment(Rho) |- bound-directly(I:identifiers) ---> V
+Rule
+ lookup(Rho, I) ~> ( )
+ -----------------------------------------------------------
+ environment(Rho) |- bound-directly(I:identifiers) ---> fail
+
+
+Funcon
+ bound-value(I:identifiers) : =>values
+ ~> follow-if-link(bound-directly(I))
+Alias
+ bound = bound-value
+/*
+ `bound-value(I)` inspects the value to which `I` is currently bound, if any,
+ and otherwise fails. If the value is a link, `bound-value(I)` returns the
+ value obtained by following the link, if any, and otherwise fails. If the
+ inspected value is not a link, `bound-value(I)` returns it.
+
+ `bound-value(I)` is used for references to non-recursive bindings and to
+ recursively-bound values when references are encapsulated in abstractions.
+*/
+
+
+#### Scope
+
+Funcon
+ closed(X:=>T) : =>T
+/*
+ `closed(X)` ensures that `X` does not depend on non-local bindings.
+*/
+Rule
+ environment(map( )) |- X ---> X'
+ -------------------------------------------
+ environment(_) |- closed(X) ---> closed(X')
+Rule
+ closed(V:T) ~> V
+
+
+Funcon
+ scope(_:environments, _:=>T) : =>T
+/*
+ `scope(D,X)` executes `D` with the current bindings, to compute an environment
+ `Rho` representing local bindings. It then executes `X` to compute the result,
+ with the current bindings extended by `Rho`, which may shadow or hide previous
+ bindings.
+
+ `closed(scope(Rho, X))` ensures that `X` can reference only the bindings
+ provided by `Rho`.
+*/
+Rule
+ environment(map-override(Rho1, Rho0)) |- X ---> X'
+ ---------------------------------------------------------------------
+ environment(Rho0) |- scope(Rho1:environments, X) ---> scope(Rho1, X')
+Rule
+ scope(_:environments, V:T) ~> V
+
+
+Funcon
+ accumulate(_:(=>environments)*) : =>environments
+/*
+ `accumulate(D1, D2)` executes `D1` with the current bindings, to compute an
+ environment `Rho1` representing some local bindings. It then executes `D2` to
+ compute an environment `Rho2` representing further local bindings, with the
+ current bindings extended by `Rho1`, which may shadow or hide previous
+ current bindings. The result is `Rho1` extended by `Rho2`, which may shadow
+ or hide the bindings of `Rho1`.
+
+ `accumulate(_, _)` is associative, with `map( )` as unit, and extends to any
+ number of arguments.
+*/
+Rule
+ D1 ---> D1'
+ -------------------------------------------
+ accumulate(D1, D2) ---> accumulate(D1', D2)
+Rule
+ accumulate(Rho1:environments, D2) ~> scope(Rho1, map-override(D2, Rho1))
+Rule
+ accumulate( ) ~> map( )
+Rule
+ accumulate(D1) ~> D1
+Rule
+ accumulate(D1, D2, D+) ~> accumulate(D1, accumulate(D2, D+))
+
+
+Funcon
+ collateral(Rho*:environments*) : =>environments
+ ~> checked map-unite(Rho*)
+/*
+ `collateral(D1, ...)` pre-evaluates its arguments with the current bindings,
+ and unites the resulting maps, which fails if the domains are not pairwise
+ disjoint.
+
+ `collateral(D1, D2)` is associative and commutative with `map( )` as unit,
+ and extends to any number of arguments.
+*/
+
+
+#### Recurse
+
+Funcon
+ bind-recursively(I:identifiers, E:=>values) : =>environments
+ ~> recursive({I}, bind-value(I, E))
+/*
+ `bind-recursively(I, E)` binds `I` to a link that refers to the value of `E`,
+ representing a recursive binding of `I` to the value of `E`.
+ Since `bound-value(I)` follows links, it should not be executed during the
+ evaluation of `E`.
+*/
+
+
+Funcon
+ recursive(SI:sets(identifiers), D:=>environments) : =>environments
+ ~> re-close(bind-to-forward-links(SI), D)
+/*
+ `recursive(SI, D)` executes `D` with potential recursion on the bindings of
+ the identifiers in the set `SI` (which need not be the same as the set of
+ identifiers bound by `D`).
+*/
+
+
+Auxiliary Funcon
+ re-close(M:maps(identifiers, links), D:=>environments) : =>environments
+ ~> accumulate(scope(M, D), sequential(set-forward-links(M), map( )))
+/*
+ `re-close(M, D)` first executes `D` in the scope `M`, which maps identifiers
+ to freshly allocated links. This computes an environment `Rho` where the bound
+ values may contain links, or implicit references to links in abstraction
+ values. It then sets the link for each identifier in the domain of `M` to
+ refer to its bound value in `Rho`, and returns `Rho` as the result.
+*/
+
+
+Auxiliary Funcon
+ bind-to-forward-links(SI:sets(identifiers)) : =>maps(identifiers, links)
+ ~> map-unite(interleave-map(bind-value(given, fresh-link(values)),
+ set-elements(SI)))
+/*
+ `bind-to-forward-links(SI)` binds each identifier in the set `SI` to a
+ freshly allocated link.
+*/
+
+
+Auxiliary Funcon
+ set-forward-links(M:maps(identifiers, links)) : =>null-type
+ ~> effect(interleave-map(set-link(map-lookup(M, given), bound-value(given)),
+ set-elements(map-domain(M))))
+/*
+ For each identifier `I` in the domain of `M`, `set-forward-links(M)` sets the
+ link to which `I` is mapped by `M` to the current bound value of `I`.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/index.md b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/index.md
new file mode 100644
index 0000000..cb6b402
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/index.md
@@ -0,0 +1,320 @@
+---
+layout: default
+title: "Binding"
+parent: Normal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Binding.cbs]
+-----------------------------
+
+### Binding
+
+
+
+
+
+
+
+
+
+#### Environments
+
+
+
+
+
+ An environment represents bindings of identifiers to values.
+ Mapping an identifier to ( ) represents that its binding is hidden.
+
+ Circularity in environments (due to recursive bindings) is represented using
+ bindings to cut-points called links. Funcons are provided for making
+ declarations recursive and for referring to bound values without explicit
+ mention of links, so their existence can generally be ignored.
+
+
+
+
+
+
+ An identifier is either a string of characters, or an identifier tagged with
+ some value (e.g., with the identifier of a namespace).
+
+
+
+
+
+ fresh-identifier computes an identifier distinct from all previously
+ computed identifiers.
+
+
+
+
+
+#### Current bindings
+
+
+
+
+
+
+ The environment entity allows a computation to refer to the current bindings
+ of identifiers to values.
+
+
+
+
+
+
+ initialise-binding(X) ensures that X does not depend on non-local bindings.
+ It also ensures that the linking entity (used to represent potentially cyclic
+ bindings) and the generating entity (for creating fresh identifiers) are
+ initialised.
+
+
+
+
+ bind-value(I, X) computes the environment that binds only I to the value
+ computed by X.
+
+
+
+
+
+
+ unbind(I) computes the environment that hides the binding of I.
+
+
+
+
+
+ bound-directly(I) returns the value to which I is currently bound, if any,
+ and otherwise fails.
+
+ bound-directly(I) does *not* follow links. It is used only in connection with
+ recursively-bound values when references are not encapsulated in abstractions.
+
+
+
+
+
+
+ bound-value(I) inspects the value to which I is currently bound, if any,
+ and otherwise fails. If the value is a link, bound-value(I) returns the
+ value obtained by following the link, if any, and otherwise fails. If the
+ inspected value is not a link, bound-value(I) returns it.
+
+ bound-value(I) is used for references to non-recursive bindings and to
+ recursively-bound values when references are encapsulated in abstractions.
+
+
+
+#### Scope
+
+Funcon
+ closed(X:=>T) : =>T
+
+ closed(X) ensures that X does not depend on non-local bindings.
+
+
+
+
+
+
+
+ scope(D,X) executes D with the current bindings, to compute an environment
+ Rho representing local bindings. It then executes X to compute the result,
+ with the current bindings extended by Rho, which may shadow or hide previous
+ bindings.
+
+ closed(scope(Rho, X)) ensures that X can reference only the bindings
+ provided by Rho.
+
+
+
+
+
+
+
+ accumulate(D1, D2) executes D1 with the current bindings, to compute an
+ environment Rho1 representing some local bindings. It then executes D2 to
+ compute an environment Rho2 representing further local bindings, with the
+ current bindings extended by Rho1, which may shadow or hide previous
+ current bindings. The result is Rho1 extended by Rho2, which may shadow
+ or hide the bindings of Rho1.
+
+ accumulate(_, _) is associative, with map( ) as unit, and extends to any
+ number of arguments.
+
+
+
+
+
+
+
+
+ collateral(D1, ...) pre-evaluates its arguments with the current bindings,
+ and unites the resulting maps, which fails if the domains are not pairwise
+ disjoint.
+
+ collateral(D1, D2) is associative and commutative with map( ) as unit,
+ and extends to any number of arguments.
+
+
+
+#### Recurse
+
+
+
+
+ bind-recursively(I, E) binds I to a link that refers to the value of E,
+ representing a recursive binding of I to the value of E.
+ Since bound-value(I) follows links, it should not be executed during the
+ evaluation of E.
+
+
+
+
+
+
+ recursive(SI, D) executes D with potential recursion on the bindings of
+ the identifiers in the set SI (which need not be the same as the set of
+ identifiers bound by D).
+
+
+
+
+
+
+ re-close(M, D) first executes D in the scope M, which maps identifiers
+ to freshly allocated links. This computes an environment Rho where the bound
+ values may contain links, or implicit references to links in abstraction
+ values. It then sets the link for each identifier in the domain of M to
+ refer to its bound value in Rho, and returns Rho as the result.
+
+
+
+
+
+
+ bind-to-forward-links(SI) binds each identifier in the set SI to a
+ freshly allocated link.
+
+
+
+
+
+
+ For each identifier I in the domain of M, set-forward-links(M) sets the
+ link to which I is mapped by M to the current bound value of I.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Binding.cbs]: Binding.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Normal/Binding/Binding.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/accumulate.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/accumulate.config
new file mode 100644
index 0000000..21daf12
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/accumulate.config
@@ -0,0 +1,27 @@
+general {
+ funcon-term:
+ initialise-binding
+ tuple(
+ accumulate( ),
+ accumulate(bind-value("x", true)),
+ accumulate(bind-value("x", true),
+ bind-value("y", bound-directly"x")),
+ accumulate(bind-value("x", true),
+ bind-value("y", bound-directly"x"),
+ bind-value("z", bound-directly"x")),
+ accumulate(bind-value("x", true),
+ bind-value("y", true),
+ bind-value("x", bound-directly"x")))
+ ;
+}
+
+tests {
+ result-term:
+ tuple(
+ map( ),
+ {"x"|->true},
+ {"x"|->true, "y"|->true},
+ {"x"|->true, "y"|->true, "z"|->true},
+ {"y"|->true, "x"|->true})
+ ;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bind-recursively.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bind-recursively.config
new file mode 100644
index 0000000..c7a75d4
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bind-recursively.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ initialise-binding
+ scope(
+ bind-recursively("x",
+ thunk closure
+ is-value bound-value"x"),
+ force bound-value"x")
+ ;
+}
+
+tests {
+ result-term:
+ true
+ ;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bind-value.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bind-value.config
new file mode 100644
index 0000000..6e3d821
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bind-value.config
@@ -0,0 +1,9 @@
+general {
+ funcon-term:
+ bind-value("x", 1)
+ ;
+}
+
+tests {
+ result-term: {"x"|->1};
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bound-directly.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bound-directly.config
new file mode 100644
index 0000000..d876434
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bound-directly.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-binding
+ scope(
+ {"x"|->true, "y"|->fresh-link(booleans)},
+ and(
+ bound-directly"x",
+ is-in-type(bound-directly"y", links),
+ else(bound-directly"z", true)))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bound-value.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bound-value.config
new file mode 100644
index 0000000..567a028
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/bound-value.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-binding
+ scope(
+ {"x"|->true, "y"|->fresh-initialised-link(booleans,true)},
+ and(
+ bound-value"x",
+ bound-value"y",
+ else(bound-value"z",true)))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/closed.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/closed.config
new file mode 100644
index 0000000..d2fd86e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/closed.config
@@ -0,0 +1,11 @@
+general {
+ funcon-term:
+ initialise-binding
+ scope({"x"|->1},
+ closed(else(bound-directly"x", true)))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/collateral.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/collateral.config
new file mode 100644
index 0000000..906ef86
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/collateral.config
@@ -0,0 +1,27 @@
+general {
+ funcon-term:
+ initialise-binding tuple(
+ collateral( ),
+ collateral(bind-value("x", true)),
+ collateral(bind-value("x", true),
+ bind-value("y", false)),
+ collateral(bind-value("x", true),
+ bind-value("y", false),
+ unbind"z"),
+ scope(bind-value("x",true),
+ collateral(bind-value("x", false),
+ bind-value("y", true),
+ bind-value("z", bound-directly"x"))))
+ ;
+}
+
+tests {
+ result-term:
+ tuple(
+ map( ),
+ {"x"|->true},
+ {"x"|->true, "y"|->false},
+ {"x"|->true, "y"|->false, "z"|->( )},
+ {"x"|->false,"y"|->true, "z"|->true})
+ ;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/environments.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/environments.config
new file mode 100644
index 0000000..74c0a67
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/environments.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term:
+ and(
+ is-in-type(map(),environments),
+ is-in-type({"x"|->true},environments),
+ is-in-type({"x"|->true, "y"|->false},environments))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/fresh-identifier.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/fresh-identifier.config
new file mode 100644
index 0000000..9c7ada7
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/fresh-identifier.config
@@ -0,0 +1,10 @@
+general {
+ funcon-term:
+ initialise-generating
+ not is-equal(fresh-identifier, fresh-identifier)
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/identifiers.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/identifiers.config
new file mode 100644
index 0000000..9bfdb50
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/identifiers.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term:
+ and(
+ is-in-type("x", identifiers),
+ is-in-type(identifier-tagged("x",false), identifiers),
+ is-in-type(identifier-tagged(identifier-tagged("x",true),false), identifiers),
+ is-in-type(identifier-tagged("x",identifier-tagged("x",true)), identifiers)
+ )
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/initialise-binding.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/initialise-binding.config
new file mode 100644
index 0000000..ec7df7d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/initialise-binding.config
@@ -0,0 +1,10 @@
+general {
+ funcon-term:
+ initialise-binding(print"OK")
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/recursive.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/recursive.config
new file mode 100644
index 0000000..9f6f8a2
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/recursive.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ initialise-binding
+ scope(
+ recursive(
+ {"x"},
+ bind-value("x", thunk closure
+ if-true-else(not is-equal(null-value, bound-value"x"), true, false))),
+ force bound-value"x")
+ ;
+}
+
+tests {
+ result-term:
+ true
+ ;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/scope.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/scope.config
new file mode 100644
index 0000000..80cd350
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/scope.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-binding
+ and(
+ scope(bind-value("x", false),
+ scope(bind-value("x", true),
+ bound-directly"x")),
+ scope(bind-value("x", false),
+ true))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/unbind.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/unbind.config
new file mode 100644
index 0000000..f3f63aa
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Binding/tests/unbind.config
@@ -0,0 +1,9 @@
+general {
+ funcon-term:
+ unbind("x")
+ ;
+}
+
+tests {
+ result-term: {"x"|->( )};
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/Flowing.cbs b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/Flowing.cbs
new file mode 100644
index 0000000..15907e1
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/Flowing.cbs
@@ -0,0 +1,242 @@
+### Flowing
+
+[
+ Funcon left-to-right Alias l-to-r
+ Funcon right-to-left Alias r-to-l
+ Funcon sequential Alias seq
+ Funcon effect
+ Funcon choice
+ Funcon if-true-else Alias if-else
+ Funcon while-true Alias while
+ Funcon do-while-true Alias do-while
+ Funcon interleave
+ Datatype yielding
+ Funcon signal
+ Funcon yielded
+ Funcon yield
+ Funcon yield-on-value
+ Funcon yield-on-abrupt
+ Funcon atomic
+]
+
+
+Meta-variables
+ T <: values
+ T* <: values*
+
+
+#### Sequencing
+
+Funcon
+ left-to-right(_:(=>(T)*)*) : =>(T)*
+Alias
+ l-to-r = left-to-right
+/*
+ `left-to-right(...)` computes its arguments sequentially, from left to right,
+ and gives the resulting sequence of values, provided all terminate normally.
+ For example, `integer-add(X, Y)` may interleave the computations of `X` and
+ `Y`, whereas `integer-add left-to-right(X, Y)` always computes `X` before `Y`.
+
+ When each argument of `left-to-right(...)` computes a single value, the type
+ of the result is the same as that of the argument sequence. For instance,
+ when `X:T` and `Y:T'`, the result of `left-to-right(X, Y)` is of type `(T, T')`.
+ The only effect of wrapping an argument sequence in `left-to-right(...)` is to
+ ensure that when the arguments are to be evaluated, it is done in the
+ specified order.
+*/
+Rule
+ Y ---> Y'
+ ------------------------------------------------------------
+ left-to-right(V*:(T)*, Y, Z*) ---> left-to-right(V*, Y', Z*)
+Rule
+ left-to-right(V*:(T)*) ~> V*
+
+
+Funcon
+ right-to-left(_:(=>(T)*)*) : =>(T)*
+Alias
+ r-to-l = right-to-left
+/*
+ `right-to-left(...)` computes its arguments sequentially, from right to left,
+ and gives the resulting sequence of values, provided all terminate normally.
+
+ Note that `right-to-left(X*)` and `reverse left-to-right reverse(X*)` are
+ not equivalent: `reverse(X*)` interleaves the evaluation of `X*`.
+*/
+Rule
+ Y ---> Y'
+ ------------------------------------------------------------
+ right-to-left(X*, Y, V*:(T)*) ---> right-to-left(X*, Y', V*)
+Rule
+ right-to-left(V*:(T)*) ~> V*
+
+
+Funcon
+ sequential(_:(=>null-type)*, _:=>T) : =>T
+Alias
+ seq = sequential
+/*
+ `sequential(X, ...)` computes its arguments in the given order. On normal
+ termination, it returns the value of the last argument; the other arguments
+ all compute `null-value`.
+
+ Binary `sequential(X, Y)` is associative, with unit `null-value`.
+*/
+Rule
+ X ---> X'
+ -----------------------------------------
+ sequential(X, Y+) ---> sequential(X', Y+)
+Rule
+ sequential(null-value, Y+) ~> sequential(Y+)
+Rule
+ sequential(Y) ~> Y
+
+
+Funcon
+ effect(V*:T*) : =>null-type
+ ~> null-value
+/*
+ `effect(...)` interleaves the computations of its arguments, then discards
+ all the computed values.
+*/
+
+
+#### Choosing
+
+Funcon
+ choice(_:(=>T)+) : =>T
+/*
+ `choice(Y, ...)` selects one of its arguments, then computes it.
+ It is associative and commutative.
+*/
+Rule
+ choice(X*, Y, Z*) ~> Y
+
+
+Funcon
+ if-true-else(_:booleans, _:=>T, _:=>T) : =>T
+Alias
+ if-else = if-true-else
+/*
+ `if-true-else(B, X, Y)` evaluates `B` to a Boolean value, then reduces
+ to `X` or `Y`, depending on the value of `B`.
+*/
+Rule
+ if-true-else(true, X, Y) ~> X
+Rule
+ if-true-else(false, X, Y) ~> Y
+
+
+#### Iterating
+
+Funcon
+ while-true(B:=>booleans, X:=>null-type) : =>null-type
+ ~> if-true-else(B, sequential(X, while-true(B, X)), null-value)
+Alias
+ while = while-true
+/*
+ `while-true(B, X)` evaluates `B` to a Boolean value. Depending on the value
+ of `B`, it either executes `X` and iterates, or terminates normally.
+
+ The effect of abruptly breaking the iteration is obtained by the combination
+ `handle-break(while-true(B, X))`, and that of abruptly continuing the iteration by
+ `while-true(B, handle-continue(X))`.
+*/
+
+Funcon
+ do-while-true(X:=>null-type, B:=>booleans) : =>null-type
+ ~> sequential(X, if-true-else(B, do-while-true(X, B), null-value))
+Alias
+ do-while = do-while-true
+/*
+ `do-while-true(X, B)` is equivalent to `sequential(X, while-true(B, X))`.
+*/
+
+
+#### Interleaving
+
+Funcon
+ interleave(_:T*) : =>T*
+/*
+ `interleave(...)` computes its arguments in any order, possibly interleaved,
+ and returns the resulting sequence of values, provided all terminate normally.
+ Fairness of interleaving is not required, so pure left-to-right computation
+ is allowed.
+
+ `atomic(X)` prevents interleaving in `X`, except after transitions that emit
+ a `yielded(signal)`.
+*/
+Rule
+ interleave(V*:T*) ~> V*
+
+
+Datatype
+ yielding ::= signal
+
+
+Entity
+ _ --yielded(_:yielding?)-> _
+/*
+ `yielded(signal)` in a label on a transition allows interleaving at that point
+ in the enclosing atomic computation.
+ `yielded( )` indicates interleaving at that point in an atomic computation
+ is not allowed.
+*/
+
+
+Funcon
+ yield : =>null-type
+ ~> yield-on-value(null-value)
+
+
+Funcon
+ yield-on-value(_:T) : =>T
+/*
+ `yield-on-value(X)` allows interleaving in an enclosing atomic computation
+ on normal termination of `X`.
+*/
+Rule
+ yield-on-value(V:T) --yielded(signal)-> V
+
+
+Funcon
+ yield-on-abrupt(_:=>T) : =>T
+/*
+ `yield-on-abrupt(X)` ensures that abrupt termination of `X` is propagated
+ through an enclosing atomic computation.
+*/
+Rule
+ X --abrupt(V:T),yielded(_?)-> X'
+ --------------------------------------------------------------------
+ yield-on-abrupt(X) --abrupt(V),yielded(signal)-> yield-on-abrupt(X')
+Rule
+ X --abrupt( )-> X'
+ ----------------------------------------------------
+ yield-on-abrupt(X) --abrupt( )-> yield-on-abrupt(X')
+Rule
+ yield-on-abrupt(V:T) ~> V
+
+
+Funcon
+ atomic(_:=>T) : =>T
+/*
+ `atomic(X)` computes `X`, but controls its potential interleaving with other
+ computations: interleaving is only allowed following a transition of `X` that
+ emits `yielded(signal)`.
+*/
+Rule
+ X --yielded( )->1 X'
+ atomic(X') --yielded( )->2 X''
+ -----------------------------------------------
+ atomic(X) --yielded( )->1 ; --yielded( )->2 X''
+Rule
+ X --yielded( )-> V
+ V : T
+ ---------------------------
+ atomic(X) --yielded( )-> V
+Rule
+ atomic(V:T) ~> V
+Rule
+ X --yielded(signal)-> X'
+ -----------------------------------
+ atomic(X) --yielded( )-> atomic(X')
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/index.md b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/index.md
new file mode 100644
index 0000000..0768615
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/index.md
@@ -0,0 +1,289 @@
+---
+layout: default
+title: "Flowing"
+parent: Normal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Flowing.cbs]
+-----------------------------
+
+### Flowing
+
+
+
+
+
+
+
+
+
+#### Sequencing
+
+
+Funcon
+ left-to-right(_:(=>(T)*)*) : =>(T)*
+Alias
+ l-to-r = left-to-right
+
+
+ left-to-right(...) computes its arguments sequentially, from left to right,
+ and gives the resulting sequence of values, provided all terminate normally.
+ For example, integer-add(X, Y) may interleave the computations of X and
+ Y, whereas integer-add left-to-right(X, Y) always computes X before Y.
+
+ When each argument of left-to-right(...) computes a single value, the type
+ of the result is the same as that of the argument sequence. For instance,
+ when X:T and Y:T′, the result of left-to-right(X, Y) is of type (T, T′).
+ The only effect of wrapping an argument sequence in left-to-right(...) is to
+ ensure that when the arguments are to be evaluated, it is done in the
+ specified order.
+
+
+
+Funcon
+ right-to-left(_:(=>(T)*)*) : =>(T)*
+Alias
+ r-to-l = right-to-left
+
+
+ right-to-left(...) computes its arguments sequentially, from right to left,
+ and gives the resulting sequence of values, provided all terminate normally.
+
+ Note that right-to-left(X*) and reverse left-to-right reverse(X*) are
+ not equivalent: reverse(X*) interleaves the evaluation of X*.
+
+
+
+
+
+
+ sequential(X, ...) computes its arguments in the given order. On normal
+ termination, it returns the value of the last argument; the other arguments
+ all compute null-value.
+
+ Binary sequential(X, Y) is associative, with unit null-value.
+
+
+
+
+
+
+
+
+ effect(...) interleaves the computations of its arguments, then discards
+ all the computed values.
+
+
+
+#### Choosing
+
+Funcon
+ choice(_:(=>T)+) : =>T
+
+ choice(Y, ...) selects one of its arguments, then computes it.
+ It is associative and commutative.
+
+
+
+
+
+
+ if-true-else(B, X, Y) evaluates B to a Boolean value, then reduces
+ to X or Y, depending on the value of B.
+
+
+
+
+
+#### Iterating
+
+
+
+
+
+ while-true(B, X) evaluates B to a Boolean value. Depending on the value
+ of B, it either executes X and iterates, or terminates normally.
+
+ The effect of abruptly breaking the iteration is obtained by the combination
+ handle-break(while-true(B, X)), and that of abruptly continuing the iteration by
+ while-true(B, handle-continue(X)).
+
+
+
+
+ do-while-true(X, B) is equivalent to sequential(X, while-true(B, X)).
+
+
+
+#### Interleaving
+
+Funcon
+ interleave(_:T*) : =>T*
+
+ interleave(...) computes its arguments in any order, possibly interleaved,
+ and returns the resulting sequence of values, provided all terminate normally.
+ Fairness of interleaving is not required, so pure left-to-right computation
+ is allowed.
+
+ atomic(X) prevents interleaving in X, except after transitions that emit
+ a yielded(signal).
+
+
+
+
+
+Datatype
+ yielding ::= signal
+
+
+
+ yielded(signal) in a label on a transition allows interleaving at that point
+ in the enclosing atomic computation.
+ yielded( ) indicates interleaving at that point in an atomic computation
+ is not allowed.
+
+
+
+
+
+
+
+Funcon
+ yield-on-value(_:T) : =>T
+
+ yield-on-value(X) allows interleaving in an enclosing atomic computation
+ on normal termination of X.
+
+
+
+
+
+Funcon
+ yield-on-abrupt(_:=>T) : =>T
+
+ yield-on-abrupt(X) ensures that abrupt termination of X is propagated
+ through an enclosing atomic computation.
+
+
+
+
+
+Funcon
+ atomic(_:=>T) : =>T
+
+ atomic(X) computes X, but controls its potential interleaving with other
+ computations: interleaving is only allowed following a transition of X that
+ emits yielded(signal).
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Flowing.cbs]: Flowing.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Normal/Flowing/Flowing.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/atomic.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/atomic.config
new file mode 100644
index 0000000..f890bed
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/atomic.config
@@ -0,0 +1,27 @@
+general {
+ funcon-term:
+ finalise-failing
+ sequential(
+ atomic(tuple()),
+ atomic(print 1),
+ atomic sequential(print 2,print 3),
+ interleave(
+ atomic sequential(print 4,print 5),
+ print 6),
+ interleave(
+ atomic sequential(yield-on-value print 7,print 8),
+ print 9),
+ else(
+ atomic yield-on-abrupt sequential(print 10,fail),
+ print 11))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [tuple(), 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11];
+//Also possible:
+// standard-out: [................, 6, 4, 5, ...............];
+// standard-out: [........................., 7, 9, 8, ......];
+// standard-out: [........................., 9, 7, 8, ......];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/choice.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/choice.config
new file mode 100644
index 0000000..79fb51d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/choice.config
@@ -0,0 +1,19 @@
+general {
+ funcon-term:
+ sequential(
+ print choice(1),
+ choice(print 2, print 3),
+ choice(print 4, print 5, print 6)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 4];
+//Also possible:
+// standard-out: [1, 3, 6];
+// standard-out: [., 3, .];
+// standard-out: [...., 5];
+// standard-out: [...., 6];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/do-while.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/do-while.config
new file mode 100644
index 0000000..394fde5
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/do-while.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ sequential(
+ do-while(print 1,false),
+ else(
+ do-while(
+ sequential(print 2, fail),
+ sequential(print"ERROR", true)),
+ print"OK"))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1,2,"OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/effect.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/effect.config
new file mode 100644
index 0000000..c882896
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/effect.config
@@ -0,0 +1,10 @@
+general {
+ funcon-term:
+ effect sequential(print 1, 2)
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/if-true-else.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/if-true-else.config
new file mode 100644
index 0000000..02a166d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/if-true-else.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term:
+ if-true-else(not false,
+ if-true-else(not true,fail,print"OK"),
+ fail)
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/interleave.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/interleave.config
new file mode 100644
index 0000000..fc4b45f
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/interleave.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term:
+ sequential(
+ print tuple interleave( ),
+ interleave(print 1),
+ effect tuple interleave(print 2,print 3),
+ effect tuple interleave(sequential(print 4,print 5),print 6))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [tuple(), 1, 2, 3, 4, 5, 6];
+//Also possible:
+// standard-out: [.........., 3, 2, .......];
+// standard-out: [................, 4, 6, 5];
+// standard-out: [................, 6, 4, 5];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/left-to-right.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/left-to-right.config
new file mode 100644
index 0000000..a17625e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/left-to-right.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term:
+ sequential(
+ print tuple left-to-right ( ),
+ effect left-to-right(print 1),
+ effect tuple left-to-right(print 2, print 3),
+ effect tuple left-to-right(print 4, print 5, print 6),
+ effect integer-add left-to-right(
+ sequential(print 7, 7),
+ sequential(print 8, 8))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [tuple(), 1, 2, 3, 4, 5, 6, 7, 8];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/right-to-left.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/right-to-left.config
new file mode 100644
index 0000000..30b2b3e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/right-to-left.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term:
+ sequential(
+ print tuple right-to-left ( ),
+ effect right-to-left(print 1),
+ effect right-to-left(print 3, print 2),
+ effect right-to-left(print 6, print 5, print 4),
+ effect integer-add right-to-left(
+ sequential(print 8, 8),
+ sequential(print 7, 7))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [tuple(), 1, 2, 3, 4, 5, 6, 7, 8];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/sequential.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/sequential.config
new file mode 100644
index 0000000..fec4e80
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/sequential.config
@@ -0,0 +1,13 @@
+general {
+ funcon-term:
+ sequential(
+ sequential(print 1, print 2),
+ print sequential(print 3, print 4, 5)
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4, 5];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/while.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/while.config
new file mode 100644
index 0000000..27f4475
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Flowing/tests/while.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ sequential(
+ while(false,sequential(print"ERROR",fail)),
+ else(
+ while(
+ sequential(print 1, true),
+ sequential(print 2, fail)),
+ print"OK"))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1,2,"OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/Generating.cbs b/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/Generating.cbs
new file mode 100644
index 0000000..8c54372
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/Generating.cbs
@@ -0,0 +1,58 @@
+### Generating
+
+[
+ Type atoms
+ Entity used-atom-set
+ Funcon initialise-generating
+ Funcon fresh-atom
+ Funcon use-atom-not-in
+]
+
+
+Meta-variables
+ T <: values
+
+
+Built-in Type
+ atoms
+/*
+ `atoms` is the type of values used as distinguishable tags.
+ Notation for individual atoms is not provided.
+*/
+
+
+Entity
+ < _ , used-atom-set(_:sets(atoms)) > ---> < _ , used-atom-set(_:sets(atoms)) >
+
+
+Built-in Funcon
+ initialise-generating(_:=>T) : =>T
+/*
+ The initial value of the `used-atom-set(SA)` entity is unspecified. It could
+ contains atoms that are reserved for internal use.
+*/
+
+
+Funcon
+ fresh-atom : =>atoms
+/*
+ `fresh-atom` computes an atom distinct from all previously computed atoms.
+*/
+Rule
+ element-not-in(atoms, SA) ~> A
+ -----------------------------------------------
+ < fresh-atom , used-atom-set(SA) >
+ ---> < A , used-atom-set(set-insert(A, SA)) >
+
+
+Funcon
+ use-atom-not-in(_:sets(atoms)) : =>atoms
+/*
+ `use-atom-not-in(SA)` computes an atom not in the set `SA`, and inserts it
+ in the `used-atom-set(SA')` entity, in case it was not previously used.
+*/
+Rule
+ element-not-in(atoms, SA) ~> A
+ --------------------------------------------------------
+ < use-atom-not-in(SA:sets(atoms)) , used-atom-set(SA') >
+ ---> < A , used-atom-set(set-insert(A, SA')) >
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/index.md b/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/index.md
new file mode 100644
index 0000000..18b4b8a
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/index.md
@@ -0,0 +1,97 @@
+---
+layout: default
+title: "Generating"
+parent: Normal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Generating.cbs]
+-----------------------------
+
+### Generating
+
+
+
+
+
+
+
+
+
+
+
+ atoms is the type of values used as distinguishable tags.
+ Notation for individual atoms is not provided.
+
+
+
+Entity
+ < _ , used-atom-set(_:sets(atoms)) > ---> < _ , used-atom-set(_:sets(atoms)) >
+
+
+
+Built-in Funcon
+ initialise-generating(_:=>T) : =>T
+
+ The initial value of the used-atom-set(SA) entity is unspecified. It could
+ contains atoms that are reserved for internal use.
+
+
+
+Funcon
+ fresh-atom : =>atoms
+
+ fresh-atom computes an atom distinct from all previously computed atoms.
+
+
+
+
+
+
+
+ use-atom-not-in(SA) computes an atom not in the set SA, and inserts it
+ in the used-atom-set(SA′) entity, in case it was not previously used.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Generating.cbs]: Generating.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Normal/Generating/Generating.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/tests/fresh-atom.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/tests/fresh-atom.config
new file mode 100644
index 0000000..94d8bd9
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/tests/fresh-atom.config
@@ -0,0 +1,11 @@
+general {
+ funcon-term:
+ initialise-generating
+ give(fresh-atom,
+ check-true not is-equal(given, fresh-atom))
+ ;
+}
+
+tests {
+ result-term: null-value;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/tests/use-atom-not-in.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/tests/use-atom-not-in.config
new file mode 100644
index 0000000..b19166e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Generating/tests/use-atom-not-in.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term:
+ initialise-generating
+ give(fresh-atom,
+ print is-equal(use-atom-not-in{given}, use-atom-not-in{given}))
+ ;
+}
+
+tests {
+ result-term: null-value;
+// standard-out: [ false ];
+//Also possible:
+ standard-out: [ true ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/Giving.cbs b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/Giving.cbs
new file mode 100644
index 0000000..5c01f19
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/Giving.cbs
@@ -0,0 +1,212 @@
+### Giving
+
+[
+ Entity given-value
+ Funcon initialise-giving
+ Funcon give
+ Funcon given
+ Funcon no-given
+ Funcon left-to-right-map
+ Funcon interleave-map
+ Funcon left-to-right-repeat
+ Funcon interleave-repeat
+ Funcon left-to-right-filter
+ Funcon interleave-filter
+ Funcon fold-left
+ Funcon fold-right
+]
+
+
+Meta-variables
+ T, T' <: values
+ T? <: values?
+
+
+Entity
+ given-value(_:values?) |- _ ---> _
+/*
+ The given-value entity allows a computation to refer to a single
+ previously-computed `V:values`. The given value `( )` represents
+ the absence of a current given value.
+*/
+
+
+Funcon
+ initialise-giving(X:( )=>T') : ( )=>T'
+ ~> no-given(X)
+/*
+ `initialise-giving(X)` ensures that the entities used by the funcons for
+ giving are properly initialised.
+*/
+
+
+Funcon
+ give(_:T, _:T=>T') : =>T'
+/*
+ `give(X, Y)` executes `X`, possibly referring to the current `given` value,
+ to compute a value `V`. It then executes `Y` with `V` as the `given` value,
+ to compute the result.
+*/
+Rule
+ given-value(V) |- Y ---> Y'
+ ------------------------------------------------
+ given-value(_?) |- give(V:T, Y) ---> give(V, Y')
+Rule
+ give(_:T, W:T') ~> W
+
+
+Funcon
+ given : T=>T
+/*
+ `given` refers to the current given value.
+*/
+Rule
+ given-value(V:values) |- given ---> V
+Rule
+ given-value( ) |- given ---> fail
+
+
+Funcon
+ no-given(_:( )=>T') : ( )=>T'
+/*
+ `no-given(X)` computes `X` without references to the current given value.
+*/
+Rule
+ given-value( ) |- X ---> X'
+ ------------------------------------------------
+ given-value(_?) |- no-given(X) ---> no-given(X')
+Rule
+ no-given(U:T') ~> U
+
+
+#### Mapping
+
+/*
+ Maps on collection values can be expressed directly, e.g.,
+ `list(left-to-right-map(F, list-elements(L)))`.
+*/
+
+Funcon
+ left-to-right-map(_:T=>T', _:(T)*) : =>(T')*
+/*
+ `left-to-right-map(F, V*)` computes `F` for each value in `V*` from left
+ to right, returning the sequence of resulting values.
+*/
+
+Rule
+ left-to-right-map(F, V:T, V*:(T)*)
+ ~> left-to-right(give(V, F), left-to-right-map(F, V*))
+Rule
+ left-to-right-map(_, ( )) ~> ( )
+
+
+Funcon
+ interleave-map(_:T=>T', _:(T)*) : =>(T')*
+/*
+ `interleave-map(F, V*)` computes `F` for each value in `V*` interleaved,
+ returning the sequence of resulting values.
+*/
+Rule
+ interleave-map(F, V:T, V*:(T)*)
+ ~> interleave(give(V, F), interleave-map(F, V*))
+Rule
+ interleave-map(_, ( )) ~> ( )
+
+
+Funcon
+ left-to-right-repeat(_:integers=>T', _:integers, _:integers) : =>(T')*
+/*
+ `left-to-right-repeat(F, M, N)` computes `F` for each value from `M` to `N`
+ sequentially, returning the sequence of resulting values.
+*/
+Rule
+ is-less-or-equal(M, N) == true
+ -------------------------------------------------------------------------
+ left-to-right-repeat(F, M:integers, N:integers)
+ ~> left-to-right(give(M, F), left-to-right-repeat(F, int-add(M, 1), N))
+Rule
+ is-less-or-equal(M, N) == false
+ ----------------------------------------------
+ left-to-right-repeat(_, M:integers, N:integers) ~> ( )
+
+
+Funcon
+ interleave-repeat(_:integers=>T', _:integers, _:integers) : =>(T')*
+/*
+ `interleave-repeat(F, M, N)` computes `F` for each value from `M` to `N`
+ interleaved, returning the sequence of resulting values.
+*/
+Rule
+ is-less-or-equal(M, N) == true
+ -------------------------------------------------------------------
+ interleave-repeat(F, M:integers, N:integers)
+ ~> interleave(give(M, F), interleave-repeat(F, int-add(M, 1), N))
+Rule
+ is-less-or-equal(M, N) == false
+ -------------------------------------------
+ interleave-repeat(_, M:integers, N:integers) ~> ( )
+
+
+#### Filtering
+
+/*
+ Filters on collections of values can be expressed directly, e.g.,
+ `list(left-to-right-filter(P, list-elements(L)))` to filter a list `L`.
+*/
+
+
+Funcon
+ left-to-right-filter(_:T=>booleans, _:(T)*) : =>(T)*
+/*
+ `left-to-right-filter(P, V*)` computes `P` for each value in `V*` from left
+ to right, returning the sequence of argument values for which the result is
+ `true`.
+*/
+Rule
+ left-to-right-filter(P, V:T, V*:(T)*)
+ ~> left-to-right(when-true(give(V, P), V), left-to-right-filter(P, V*))
+Rule
+ left-to-right-filter(_) ~> ( )
+
+
+Funcon
+ interleave-filter(_:T=>booleans, _:(T)*) : =>(T)*
+/*
+ `interleave-filter(P, V*)` computes `P` for each value in `V*` interleaved,
+ returning the sequence of argument values for which the result is `true`.
+*/
+Rule
+ interleave-filter(P, V:T, V*:(T)*)
+ ~> interleave(when-true(give(V, P), V), interleave-filter(P, V*))
+Rule
+ interleave-filter(_) ~> ( )
+
+
+#### Folding
+
+Funcon
+ fold-left(_:tuples(T,T')=>T, _:T, _:(T')*) : =>T
+/*
+ `fold-left(F, A, V*)` reduces a sequence `V*` to a single value by folding it
+ from the left, using `A` as the initial accumulator value, and iteratively
+ updating the accumulator by giving `F` the pair of the accumulator value and
+ the first of the remaining arguments.
+*/
+Rule
+ fold-left(_, A:T, ( )) ~> A
+Rule
+ fold-left(F, A:T, V:T', V*:(T')*) ~> fold-left(F, give(tuple(A, V), F), V*)
+
+
+Funcon
+ fold-right(_:tuples(T,T')=>T', _:T', _:(T)*) : =>T'
+/*
+ `fold-right(F, A, V*)` reduces a sequence `V*` to a single value by folding it
+ from the right, using `A` as the initial accumulator value, and iteratively
+ updating the accumulator by giving `F` the pair of the the last of the
+ remaining arguments and the accumulator value.
+*/
+Rule
+ fold-right(_, A:T', ( )) ~> A
+Rule
+ fold-right(F, A:T', V*:(T)*, V:T) ~> give(tuple(V, fold-right(F, A, V*)), F)
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/index.md b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/index.md
new file mode 100644
index 0000000..66ff04b
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/index.md
@@ -0,0 +1,260 @@
+---
+layout: default
+title: "Giving"
+parent: Normal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Giving.cbs]
+-----------------------------
+
+### Giving
+
+
+
+
+
+
+
+
+
+Entity
+ given-value(_:values?) |- _ ---> _
+
+
+ The given-value entity allows a computation to refer to a single
+ previously-computed V:values. The given value ( ) represents
+ the absence of a current given value.
+
+
+
+Funcon
+ initialise-giving(X:( )=>T′) : ( )=>T′
+ ~> no-given(X)
+
+
+ initialise-giving(X) ensures that the entities used by the funcons for
+ giving are properly initialised.
+
+
+
+Funcon
+ give(_:T, _:T=>T′) : =>T′
+
+ give(X, Y) executes X, possibly referring to the current given value,
+ to compute a value V. It then executes Y with V as the given value,
+ to compute the result.
+
+
+
+
+
+
+
+ given refers to the current given value.
+
+
+
+
+
+Funcon
+ no-given(_:( )=>T′) : ( )=>T′
+
+ no-given(X) computes X without references to the current given value.
+
+
+
+
+
+#### Mapping
+
+
+ Maps on collection values can be expressed directly, e.g.,
+ list(left-to-right-map(F, list-elements(L))).
+
+
+Funcon
+ left-to-right-map(_:T=>T′, _:(T)*) : =>(T′)*
+
+ left-to-right-map(F, V*) computes F for each value in V* from left
+ to right, returning the sequence of resulting values.
+
+
+
+
+
+Funcon
+ interleave-map(_:T=>T′, _:(T)*) : =>(T′)*
+
+ interleave-map(F, V*) computes F for each value in V* interleaved,
+ returning the sequence of resulting values.
+
+
+
+
+
+
+
+ left-to-right-repeat(F, M, N) computes F for each value from M to N
+ sequentially, returning the sequence of resulting values.
+
+Rule
+ is-less-or-equal(M, N) == true
+ -------------------------------------------------------------------------
+ left-to-right-repeat(F, M:integers, N:integers)
+ ~> left-to-right(give(M, F), left-to-right-repeat(F, int-add(M, 1), N))
+Rule
+ is-less-or-equal(M, N) == false
+ ----------------------------------------------
+ left-to-right-repeat(_, M:integers, N:integers) ~> ( )
+
+
+
+
+
+ interleave-repeat(F, M, N) computes F for each value from M to N
+ interleaved, returning the sequence of resulting values.
+
+Rule
+ is-less-or-equal(M, N) == true
+ -------------------------------------------------------------------
+ interleave-repeat(F, M:integers, N:integers)
+ ~> interleave(give(M, F), interleave-repeat(F, int-add(M, 1), N))
+Rule
+ is-less-or-equal(M, N) == false
+ -------------------------------------------
+ interleave-repeat(_, M:integers, N:integers) ~> ( )
+
+
+
+#### Filtering
+
+
+ Filters on collections of values can be expressed directly, e.g.,
+ list(left-to-right-filter(P, list-elements(L))) to filter a list L.
+
+
+
+Funcon
+ left-to-right-filter(_:T=>booleans, _:(T)*) : =>(T)*
+
+ left-to-right-filter(P, V*) computes P for each value in V* from left
+ to right, returning the sequence of argument values for which the result is
+ true.
+
+
+
+
+
+Funcon
+ interleave-filter(_:T=>booleans, _:(T)*) : =>(T)*
+
+ interleave-filter(P, V*) computes P for each value in V* interleaved,
+ returning the sequence of argument values for which the result is true.
+
+
+
+
+
+#### Folding
+
+Funcon
+ fold-left(_:tuples(T,T′)=>T, _:T, _:(T′)*) : =>T
+
+ fold-left(F, A, V*) reduces a sequence V* to a single value by folding it
+ from the left, using A as the initial accumulator value, and iteratively
+ updating the accumulator by giving F the pair of the accumulator value and
+ the first of the remaining arguments.
+
+
+
+
+
+Funcon
+ fold-right(_:tuples(T,T′)=>T′, _:T′, _:(T)*) : =>T′
+
+ fold-right(F, A, V*) reduces a sequence V* to a single value by folding it
+ from the right, using A as the initial accumulator value, and iteratively
+ updating the accumulator by giving F the pair of the the last of the
+ remaining arguments and the accumulator value.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Giving.cbs]: Giving.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Normal/Giving/Giving.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/fold-left.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/fold-left.config
new file mode 100644
index 0000000..c9d8d50
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/fold-left.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-giving
+ sequential(
+ print [ fold-left(fail, 1, ( )) ],
+ fold-left(
+ sequential(print given, given),
+ 1, 2, 3))
+ ;
+}
+
+tests {
+ result-term: tuple(tuple(1,2),3);
+ standard-out: [ [ 1 ], tuple(1,2), tuple(tuple(1,2),3) ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/fold-right.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/fold-right.config
new file mode 100644
index 0000000..122c629
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/fold-right.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-giving
+ sequential(
+ print [ fold-right(fail, 1, ( )) ],
+ fold-right(
+ sequential(print given, given),
+ 1, 2, 3))
+ ;
+}
+
+tests {
+ result-term: tuple(3,tuple(2,1));
+ standard-out: [ [ 1 ], tuple(2,1), tuple(3,tuple(2,1)) ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/give.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/give.config
new file mode 100644
index 0000000..8d6b87c
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/give.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term:
+ initialise-giving
+ give(
+ sequential(
+ print 1,
+ 2),
+ sequential(
+ print given,
+ give(3, print given),
+ print integer-add(given,2)))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/interleave-filter.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/interleave-filter.config
new file mode 100644
index 0000000..8bc06f0
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/interleave-filter.config
@@ -0,0 +1,21 @@
+general {
+ funcon-term:
+ initialise-giving
+ sequential(
+ print [ interleave-filter(true, ( )) ],
+ tuple interleave-filter(
+ sequential(print given, is-less(given,3)),
+ 1, 2, 3))
+ ;
+}
+
+tests {
+ result-term: tuple(1, 2);
+ standard-out: [ [ ], 1, 2, 3 ];
+//Also:
+// standard-out: [ [ ], 1, 3, 2 ];
+// standard-out: [ [ ], 2, 1, 3 ];
+// standard-out: [ [ ], 2, 3, 1 ];
+// standard-out: [ [ ], 3, 1, 2 ];
+// standard-out: [ [ ], 3, 2, 1 ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/interleave-map.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/interleave-map.config
new file mode 100644
index 0000000..dc524d5
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/interleave-map.config
@@ -0,0 +1,20 @@
+general {
+ funcon-term:
+ initialise-giving
+ sequential(
+ print [ interleave-map(fail, ( )) ],
+ tuple interleave-map(
+ sequential(print integer-add(given,2), given),
+ sequential(print 1, 1),
+ sequential(print 2, 2)))
+ ;
+}
+
+tests {
+ result-term: tuple(1, 2);
+ standard-out: [ [ ], 1, 2, 3, 4];
+//Also:
+// standard-out: [ [ ], 2, 1, 3, 4];
+// standard-out: [ [ ], 1, 2, 4, 3];
+// standard-out: [ [ ], 2, 1, 4, 3];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/interleave-repeat.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/interleave-repeat.config
new file mode 100644
index 0000000..03a857e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/interleave-repeat.config
@@ -0,0 +1,23 @@
+general {
+ funcon-term:
+ initialise-giving
+ sequential(
+ print [ interleave-repeat(fail, 2, 1) ],
+ tuple interleave-repeat(
+ sequential(print integer-add(given,2), given),
+ sequential(print 1, 1),
+ sequential(print 2, 3)))
+ ;
+}
+
+tests {
+ result-term: tuple(1, 2, 3);
+ standard-out: [ [ ], 1, 2, 3, 4, 5];
+//Also:
+// standard-out: [ [ ], ...., 3, 5, 4];
+// standard-out: [ [ ], ...., 4, 3, 5];
+// standard-out: [ [ ], ...., 4, 5, 3];
+// standard-out: [ [ ], ...., 5, 3, 4];
+// standard-out: [ [ ], ...., 5, 4, 3];
+// standard-out: [ [ ], 2, 1, .......];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/left-to-right-filter.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/left-to-right-filter.config
new file mode 100644
index 0000000..73a1639
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/left-to-right-filter.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-giving
+ sequential(
+ print [ left-to-right-filter(true, ( )) ],
+ tuple left-to-right-filter(
+ sequential(print given, is-less(given,42)),
+ 42, 1, 43, 44, 2, 3, 45))
+ ;
+}
+
+tests {
+ result-term: tuple(1, 2, 3);
+ standard-out: [ [ ], 42, 1, 43, 44, 2, 3, 45 ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/left-to-right-map.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/left-to-right-map.config
new file mode 100644
index 0000000..5d50f2f
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/left-to-right-map.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term:
+ initialise-giving
+ sequential(
+ print [ left-to-right-map(fail, ( )) ],
+ tuple left-to-right-map(
+ sequential(print integer-add(given,2), given),
+ sequential(print 1, 1),
+ sequential(print 2, 2)))
+ ;
+}
+
+tests {
+ result-term: tuple(1, 2);
+ standard-out: [ [ ], 1, 2, 3, 4];
+//Also:
+// standard-out: [ [ ], 2, 1, 3, 4];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/left-to-right-repeat.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/left-to-right-repeat.config
new file mode 100644
index 0000000..11c93a5
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/left-to-right-repeat.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term:
+ initialise-giving
+ sequential(
+ print [ left-to-right-repeat(fail, 2, 1) ],
+ tuple left-to-right-repeat(
+ sequential(print integer-add(given,2), given),
+ sequential(print 1, 1),
+ sequential(print 2, 3)))
+ ;
+}
+
+tests {
+ result-term: tuple(1, 2, 3);
+ standard-out: [ [ ], 1, 2, 3, 4, 5];
+//Also:
+// standard-out: [ [ ], 2, 1, 3, 4, 5];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/no-given.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/no-given.config
new file mode 100644
index 0000000..b74b9c6
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Giving/tests/no-given.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ initialise-giving
+ give(
+ 1,
+ no-given
+ else(
+ print given,
+ print"OK"))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/Interacting.cbs b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/Interacting.cbs
new file mode 100644
index 0000000..2e227ae
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/Interacting.cbs
@@ -0,0 +1,59 @@
+### Interacting
+
+#### Output
+
+[
+ Entity standard-out
+ Funcon print
+]
+
+
+Entity
+ _ -- standard-out!(_:values*) -> _
+/*
+ This entity represents the sequence of values output by a particular
+ transition, where the empty sequence `( )` represents the lack of output.
+ Composition of transitions concatenates their output sequences.
+*/
+
+
+Funcon
+ print(_:values*) : =>null-type
+/*
+ `print(X*)` evaluates the arguments `X*` and emits the resulting sequence of
+ values on the standard-out channel. `print( )` has no effect.
+*/
+Rule
+ print(V*:values*) -- standard-out!(V*) -> null-value
+
+
+#### Input
+
+[
+ Entity standard-in
+ Funcon read
+]
+
+Entity
+ _ -- standard-in?(_:values*) -> _
+/*
+ This entity represents the sequence of values input by a particular
+ transition, where the empty sequence `( )` represents that no values are
+ input. The value `null-value` represents the end of the input.
+
+ Composition of transitions concatenates their input sequences, except that
+ when the first sequence ends with `null-value`, the second seqeunce has to be
+ just `null-value`.
+*/
+
+
+Funcon
+ read : =>values
+/*
+ `read` inputs a single value from the standard-in channel, and returns it.
+ If the end of the input has been reached, `read` fails.
+*/
+Rule
+ read -- standard-in?(V:~null-type) -> V
+Rule
+ read -- standard-in?(null-value) -> fail
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/index.md b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/index.md
new file mode 100644
index 0000000..e583c18
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/index.md
@@ -0,0 +1,99 @@
+---
+layout: default
+title: "Interacting"
+parent: Normal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Interacting.cbs]
+-----------------------------
+
+### Interacting
+
+#### Output
+
+
+
+
+
+Entity
+ _ -- standard-out!(_:values*) -> _
+
+
+ This entity represents the sequence of values output by a particular
+ transition, where the empty sequence ( ) represents the lack of output.
+ Composition of transitions concatenates their output sequences.
+
+
+
+
+
+ print(X*) evaluates the arguments X* and emits the resulting sequence of
+ values on the standard-out channel. print( ) has no effect.
+
+
+
+
+
+#### Input
+
+
+
+
+Entity
+ _ -- standard-in?(_:values*) -> _
+
+
+ This entity represents the sequence of values input by a particular
+ transition, where the empty sequence ( ) represents that no values are
+ input. The value null-value represents the end of the input.
+
+ Composition of transitions concatenates their input sequences, except that
+ when the first sequence ends with null-value, the second seqeunce has to be
+ just null-value.
+
+
+
+
+
+ read inputs a single value from the standard-in channel, and returns it.
+ If the end of the input has been reached, read fails.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Interacting.cbs]: Interacting.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Normal/Interacting/Interacting.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/print-1.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/print-1.config
new file mode 100644
index 0000000..0127f55
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/print-1.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term:
+ sequential(
+ print( ),
+ print( list-elements list-nil ))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/print-2.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/print-2.config
new file mode 100644
index 0000000..eef12d2
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/print-2.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term:
+ sequential(
+ print 1,
+ print(2,3),
+ print true,
+ print(sequential(print tuple null-value, "OK")))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [ 1, 2, 3, true, tuple(null-value), "OK" ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/read-1.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/read-1.config
new file mode 100644
index 0000000..2dbe90b
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/read-1.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term: print(reverse(read, read, read));
+}
+
+inputs {
+ standard-in: (1,2,3);
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [3,2,1];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/read-2.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/read-2.config
new file mode 100644
index 0000000..9518fc9
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/read-2.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term: print(read, else(read, "OK"));
+}
+
+inputs {
+ standard-in: 1;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, "OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/read-3.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/read-3.config
new file mode 100644
index 0000000..808bf80
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Interacting/tests/read-3.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term: print(read, read, else(read, "OK"));
+}
+
+inputs {
+ standard-in: (1,2);
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, "OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/Linking.cbs b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/Linking.cbs
new file mode 100644
index 0000000..975e1d4
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/Linking.cbs
@@ -0,0 +1,67 @@
+### Linking
+
+[
+ Datatype links
+ Funcon initialise-linking
+ Funcon link
+ Funcon fresh-link
+ Funcon fresh-initialised-link Alias fresh-init-link
+ Funcon set-link
+ Funcon follow-if-link
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ links ::= link(_:variables)
+
+
+Funcon
+ initialise-linking(X:=>T) : =>T
+ ~> initialise-storing(X)
+/*
+ `initialise-linking(X)` ensures that the entities used by the funcons for
+ linking are properly initialised.
+*/
+
+
+Funcon
+ fresh-link(T) : =>links
+ ~> link(allocate-variable(T))
+
+
+Funcon
+ fresh-initialised-link(T, V:T) : =>links
+ ~> link(allocate-initialised-variable(T, V))
+Alias
+ fresh-init-link = fresh-initialised-link
+
+
+Funcon
+ set-link(_:links, _:T) : =>null-type
+/*
+ The value of a link can be set only once.
+*/
+Rule
+ set-link(link(Var:variables), V:T) ~> initialise-variable(Var, V)
+
+
+Funcon
+ follow-link(_:links) : =>values
+Rule
+ follow-link(link(Var:variables)) ~> assigned(Var)
+
+
+Funcon
+ follow-if-link(_:values) : =>values
+/*
+ If `V` is a link, `follow-if-link(V)` computes the set value, and
+ otherwise it evaluates to `V`.
+*/
+Rule
+ follow-if-link(link(Var:variables)) ~> assigned(Var)
+Rule
+ follow-if-link(V:~links) ~> V
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/index.md b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/index.md
new file mode 100644
index 0000000..5acf16a
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/index.md
@@ -0,0 +1,106 @@
+---
+layout: default
+title: "Linking"
+parent: Normal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Linking.cbs]
+-----------------------------
+
+### Linking
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ initialise-linking(X) ensures that the entities used by the funcons for
+ linking are properly initialised.
+
+
+
+
+
+
+
+
+
+
+
+ The value of a link can be set only once.
+
+
+
+
+
+
+
+
+
+ If V is a link, follow-if-link(V) computes the set value, and
+ otherwise it evaluates to V.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Linking.cbs]: Linking.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Normal/Linking/Linking.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/follow-if-link.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/follow-if-link.config
new file mode 100644
index 0000000..ad91025
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/follow-if-link.config
@@ -0,0 +1,20 @@
+general {
+ funcon-term:
+ initialise-linking
+ give(fresh-link(booleans),
+ sequential(
+ set-link(given, true),
+ if-true-else(
+ follow-if-link(given),
+ if-true-else(
+ is-equal(follow-if-link(42),42),
+ print"OK",
+ fail),
+ fail)))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/follow-link.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/follow-link.config
new file mode 100644
index 0000000..6de26f8
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/follow-link.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term:
+ initialise-linking
+ give(fresh-link(booleans),
+ sequential(
+ set-link(given, true),
+ print"OK",
+ if-true-else(
+ follow-link(given),
+ print"OK",
+ fail)))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK", "OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/fresh-initialised-link.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/fresh-initialised-link.config
new file mode 100644
index 0000000..66471f0
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/fresh-initialised-link.config
@@ -0,0 +1,10 @@
+general {
+ funcon-term:
+ initialise-linking
+ not is-equal(fresh-initialised-link(integers,42), fresh-initialised-link(integers,42))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/fresh-link.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/fresh-link.config
new file mode 100644
index 0000000..b8ec1b2
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/fresh-link.config
@@ -0,0 +1,10 @@
+general {
+ funcon-term:
+ initialise-linking
+ not is-equal(fresh-link(values), fresh-link(values))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/initialise-linking.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/initialise-linking.config
new file mode 100644
index 0000000..5bf9ac9
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/initialise-linking.config
@@ -0,0 +1,10 @@
+general {
+ funcon-term:
+ initialise-linking(print"OK")
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/links.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/links.config
new file mode 100644
index 0000000..45cd5fe
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/links.config
@@ -0,0 +1,10 @@
+general {
+ funcon-term:
+ initialise-linking
+ is-in-type(link(allocate-variable(values)), links)
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/set-link.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/set-link.config
new file mode 100644
index 0000000..c20b396
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Linking/tests/set-link.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ initialise-linking
+ give(fresh-link(booleans),
+ sequential(
+ set-link(given, true),
+ print"OK",
+ else(
+ set-link(given,false),
+ print"OK")))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK", "OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/Storing.cbs b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/Storing.cbs
new file mode 100644
index 0000000..f8c4269
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/Storing.cbs
@@ -0,0 +1,346 @@
+### Storing
+
+[
+ Datatype locations Alias locs
+ Type stores
+ Entity store
+ Funcon initialise-storing
+ Funcon store-clear
+ Datatype variables Alias vars
+ Funcon variable Alias var
+ Funcon allocate-variable Alias alloc
+ Funcon recycle-variables Alias recycle
+ Funcon initialise-variable Alias init
+ Funcon allocate-initialised-variable Alias alloc-init
+ Funcon assign
+ Funcon assigned
+ Funcon current-value
+ Funcon un-assign
+ Funcon structural-assign
+ Funcon structural-assigned
+]
+
+
+Meta-variables
+ T, T' <: values
+
+
+#### Stores
+
+Type
+ locations ~> atoms
+Alias
+ locs = locations
+/*
+ A storage location is represented by an atom.
+*/
+
+
+Type
+ stores ~> maps(locations, values?)
+/*
+ The domain of a store is the set of currently allocated locations.
+ Mapping a location to `( )` models the absence of its stored value;
+ removing it from the store allows it to be re-allocated.
+*/
+
+
+Entity
+ < _ , store(_:stores) > ---> < _ , store(_:stores) >
+/*
+ The current store is a mutable entity.
+ A transition ``< X , store(Sigma) > ---> < X' , store(Sigma') >`` models
+ a step from `X` to `X'` where the difference between `Sigma` and `Sigma'`
+ (if any) corresponds to storage effects.
+*/
+
+
+Funcon
+ store-clear : =>null-type
+Rule
+ < store-clear , store(_) > ---> < null-value , store(map( )) >
+/*
+ `store-clear` ensures the store is empty.
+*/
+
+
+Funcon
+ initialise-storing(X:=>T) : =>T
+ ~> sequential(store-clear,
+ initialise-giving(initialise-generating(X)))
+Alias
+ init-storing = initialise-storing
+/*
+ `initialise-storing(X)` ensures that the entities used by the funcons for
+ storing are properly initialised.
+*/
+
+
+#### Simple variables
+
+/*
+ Simple variables may store primitive or structured values. The type of
+ values stored by a variable is fixed when it is allocated. For instance,
+ `allocate-variable(integers)` allocates a simple integer variable, and
+ `allocate-variable(vectors(integers))` allocates a structured variable for
+ storing vectors of integers, which can be updated only monolithically.
+*/
+
+Datatype
+ variables ::= variable(_:locations, _:value-types)
+Alias
+ vars = variables
+Alias
+ var = variable
+/*
+ `variables` is the type of simple variables that can store values of
+ a particular type.
+
+ `variable(L, T)` constructs a simple variable for storing values of
+ type `T` at location `L`. Variables at different locations are independent.
+
+ Note that `variables` is a subtype of `datatype-values`.
+*/
+
+
+Funcon
+ allocate-variable(T:types) : =>variables
+Alias
+ alloc = allocate-variable
+/*
+ `allocate-variable(T)` gives a simple variable whose location is not in the
+ current store. Subsequent uses of `allocate-variable(T')` give independent
+ variables, except after `recycle-variables(V,...)` or `store-clear`.
+*/
+Rule
+ < use-atom-not-in(dom(Sigma)) , store(Sigma) > ---> < L , store(Sigma') >
+ map-override({L |-> ( )}, Sigma') ~> Sigma''
+ -------------------------------------------------------------------------
+ < allocate-variable(T:types) , store(Sigma) >
+ ---> < variable(L, T) , store(Sigma'') >
+
+
+Funcon
+ recycle-variables(_:variables+) : =>null-type
+Alias
+ recycle = recycle-variables
+/*
+ `recycle-variables(Var,...)` removes the locations of `Var`, ..., from the
+ current store, so that they may subsequently be re-allocated.
+*/
+Rule
+ is-in-set(L, dom(Sigma)) == true
+ ---------------------------------------------------------------------
+ < recycle-variables(variable(L:locations, T:types)) , store(Sigma) >
+ ---> < null-value , store(map-delete(Sigma, {L})) >
+Rule
+ is-in-set(L, dom(Sigma)) == false
+ ---------------------------------------------------------------------
+ < recycle-variables(variable(L:locations, T:types)) , store(Sigma) >
+ ---> < fail , store(Sigma) >
+Rule
+ recycle-variables(Var:variables, Var+:variables+)
+ ~> sequential(recycle-variables(Var), recycle-variables(Var+))
+
+
+Funcon
+ initialise-variable(_:variables, _:values) : =>null-type
+Alias
+ init = initialise-variable
+/*
+ `initialise-variable(Var, Val)` assigns `Val` as the initial value of `Var`,
+ and gives `null-value`. If `Var` already has an assigned value, it fails.
+*/
+Rule
+ and(is-in-set(L, dom(Sigma)),
+ not is-value(map-lookup(Sigma, L)),
+ is-in-type(Val, T))
+ == true
+ ----------------------------------------------------------------------------
+ < initialise-variable(variable(L:locations, T:types), Val:values) ,
+ store(Sigma) > ---> < null-value , store(map-override({L|->Val}, Sigma)) >
+Rule
+ and(is-in-set(L, dom(Sigma)),
+ not is-value(map-lookup(Sigma, L)),
+ is-in-type(Val, T))
+ == false
+ ----------------------------------------------------------------------------
+ < initialise-variable(variable(L:locations, T:types), Val:values) ,
+ store(Sigma) > ---> < fail , store(Sigma) >
+
+
+Funcon
+ allocate-initialised-variable(T, Val:T) : =>variables
+ ~> give(allocate-variable(T),
+ sequential(initialise-variable(given, Val), given))
+Alias
+ alloc-init = allocate-initialised-variable
+/*
+ `allocate-initialised-variable(T, Val)` allocates a simple variable for
+ storing values of type `T`, initialises its value to `Val`, and returns the
+ variable.
+*/
+
+
+Funcon
+ assign(_:variables, _:values) : =>null-type
+/*
+ `assign(Var, Val)` assigns the value `Val` to the variable `Var`,
+ provided that `Var` was allocated with a type that contains `Val`.
+*/
+Rule
+ and(is-in-set(L, dom(Sigma)), is-in-type(Val, T)) == true
+ -----------------------------------------------------------------------
+ < assign(variable(L:locations, T:types), Val:values) ,
+ store(Sigma) > ---> < null-value , store(map-override({L|->Val}, Sigma)) >
+Rule
+ and(is-in-set(L, dom(Sigma)), is-in-type(Val, T)) == false
+ --------------------------------------------------------------------------
+ < assign(variable(L:locations,T:types), Val:values) ,
+ store(Sigma) > ---> < fail , store(Sigma) >
+
+
+Funcon
+ assigned(_:variables) : =>values
+/*
+ `assigned(Var)` gives the value assigned to the variable `Var`,
+ failing if no value is currently assigned.
+*/
+Rule
+ map-lookup(Sigma, L) ~> (Val:values)
+ ------------------------------------------------------------------
+ < assigned(variable(L:locations, T:types)) , store(Sigma) >
+ ---> < Val , store(Sigma) >
+Rule
+ map-lookup(Sigma, L) == ( )
+ ------------------------------------------------------------------
+ < assigned(variable(L:locations, T:types)) , store(Sigma) >
+ ---> < fail , store(Sigma) >
+
+
+Funcon
+ current-value(_:values) : =>values
+/*
+ `current-value(V)` gives the same result as `assigned(V)` when `V` is a
+ simple variable, and otherwise gives `V`.
+
+ It represents implicit dereferencing of a value that might be a variable.
+*/
+Rule
+ current-value(Var:variables) ~> assigned(Var)
+Rule
+ current-value(U:~variables) ~> U
+
+
+Funcon
+ un-assign(_:variables) : =>null-type
+/*
+ `un-assign(Var)` remove the value assigned to the variable `Var`.
+*/
+Rule
+ is-in-set(L, dom(Sigma)) == true
+ --------------------------------------------------------------------------
+ < un-assign(variable(L:locations, T:types)) , store(Sigma) >
+ ---> < null-value , store(map-override({L |-> ( )}, Sigma)) >
+Rule
+ is-in-set(L, dom(Sigma)) == false
+ --------------------------------------------------------------------------
+ < un-assign(variable(L:locations, T:types)) , store(Sigma) >
+ ---> < fail , store(Sigma) >
+
+
+#### Structured variables
+
+/*
+ Structured variables are structured values where some components are
+ simple variables. Such component variables can be selected using the
+ same funcons as for selecting components of structured values.
+
+ Structured variables containing both simple variables and values correspond
+ to hybrid structures where particular components are mutable.
+
+ All datatypes (except for abstractions) can be used to form structured
+ variables. So can maps, but not sets or multisets.
+
+ Structural generalisations of `assign(Var, Val)` and
+ `assigned(Var)` access all the simple variables contained in a
+ structured variable. Assignment requires each component value of a hybrid
+ structured variable to be equal to the corresponding component of the
+ structured value.
+*/
+
+Funcon
+ structural-assign(_:values, _:values) : =>null-type
+/*
+ `structural-assign(V1, V2)` takes a (potentially) structured variable
+ `V1`and a (potentially) structured value `V2`. Provided that the structure
+ and all non-variable values in `V1` match the structure and corresponding
+ values of `V2`, all the simple variables in `V1` are assigned the
+ corresponding values of `V2`; otherwise the assignment fails.
+*/
+Rule
+ structural-assign(V1:variables, V2:values)
+ ~> assign(V1, V2)
+Rule
+ V1 : ~(variables)
+ V1 ~> datatype-value(I1:identifiers, V1*:values*)
+ V2 ~> datatype-value(I2:identifiers, V2*:values*)
+ -----------------------------------------------------------------------
+ structural-assign(V1:datatype-values, V2:datatype-values)
+ ~> sequential(
+ check-true(is-equal(I1, I2)),
+ effect(tuple(interleave-map(
+ structural-assign(tuple-elements(given)),
+ tuple-zip(tuple(V1*), tuple(V2*))))),
+ null-value)
+/*
+ Note that simple variables are datatype values.
+*/
+Rule
+ dom(M1) == {}
+ ------------------------------------------------------
+ structural-assign(M1:maps(_,_), M2:maps(_,_))
+ ~> check-true(is-equal(dom(M2), { }))
+Rule
+ some-element(dom(M1)) ~> K
+ ----------------------------------------------------------------------------
+ structural-assign(M1:maps(_, _), M2:maps(_, _))
+ ~> sequential(check-true(is-in-set(K, dom(M2))),
+ structural-assign(map-lookup(M1, K), map-lookup(M2, K)),
+ structural-assign(map-delete(M1, {K}), map-delete(M2, {K})))
+Rule
+ V1 : ~(datatype-values|maps(_, _))
+ ---------------------------------------------------------------
+ structural-assign(V1:values,V2:values)
+ ~> check-true(is-equal(V1, V2))
+
+
+Funcon
+ structural-assigned(_:values) : =>values
+/*
+ `structural-assigned(V)` takes a (potentially) structured variable `V`,
+ and computes the value of `V` with all simple variables in `V` replaced by
+ their assigned values, failing if any of them do not have assigned values.
+
+ When `V` is just a simple variable or a (possibly structured) value with no
+ component variables, `structural-assigned(V)` gives the same result as
+ `current-value(V)`.
+*/
+Rule
+ structural-assigned(Var:variables) ~> assigned(Var)
+Rule
+ V : ~(variables)
+ V ~> datatype-value(I:identifiers, V*:values*)
+ ----------------------------------------------------------------------------
+ structural-assigned(V:datatype-values)
+ ~> datatype-value(I, interleave-map(structural-assigned(given), V*))
+/*
+ Note that simple variables are datatype values.
+*/
+Rule
+ structural-assigned(M:maps(_, _))
+ ~> map(interleave-map(structural-assigned(given), map-elements(M)))
+Rule
+ U : ~(datatype-values|maps(_, _))
+ ------------------------------------------
+ structural-assigned(U:values) ~> U
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/index.md b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/index.md
new file mode 100644
index 0000000..7c0c7c0
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/index.md
@@ -0,0 +1,392 @@
+---
+layout: default
+title: "Storing"
+parent: Normal
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Storing.cbs]
+-----------------------------
+
+### Storing
+
+
+
+
+
+Meta-variables
+ T, T′ <: values
+
+
+
+#### Stores
+
+
+
+
+
+ A storage location is represented by an atom.
+
+
+
+
+
+
+ The domain of a store is the set of currently allocated locations.
+ Mapping a location to ( ) models the absence of its stored value;
+ removing it from the store allows it to be re-allocated.
+
+
+
+Entity
+ < _ , store(_:stores) > ---> < _ , store(_:stores) >
+
+
+ The current store is a mutable entity.
+ A transition < X , store(Sigma) > ---> < X′ , store(Sigma′) > models
+ a step from X to X′ where the difference between Sigma and Sigma′
+ (if any) corresponds to storage effects.
+
+
+
+
+ store-clear ensures the store is empty.
+
+
+
+
+ initialise-storing(X) ensures that the entities used by the funcons for
+ storing are properly initialised.
+
+
+
+#### Simple variables
+
+
+ Simple variables may store primitive or structured values. The type of
+ values stored by a variable is fixed when it is allocated. For instance,
+ allocate-variable(integers) allocates a simple integer variable, and
+ allocate-variable(vectors(integers)) allocates a structured variable for
+ storing vectors of integers, which can be updated only monolithically.
+
+
+
+
+
+
+ variables is the type of simple variables that can store values of
+ a particular type.
+
+ variable(L, T) constructs a simple variable for storing values of
+ type T at location L. Variables at different locations are independent.
+
+ Note that variables is a subtype of datatype-values.
+
+
+
+
+ allocate-variable(T) gives a simple variable whose location is not in the
+ current store. Subsequent uses of allocate-variable(T′) give independent
+ variables, except after recycle-variables(V,...) or store-clear.
+
+
+
+
+
+
+ recycle-variables(Var,...) removes the locations of Var, ..., from the
+ current store, so that they may subsequently be re-allocated.
+
+Rule
+ is-in-set(L, dom(Sigma)) == true
+ ---------------------------------------------------------------------
+ < recycle-variables(variable(L:locations, T:types)) , store(Sigma) >
+ ---> < null-value , store(map-delete(Sigma, {L})) >
+Rule
+ is-in-set(L, dom(Sigma)) == false
+ ---------------------------------------------------------------------
+ < recycle-variables(variable(L:locations, T:types)) , store(Sigma) >
+ ---> < fail , store(Sigma) >
+Rule
+ recycle-variables(Var:variables, Var+:variables+)
+ ~> sequential(recycle-variables(Var), recycle-variables(Var+))
+
+
+
+
+ initialise-variable(Var, Val) assigns Val as the initial value of Var,
+ and gives null-value. If Var already has an assigned value, it fails.
+
+Rule
+ and(is-in-set(L, dom(Sigma)),
+ not is-value(map-lookup(Sigma, L)),
+ is-in-type(Val, T))
+ == true
+ ----------------------------------------------------------------------------
+ < initialise-variable(variable(L:locations, T:types), Val:values) ,
+ store(Sigma) > ---> < null-value , store(map-override({L|->Val}, Sigma)) >
+Rule
+ and(is-in-set(L, dom(Sigma)),
+ not is-value(map-lookup(Sigma, L)),
+ is-in-type(Val, T))
+ == false
+ ----------------------------------------------------------------------------
+ < initialise-variable(variable(L:locations, T:types), Val:values) ,
+ store(Sigma) > ---> < fail , store(Sigma) >
+
+
+
+
+ allocate-initialised-variable(T, Val) allocates a simple variable for
+ storing values of type T, initialises its value to Val, and returns the
+ variable.
+
+
+
+
+
+ assign(Var, Val) assigns the value Val to the variable Var,
+ provided that Var was allocated with a type that contains Val.
+
+Rule
+ and(is-in-set(L, dom(Sigma)), is-in-type(Val, T)) == true
+ -----------------------------------------------------------------------
+ < assign(variable(L:locations, T:types), Val:values) ,
+ store(Sigma) > ---> < null-value , store(map-override({L|->Val}, Sigma)) >
+Rule
+ and(is-in-set(L, dom(Sigma)), is-in-type(Val, T)) == false
+ --------------------------------------------------------------------------
+ < assign(variable(L:locations,T:types), Val:values) ,
+ store(Sigma) > ---> < fail , store(Sigma) >
+
+
+
+
+
+ assigned(Var) gives the value assigned to the variable Var,
+ failing if no value is currently assigned.
+
+
+
+
+
+
+
+ current-value(V) gives the same result as assigned(V) when V is a
+ simple variable, and otherwise gives V.
+
+ It represents implicit dereferencing of a value that might be a variable.
+
+
+
+
+
+
+
+ un-assign(Var) remove the value assigned to the variable Var.
+
+
+
+
+
+#### Structured variables
+
+
+ Structured variables are structured values where some components are
+ simple variables. Such component variables can be selected using the
+ same funcons as for selecting components of structured values.
+
+ Structured variables containing both simple variables and values correspond
+ to hybrid structures where particular components are mutable.
+
+ All datatypes (except for abstractions) can be used to form structured
+ variables. So can maps, but not sets or multisets.
+
+ Structural generalisations of assign(Var, Val) and
+ assigned(Var) access all the simple variables contained in a
+ structured variable. Assignment requires each component value of a hybrid
+ structured variable to be equal to the corresponding component of the
+ structured value.
+
+
+
+
+ structural-assign(V1, V2) takes a (potentially) structured variable
+ V1and a (potentially) structured value V2. Provided that the structure
+ and all non-variable values in V1 match the structure and corresponding
+ values of V2, all the simple variables in V1 are assigned the
+ corresponding values of V2; otherwise the assignment fails.
+
+Rule
+ structural-assign(V1:variables, V2:values)
+ ~> assign(V1, V2)
+Rule
+ V1 : ~(variables)
+ V1 ~> datatype-value(I1:identifiers, V1*:values*)
+ V2 ~> datatype-value(I2:identifiers, V2*:values*)
+ -----------------------------------------------------------------------
+ structural-assign(V1:datatype-values, V2:datatype-values)
+ ~> sequential(
+ check-true(is-equal(I1, I2)),
+ effect(tuple(interleave-map(
+ structural-assign(tuple-elements(given)),
+ tuple-zip(tuple(V1*), tuple(V2*))))),
+ null-value)
+
+
+ Note that simple variables are datatype values.
+
+Rule
+ dom(M1) == {}
+ ------------------------------------------------------
+ structural-assign(M1:maps(_,_), M2:maps(_,_))
+ ~> check-true(is-equal(dom(M2), { }))
+Rule
+ some-element(dom(M1)) ~> K
+ ----------------------------------------------------------------------------
+ structural-assign(M1:maps(_, _), M2:maps(_, _))
+ ~> sequential(check-true(is-in-set(K, dom(M2))),
+ structural-assign(map-lookup(M1, K), map-lookup(M2, K)),
+ structural-assign(map-delete(M1, {K}), map-delete(M2, {K})))
+Rule
+ V1 : ~(datatype-values|maps(_, _))
+ ---------------------------------------------------------------
+ structural-assign(V1:values,V2:values)
+ ~> check-true(is-equal(V1, V2))
+
+
+
+
+
+ structural-assigned(V) takes a (potentially) structured variable V,
+ and computes the value of V with all simple variables in V replaced by
+ their assigned values, failing if any of them do not have assigned values.
+
+ When V is just a simple variable or a (possibly structured) value with no
+ component variables, structural-assigned(V) gives the same result as
+ current-value(V).
+
+
+
+
+ Note that simple variables are datatype values.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Storing.cbs]: Storing.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Computations/Normal/Storing/Storing.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/allocate-initialised-variable.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/allocate-initialised-variable.config
new file mode 100644
index 0000000..fac481e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/allocate-initialised-variable.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ allocate-initialised-variable(booleans,true),
+ check-true(assigned(given)))
+ ;
+}
+
+tests {
+ result-term: null-value;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/allocate-variable.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/allocate-variable.config
new file mode 100644
index 0000000..a592e56
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/allocate-variable.config
@@ -0,0 +1,10 @@
+general {
+ funcon-term:
+ initialise-storing
+ not is-equal(allocate-variable(values), allocate-variable(values))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/assign.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/assign.config
new file mode 100644
index 0000000..d313c68
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/assign.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ allocate-initialised-variable(booleans,false),
+ sequential(
+ assign(given,true),
+ else(assign(given,42), print"OK")))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/assigned.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/assigned.config
new file mode 100644
index 0000000..041e9c6
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/assigned.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ allocate-initialised-variable(booleans,true),
+ sequential(
+ check-true assigned(given),
+ store-clear,
+ else(assigned(given), print"OK")))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/current-value-2.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/current-value-2.config
new file mode 100644
index 0000000..0f03572
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/current-value-2.config
@@ -0,0 +1,29 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ { "a" |-> allocate-initialised-variable(booleans,false),
+ "b" |-> 42,
+ "c" |-> allocate-initialised-variable(booleans,true),
+ "d" |-> 13 },
+ sequential(
+ check-true is-equal(
+ current-value(map()),
+ map()),
+ check-true is-equal(
+ current-value(given),
+ {"a"|->variable(atom("@1"), booleans),"b"|->42
+ ,"c"|->variable(atom("@2"), booleans),"d"|->13}),
+ check-true is-equal(
+ current-value(lookup(given,"a")),false),
+ check-true is-equal(
+ current-value(lookup(given,"c")),true),
+ check-true is-equal(
+ current-value{42},
+ {42})))
+ ;
+}
+
+tests {
+ result-term: null-value;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/current-value.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/current-value.config
new file mode 100644
index 0000000..c078996
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/current-value.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term:
+ initialise-storing
+ sequential(
+ check-true is-equal(
+ current-value(allocate-initialised-variable(integers,42)),
+ 42),
+ check-true is-equal(current-value(42), 42))
+ ;
+}
+
+tests {
+ result-term: null-value;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/initialise-storing.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/initialise-storing.config
new file mode 100644
index 0000000..89c8a54
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/initialise-storing.config
@@ -0,0 +1,10 @@
+general {
+ funcon-term:
+ initialise-storing(print"OK")
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/initialise-variable.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/initialise-variable.config
new file mode 100644
index 0000000..ee00924
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/initialise-variable.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ give(
+ allocate-variable(booleans),
+ sequential(initialise-variable(given,true),given)),
+ else(initialise-variable(given,true), print"OK"))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/locations.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/locations.config
new file mode 100644
index 0000000..975ad54
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/locations.config
@@ -0,0 +1,10 @@
+general {
+ funcon-term:
+ initialise-storing
+ is-in-type(fresh-atom, locations)
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/recycle-variables-1.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/recycle-variables-1.config
new file mode 100644
index 0000000..0c38482
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/recycle-variables-1.config
@@ -0,0 +1,13 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ allocate-variable(booleans),
+ recycle-variables(given))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ store: map();
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/recycle-variables-2.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/recycle-variables-2.config
new file mode 100644
index 0000000..9459670
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/recycle-variables-2.config
@@ -0,0 +1,13 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ allocate-variable(booleans),
+ recycle-variables(given,allocate-variable(booleans)))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ store: map();
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/recycle-variables-3.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/recycle-variables-3.config
new file mode 100644
index 0000000..5c23e31
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/recycle-variables-3.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ allocate-variable(booleans),
+ sequential(
+ recycle-variables(given),
+ else(recycle-variables(given), print"OK")))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/store-clear.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/store-clear.config
new file mode 100644
index 0000000..e7672a5
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/store-clear.config
@@ -0,0 +1,13 @@
+general {
+ funcon-term:
+ initialise-storing
+ sequential(
+ effect allocate-variable(booleans),
+ store-clear)
+ ;
+}
+
+tests {
+ result-term: null-value;
+ store: map();
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/stores.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/stores.config
new file mode 100644
index 0000000..63f11fc
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/stores.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(fresh-atom,
+ and(
+ is-in-type(map(),stores),
+ is-in-type({given|->true},stores),
+ is-in-type({given|->true, fresh-atom|->()},stores)))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assign-1.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assign-1.config
new file mode 100644
index 0000000..09e7351
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assign-1.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ allocate-initialised-variable(booleans,false),
+ sequential(
+ structural-assign(given,true),
+ else(structural-assign(given,42), print"OK")))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assign-2.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assign-2.config
new file mode 100644
index 0000000..5660534
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assign-2.config
@@ -0,0 +1,22 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ tuple(
+ allocate-initialised-variable(booleans,false),
+ 42,
+ allocate-initialised-variable(booleans,true)),
+ sequential(
+ structural-assign(given,tuple(true,42,false)),
+ else(
+ structural-assign(given,[true,42,false]),
+ structural-assign(given,tuple(true,99,false)),
+ structural-assign(given,false),
+ print"OK")))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assign-3.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assign-3.config
new file mode 100644
index 0000000..3ee799e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assign-3.config
@@ -0,0 +1,25 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ { "a" |-> allocate-initialised-variable(booleans,false),
+ "b" |-> 42,
+ "c" |-> allocate-initialised-variable(booleans,true) },
+ sequential(
+ structural-assign(map(),map()),
+ structural-assign(given,{"a"|->true,"b"|->42,"c"|->false}),
+ structural-assign(true,true),
+ else(
+ structural-assign(given,{"a"|->true,"b"|->99,"c"|->false}),
+ structural-assign(given,{"a"|->true,"c"|->false}),
+ structural-assign(given,map()),
+ structural-assign(given,{"a"|->true,"b"|->42,"c"|->false,"d"|->()}),
+ structural-assign(true,false),
+ print"OK")))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-1.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-1.config
new file mode 100644
index 0000000..b6e4e8f
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-1.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ allocate-initialised-variable(booleans,true),
+ check-true structural-assigned(given))
+ ;
+}
+
+tests {
+ result-term: null-value;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-2.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-2.config
new file mode 100644
index 0000000..45adf49
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-2.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ tuple(
+ allocate-initialised-variable(booleans,false),
+ 42,
+ allocate-initialised-variable(booleans,true)),
+ check-true is-equal(
+ structural-assigned(given),
+ tuple(false,42,true)))
+ ;
+}
+
+tests {
+ result-term: null-value;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-3.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-3.config
new file mode 100644
index 0000000..90144b1
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-3.config
@@ -0,0 +1,23 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ { "a" |-> allocate-initialised-variable(booleans,true),
+ "b" |-> 42,
+ "c" |-> allocate-initialised-variable(booleans,false) },
+ sequential(
+ check-true is-equal(
+ structural-assigned(map()),
+ map()),
+ check-true is-equal(
+ structural-assigned(given),
+ {"a"|->true,"b"|->42,"c"|->false}),
+ check-true is-equal(
+ structural-assigned{42},
+ {42})))
+ ;
+}
+
+tests {
+ result-term: null-value;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-4.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-4.config
new file mode 100644
index 0000000..1483921
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/structural-assigned-4.config
@@ -0,0 +1,24 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ { "a" |-> allocate-initialised-variable(booleans,false),
+ "b" |-> 42,
+ "c" |-> allocate-initialised-variable(booleans,true),
+ "d" |-> 13 },
+ sequential(
+ check-true is-equal(
+ structural-assigned(map()),
+ map()),
+ check-true is-equal(
+ structural-assigned(given),
+ {"a"|->false,"b"|->42,"c"|->true,"d"|->13}),
+ check-true is-equal(
+ structural-assigned{42},
+ {42})))
+ ;
+}
+
+tests {
+ result-term: null-value;
+}
diff --git a/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/un-assign.config b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/un-assign.config
new file mode 100644
index 0000000..f1589e1
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Computations/Normal/Storing/tests/un-assign.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term:
+ initialise-storing
+ give(
+ allocate-initialised-variable(booleans,true),
+ sequential(
+ check-true assigned(given),
+ un-assign(given),
+ else(
+ assigned(given),
+ print"OK")))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Funcons-Index/Funcons-Index.cbs b/IBAF-cbs/Funcons-beta/Funcons-Index/Funcons-Index.cbs
new file mode 100644
index 0000000..2efa34e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Funcons-Index/Funcons-Index.cbs
@@ -0,0 +1,577 @@
+# Computations
+
+## Types of computation
+[
+ Funcon computation-types
+]
+
+## Normal computation
+
+### Flowing
+[
+ Funcon left-to-right Alias l-to-r
+ Funcon right-to-left Alias r-to-l
+ Funcon sequential Alias seq
+ Funcon effect
+ Funcon choice
+ Funcon if-true-else Alias if-else
+ Funcon while-true Alias while
+ Funcon do-while-true Alias do-while
+ Funcon interleave
+ Datatype yielding
+ Funcon signal
+ Funcon yielded
+ Funcon yield
+ Funcon yield-on-value
+ Funcon yield-on-abrupt
+ Funcon atomic
+]
+
+### Giving
+[
+ Entity given-value
+ Funcon initialise-giving
+ Funcon give
+ Funcon given
+ Funcon no-given
+ Funcon left-to-right-map
+ Funcon interleave-map
+ Funcon left-to-right-repeat
+ Funcon interleave-repeat
+ Funcon left-to-right-filter
+ Funcon interleave-filter
+ Funcon fold-left
+ Funcon fold-right
+]
+
+### Binding
+[
+ Type environments Alias envs
+ Datatype identifiers Alias ids
+ Funcon identifier-tagged Alias id-tagged
+ Funcon fresh-identifier
+ Entity environment Alias env
+ Funcon initialise-binding
+ Funcon bind-value Alias bind
+ Funcon unbind
+ Funcon bound-directly
+ Funcon bound-value Alias bound
+ Funcon closed
+ Funcon scope
+ Funcon accumulate
+ Funcon collateral
+ Funcon bind-recursively
+ Funcon recursive
+]
+
+### Generating
+[
+ Type atoms
+ Entity used-atom-set
+ Funcon initialise-generating
+ Funcon fresh-atom
+ Funcon use-atom-not-in
+]
+
+### Storing
+[
+ Datatype locations Alias locs
+ Type stores
+ Entity store
+ Funcon initialise-storing
+ Funcon store-clear
+ Datatype variables Alias vars
+ Funcon variable Alias var
+ Funcon allocate-variable Alias alloc
+ Funcon recycle-variables Alias recycle
+ Funcon initialise-variable Alias init
+ Funcon allocate-initialised-variable Alias alloc-init
+ Funcon assign
+ Funcon assigned
+ Funcon current-value
+ Funcon un-assign
+ Funcon structural-assign
+ Funcon structural-assigned
+]
+
+### Linking
+[
+ Datatype links
+ Funcon initialise-linking
+ Funcon link
+ Funcon fresh-link
+ Funcon fresh-initialised-link Alias fresh-init-link
+ Funcon set-link
+ Funcon follow-if-link
+]
+
+### Interacting
+
+#### Input
+[
+ Entity standard-in
+ Funcon read
+]
+
+#### Output
+[
+ Entity standard-out
+ Funcon print
+]
+
+## Abnormal computation
+
+### Terminating abruptly
+[
+ Funcon stuck
+ Entity abrupted
+ Funcon finalise-abrupting
+ Funcon abrupt
+ Funcon handle-abrupt
+ Funcon finally
+]
+
+### Failing
+[
+ Datatype failing
+ Funcon failed
+ Funcon finalise-failing
+ Funcon fail
+ Funcon else
+ Funcon else-choice
+ Funcon checked
+ Funcon check-true
+]
+
+### Throwing
+[
+ Datatype throwing
+ Funcon thrown
+ Funcon finalise-throwing
+ Funcon throw
+ Funcon handle-thrown
+ Funcon handle-recursively
+ Funcon catch-else-throw
+]
+
+### Returning
+[
+ Datatype returning
+ Funcon returned
+ Funcon finalise-returning
+ Funcon return
+ Funcon handle-return
+]
+
+### Breaking
+[
+ Datatype breaking
+ Funcon broken
+ Funcon finalise-breaking
+ Funcon break
+ Funcon handle-break
+]
+
+### Continuing
+[
+ Datatype continuing
+ Funcon continued
+ Funcon finalise-continuing
+ Funcon continue
+ Funcon handle-continue
+]
+
+### Controlling
+[
+ Datatype continuations
+ Funcon continuation
+ Entity plug-signal
+ Funcon hole
+ Funcon resume-continuation
+ Entity control-signal
+ Funcon control
+ Funcon delimit-current-continuation Alias delimit-cc
+]
+
+
+# Values
+
+## Value Types
+[
+ Type values Alias vals
+ Type value-types Alias types
+ Type empty-type
+ Funcon is-in-type Alias is
+ Funcon is-value Alias is-val
+ Funcon when-true Alias when
+ Type cast-to-type Alias cast
+ Type ground-values Alias ground-vals
+ Funcon is-equal Alias is-eq
+]
+
+## Primitive values
+
+### Booleans
+[
+ Datatype booleans Alias bools
+ Funcon true
+ Funcon false
+ Funcon not
+ Funcon implies
+ Funcon and
+ Funcon or
+ Funcon exclusive-or Alias xor
+]
+
+### Integers
+[
+ Type integers Alias ints
+ Type integers-from Alias from
+ Type integers-up-to Alias up-to
+ Type bounded-integers Alias bounded-ints
+ Type positive-integers Alias pos-ints
+ Type negative-integers Alias neg-ints
+ Type natural-numbers Alias nats
+ Funcon natural-successor Alias nat-succ
+ Funcon natural-predecessor Alias nat-pred
+ Funcon integer-add Alias int-add
+ Funcon integer-subtract Alias int-sub
+ Funcon integer-multiply Alias int-mul
+ Funcon integer-divide Alias int-div
+ Funcon integer-modulo Alias int-mod
+ Funcon integer-power Alias int-pow
+ Funcon integer-absolute-value Alias int-abs
+ Funcon integer-negate Alias int-neg
+ Funcon integer-is-less Alias is-less
+ Funcon integer-is-less-or-equal Alias is-less-or-equal
+ Funcon integer-is-greater Alias is-greater
+ Funcon integer-is-greater-or-equal Alias is-greater-or-equal
+ Funcon binary-natural Alias binary
+ Funcon octal-natural Alias octal
+ Funcon decimal-natural Alias decimal
+ Funcon hexadecimal-natural Alias hexadecimal
+ Funcon integer-sequence
+]
+
+### Floats
+[
+ Datatype float-formats
+ Funcon binary32
+ Funcon binary64
+ Funcon binary128
+ Funcon decimal64
+ Funcon decimal128
+ Type floats
+ Funcon float
+ Funcon quiet-not-a-number Alias qNaN
+ Funcon signaling-not-a-number Alias sNaN
+ Funcon positive-infinity Alias pos-inf
+ Funcon negative-infinity Alias neg-inf
+ Funcon float-convert
+ Funcon float-equal
+ Funcon float-is-less
+ Funcon float-is-less-or-equal
+ Funcon float-is-greater
+ Funcon float-is-greater-or-equal
+ Funcon float-negate
+ Funcon float-absolute-value
+ Funcon float-add
+ Funcon float-subtract
+ Funcon float-multiply
+ Funcon float-multiply-add
+ Funcon float-divide
+ Funcon float-remainder
+ Funcon float-sqrt
+ Funcon float-integer-power
+ Funcon float-float-power
+ Funcon float-round-ties-to-even
+ Funcon float-round-ties-to-infinity
+ Funcon float-floor
+ Funcon float-ceiling
+ Funcon float-truncate
+ Funcon float-pi
+ Funcon float-e
+ Funcon float-log
+ Funcon float-log10
+ Funcon float-exp
+ Funcon float-sin
+ Funcon float-cos
+ Funcon float-tan
+ Funcon float-asin
+ Funcon float-acos
+ Funcon float-atan
+ Funcon float-sinh
+ Funcon float-cosh
+ Funcon float-tanh
+ Funcon float-asinh
+ Funcon float-acosh
+ Funcon float-atanh
+ Funcon float-atan2
+]
+
+### Characters
+[
+ Type characters Alias chars
+ Datatype unicode-characters Alias unicode-chars
+ Type unicode-points
+ Funcon unicode-character Alias unicode-char
+ Funcon unicode-point Alias unicode
+ Type basic-multilingual-plane-characters Alias bmp-chars
+ Type basic-multilingual-plane-points
+ Type iso-latin-1-characters Alias latin-1-chars
+ Type iso-latin-1-points
+ Type ascii-characters Alias ascii-chars
+ Type ascii-points
+ Funcon ascii-character Alias ascii-char
+ Funcon utf-8
+ Funcon utf-16
+ Funcon utf-32
+ Funcon backspace
+ Funcon horizontal-tab
+ Funcon line-feed
+ Funcon form-feed
+ Funcon carriage-return
+ Funcon double-quote
+ Funcon single-quote
+ Funcon backslash
+]
+
+### The null value
+
+[
+ Datatype null-type
+ Funcon null-value Alias null
+]
+
+## Composite values
+
+### Sequences of values
+[
+ Funcon length
+ Funcon index
+ Funcon is-in
+ Funcon first
+ Funcon second
+ Funcon third
+ Funcon first-n
+ Funcon drop-first-n
+ Funcon reverse
+ Funcon n-of
+ Funcon intersperse
+]
+
+### Datatypes
+[
+ Funcon datatype-value
+ Funcon datatype-value-id
+ Funcon datatype-value-elements
+]
+
+### Tuples
+[
+ Datatype tuples
+ Funcon tuple-elements
+ Funcon tuple-zip
+]
+
+### Lists
+[
+ Datatype lists
+ Funcon list
+ Funcon list-elements
+ Funcon list-nil Alias nil
+ Funcon list-cons Alias cons
+ Funcon list-head Alias head
+ Funcon list-tail Alias tail
+ Funcon list-length
+ Funcon list-append
+]
+
+### Strings
+[
+ Type strings
+ Funcon string
+ Funcon string-append
+ Funcon to-string
+]
+
+### Vectors
+[
+ Datatype vectors
+ Funcon vector
+ Funcon vector-elements
+]
+
+### Bits and bit vectors
+[
+ Type bits
+ Datatype bit-vectors
+ Funcon bit-vector
+ Type bytes Alias octets
+ Funcon bit-vector-not
+ Funcon bit-vector-and
+ Funcon bit-vector-or
+ Funcon bit-vector-xor
+ Funcon bit-vector-shift-left
+ Funcon bit-vector-logical-shift-right
+ Funcon bit-vector-arithmetic-shift-right
+ Funcon integer-to-bit-vector
+ Funcon bit-vector-to-integer
+ Funcon bit-vector-to-natural
+ Funcon unsigned-bit-vector-maximum
+ Funcon signed-bit-vector-maximum
+ Funcon signed-bit-vector-minimum
+ Funcon is-in-signed-bit-vector
+ Funcon is-in-unsigned-bit-vector
+]
+
+### Sets
+[
+ Type sets
+ Funcon set
+ Funcon set-elements
+ Funcon is-in-set
+ Funcon is-subset
+ Funcon set-insert
+ Funcon set-unite
+ Funcon set-intersect
+ Funcon set-difference
+ Funcon set-size
+ Funcon some-element
+ Funcon element-not-in
+]
+
+### Maps
+[
+ Type maps
+ Funcon map
+ Funcon map-elements
+ Funcon map-lookup Alias lookup
+ Funcon map-domain Alias dom
+ Funcon map-override
+ Funcon map-unite
+ Funcon map-delete
+]
+
+### Multisets (bags)
+[
+ Type multisets
+ Funcon multiset
+ Funcon multiset-elements
+ Funcon multiset-occurrences
+ Funcon multiset-insert
+ Funcon multiset-delete
+ Funcon is-submultiset
+]
+
+### Trees
+[
+ Datatype trees
+ Funcon tree
+ Funcon tree-root-value
+ Funcon tree-branch-sequence
+ Funcon single-branching-sequence
+ Funcon forest-root-value-sequence
+ Funcon forest-branch-sequence
+ Funcon forest-value-sequence
+]
+
+### Graphs
+[
+ Type directed-graphs
+ Funcon is-cyclic
+ Funcon topological-sort
+]
+
+### References and pointers
+[
+ Datatype references
+ Funcon reference
+ Type pointers
+ Funcon dereference
+]
+
+### Records
+[
+ Datatype records
+ Funcon record
+ Funcon record-map
+ Funcon record-select
+]
+
+### Variants
+[
+ Datatype variants
+ Funcon variant
+ Funcon variant-id
+ Funcon variant-value
+]
+
+### Classes
+[
+ Datatype classes
+ Funcon class
+ Funcon class-instantiator
+ Funcon class-feature-map
+ Funcon class-superclass-name-sequence
+ Funcon class-name-tree
+ Funcon is-subclass-name
+ Funcon class-name-single-inheritance-feature-map
+]
+
+### Objects
+[
+ Datatype objects
+ Funcon object
+ Funcon object-identity
+ Funcon object-class-name
+ Funcon object-feature-map
+ Funcon object-subobject-sequence
+ Funcon object-tree
+ Funcon object-single-inheritance-feature-map
+]
+
+## Abstraction values
+
+### Generic abstractions
+[
+ Type abstractions
+ Funcon abstraction
+ Funcon closure
+ Funcon enact
+]
+
+### Thunks
+[
+ Datatype thunks
+ Funcon thunk
+ Funcon force
+]
+
+### Functions
+[
+ Datatype functions
+ Funcon function
+ Funcon apply
+ Funcon supply
+ Funcon compose
+ Funcon uncurry
+ Funcon curry
+ Funcon partial-apply
+]
+
+### Patterns
+[
+ Datatype patterns
+ Funcon pattern
+ Funcon pattern-any
+ Funcon pattern-bind
+ Funcon pattern-type
+ Funcon pattern-else
+ Funcon pattern-unite
+ Funcon match
+ Funcon match-loosely
+ Funcon case-match
+ Funcon case-match-loosely
+ Funcon case-variant-value
+]
diff --git a/IBAF-cbs/Funcons-beta/Funcons-Index/index.md b/IBAF-cbs/Funcons-beta/Funcons-Index/index.md
new file mode 100644
index 0000000..84c6143
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Funcons-Index/index.md
@@ -0,0 +1,654 @@
+---
+layout: default
+title: "Funcons-Index"
+parent: Funcons-beta
+
+
+---
+
+[Funcons-beta] : [Funcons-Index.cbs]
+-----------------------------
+
+# Computations
+
+## Types of computation
+
+
+
+## Normal computation
+
+### Flowing
+
+
+
+### Giving
+
+
+
+### Binding
+
+
+
+### Generating
+
+
+
+### Storing
+
+
+
+### Linking
+
+
+
+### Interacting
+
+#### Input
+
+
+
+#### Output
+
+
+
+## Abnormal computation
+
+### Terminating abruptly
+
+
+
+### Failing
+
+
+
+### Throwing
+
+
+
+### Returning
+
+
+
+### Breaking
+
+
+
+### Continuing
+
+
+
+### Controlling
+
+
+
+
+# Values
+
+## Value Types
+
+
+
+## Primitive values
+
+### Booleans
+
+
+
+### Integers
+
+
+
+### Floats
+
+
+
+### Characters
+
+
+
+### The null value
+
+
+
+
+## Composite values
+
+### Sequences of values
+
+
+
+### Datatypes
+
+
+
+### Tuples
+
+
+
+### Lists
+
+
+
+### Strings
+
+
+
+### Vectors
+
+
+
+### Bits and bit vectors
+
+
+
+### Sets
+
+
+
+### Maps
+
+
+
+### Multisets (bags)
+
+
+
+### Trees
+
+
+
+### Graphs
+
+
+
+### References and pointers
+
+
+
+### Records
+
+
+
+### Variants
+
+
+
+### Classes
+
+
+
+### Objects
+
+
+
+## Abstraction values
+
+### Generic abstractions
+
+
+
+### Thunks
+
+
+
+### Functions
+
+
+
+### Patterns
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Funcons-Index.cbs]: Funcons-Index.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Funcons-Index/Funcons-Index.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/Functions.cbs b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/Functions.cbs
new file mode 100644
index 0000000..3c05296
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/Functions.cbs
@@ -0,0 +1,92 @@
+### Functions
+
+[
+ Datatype functions
+ Funcon function
+ Funcon apply
+ Funcon supply
+ Funcon compose
+ Funcon uncurry
+ Funcon curry
+ Funcon partial-apply
+]
+
+
+Meta-variables
+ T, T', T1, T2 <: values
+
+
+Datatype
+ functions(T,T') ::= function(A:abstractions(T=>T'))
+/*
+ `functions(T, T')` consists of abstractions whose bodies may depend on
+ a given value of type `T`, and whose executions normally compute values
+ of type `T'`.
+ `function(abstraction(X))` evaluates to a function with dynamic bindings,
+ `function(closure(X))` computes a function with static bindings.
+*/
+
+
+Funcon
+ apply(_:functions(T, T'), _:T) : =>T'
+/*
+ `apply(F, V)` applies the function `F` to the argument value `V`.
+ This corresponds to call by value; using thunks as argument values
+ corresponds to call by name. Moreover, using tuples as argument values
+ corresponds to application to multiple arguments.
+*/
+Rule
+ apply(function(abstraction(X)), V:T) ~> give(V, X)
+
+
+Funcon
+ supply(_:functions(T, T'), _:T) : =>thunks(T')
+/*
+ `supply(F, V)` determines the argument value of a function application,
+ but returns a thunk that defers executing the body of the function.
+*/
+Rule
+ supply(function(abstraction(X)), V:T) ~> thunk(abstraction(give(V, X)))
+
+
+Funcon
+ compose(_:functions(T2, T'), _:functions(T1, T2)) : =>functions(T1, T')
+/*
+ `compose(F2, F1)` returns the function that applies `F1` to its argument,
+ then applies `F2` to the result of `F1`.
+*/
+Rule
+ compose(function(abstraction(Y)), function(abstraction(X)))
+ ~> function(abstraction(give(X, Y)))
+
+
+Funcon
+ uncurry(F:functions(T1, functions(T2, T'))) :
+ =>functions(tuples(T1, T2), T')
+ ~> function(abstraction(
+ apply(
+ apply(F, checked index(1, tuple-elements given)),
+ checked index(2, tuple-elements given))))
+/*
+ `uncurry(F)` takes a curried function `F` and returns a function that takes
+ a pair of arguments..
+*/
+
+
+Funcon
+ curry(F:functions(tuples(T1, T2), T')) : =>functions(T1, functions(T2, T'))
+ ~> function(abstraction(partial-apply(F, given)))
+/*
+ `curry(F)` takes a function `F` that takes a pair of arguments, and returns
+ the corresponding 'curried' function.
+*/
+
+
+Funcon
+ partial-apply(F:functions(tuples(T1, T2), T'), V:T1) : =>functions(T2, T')
+ ~> function(abstraction(apply(F,tuple(V,given))))
+/*
+ `partial-apply(F, V)` takes a function `F` that takes a pair of arguments,
+ and determines the first argument, returning a function of the second
+ argument.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/index.md b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/index.md
new file mode 100644
index 0000000..a8dc41d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/index.md
@@ -0,0 +1,135 @@
+---
+layout: default
+title: "Functions"
+parent: Abstraction
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Functions.cbs]
+-----------------------------
+
+### Functions
+
+
+
+
+
+Meta-variables
+ T, T′, T1, T2 <: values
+
+
+
+Datatype
+ functions(T,T′) ::= function(A:abstractions(T=>T′))
+
+
+ functions(T, T′) consists of abstractions whose bodies may depend on
+ a given value of type T, and whose executions normally compute values
+ of type T′.
+ function(abstraction(X)) evaluates to a function with dynamic bindings,
+ function(closure(X)) computes a function with static bindings.
+
+
+
+Funcon
+ apply(_:functions(T, T′), _:T) : =>T′
+
+ apply(F, V) applies the function F to the argument value V.
+ This corresponds to call by value; using thunks as argument values
+ corresponds to call by name. Moreover, using tuples as argument values
+ corresponds to application to multiple arguments.
+
+
+
+
+
+
+
+ supply(F, V) determines the argument value of a function application,
+ but returns a thunk that defers executing the body of the function.
+
+
+
+
+
+
+
+ compose(F2, F1) returns the function that applies F1 to its argument,
+ then applies F2 to the result of F1.
+
+
+
+
+
+
+
+
+ uncurry(F) takes a curried function F and returns a function that takes
+ a pair of arguments..
+
+
+
+
+
+
+ curry(F) takes a function F that takes a pair of arguments, and returns
+ the corresponding 'curried' function.
+
+
+
+
+
+
+ partial-apply(F, V) takes a function F that takes a pair of arguments,
+ and determines the first argument, returning a function of the second
+ argument.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Functions.cbs]: Functions.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Abstraction/Functions/Functions.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/apply.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/apply.config
new file mode 100644
index 0000000..fea3d2d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/apply.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ apply(
+ sequential(print 1, function abstraction print given),
+ sequential(print 2 , 3))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3];
+//Also:
+// standard-out: [2, 1, 3];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/compose.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/compose.config
new file mode 100644
index 0000000..e4dc260
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/compose.config
@@ -0,0 +1,20 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ scope(
+ bind-value("f",
+ function abstraction
+ sequential(print given, integer-add(1,given))),
+ print apply(
+ compose(
+ bound-value"f",
+ function abstraction sequential(print 1, 2)),
+ 99))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/curry.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/curry.config
new file mode 100644
index 0000000..9ba8690
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/curry.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ scope(
+ bind-value("f",
+ function abstraction print given),
+ apply(
+ apply(curry(bound-value"f"), 1),
+ 2))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [tuple(1,2)];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/function-abstraction.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/function-abstraction.config
new file mode 100644
index 0000000..a0008dd
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/function-abstraction.config
@@ -0,0 +1,27 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ scope(
+ bind-value("x",99),
+ give(
+ 99,
+ give(
+ function abstraction(
+ sequential(
+ print given,
+ print bound-value"x")),
+ scope(
+ bind-value("x",4),
+ apply(
+ sequential(print 1, given),
+ sequential(print 2, 3))))))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4];
+//Also:
+// standard-out: [2, 1, 3, 4];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/function-closure.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/function-closure.config
new file mode 100644
index 0000000..7d4b62f
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/function-closure.config
@@ -0,0 +1,27 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ scope(
+ bind-value("x",4),
+ give(
+ 99,
+ give(
+ function closure(
+ sequential(
+ print given,
+ print bound-value"x")),
+ scope(
+ bind-value("x",99),
+ apply(
+ sequential(print 1, given),
+ sequential(print 2, 3))))))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3, 4];
+//Also:
+// standard-out: [2, 1, 3, 4];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/partial-apply.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/partial-apply.config
new file mode 100644
index 0000000..39c4c87
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/partial-apply.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ scope(
+ bind-value("f",
+ function abstraction print given),
+ apply(
+ partial-apply(bound-value"f", 1),
+ 2))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [tuple(1,2)];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/supply.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/supply.config
new file mode 100644
index 0000000..078ff1a
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/supply.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ force(
+ supply(
+ sequential(print 1, function abstraction print given),
+ sequential(print 2 , 3)))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2, 3];
+//Also:
+// standard-out: [2, 1, 3];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/uncurry.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/uncurry.config
new file mode 100644
index 0000000..1664459
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Functions/tests/uncurry.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ scope(
+ bind-value("f",
+ uncurry function abstraction
+ sequential(print given,
+ function abstraction print given)),
+ apply(bound-value"f", tuple(1,2)))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 2];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/Generic.cbs b/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/Generic.cbs
new file mode 100644
index 0000000..3710dd5
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/Generic.cbs
@@ -0,0 +1,49 @@
+### Generic abstractions
+
+[
+ Type abstractions
+ Funcon abstraction
+ Funcon closure
+ Funcon enact
+]
+
+
+Meta-variables
+ T <: values
+ T? <: values?
+
+
+Type
+ abstractions(_:computation-types)
+
+
+Funcon
+ abstraction(_:T?=>T) : abstractions(T?=>T)
+/*
+ The funcon `abstraction(X)` forms abstraction values from computations.
+
+ References to bindings of identifiers in `X` are dynamic.
+ The funcon `closure(X)` forms abstractions with static bindings.
+*/
+
+
+Funcon
+ closure(_:T?=>T) : =>abstractions(T?=>T)
+/*
+ `closure(X)` computes a closed abstraction from the computation `X`.
+ In contrast to `abstraction(X)`, references to bindings of identifiers
+ in `X` are static. Moreover, `closure(X)` is not a value constructor,
+ so it cannot be used in pattern terms in rules.
+*/
+Rule
+ environment(Rho) |- closure(X) ---> abstraction(closed(scope(Rho, X)))
+
+
+Funcon
+ enact(_:abstractions(T?=>T)) : T?=>T
+/*
+ `enact(A)` executes the computation of the abstraction `A`,
+ with access to all the current entities.
+*/
+Rule
+ enact(abstraction(X)) ~> X
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/index.md b/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/index.md
new file mode 100644
index 0000000..847d7d7
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/index.md
@@ -0,0 +1,85 @@
+---
+layout: default
+title: "Generic"
+parent: Abstraction
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Generic.cbs]
+-----------------------------
+
+### Generic abstractions
+
+
+
+
+
+
+
+
+
+
+
+
+ The funcon abstraction(X) forms abstraction values from computations.
+
+ References to bindings of identifiers in X are dynamic.
+ The funcon closure(X) forms abstractions with static bindings.
+
+
+
+
+
+ closure(X) computes a closed abstraction from the computation X.
+ In contrast to abstraction(X), references to bindings of identifiers
+ in X are static. Moreover, closure(X) is not a value constructor,
+ so it cannot be used in pattern terms in rules.
+
+
+
+
+
+
+
+ enact(A) executes the computation of the abstraction A,
+ with access to all the current entities.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Generic.cbs]: Generic.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Abstraction/Generic/Generic.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/tests/abstraction.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/tests/abstraction.config
new file mode 100644
index 0000000..0a2bf5a
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/tests/abstraction.config
@@ -0,0 +1,25 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ scope(
+ bind-value("x",99),
+ give(
+ tuple(
+ 99,
+ abstraction(
+ sequential(
+ print first tuple-elements given,
+ print bound-value"x"))),
+ scope(
+ bind-value("x",42),
+ give(
+ tuple(42, second tuple-elements given),
+ enact second tuple-elements given))))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [42, 42];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/tests/closure.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/tests/closure.config
new file mode 100644
index 0000000..09016ed
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Generic/tests/closure.config
@@ -0,0 +1,25 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ scope(
+ bind-value("x",42),
+ give(
+ tuple(
+ 99,
+ closure(
+ sequential(
+ print first tuple-elements given,
+ print bound-value"x"))),
+ scope(
+ bind-value("x",99),
+ give(
+ tuple(42, second tuple-elements given),
+ enact second tuple-elements given))))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [42, 42];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/Patterns.cbs b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/Patterns.cbs
new file mode 100644
index 0000000..741e53b
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/Patterns.cbs
@@ -0,0 +1,224 @@
+### Patterns
+
+[
+ Datatype patterns
+ Funcon pattern
+ Funcon pattern-any
+ Funcon pattern-bind
+ Funcon pattern-type
+ Funcon pattern-else
+ Funcon pattern-unite
+ Funcon match
+ Funcon match-loosely
+ Funcon case-match
+ Funcon case-match-loosely
+ Funcon case-variant-value
+]
+
+/*
+ General patterns are simple patterns or structured patterns.
+ Matching a pattern to a value either computes an environment or fails.
+
+ Simple patterns are constructed from abstractions whose bodies depend on
+ a given value, and whose executions either compute environments or fail.
+
+ Structured patterns are composite values whose components may include
+ simple patterns as well as other values.
+
+ Matching a structured value to a structured pattern is similar to assigning
+ a structured value to a structured variable, with simple pattern components
+ matching component values analogously to simple variable components assigned
+ component values.
+
+ Note that patterns match only values, not (empty or proper) sequences.
+*/
+
+
+Meta-variables
+ T, T' <: values
+
+
+#### Simple patterns
+
+Datatype
+ patterns ::= pattern(_:abstractions(values=>environments))
+/*
+ `patterns` is the type of simple patterns that can match values of a
+ particular type.
+
+ `pattern(abstraction(X))` constructs a pattern with dynamic bindings, and
+ `pattern(closure(X))` computes a pattern with static bindings. However,
+ there is no difference between dynamic and static bindings when the pattern
+ is matched in the same scope where it is constructed.
+*/
+
+
+Funcon
+ pattern-any : =>patterns
+ ~> pattern(abstraction(map( )))
+/*
+ `pattern-any` matches any value, computing the empty environment.
+*/
+
+
+Funcon
+ pattern-bind(I:identifiers) : =>patterns
+ ~> pattern(abstraction(bind-value(I, given)))
+/*
+ `pattern-bind(I)` matches any value, computing the environment binding `I`
+ to that value.
+*/
+
+
+Funcon
+ pattern-type(T) : =>patterns
+ ~> pattern(abstraction(if-true-else(is-in-type(given, T), map( ), fail)))
+/*
+ `pattern-type(T)` matches any value of type `T`, computing the empty
+ environment.
+*/
+
+
+Funcon
+ pattern-else(_:values, _:values) : =>patterns
+Rule
+ pattern-else(P1:values, P2:values)
+ ~> pattern(abstraction(else(match(given, P1), match(given, P2))))
+/*
+ `pattern-else(P1, P2)` matches all values matched by `P1` or by `P2`.
+ If a value matches `P1`, that match gives the computed environment;
+ if a value does not match `P1` but matches `P2`, that match gives
+ the computed environment; otherwise the match fails.
+*/
+
+
+Funcon
+ pattern-unite(_:values, _:values) : =>patterns
+Rule
+ pattern-unite(P1:values, P2:values)
+ ~> pattern(abstraction(collateral(match(given, P1), match(given, P2))))
+/*
+ `pattern-unite(P1, P2)` matches all values matched by both `P1` and `P2`,
+ then uniting the computed environments, which fails if the domains of the
+ environments overlap.
+*/
+
+
+#### Pattern matching
+
+Funcon
+ match(_:values, _:values) : =>environments
+/*
+ `match(V, P)` takes a (potentially structured) value `V` and a
+ (potentially structured) pattern `P`. Provided that the structure and all
+ components of `P` exactly match the structure and corresponding components
+ of `V`, the environments computed by the simple pattern matches are united.
+*/
+Rule
+ match(V:values, pattern(abstraction(X))) ~> give(V, X)
+Rule
+ I2 =/= "pattern"
+ --------------------------------------------
+ match(datatype-value(I1:identifiers, V1*:values*),
+ datatype-value(I2:identifiers, V2*:values*))
+ ~> sequential(
+ check-true(is-equal(I1, I2)),
+ check-true(is-equal(length V1*, length V2*)),
+ collateral(interleave-map(
+ match(tuple-elements(given)),
+ tuple-zip(tuple(V1*), tuple(V2*)))))
+Rule
+ dom(M2) == {}
+ ------------------------------------------------------
+ match(M1:maps(_,_), M2:maps(_,_))
+ ~> if-true-else(is-equal(dom(M1), {}), map( ), fail)
+Rule
+ dom(M2) =/= {}
+ some-element(dom(M2)) ~> K
+ -------------------------------------------------------
+ match(M1:maps(_,_), M2:maps(_,_))
+ ~> if-true-else(
+ is-in-set(K, dom(M1)),
+ collateral(
+ match(map-lookup(M1, K), map-lookup(M2, K)),
+ match(map-delete(M1, {K}), map-delete(M2, {K}))),
+ fail)
+Rule
+ P : ~(datatype-values|maps(_,_))
+ -----------------------------------------------
+ match(V:values, P:values)
+ ~> if-true-else(is-equal(V, P), map( ), fail)
+
+
+Funcon
+ match-loosely(_:values, _:values) : =>environments
+/*
+ `match-loosely(V, P)` takes a (potentially structured) value `V` and a
+ (potentially structured) pattern `P`. Provided that the structure and all
+ components of `P` loosely match the structure and corresponding components
+ of `V`, the environments computed by the simple pattern matches are united.
+*/
+Rule
+ match-loosely(V:values, pattern(abstraction(X))) ~> give(V, X)
+Rule
+ I2 =/= "pattern"
+ ---------------------------------------------------
+ match-loosely(datatype-value(I1:identifiers, V1*:values*),
+ datatype-value(I2:identifiers, V2*:values*))
+ ~> sequential(
+ check-true(is-equal(I1, I2)),
+ check-true(is-equal(length V1*, length V2*)),
+ collateral(interleave-map(
+ match-loosely(tuple-elements(given)),
+ tuple-zip(tuple(V1*), tuple(V2*)))))
+Rule
+ dom(M2) == {}
+ -------------------------------------------------
+ match-loosely(M1:maps(_,_), M2:maps(_,_)) ~> map()
+Rule
+ dom(M2) =/= {}
+ some-element(dom(M2)) ~> K
+ --------------------------------------------------------------
+ match-loosely(M1:maps(_,_), M2:maps(_,_))
+ ~> if-true-else(
+ is-in-set(K, dom(M1)),
+ collateral(
+ match-loosely(map-lookup(M1, K), map-lookup(M2, K)),
+ match-loosely(map-delete(M1, {K}), map-delete(M2, {K}))),
+ fail)
+Rule
+ P : ~(datatype-values|maps(_,_))
+ -------------------------------------------
+ match-loosely(DV:values, P:values)
+ ~> if-true-else(is-equal(DV, P), map( ), fail)
+
+
+Funcon
+ case-match(_:values, _:=>T') : =>T'
+/*
+ `case-match(P, X)` matches `P` exactly to the given value.
+ If the match succeeds, the computed bindings have scope `X`.
+*/
+Rule
+ case-match(P:values, X) ~> scope(match(given, P), X)
+
+
+Funcon
+ case-match-loosely(_:values, _:=>T') : =>T'
+/*
+ `case-match(P, X)` matches `P` loosely to the given value.
+ If the match succeeds, the computed bindings have scope `X`.
+*/
+Rule
+ case-match-loosely(P:values, X) ~> scope(match-loosely(given, P), X)
+
+
+Funcon
+ case-variant-value(_:identifiers) : =>values
+/*
+ `case-variant-value(I)` matches values of variant `I`, then
+ giving the value contained in the variant.
+*/
+Rule
+ case-variant-value(I:identifiers) ~>
+ case-match(variant(I, pattern-any), variant-value(given))
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/index.md b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/index.md
new file mode 100644
index 0000000..c2fa4a4
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/index.md
@@ -0,0 +1,267 @@
+---
+layout: default
+title: "Patterns"
+parent: Abstraction
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Patterns.cbs]
+-----------------------------
+
+### Patterns
+
+
+
+
+
+ General patterns are simple patterns or structured patterns.
+ Matching a pattern to a value either computes an environment or fails.
+
+ Simple patterns are constructed from abstractions whose bodies depend on
+ a given value, and whose executions either compute environments or fail.
+
+ Structured patterns are composite values whose components may include
+ simple patterns as well as other values.
+
+ Matching a structured value to a structured pattern is similar to assigning
+ a structured value to a structured variable, with simple pattern components
+ matching component values analogously to simple variable components assigned
+ component values.
+
+ Note that patterns match only values, not (empty or proper) sequences.
+
+
+
+Meta-variables
+ T, T′ <: values
+
+
+
+#### Simple patterns
+
+
+
+
+ patterns is the type of simple patterns that can match values of a
+ particular type.
+
+ pattern(abstraction(X)) constructs a pattern with dynamic bindings, and
+ pattern(closure(X)) computes a pattern with static bindings. However,
+ there is no difference between dynamic and static bindings when the pattern
+ is matched in the same scope where it is constructed.
+
+
+
+
+
+
+ pattern-any matches any value, computing the empty environment.
+
+
+
+
+
+
+ pattern-bind(I) matches any value, computing the environment binding I
+ to that value.
+
+
+
+
+
+
+ pattern-type(T) matches any value of type T, computing the empty
+ environment.
+
+
+
+
+ pattern-else(P1, P2) matches all values matched by P1 or by P2.
+ If a value matches P1, that match gives the computed environment;
+ if a value does not match P1 but matches P2, that match gives
+ the computed environment; otherwise the match fails.
+
+
+
+
+ pattern-unite(P1, P2) matches all values matched by both P1 and P2,
+ then uniting the computed environments, which fails if the domains of the
+ environments overlap.
+
+
+
+#### Pattern matching
+
+
+
+ match(V, P) takes a (potentially structured) value V and a
+ (potentially structured) pattern P. Provided that the structure and all
+ components of P exactly match the structure and corresponding components
+ of V, the environments computed by the simple pattern matches are united.
+
+Rule
+ match(V:values, pattern(abstraction(X))) ~> give(V, X)
+Rule
+ I2 =/= "pattern"
+ --------------------------------------------
+ match(datatype-value(I1:identifiers, V1*:values*),
+ datatype-value(I2:identifiers, V2*:values*))
+ ~> sequential(
+ check-true(is-equal(I1, I2)),
+ check-true(is-equal(length V1*, length V2*)),
+ collateral(interleave-map(
+ match(tuple-elements(given)),
+ tuple-zip(tuple(V1*), tuple(V2*)))))
+Rule
+ dom(M2) == {}
+ ------------------------------------------------------
+ match(M1:maps(_,_), M2:maps(_,_))
+ ~> if-true-else(is-equal(dom(M1), {}), map( ), fail)
+Rule
+ dom(M2) =/= {}
+ some-element(dom(M2)) ~> K
+ -------------------------------------------------------
+ match(M1:maps(_,_), M2:maps(_,_))
+ ~> if-true-else(
+ is-in-set(K, dom(M1)),
+ collateral(
+ match(map-lookup(M1, K), map-lookup(M2, K)),
+ match(map-delete(M1, {K}), map-delete(M2, {K}))),
+ fail)
+Rule
+ P : ~(datatype-values|maps(_,_))
+ -----------------------------------------------
+ match(V:values, P:values)
+ ~> if-true-else(is-equal(V, P), map( ), fail)
+
+
+
+
+
+ match-loosely(V, P) takes a (potentially structured) value V and a
+ (potentially structured) pattern P. Provided that the structure and all
+ components of P loosely match the structure and corresponding components
+ of V, the environments computed by the simple pattern matches are united.
+
+Rule
+ match-loosely(V:values, pattern(abstraction(X))) ~> give(V, X)
+Rule
+ I2 =/= "pattern"
+ ---------------------------------------------------
+ match-loosely(datatype-value(I1:identifiers, V1*:values*),
+ datatype-value(I2:identifiers, V2*:values*))
+ ~> sequential(
+ check-true(is-equal(I1, I2)),
+ check-true(is-equal(length V1*, length V2*)),
+ collateral(interleave-map(
+ match-loosely(tuple-elements(given)),
+ tuple-zip(tuple(V1*), tuple(V2*)))))
+Rule
+ dom(M2) == {}
+ -------------------------------------------------
+ match-loosely(M1:maps(_,_), M2:maps(_,_)) ~> map()
+Rule
+ dom(M2) =/= {}
+ some-element(dom(M2)) ~> K
+ --------------------------------------------------------------
+ match-loosely(M1:maps(_,_), M2:maps(_,_))
+ ~> if-true-else(
+ is-in-set(K, dom(M1)),
+ collateral(
+ match-loosely(map-lookup(M1, K), map-lookup(M2, K)),
+ match-loosely(map-delete(M1, {K}), map-delete(M2, {K}))),
+ fail)
+Rule
+ P : ~(datatype-values|maps(_,_))
+ -------------------------------------------
+ match-loosely(DV:values, P:values)
+ ~> if-true-else(is-equal(DV, P), map( ), fail)
+
+
+
+Funcon
+ case-match(_:values, _:=>T′) : =>T′
+
+ case-match(P, X) matches P exactly to the given value.
+ If the match succeeds, the computed bindings have scope X.
+
+
+
+
+
+Funcon
+ case-match-loosely(_:values, _:=>T′) : =>T′
+
+ case-match(P, X) matches P loosely to the given value.
+ If the match succeeds, the computed bindings have scope X.
+
+
+
+
+
+
+
+ case-variant-value(I) matches values of variant I, then
+ giving the value contained in the variant.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Patterns.cbs]: Patterns.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Abstraction/Patterns/Patterns.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/case-match-loosely.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/case-match-loosely.config
new file mode 100644
index 0000000..57045a2
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/case-match-loosely.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ give({"a"|->false,"b"|->true},
+ case-match-loosely(
+ {"b"|->pattern-bind"d"},
+ bound-value"d"))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/case-match.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/case-match.config
new file mode 100644
index 0000000..00cba71
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/case-match.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ give({"a"|->false,"b"|->true},
+ case-match(
+ {"b"|->pattern-bind"d","a"|->pattern-bind"c"},
+ bound-value"d"))
+ ;
+}
+
+tests {
+ result-term: true;
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/case-variant-value.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/case-variant-value.config
new file mode 100644
index 0000000..7e37dfc
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/case-variant-value.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ give(
+ variant("a",true),
+ sequential (
+ print case-variant-value("a"),
+ else(
+ effect case-variant-value"b",
+ print"OK")))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [true, "OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/match-loosely.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/match-loosely.config
new file mode 100644
index 0000000..b1fa0bf
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/match-loosely.config
@@ -0,0 +1,36 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ sequential(
+ check-true is-equal(
+ match-loosely([],[]), map()),
+ check-true is-equal(
+ match-loosely([false],[pattern-bind"b"]),
+ {"b"|->false}),
+ check-true is-equal(
+ match-loosely([false,true],[pattern-bind"a",pattern-bind"b"]),
+ {"a"|->false,"b"|->true}),
+ check-true is-equal(
+ match-loosely({"a"|->false},map()), map()),
+ check-true is-equal(
+ match-loosely({"a"|->false,"b"|->true},{"b"|->pattern-bind"d"}),
+ {"d"|->true}),
+ check-true is-equal(
+ match-loosely(true,true), map()),
+ else(
+ effect match-loosely([],[false]),
+ effect match-loosely([false],[false,false]),
+ effect match-loosely([false,true],[pattern-bind"a",pattern-bind"a"]),
+ effect match-loosely(map(),{"a"|->true}),
+ effect match-loosely({"a"|->true},{"a"|->false}),
+ effect match-loosely({"b"|->true},{"b"|->pattern-any,"c"|->pattern-any}),
+ effect match-loosely(false,true),
+ print"OK"))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/match.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/match.config
new file mode 100644
index 0000000..e9a4473
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/match.config
@@ -0,0 +1,35 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ sequential(
+ check-true is-equal(
+ match([],[]), map()),
+ check-true is-equal(
+ match([false],[pattern-bind"b"]),
+ {"b"|->false}),
+ check-true is-equal(
+ match([false,true],[pattern-bind"a",pattern-bind"b"]),
+ {"a"|->false,"b"|->true}),
+ check-true is-equal(
+ match(map(),map()), map()),
+ check-true is-equal(
+ match({"a"|->false,"b"|->true},{"b"|->pattern-bind"d","a"|->pattern-bind"c"}),
+ {"c"|->false,"d"|->true}),
+ check-true is-equal(
+ match(true,true), map()),
+ else(
+ effect match([],[false]),
+ effect match([false],[false,false]),
+ effect match([false,true],[pattern-bind"a",pattern-bind"a"]),
+ effect match(map(),{"a"|->true}),
+ effect match({"b"|->true},{"b"|->pattern-any,"c"|->pattern-any}),
+ effect match(false,true),
+ print"OK"))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-any.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-any.config
new file mode 100644
index 0000000..4af03e7
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-any.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ sequential(
+ check-true is-equal(match(not true,pattern-any), map()),
+ check-true is-equal(match([42],pattern-any), map()),
+ check-true is-equal(match(abstraction null-value,pattern-any), map()),
+ check-true is-equal(match(list(42),pattern-any), map()),
+ check-true is-equal(match(tuple(42),pattern-any), map()),
+ print"OK")
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-bind.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-bind.config
new file mode 100644
index 0000000..045a6d1
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-bind.config
@@ -0,0 +1,19 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ sequential(
+ check-true is-equal(match(false,pattern-bind"it"), {"it"|->false}),
+ check-true is-equal(match([42],pattern-bind"it"), {"it"|->[42]}),
+ check-true is-equal(dom match(abstraction null-value,pattern-bind"it"), {"it"}),
+ check-true is-equal(match(abstraction 12,abstraction(pattern-bind "it")), {"it" |-> 12}),
+ check-true is-equal(match(vector(42),pattern-bind"it"), {"it"|->vector(42)}),
+ check-true is-equal(match(tuple(42),pattern-bind"it"), {"it"|->tuple(42)}),
+ print"OK")
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-else.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-else.config
new file mode 100644
index 0000000..828e1ba
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-else.config
@@ -0,0 +1,19 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ sequential(
+ check-true is-equal(
+ match(false,pattern-else(pattern-bind"a",pattern-bind"b")), {"a"|->false}),
+ check-true is-equal(
+ match(false,pattern-else(pattern-type integers,pattern-bind"b")), {"b"|->false}),
+ else(
+ effect match(false,pattern-else(pattern-type integers,pattern-type atoms)),
+ print"OK"))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-type.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-type.config
new file mode 100644
index 0000000..496698c
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-type.config
@@ -0,0 +1,24 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ sequential(
+ check-true is-equal(match(false,pattern-type booleans), map()),
+ check-true is-equal(match([42],pattern-type lists(integers)), map()),
+ check-true is-equal(match(abstraction null-value,pattern-type abstractions(values=>values)), map()),
+ check-true is-equal(match(list(true),pattern-type lists(booleans)), map()),
+ check-true is-equal(match(tuple(42,true),pattern-type tuples(integers,booleans)), map()),
+ effect else(
+ match(true,pattern-type integers),
+ match([42],pattern-type lists(booleans)),
+ match(abstraction null-value,pattern-type atoms),
+ match(list(true),pattern-type lists(integers)),
+ match(tuple(42,true),pattern-type tuples(booleans,integers)),
+ print"OK"))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-unite.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-unite.config
new file mode 100644
index 0000000..d1e23f4
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Patterns/tests/pattern-unite.config
@@ -0,0 +1,19 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ sequential(
+ check-true is-equal(
+ match(false,pattern-unite(pattern-bind"a",pattern-bind"b")), {"a"|->false,"b"|->false}),
+ check-true is-equal(
+ match(false,pattern-unite(pattern-type booleans,pattern-bind"b")), {"b"|->false}),
+ else(
+ effect match(false,pattern-unite(pattern-bind"a",pattern-bind"a")),
+ print"OK"))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/Thunks.cbs b/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/Thunks.cbs
new file mode 100644
index 0000000..95a6b25
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/Thunks.cbs
@@ -0,0 +1,30 @@
+### Thunks
+
+[
+ Datatype thunks
+ Funcon thunk
+ Funcon force
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ thunks(T) ::= thunk(_:abstractions(()=>T))
+/*
+ `thunks(T)` consists of abstractions whose bodies do not depend on
+ a given value, and whose executions normally compute values of type `T`.
+ `thunk(abstraction(X))` evaluates to a thunk with dynamic bindings,
+ `thunk(closure(X))` computes a thunk with static bindings.
+*/
+
+
+Funcon
+ force(_:thunks(T)) : =>T
+/*
+ `force(H)` enacts the abstraction of the thunk `H`.
+*/
+Rule
+ force(thunk(abstraction(X))) ~> no-given(X)
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/index.md b/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/index.md
new file mode 100644
index 0000000..69830e0
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/index.md
@@ -0,0 +1,68 @@
+---
+layout: default
+title: "Thunks"
+parent: Abstraction
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Thunks.cbs]
+-----------------------------
+
+### Thunks
+
+
+
+
+
+
+
+
+
+
+
+
+ thunks(T) consists of abstractions whose bodies do not depend on
+ a given value, and whose executions normally compute values of type T.
+ thunk(abstraction(X)) evaluates to a thunk with dynamic bindings,
+ thunk(closure(X)) computes a thunk with static bindings.
+
+
+
+Funcon
+ force(_:thunks(T)) : =>T
+
+ force(H) enacts the abstraction of the thunk H.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Thunks.cbs]: Thunks.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Abstraction/Thunks/Thunks.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/tests/thunk-abstraction.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/tests/thunk-abstraction.config
new file mode 100644
index 0000000..0650de8
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/tests/thunk-abstraction.config
@@ -0,0 +1,25 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ scope(
+ bind-value("x",99),
+ give(
+ tuple(
+ 99,
+ thunk abstraction(
+ sequential(
+ print bound-value"x",
+ print first tuple-elements bound-value"tup"))),
+ scope(
+ collateral(
+ bind-value("x",42),
+ bind-value("tup",tuple(42, second tuple-elements given))),
+ force second tuple-elements given)))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [42, 42];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/tests/thunk-closure.config b/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/tests/thunk-closure.config
new file mode 100644
index 0000000..4eee91c
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Abstraction/Thunks/tests/thunk-closure.config
@@ -0,0 +1,27 @@
+general {
+ funcon-term:
+ initialise-giving
+ initialise-binding
+ scope(
+ bind-value("x",99),
+ give(
+ tuple(
+ 99,
+ thunk closure(
+ sequential(
+ print bound-value"x",
+ print first tuple-elements bound-value"tup"))),
+ scope(
+ collateral(
+ bind-value("x",42),
+ bind-value("tup",tuple(42, second tuple-elements given))),
+ else(
+ force second tuple-elements given,
+ print 77))))
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [99, 77];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Bits/Bits.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Bits/Bits.cbs
new file mode 100644
index 0000000..2ce4ec9
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Bits/Bits.cbs
@@ -0,0 +1,110 @@
+### Bits and bit vectors
+
+[
+ Type bits
+ Datatype bit-vectors
+ Funcon bit-vector
+ Type bytes Alias octets
+ Funcon bit-vector-not
+ Funcon bit-vector-and
+ Funcon bit-vector-or
+ Funcon bit-vector-xor
+ Funcon bit-vector-shift-left
+ Funcon bit-vector-logical-shift-right
+ Funcon bit-vector-arithmetic-shift-right
+ Funcon integer-to-bit-vector
+ Funcon bit-vector-to-integer
+ Funcon bit-vector-to-natural
+ Funcon unsigned-bit-vector-maximum
+ Funcon signed-bit-vector-maximum
+ Funcon signed-bit-vector-minimum
+ Funcon is-in-signed-bit-vector
+ Funcon is-in-unsigned-bit-vector
+]
+
+
+#### Bits
+
+Type
+ bits ~> booleans
+/*
+ `false` represents the absence of a bit, `true` its presence.
+*/
+
+
+#### Bit vectors
+
+Datatype
+ bit-vectors(N:natural-numbers) ::= bit-vector(_:bits^N)
+
+Type
+ bytes ~> bit-vectors(8)
+Alias
+ octets = bytes
+
+Meta-variables
+ BT <: bit-vectors(_)
+
+Built-in Funcon
+ bit-vector-not(_:BT) : =>BT
+Built-in Funcon
+ bit-vector-and(_:BT, _:BT) : =>BT
+Built-in Funcon
+ bit-vector-or(_:BT, _:BT) : =>BT
+Built-in Funcon
+ bit-vector-xor(_:BT, _:BT) : =>BT
+/*
+ The above four funcons are the natural extensions of funcons from `booleans`
+ to `bit-vectors(N)` of the same length.
+*/
+
+Built-in Funcon
+ bit-vector-shift-left(_:BT, _:natural-numbers) : BT
+Built-in Funcon
+ bit-vector-logical-shift-right(_:BT, _:natural-numbers) : BT
+Built-in Funcon
+ bit-vector-arithmetic-shift-right(_:BT, _:natural-numbers) : BT
+
+Built-in Funcon
+ integer-to-bit-vector(_:integers, N:natural-numbers) : bit-vectors(N)
+/*
+ `integer-to-bit-vector(M, N)` converts an integer `M` to a bit-vector of
+ length `N`, using Two's Complement representation. If the integer is out of
+ range of the representation, it will wrap around (modulo 2^N).
+*/
+
+Built-in Funcon
+ bit-vector-to-integer(_:BT) : =>integers
+/*
+ `bit-vector-to-integer(B)` interprets a bit-vector `BV` as an integer
+ in Two's Complement representation.
+*/
+
+Built-in Funcon
+ bit-vector-to-natural(_:BT) : =>natural-numbers
+/*
+ `bit-vector-to-natural(BV)` interprets a bit-vector `BV` as a natural number
+ in unsigned representation.
+*/
+
+Funcon
+ unsigned-bit-vector-maximum(N:natural-numbers) : =>natural-numbers
+ ~> integer-subtract(integer-power(2, N), 1)
+
+Funcon
+ signed-bit-vector-maximum(N:natural-numbers) : =>integers
+ ~> integer-subtract(integer-power(2, integer-subtract(N, 1)), 1)
+
+Funcon
+ signed-bit-vector-minimum(N:natural-numbers) : =>integers
+ ~> integer-negate(integer-power(2, integer-subtract(N, 1)))
+
+Funcon
+ is-in-signed-bit-vector(M:integers, N:natural-numbers) : =>booleans
+ ~> and(integer-is-less-or-equal(M, signed-bit-vector-maximum(N)),
+ integer-is-greater-or-equal(M, signed-bit-vector-minimum(N)))
+
+Funcon
+ is-in-unsigned-bit-vector(M:integers, N:natural-numbers) : =>booleans
+ ~> and(integer-is-less-or-equal(M, unsigned-bit-vector-maximum(N)),
+ integer-is-greater-or-equal(M, 0))
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Bits/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Bits/index.md
new file mode 100644
index 0000000..f6ad503
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Bits/index.md
@@ -0,0 +1,152 @@
+---
+layout: default
+title: "Bits"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Bits.cbs]
+-----------------------------
+
+### Bits and bit vectors
+
+
+
+
+
+#### Bits
+
+
+
+
+ false represents the absence of a bit, true its presence.
+
+
+
+#### Bit vectors
+
+
+
+
+
+
+
+
+
+Built-in Funcon
+ bit-vector-not(_:BT) : =>BT
+Built-in Funcon
+ bit-vector-and(_:BT, _:BT) : =>BT
+Built-in Funcon
+ bit-vector-or(_:BT, _:BT) : =>BT
+Built-in Funcon
+ bit-vector-xor(_:BT, _:BT) : =>BT
+
+ The above four funcons are the natural extensions of funcons from booleans
+ to bit-vectors(N) of the same length.
+
+
+
+Built-in Funcon
+ bit-vector-logical-shift-right(_:BT, _:natural-numbers) : BT
+Built-in Funcon
+ bit-vector-arithmetic-shift-right(_:BT, _:natural-numbers) : BT
+
+
+ integer-to-bit-vector(M, N) converts an integer M to a bit-vector of
+ length N, using Two's Complement representation. If the integer is out of
+ range of the representation, it will wrap around (modulo 2^N).
+
+
+Built-in Funcon
+ bit-vector-to-integer(_:BT) : =>integers
+
+ bit-vector-to-integer(B) interprets a bit-vector BV as an integer
+ in Two's Complement representation.
+
+
+
+
+ bit-vector-to-natural(BV) interprets a bit-vector BV as a natural number
+ in unsigned representation.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Bits.cbs]: Bits.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Bits/Bits.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Classes/Classes.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/Classes.cbs
new file mode 100644
index 0000000..10b834e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/Classes.cbs
@@ -0,0 +1,86 @@
+### Classes
+
+[
+ Datatype classes
+ Funcon class
+ Funcon class-instantiator
+ Funcon class-feature-map
+ Funcon class-superclass-name-sequence
+ Funcon class-name-tree
+ Funcon is-subclass-name
+ Funcon class-name-single-inheritance-feature-map
+]
+
+
+Datatype
+ classes ::=
+ class(_:thunks(references(objects)), _:environments, _:identifiers*)
+/*
+ `class(Thunk, Env, C*)` is a class with:
+ * a thunk `Thunk` for instantiating the class,
+ * an environment `Env` with the features declared by the class, and
+ * a sequence `C*` of names of direct superclasses.
+ `class(Thunk, Env)` is a base class, having no superclasses.
+ `class(Thunk, Env, C)` is a class with a single superclass.
+
+ Class instantiation forces its thunk to compute a reference to an object.
+
+ Features are inherited from superclasses. When features with the same name
+ are declared in simultaneously inherited classes, the order of the superclass
+ identifiers in `C*` may affect resolution of references to features.
+ Overloading of feature names is supported by using type maps as features.
+
+ The class table is represented by binding class names to classes.
+ The class superclass hierarchy is assumed to be acyclic.
+*/
+
+Funcon
+ class-instantiator(_:classes) : =>thunks(references(objects))
+Rule
+ class-instantiator
+ class(Thunk:thunks(_), Envs:environments, C*:identifiers*) ~> Thunk
+
+Funcon
+ class-feature-map(_:classes) : =>environments
+Rule
+ class-feature-map
+ class(Thunk:thunks(_), Env:environments, C*:identifiers*) ~> Env
+
+Funcon
+ class-superclass-name-sequence(_:classes) : =>identifiers*
+Rule
+ class-superclass-name-sequence
+ class(Thunk:thunks(_), Env:environments, C*:identifiers*) ~> C*
+
+Funcon
+ class-name-tree(_:identifiers) : =>trees(identifiers)
+/*
+ `class-name-tree C` forms a tree where the branches are the class name
+ trees for the superclasses of `C`.
+*/
+Rule
+ class-name-tree(C : identifiers)
+ ~> tree(C,
+ interleave-map(
+ class-name-tree given,
+ class-superclass-name-sequence bound-value C))
+
+
+Funcon
+ is-subclass-name(C:identifiers, C':identifiers) : =>booleans
+ ~> is-in-set(C, { forest-value-sequence class-name-tree C' })
+/*
+ The result of `is-subclass-name(C, C')` does not depend on the order of
+ the names in `forest-value-sequence class-name-tree C'`.
+*/
+
+
+Funcon
+ class-name-single-inheritance-feature-map(C:identifiers) : =>environments
+ ~> map-override interleave-map(
+ class-feature-map bound-value given,
+ single-branching-sequence class-name-tree C)
+/*
+ For multiple inheritance, different resolution orders can be specified
+ by using different linearisations of the class name tree.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Classes/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/index.md
new file mode 100644
index 0000000..78054d5
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/index.md
@@ -0,0 +1,125 @@
+---
+layout: default
+title: "Classes"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Classes.cbs]
+-----------------------------
+
+### Classes
+
+
+
+
+
+
+
+
+ class(Thunk, Env, C*) is a class with:
+ * a thunk Thunk for instantiating the class,
+ * an environment Env with the features declared by the class, and
+ * a sequence C* of names of direct superclasses.
+ class(Thunk, Env) is a base class, having no superclasses.
+ class(Thunk, Env, C) is a class with a single superclass.
+
+ Class instantiation forces its thunk to compute a reference to an object.
+
+ Features are inherited from superclasses. When features with the same name
+ are declared in simultaneously inherited classes, the order of the superclass
+ identifiers in C* may affect resolution of references to features.
+ Overloading of feature names is supported by using type maps as features.
+
+ The class table is represented by binding class names to classes.
+ The class superclass hierarchy is assumed to be acyclic.
+
+
+
+
+
+
+
+
+
+
+ class-name-tree C forms a tree where the branches are the class name
+ trees for the superclasses of C.
+
+
+
+
+
+
+
+
+ The result of is-subclass-name(C, C′) does not depend on the order of
+ the names in forest-value-sequence class-name-tree C′.
+
+
+
+
+
+
+ For multiple inheritance, different resolution orders can be specified
+ by using different linearisations of the class name tree.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Classes.cbs]: Classes.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Classes/Classes.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-feature-map.config b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-feature-map.config
new file mode 100644
index 0000000..7d024d4
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-feature-map.config
@@ -0,0 +1,120 @@
+//[https://en.wikipedia.org/wiki/C3_linearization]:
+//class O
+//class A extends O
+//class B extends O
+//class C extends O
+//class D extends O
+//class E extends O
+//class K1 extends A, B, C
+//class K2 extends D, B, E
+//class K3 extends D, A
+//class Z extends K1, K2, K3
+
+
+general {
+ funcon-term:
+ initialise-giving initialise-generating initialise-binding finalise-failing
+ scope(collateral(
+ {"O" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"O",map()),
+ map())}
+ ,
+ {"A" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"A",map(),
+ object(fresh-atom,"O",map())),
+ {"a" |-> 1}, "O")}
+ ,
+ {"B" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"B",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"C" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"C",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"D" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"D",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"E" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"K1" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ {"k1" |-> 1, "a" |-> 2} , "A", "B", "C")}
+ ,
+ {"K2" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "B", "E")}
+ ,
+ {"K3" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "A")}
+ ,
+ {"Z" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"Z",map(),
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())))),
+ map(), "K1", "K2", "K3")}
+ ),
+ sequential(
+ print class-feature-map bound-value "O",
+ print class-feature-map bound-value "A",
+ print class-feature-map bound-value "K1"
+ )
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ map()
+ ,
+ {"a" |-> 1 }
+ ,
+ {"k1" |-> 1, "a" |-> 2}
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-instantiator.config b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-instantiator.config
new file mode 100644
index 0000000..268fc7b
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-instantiator.config
@@ -0,0 +1,127 @@
+//[https://en.wikipedia.org/wiki/C3_linearization]:
+//class O
+//class A extends O
+//class B extends O
+//class C extends O
+//class D extends O
+//class E extends O
+//class K1 extends A, B, C
+//class K2 extends D, B, E
+//class K3 extends D, A
+//class Z extends K1, K2, K3
+
+
+general {
+ funcon-term:
+ initialise-giving initialise-generating initialise-binding finalise-failing
+ scope(collateral(
+ {"O" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"O",map()),
+ map())}
+ ,
+ {"A" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"A",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"B" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"B",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"C" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"C",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"D" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"D",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"E" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"K1" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ map(), "A", "B", "C")}
+ ,
+ {"K2" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "B", "E")}
+ ,
+ {"K3" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "A")}
+ ,
+ {"Z" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"Z",map(),
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())))),
+ map(), "K1", "K2", "K3")}
+ ),
+ sequential(
+ print class-instantiator bound-value "O",
+ print class-instantiator bound-value "A",
+ print class-instantiator bound-value "K1"
+ )
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ thunk abstraction reference
+ object(fresh-atom,"O",map())
+ ,
+ thunk abstraction reference
+ object(fresh-atom,"A",map(),
+ object(fresh-atom,"O",map()))
+ ,
+ thunk abstraction reference
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map())))
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-name-single-inheritance-feature-map.config b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-name-single-inheritance-feature-map.config
new file mode 100644
index 0000000..7fdac61
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-name-single-inheritance-feature-map.config
@@ -0,0 +1,127 @@
+//[https://en.wikipedia.org/wiki/C3_linearization]:
+//class O
+//class A extends O
+//class B extends O
+//class C extends O
+//class D extends O
+//class E extends O
+//class K1 extends A, B, C
+//class K2 extends D, B, E
+//class K3 extends D, A
+//class Z extends K1, K2, K3
+
+
+general {
+ funcon-term:
+ initialise-giving initialise-generating initialise-binding finalise-failing
+ scope(collateral(
+ {"O" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"O",map()),
+ map())}
+ ,
+ {"A" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"A",map(),
+ object(fresh-atom,"O",map())),
+ {"a" |-> 1}, "O")}
+ ,
+ {"B" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"B",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"C" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"C",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"D" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"D",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"E" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"K1" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ {"k1" |-> 1, "a" |-> 2} , "A", "B", "C")}
+ ,
+ {"K2" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "B", "E")}
+ ,
+ {"K3" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "A")}
+ ,
+ {"K4" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map()))),
+ {"k4" |-> 1, "a" |-> 2}, "A")}
+ ,
+ {"Z" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"Z",map(),
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())))),
+ map(), "K1", "K2", "K3")}
+ ),
+ sequential(
+ print class-name-single-inheritance-feature-map "O",
+ print class-name-single-inheritance-feature-map "A",
+ print class-name-single-inheritance-feature-map "K4"
+ )
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ map()
+ ,
+ {"a" |-> 1 }
+ ,
+ {"k4" |-> 1, "a" |-> 2}
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-name-tree.config b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-name-tree.config
new file mode 100644
index 0000000..28c9006
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-name-tree.config
@@ -0,0 +1,129 @@
+//[https://en.wikipedia.org/wiki/C3_linearization]:
+//class O
+//class A extends O
+//class B extends O
+//class C extends O
+//class D extends O
+//class E extends O
+//class K1 extends A, B, C
+//class K2 extends D, B, E
+//class K3 extends D, A
+//class Z extends K1, K2, K3
+
+
+general {
+ funcon-term:
+ initialise-giving initialise-generating initialise-binding finalise-failing
+ scope(collateral(
+ {"O" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"O",map()),
+ map())}
+ ,
+ {"A" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"A",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"B" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"B",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"C" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"C",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"D" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"D",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"E" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"K1" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ map(), "A", "B", "C")}
+ ,
+ {"K2" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "B", "E")}
+ ,
+ {"K3" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "A")}
+ ,
+ {"Z" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"Z",map(),
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())))),
+ map(), "K1", "K2", "K3")}
+ ),
+ sequential(
+ print class-name-tree "O",
+ print class-name-tree "A",
+ print class-name-tree "K1",
+ print class-name-tree "Z"
+ )
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ tree("O")
+ ,
+ tree("A", tree("O"))
+ ,
+ tree("K1", tree("A", tree("O")), tree("B", tree("O")), tree("C", tree("O")))
+ ,
+ tree("Z",
+ tree("K1", tree("A", tree("O")), tree("B", tree("O")), tree("C", tree("O")))
+ ,
+ tree("K2", tree("D", tree("O")), tree("B", tree("O")), tree("E", tree("O")))
+ ,
+ tree("K3", tree("D", tree("O")), tree("A", tree("O")))
+ )
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-superclass-name-sequence.config b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-superclass-name-sequence.config
new file mode 100644
index 0000000..9cd2cc0
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class-superclass-name-sequence.config
@@ -0,0 +1,120 @@
+//[https://en.wikipedia.org/wiki/C3_linearization]:
+//class O
+//class A extends O
+//class B extends O
+//class C extends O
+//class D extends O
+//class E extends O
+//class K1 extends A, B, C
+//class K2 extends D, B, E
+//class K3 extends D, A
+//class Z extends K1, K2, K3
+
+
+general {
+ funcon-term:
+ initialise-giving initialise-generating initialise-binding finalise-failing
+ scope(collateral(
+ {"O" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"O",map()),
+ map())}
+ ,
+ {"A" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"A",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"B" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"B",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"C" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"C",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"D" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"D",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"E" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"K1" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ map(), "A", "B", "C")}
+ ,
+ {"K2" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "B", "E")}
+ ,
+ {"K3" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "A")}
+ ,
+ {"Z" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"Z",map(),
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())))),
+ map(), "K1", "K2", "K3")}
+ ),
+ sequential(
+ print [class-superclass-name-sequence bound-value "O"],
+ print [class-superclass-name-sequence bound-value "A"],
+ print [class-superclass-name-sequence bound-value "K1"]
+ )
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ []
+ ,
+ ["O"]
+ ,
+ ["A", "B", "C"]
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class.config b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class.config
new file mode 100644
index 0000000..fb01928
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/class.config
@@ -0,0 +1,142 @@
+//[https://en.wikipedia.org/wiki/C3_linearization]:
+//class O
+//class A extends O
+//class B extends O
+//class C extends O
+//class D extends O
+//class E extends O
+//class K1 extends A, B, C
+//class K2 extends D, B, E
+//class K3 extends D, A
+//class Z extends K1, K2, K3
+
+
+general {
+ funcon-term:
+ initialise-giving initialise-generating initialise-binding finalise-failing
+ scope(collateral(
+ {"O" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"O",map()),
+ map())}
+ ,
+ {"A" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"A",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"B" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"B",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"C" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"C",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"D" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"D",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"E" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"K1" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ map(), "A", "B", "C")}
+ ,
+ {"K2" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "B", "E")}
+ ,
+ {"K3" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "A")}
+ ,
+ {"Z" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"Z",map(),
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())))),
+ map(), "K1", "K2", "K3")}
+ ),
+ sequential(
+ print bound-value "O",
+ print bound-value "A",
+ print bound-value "K1",
+ print bound-value "Z"
+ )
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ class(thunk abstraction reference object(fresh-atom,"O",map()), map())
+ ,
+ class(thunk abstraction reference
+ object(fresh-atom,"A",map(), object(fresh-atom,"O",map())), map(), "O")
+ ,
+ class(thunk abstraction reference
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ map(), "A", "B", "C")
+ ,
+ class(thunk abstraction reference
+ object(fresh-atom,"Z",map(),
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())))),
+ map(), "K1", "K2", "K3")
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/is-subclass-name.config b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/is-subclass-name.config
new file mode 100644
index 0000000..251f810
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Classes/tests/is-subclass-name.config
@@ -0,0 +1,124 @@
+//[https://en.wikipedia.org/wiki/C3_linearization]:
+//class O
+//class A extends O
+//class B extends O
+//class C extends O
+//class D extends O
+//class E extends O
+//class K1 extends A, B, C
+//class K2 extends D, B, E
+//class K3 extends D, A
+//class Z extends K1, K2, K3
+
+
+general {
+ funcon-term:
+ initialise-giving initialise-generating initialise-binding finalise-failing
+ scope(collateral(
+ {"O" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"O",map()),
+ map())}
+ ,
+ {"A" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"A",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"B" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"B",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"C" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"C",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"D" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"D",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"E" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"O",map())),
+ map(), "O")}
+ ,
+ {"K1" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ map(), "A", "B", "C")}
+ ,
+ {"K2" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "B", "E")}
+ ,
+ {"K3" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map()))),
+ map(), "D", "A")}
+ ,
+ {"Z" |->
+ class(
+ thunk abstraction reference
+ object(fresh-atom,"Z",map(),
+ object(fresh-atom,"K1",map(),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"C",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K2",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"B",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"E",map(),object(fresh-atom,"O",map()))),
+ object(fresh-atom,"K3",map(),
+ object(fresh-atom,"D",map(),object(fresh-atom,"O",map())),
+ object(fresh-atom,"A",map(),object(fresh-atom,"O",map())))),
+ map(), "K1", "K2", "K3")}
+ ),
+ sequential(
+ print {forest-value-sequence class-name-tree "O"},
+ print {forest-value-sequence class-name-tree "A"},
+ print {forest-value-sequence class-name-tree "K1"},
+ print {forest-value-sequence class-name-tree "K2"},
+ print {forest-value-sequence class-name-tree "K3"},
+ print {forest-value-sequence class-name-tree "Z"}
+ )
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ {"O"},
+ {"A","O"},
+ {"A","B","C","K1","O"},
+ {"B","D","E","K2","O"},
+ {"A","D","K3","O"},
+ {"A","B","C","D","E","K1","K2","K3","O","Z"}
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Datatypes/Datatypes.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Datatypes/Datatypes.cbs
new file mode 100644
index 0000000..209cd77
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Datatypes/Datatypes.cbs
@@ -0,0 +1,41 @@
+### Datatypes
+
+[
+ Type datatype-values
+ Funcon datatype-value
+ Funcon datatype-value-id
+ Funcon datatype-value-elements
+]
+
+/*
+ A datatype value consists of an identifier and a sequence of values.
+
+ 'Datatype T ::= ...' declares the type `T` to refer to a fresh value
+ constructor in `types`, and asserts ``T <: datatype-values``.
+
+ Each constructor funcon 'F(_:T1,...,_:Tn)' of the datatype declaration
+ generates values in `T` of the form `datatype-value("F", V1, ..., Vn)` from
+ `V1:T1`, ..., `Vn:Tn`.
+
+ Note that a computation `X` cannot be directly included in datatype values:
+ it is necessary to encapsulate it in `abstraction(X)`.
+
+ 'Datatype T', followed by declarations of constructor funcons for 'T',
+ allows specification of GADTs.
+*/
+
+Built-in Type
+ datatype-values
+
+Built-in Funcon
+ datatype-value(_:identifiers, _:values*) : datatype-values
+
+Funcon
+ datatype-value-id(_:datatype-values) : =>identifiers
+Rule
+ datatype-value-id(datatype-value(I:identifiers, _*:values*)) ~> I
+
+Funcon
+ datatype-value-elements(_:datatype-values) : =>values*
+Rule
+ datatype-value-elements(datatype-value(_:identifiers, V*:values*)) ~> V*
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Datatypes/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Datatypes/index.md
new file mode 100644
index 0000000..b1d6135
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Datatypes/index.md
@@ -0,0 +1,76 @@
+---
+layout: default
+title: "Datatypes"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Datatypes.cbs]
+-----------------------------
+
+### Datatypes
+
+
+
+
+
+ A datatype value consists of an identifier and a sequence of values.
+
+ 'Datatype T ::= ...' declares the type T to refer to a fresh value
+ constructor in types, and asserts T <: datatype-values.
+
+ Each constructor funcon 'F(_:T1,...,_:Tn)' of the datatype declaration
+ generates values in T of the form datatype-value("F", V1, ..., Vn) from
+ V1:T1, ..., Vn:Tn.
+
+ Note that a computation X cannot be directly included in datatype values:
+ it is necessary to encapsulate it in abstraction(X).
+
+ 'Datatype T', followed by declarations of constructor funcons for 'T',
+ allows specification of GADTs.
+
+
+Built-in Type
+ datatype-values
+
+
+
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Datatypes.cbs]: Datatypes.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Datatypes/Datatypes.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Graphs/Graphs.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Graphs/Graphs.cbs
new file mode 100644
index 0000000..051dd7e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Graphs/Graphs.cbs
@@ -0,0 +1,33 @@
+### Graphs
+
+[
+ Type directed-graphs
+ Funcon is-cyclic
+ Funcon topological-sort
+]
+
+Meta-variables
+ GT <: ground-values
+
+Type
+ directed-graphs(GT) ~> maps(GT, sets(GT))
+/*
+ `directed-graphs(GT)` models directed graphs with vertices of type `GT`,
+ represented as maps from vertices to the set of vertices to which the
+ vertex has an edge. E.g., the graph
+
+ (1)--->(2)
+
+ would be represented as `{ 1 |-> {2}, 2 |-> {} }`
+*/
+
+Built-in Funcon
+ is-cyclic(_:directed-graphs(GT)) : =>booleans
+
+Built-in Funcon
+ topological-sort(_:directed-graphs(GT)) : =>(GT)*
+/*
+ `topological-sort(DG)` returns a topological ordering of the vertices
+ of the graph `DG`, as a sequence of vertices, provided that `DG` is not
+ cyclic.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Graphs/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Graphs/index.md
new file mode 100644
index 0000000..1a67395
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Graphs/index.md
@@ -0,0 +1,69 @@
+---
+layout: default
+title: "Graphs"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Graphs.cbs]
+-----------------------------
+
+### Graphs
+
+
+
+
+
+
+
+
+
+
+ directed-graphs(GT) models directed graphs with vertices of type GT,
+ represented as maps from vertices to the set of vertices to which the
+ vertex has an edge. E.g., the graph
+
+ (1)--->(2)
+
+ would be represented as { 1 |-> {2}, 2 |-> {} }
+
+
+
+
+
+ topological-sort(DG) returns a topological ordering of the vertices
+ of the graph DG, as a sequence of vertices, provided that DG is not
+ cyclic.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Graphs.cbs]: Graphs.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Graphs/Graphs.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Lists/Lists.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Lists/Lists.cbs
new file mode 100644
index 0000000..bb4312d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Lists/Lists.cbs
@@ -0,0 +1,98 @@
+### Lists
+
+[
+ Datatype lists
+ Funcon list
+ Funcon list-elements
+ Funcon list-nil Alias nil
+ Funcon list-cons Alias cons
+ Funcon list-head Alias head
+ Funcon list-tail Alias tail
+ Funcon list-length
+ Funcon list-append
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ lists(T) ::= list(_:(T)*)
+/*
+ `lists(T)` is the type of possibly-empty finite lists `[V1,...,Vn]`
+ where `V1:T`, ..., `Vn:T`.
+
+ N.B. `[T]` is always a single list value, and *not* interpreted as the
+ type `lists(T)`.
+
+ The notation `[V1, ..., Vn]` for `list(V1, ..., Vn)` is built-in.
+*/
+Assert
+ [V*:values*] == list(V*)
+
+
+Funcon
+ list-elements(_:lists(T)) : =>(T)*
+Rule
+ list-elements(list(V*:values*)) ~> V*
+
+
+Funcon
+ list-nil : =>lists(_)
+ ~> [ ]
+Alias
+ nil = list-nil
+
+
+Funcon
+ list-cons(_:T, _:lists(T)) : =>lists(T)
+Alias
+ cons = list-cons
+Rule
+ list-cons(V:values, [V*:values*]) ~> [V, V*]
+
+
+Funcon
+ list-head(_:lists(T)) : =>(T)?
+Alias
+ head = list-head
+Rule
+ list-head[V:values, _*:values*] ~> V
+Rule
+ list-head[ ] ~> ( )
+
+
+Funcon
+ list-tail(_:lists(T)) : =>(lists(T))?
+Alias
+ tail = list-tail
+Rule
+ list-tail[_:values, V*:values*] ~> [V*]
+Rule
+ list-tail[ ] ~> ( )
+
+
+Funcon
+ list-length(_:lists(T)) : =>natural-numbers
+Rule
+ list-length[V*:values*] ~> length(V*)
+
+
+Funcon
+ list-append(_:(lists(T))*) : =>lists(T)
+Rule
+ list-append([V1*:values*], [V2*:values*]) ~> [V1*, V2*]
+Rule
+ list-append(L1:lists(_), L2:lists(_), L3:lists(_), L*:(lists(_))*)
+ ~> list-append(L1, list-append(L2, L3, L*))
+Rule
+ list-append( ) ~> [ ]
+Rule
+ list-append(L:lists(_)) ~> L
+
+
+/*
+ Datatypes of infinite and possibly-infinite lists can be specified as
+ algebraic datatypes using abstractions.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Lists/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Lists/index.md
new file mode 100644
index 0000000..076e88d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Lists/index.md
@@ -0,0 +1,132 @@
+---
+layout: default
+title: "Lists"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Lists.cbs]
+-----------------------------
+
+### Lists
+
+
+
+
+
+
+
+
+
+Datatype
+ lists(T) ::= list(_:(T)*)
+
+
+ lists(T) is the type of possibly-empty finite lists [V1,...,Vn]
+ where V1:T, ..., Vn:T.
+
+ N.B. [T] is always a single list value, and *not* interpreted as the
+ type lists(T).
+
+ The notation [V1, ..., Vn] for list(V1, ..., Vn) is built-in.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Datatypes of infinite and possibly-infinite lists can be specified as
+ algebraic datatypes using abstractions.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Lists.cbs]: Lists.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Lists/Lists.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Lists/tests/lists.config b/IBAF-cbs/Funcons-beta/Values/Composite/Lists/tests/lists.config
new file mode 100644
index 0000000..d664c53
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Lists/tests/lists.config
@@ -0,0 +1,30 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(tuple list-elements list( ), tuple( )))
+ , check-true(is-equal(tuple list-elements list(1), tuple(1)))
+ , check-true(is-equal(tuple list-elements list(1,2,1,3), tuple(1,2,1,3)))
+ , check-true(is-equal(list-nil, list( )))
+ , check-true(is-equal(list-cons(1,list( )), list(1)))
+ , check-true(is-equal(list-cons(1,list(2,3)), list(1,2,3)))
+ , check-true(is-equal(list-head(list(1)), 1))
+ , check-true(is-equal(list-head(list(1,2,3)), 1))
+ , check-true(not is-value list-head(list( )))
+ , check-true(is-equal(list-tail(list(1)), list( )))
+ , check-true(is-equal(list-tail(list(1,2,3)), list(2,3)))
+ , check-true(not is-value list-tail(list( )))
+ , check-true(is-equal(list-append( ), list( )))
+ , check-true(is-equal(list-append(list( )), list( )))
+ , check-true(is-equal(list-append(list(1,2,3,4)), list(1,2,3,4)))
+ , check-true(is-equal(list-append(list(1,2), list(3,4)), list(1,2,3,4)))
+ , check-true(is-equal(list-append(list(1), list(2,3,4)), list(1,2,3,4)))
+ , check-true(is-equal(list-append(list( ), list(1,2,3,4)), list(1,2,3,4)))
+ , check-true(is-equal(list-append(list(1,2,3,4),list( )), list(1,2,3,4)))
+ , check-true(is-equal(list-append(list(1),list(2),list(3,4)), list(1,2,3,4)))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Maps/Maps.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/Maps.cbs
new file mode 100644
index 0000000..17b0c84
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/Maps.cbs
@@ -0,0 +1,111 @@
+### Maps
+
+[
+ Type maps
+ Funcon map
+ Funcon map-elements
+ Funcon map-lookup Alias lookup
+ Funcon map-domain Alias dom
+ Funcon map-override
+ Funcon map-unite
+ Funcon map-delete
+]
+
+
+Meta-variables
+ GT <: ground-values
+ T? <: values?
+
+
+Built-in Type
+ maps(GT, T?)
+/*
+ `maps(GT, T?)` is the type of possibly-empty finite maps from values of
+ type `GT` to optional values of type `T?`.
+*/
+
+
+Built-in Funcon
+ map(_:(tuples(GT, T?))*) : =>(maps(GT, T?))?
+/*
+ `map(tuple(K1, V1?), ..., tuple(Kn, Vn?))` constructs a map from
+ `K1` to `V1?`, ..., `Kn` to `Vn?`, provided that `K1`, ..., `Kn`
+ are distinct, otherwise the result is `( )`.
+
+ Note that `map(...)` is not a constructor operation.
+
+ The built-in notation `{K1|->V1?, ..., Kn|->Vn?}` is equivalent to
+ `map(tuple(K1, V1?), ..., tuple(Kn, Vn?))`. Note however that in general,
+ maps cannot be identified with sets of tuples, since the values `Vi?` are
+ not restricted to `ground-values`.
+
+ When ``T? <: types``, ``maps(GT, T?) <: types``. The type `MT:maps(GT, T?)`
+ represents the set of value-maps `MV:maps(GT, values?)` such that
+ `dom(MV)` is a subset of `dom(MT)` and for all `K` in `dom(MV)`,
+ ``map-lookup(MV, K) : map-lookup(MT, K)``.
+*/
+
+
+Built-in Funcon
+ map-elements(_:maps(GT, T?)) : =>(tuples(GT, T?))*
+/*
+ The sequence of tuples `(tuple(K1, V1?), ..., tuple(Kn, Vn?))` given by
+ `map-elements(M)` contains each mapped value `Ki` just once. The order of
+ the elements is unspecified, and may vary between maps.
+*/
+Assert
+ map(map-elements(M)) == M
+
+
+Built-in Funcon
+ map-lookup(_:maps(GT, T?), K:GT) : =>(T?)?
+Alias
+ lookup = map-lookup
+/*
+ `map-lookup(M,K)` gives the optional value to which `K` is mapped by `M`,
+ if any, and otherwise `( )`.
+*/
+
+
+Built-in Funcon
+ map-domain(_:maps(GT, T?)) : =>sets(GT)
+Alias
+ dom = map-domain
+/*
+ `map-domain(M)` gives the set of values mapped by `M`.
+
+ `map-lookup(M, K)` is always `( )` when `K` is not in `map-domain(M)`.
+*/
+
+
+Built-in Funcon
+ map-override(_:(maps(GT, T?))*) : =>maps(GT,T?)
+/*
+ `map-override(...)` takes a sequence of maps. It returns the map whose
+ domain is the union of their domains, and which maps each of those values
+ to the same optional value as the first map in the sequence in whose domain
+ it occurs
+ .
+ When the domains of the `M*` are disjoint, `map-override(M*)` is equivalent
+ to `map-unite(M*)`.
+*/
+
+
+Built-in Funcon
+ map-unite(_:(maps(GT, T?))*) : =>(maps(GT, T?))?
+/*
+ `map-unite(...)` takes a sequence of maps. It returns the map whose
+ domain is the union of their domains, and which maps each of those values
+ to the same optional value as the map in the sequence in whose domain it occurs,
+ provided that those domains are disjoint - otherwise the result is `( )`.
+*/
+
+
+Built-in Funcon
+ map-delete(_:maps(GT, T?), _:sets(GT)) : =>maps(GT, T?)
+/*
+ `map-delete(M, S)` takes a map `M` and a set of values `S`, and returns the
+ map obtained from `M` by removing `S` from its domain.
+*/
+Assert
+ map-domain(map-delete(M, S)) == set-difference(map-domain(M), S)
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Maps/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/index.md
new file mode 100644
index 0000000..c5235d1
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/index.md
@@ -0,0 +1,147 @@
+---
+layout: default
+title: "Maps"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Maps.cbs]
+-----------------------------
+
+### Maps
+
+
+
+
+
+
+
+
+
+Built-in Type
+ maps(GT, T?)
+
+ maps(GT, T?) is the type of possibly-empty finite maps from values of
+ type GT to optional values of type T?.
+
+
+
+Built-in Funcon
+ map(_:(tuples(GT, T?))*) : =>(maps(GT, T?))?
+
+ map(tuple(K1, V1?), ..., tuple(Kn, Vn?)) constructs a map from
+ K1 to V1?, ..., Kn to Vn?, provided that K1, ..., Kn
+ are distinct, otherwise the result is ( ).
+
+ Note that map(...) is not a constructor operation.
+
+ The built-in notation {K1|->V1?, ..., Kn|->Vn?} is equivalent to
+ map(tuple(K1, V1?), ..., tuple(Kn, Vn?)). Note however that in general,
+ maps cannot be identified with sets of tuples, since the values Vi? are
+ not restricted to ground-values.
+
+ When T? <: types, maps(GT, T?) <: types. The type MT:maps(GT, T?)
+ represents the set of value-maps MV:maps(GT, values?) such that
+ dom(MV) is a subset of dom(MT) and for all K in dom(MV),
+ map-lookup(MV, K) : map-lookup(MT, K).
+
+
+
+Built-in Funcon
+ map-elements(_:maps(GT, T?)) : =>(tuples(GT, T?))*
+
+ The sequence of tuples (tuple(K1, V1?), ..., tuple(Kn, Vn?)) given by
+ map-elements(M) contains each mapped value Ki just once. The order of
+ the elements is unspecified, and may vary between maps.
+
+
+
+Built-in Funcon
+ map-lookup(_:maps(GT, T?), K:GT) : =>(T?)?
+Alias
+ lookup = map-lookup
+
+
+ map-lookup(M,K) gives the optional value to which K is mapped by M,
+ if any, and otherwise ( ).
+
+
+
+
+ map-domain(M) gives the set of values mapped by M.
+
+ map-lookup(M, K) is always ( ) when K is not in map-domain(M).
+
+
+
+Built-in Funcon
+ map-override(_:(maps(GT, T?))*) : =>maps(GT,T?)
+
+ map-override(...) takes a sequence of maps. It returns the map whose
+ domain is the union of their domains, and which maps each of those values
+ to the same optional value as the first map in the sequence in whose domain
+ it occurs
+ .
+ When the domains of the M* are disjoint, map-override(M*) is equivalent
+ to map-unite(M*).
+
+
+
+Built-in Funcon
+ map-unite(_:(maps(GT, T?))*) : =>(maps(GT, T?))?
+
+ map-unite(...) takes a sequence of maps. It returns the map whose
+ domain is the union of their domains, and which maps each of those values
+ to the same optional value as the map in the sequence in whose domain it occurs,
+ provided that those domains are disjoint - otherwise the result is ( ).
+
+
+
+Built-in Funcon
+ map-delete(_:maps(GT, T?), _:sets(GT)) : =>maps(GT, T?)
+
+ map-delete(M, S) takes a map M and a set of values S, and returns the
+ map obtained from M by removing S from its domain.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Maps.cbs]: Maps.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Maps/Maps.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-delete.config b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-delete.config
new file mode 100644
index 0000000..e8582b9
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-delete.config
@@ -0,0 +1,29 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print map-delete({1 |-> 2},{}),
+ print map-delete({1 |-> 2, 3 |-> 4},{}),
+ print map-delete(map(),{1}),
+ print map-delete({1 |-> 2},{1}),
+ print map-delete({1 |-> 2, 3 |-> 4},{1}),
+ print map-delete({1 |-> 2, 3 |-> 4},{3}),
+ print map-delete({1 |-> 2, 3 |-> 4},{1,3}),
+ print "OK"
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ {1 |-> 2},
+ {1 |-> 2, 3 |-> 4},
+ map(),
+ map(),
+ {3 |-> 4},
+ {1 |-> 2},
+ map(),
+ "OK"
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-domain.config b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-domain.config
new file mode 100644
index 0000000..03246d2
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-domain.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print map-domain map(),
+ print map-domain{1|->2},
+ print map-domain{1|->2,3|->4},
+ print map-domain{1|->2,3|->( )}
+ )
+ ;
+}
+
+tests {
+ result-term: null;
+ standard-out: [{}, {1}, {1,3}, {1,3}];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-elements.config b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-elements.config
new file mode 100644
index 0000000..03580e1
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-elements.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print map-elements map( ),
+ print map-elements {1|->2},
+ print map-elements {3|->4,5|->6}
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [tuple(1, 2), tuple(3, 4), tuple(5, 6) ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-lookup.config b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-lookup.config
new file mode 100644
index 0000000..27b839f
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-lookup.config
@@ -0,0 +1,22 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print map-lookup({1|->2}, 1),
+ print map-lookup({1|->2,3|->4}, 1),
+ print map-lookup({1|->2,3|->4}, 3),
+ else(
+ effect checked map-lookup(map(), 1),
+ effect checked map-lookup({1|->2}, 2),
+ effect checked map-lookup({1|->2,3|->4}, 2),
+ effect checked map-lookup({1|->2,3|->4}, 5),
+ print "OK"
+ )
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [2, 2, 4, "OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-override.config b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-override.config
new file mode 100644
index 0000000..cf29c79
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-override.config
@@ -0,0 +1,31 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print map-override({1 |-> 2},map()),
+ print map-override(map(),{1 |-> 2}),
+ print map-override({1 |-> 2},{1 |-> 2}),
+ print map-override({1 |-> 2},{3 |-> 4}),
+ print map-override({1 |-> 2},{1 |-> 4}),
+ print map-override({1 |-> 2},{1 |-> 4},{1 |-> 2}),
+ print map-override({1 |-> 2}),
+ print map-override(map()),
+ print map-override()
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ {1 |-> 2},
+ {1 |-> 2},
+ {1 |-> 2},
+ {1 |-> 2, 3 |-> 4},
+ {1 |-> 2},
+ {1 |-> 2},
+ {1 |-> 2},
+ map(),
+ map()
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-unite.config b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-unite.config
new file mode 100644
index 0000000..df7df72
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map-unite.config
@@ -0,0 +1,31 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print map-unite({1 |-> 2},map()),
+ print map-unite(map(),{1 |-> 2}),
+ print map-unite({1 |-> 2},{3 |-> 4}),
+ print map-unite({1 |-> 2}),
+ print map-unite(map()),
+ print map-unite(),
+ else(
+ effect checked map-unite({1 |-> 2},{1 |-> 4}),
+ effect checked map-unite({1 |-> 2, 3 |-> 4},{5 |-> 6, 1 |-> 7}),
+ print "OK"
+ )
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ {1 |-> 2},
+ {1 |-> 2},
+ {1 |-> 2, 3 |-> 4},
+ {1 |-> 2},
+ map(),
+ map(),
+ "OK"
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map.config b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map.config
new file mode 100644
index 0000000..07d5c85
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Maps/tests/map.config
@@ -0,0 +1,23 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print map(),
+ print {1 |-> 2},
+ print {1 |-> 2, 3 |-> 4},
+ print {1 |-> 2, 3 |-> ()},
+ print cast({1 |-> 2}, maps(integers,integers))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ map(),
+ {1 |-> 2},
+ {1 |-> 2, 3 |-> 4},
+ {1 |-> 2, 3 |-> ()},
+ {1 |-> 2}
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Multisets/Multisets.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Multisets/Multisets.cbs
new file mode 100644
index 0000000..03feccd
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Multisets/Multisets.cbs
@@ -0,0 +1,77 @@
+### Multisets (bags)
+
+[
+ Type multisets
+ Funcon multiset
+ Funcon multiset-elements
+ Funcon multiset-occurrences
+ Funcon multiset-insert
+ Funcon multiset-delete
+ Funcon is-submultiset
+]
+
+
+Meta-variables
+ GT <: ground-values
+
+
+Built-in Type
+ multisets(GT)
+/*
+ `multisets(GT)` is the type of possibly-empty finite multisets of elements
+ of `GT`.
+*/
+
+
+Built-in Funcon
+ multiset(_:(GT)*) : =>multisets(GT)
+/*
+ Note that `multiset(...)` is not a constructor operation. The order of
+ argument values is ignored, but duplicates are significant, e.g.,
+ `multiset(1, 2, 2)` is equivalent to `multiset(2, 1, 2)`, but not to
+ `multiset(1, 2)` or `multiset(2, 1)`.
+*/
+
+
+Built-in Funcon
+ multiset-elements(_:multisets(GT)) : =>(GT)*
+/*
+ For each multiset `MS`, the sequence of values `V*` returned by
+ `multiset-elements(MS)` contains each element of `MS` the same number of times
+ as `MS` does.
+ The order of the values in `V*` is unspecified, and may vary between multisets.
+*/
+Assert
+ multiset(multiset-elements(S)) == S
+
+
+Built-in Funcon
+ multiset-occurrences(_:GT, _:multisets(GT)) : =>natural-numbers
+/*
+ `multiset-occurrences(GV, MS)` returns the number of occurrences of `GV`
+ in `MS`.
+*/
+
+
+Built-in Funcon
+ multiset-insert(_:GT, _:natural-numbers, _:multisets(GT)) : =>multisets(GT)
+/*
+ `multiset-insert(GV, N, MS)` returns the multiset that differs from `MS`
+ by containing `N` more copies of `GV`.
+*/
+
+
+Built-in Funcon
+ multiset-delete(_:multisets(GT), _:GT, _:natural-numbers) : =>multisets(GT)
+/*
+ `multiset-delete(MS, GV, N)` removes `N` copies of `V` from the multiset `MS`,
+ or all copies of `GV` if there are fewer than `N` in `MS`.
+*/
+
+
+Built-in Funcon
+ is-submultiset(_:multisets(GT), _:multisets(GT)) : =>booleans
+/*
+ `is-submultiset(MS1, MS2)` tests whether every element of `MS1` has equal or
+ fewer occurrences in `MS1` than in `MS2`.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Multisets/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Multisets/index.md
new file mode 100644
index 0000000..fd7dbb6
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Multisets/index.md
@@ -0,0 +1,114 @@
+---
+layout: default
+title: "Multisets"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Multisets.cbs]
+-----------------------------
+
+### Multisets (bags)
+
+
+
+
+
+
+
+
+
+Built-in Type
+ multisets(GT)
+
+ multisets(GT) is the type of possibly-empty finite multisets of elements
+ of GT.
+
+
+
+Built-in Funcon
+ multiset(_:(GT)*) : =>multisets(GT)
+
+ Note that multiset(...) is not a constructor operation. The order of
+ argument values is ignored, but duplicates are significant, e.g.,
+ multiset(1, 2, 2) is equivalent to multiset(2, 1, 2), but not to
+ multiset(1, 2) or multiset(2, 1).
+
+
+
+Built-in Funcon
+ multiset-elements(_:multisets(GT)) : =>(GT)*
+
+ For each multiset MS, the sequence of values V* returned by
+ multiset-elements(MS) contains each element of MS the same number of times
+ as MS does.
+ The order of the values in V* is unspecified, and may vary between multisets.
+
+
+
+
+
+
+
+ multiset-occurrences(GV, MS) returns the number of occurrences of GV
+ in MS.
+
+
+
+
+
+ multiset-insert(GV, N, MS) returns the multiset that differs from MS
+ by containing N more copies of GV.
+
+
+
+
+
+ multiset-delete(MS, GV, N) removes N copies of V from the multiset MS,
+ or all copies of GV if there are fewer than N in MS.
+
+
+
+
+
+ is-submultiset(MS1, MS2) tests whether every element of MS1 has equal or
+ fewer occurrences in MS1 than in MS2.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Multisets.cbs]: Multisets.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Multisets/Multisets.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Objects/Objects.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/Objects.cbs
new file mode 100644
index 0000000..e59437b
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/Objects.cbs
@@ -0,0 +1,81 @@
+### Objects
+
+[
+ Datatype objects
+ Funcon object
+ Funcon object-identity
+ Funcon object-class-name
+ Funcon object-feature-map
+ Funcon object-subobject-sequence
+ Funcon object-tree
+ Funcon object-single-inheritance-feature-map
+]
+
+
+Datatype
+ objects ::= object(_:atoms, _:identifiers, _:environments, _:objects*)
+/*
+ `object( A, C, Env, O*)` is an object:
+ * distinguished by an atom `A`,
+ * of a class named `C`,
+ * with an environment `Env` with the features of the object, and
+ * a sequence `O*` of subobjects of the direct superclasses of `C`.
+ `object( A, C, Env)` is an object of a base class.
+ `object( A, C, Env, O')` is an object of a class with a single superclass.
+ With multiple inheritance, subobjects due to repeated inheritance of the
+ same class may be shared.
+
+ Implementations of objects generally represent an object as a vector of
+ fields, and use pointers and offsets for efficient access to individual
+ fields. The representation of objects used in this specification is
+ independent of such implementation concerns.
+*/
+
+Funcon
+ object-identity(_:objects) : =>atoms
+Rule
+ object-identity
+ object(A:atoms, _:identifiers, _:environments, _*:objects*) ~> A
+
+Funcon
+ object-class-name(_:objects) : =>identifiers
+Rule
+ object-class-name
+ object(_:atoms, C:identifiers, _:environments, _*:objects*) ~> C
+
+Funcon
+ object-feature-map(_:objects) : =>environments
+Rule
+ object-feature-map
+ object(_:atoms, _:identifiers, Env:environments, _*:objects*) ~> Env
+
+Funcon
+ object-subobject-sequence(_:objects) : =>objects*
+Rule
+ object-subobject-sequence
+ object(_:atoms, _:identifiers, _:environments, O*:objects*) ~> O*
+
+
+Funcon
+ object-tree(_:objects) : =>trees(objects)
+/*
+ `object-tree O` forms a tree where the branches are the object trees for
+ the direct subobjects of `O`.
+*/
+Rule
+ object-tree(O:objects)
+ ~> tree(O,
+ interleave-map (
+ object-tree given,
+ object-subobject-sequence O))
+
+
+Funcon
+ object-single-inheritance-feature-map(O:objects) : =>environments
+ ~> map-override left-to-right-map(
+ object-feature-map given,
+ single-branching-sequence object-tree O)
+/*
+ For multiple inheritance, different resolution orders can be specified
+ by using difference linearisations of the object tree.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Objects/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/index.md
new file mode 100644
index 0000000..cf3572a
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/index.md
@@ -0,0 +1,119 @@
+---
+layout: default
+title: "Objects"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Objects.cbs]
+-----------------------------
+
+### Objects
+
+
+
+
+
+
+
+
+ object( A, C, Env, O*) is an object:
+ * distinguished by an atom A,
+ * of a class named C,
+ * with an environment Env with the features of the object, and
+ * a sequence O* of subobjects of the direct superclasses of C.
+ object( A, C, Env) is an object of a base class.
+ object( A, C, Env, O′) is an object of a class with a single superclass.
+ With multiple inheritance, subobjects due to repeated inheritance of the
+ same class may be shared.
+
+ Implementations of objects generally represent an object as a vector of
+ fields, and use pointers and offsets for efficient access to individual
+ fields. The representation of objects used in this specification is
+ independent of such implementation concerns.
+
+
+
+
+
+
+
+
+
+
+
+
+
+ object-tree O forms a tree where the branches are the object trees for
+ the direct subobjects of O.
+
+
+
+
+
+
+
+
+ For multiple inheritance, different resolution orders can be specified
+ by using difference linearisations of the object tree.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Objects.cbs]: Objects.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Objects/Objects.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-feature-map.config b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-feature-map.config
new file mode 100644
index 0000000..239046c
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-feature-map.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ initialise-giving initialise-generating finalise-failing
+ sequential (
+ print object-feature-map object(fresh-atom,"A",map()),
+ print object-feature-map object(fresh-atom,"B",map(),
+ object(fresh-atom,"C",map()))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ map(), map()
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-identity.config b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-identity.config
new file mode 100644
index 0000000..16ee89e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-identity.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term:
+ initialise-giving initialise-generating finalise-failing
+ sequential (
+ print object-identity object(fresh-atom,"A",map()),
+ print object-identity object(fresh-atom,"B",map(),
+ object(fresh-atom,"C",map()))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ atom("@1"), atom("@2")
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-single-inheritance-feature-map.config b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-single-inheritance-feature-map.config
new file mode 100644
index 0000000..c790250
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-single-inheritance-feature-map.config
@@ -0,0 +1,28 @@
+general {
+ funcon-term:
+ initialise-giving initialise-generating finalise-failing
+ sequential (
+ print object-single-inheritance-feature-map
+ object(fresh-atom,"A",{"a"|->"A"}),
+ print object-single-inheritance-feature-map
+ object(fresh-atom,"B",{"a"|->"B"},
+ object(fresh-atom,"C",{"a"|->"C"})),
+ else(
+ is-value object-single-inheritance-feature-map
+ object(fresh-atom,"D",map(),
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"F",map())),
+ object(fresh-atom,"G",map())),
+ print "OK")
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ {"a"|->"A"},
+ {"a"|->"B"},
+ "OK"
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-subobject-sequence.config b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-subobject-sequence.config
new file mode 100644
index 0000000..b688fa4
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-subobject-sequence.config
@@ -0,0 +1,27 @@
+general {
+ funcon-term:
+ initialise-giving initialise-generating finalise-failing
+ sequential (
+ print [object-subobject-sequence
+ object(fresh-atom,"A",map())],
+ print [object-subobject-sequence
+ object(fresh-atom,"B",map(),
+ object(fresh-atom,"C",map()))],
+ print [object-subobject-sequence
+ object(fresh-atom,"D",map(),
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"F",map())),
+ object(fresh-atom,"G",map()))]
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ [],
+ [object(atom("@3"),"C",map-empty)],
+ [object(atom("@5"),"E",map-empty,object(atom("@6"),"F",map-empty)),
+ object(atom("@7"),"G",map-empty)]
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-tree.config b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-tree.config
new file mode 100644
index 0000000..1432a14
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object-tree.config
@@ -0,0 +1,32 @@
+general {
+ funcon-term:
+ initialise-giving initialise-generating finalise-failing
+ sequential (
+ print object-tree
+ object(fresh-atom,"A",map()),
+ print object-tree
+ object(fresh-atom,"B",map(),
+ object(fresh-atom,"C",map())),
+ print object-tree
+ object(fresh-atom,"D",map(),
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"F",map())),
+ object(fresh-atom,"G",map()))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ tree (object(atom("@1"),"A",map-empty)),
+ tree (object(atom("@2"),"B",map-empty,object(atom("@3"),"C",map-empty)),
+ tree (object(atom("@3"),"C",map-empty))),
+ tree (object(atom("@4"),"D",map-empty,
+ object(atom("@5"),"E",map-empty,object(atom("@6"),"F",map-empty)),
+ object(atom("@7"),"G",map-empty)),
+ tree (object(atom("@5"),"E",map-empty,object(atom("@6"),"F",map-empty)),
+ tree (object(atom("@6"),"F",map-empty))),
+ tree (object(atom("@7"),"G",map-empty)))
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object.config b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object.config
new file mode 100644
index 0000000..9706f65
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Objects/tests/object.config
@@ -0,0 +1,25 @@
+general {
+ funcon-term:
+ initialise-giving initialise-generating finalise-failing
+ sequential (
+ print object(fresh-atom,"A",map()),
+ print object(fresh-atom,"B",map(),
+ object(fresh-atom,"C",map())),
+ print object(fresh-atom,"D",map(),
+ object(fresh-atom,"E",map(),
+ object(fresh-atom,"F",map())),
+ object(fresh-atom,"G",map()))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ object(atom("@1"),"A",map-empty),
+ object(atom("@2"),"B",map-empty,object(atom("@3"),"C",map-empty)),
+ object(atom("@4"),"D",map-empty,
+ object(atom("@5"),"E",map-empty,object(atom("@6"),"F",map-empty)),
+ object(atom("@7"),"G",map-empty))
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Records/Records.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Records/Records.cbs
new file mode 100644
index 0000000..468c7f3
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Records/Records.cbs
@@ -0,0 +1,32 @@
+### Records
+
+[
+ Datatype records
+ Funcon record
+ Funcon record-map
+ Funcon record-select
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ records(T) ::= record(_:maps(identifiers,T))
+/*
+ A value of type `records(T)` contains a map from identifiers to values of
+ type `T`.
+*/
+
+
+Funcon
+ record-map(_:records(T)) : =>maps(identifiers,T)
+Rule
+ record-map(record(M:maps(_,_))) ~> M
+
+
+Funcon
+ record-select(R:records(T), I:identifiers) : =>T?
+ ~> map-lookup(record-map(R), I)
+
\ No newline at end of file
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Records/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Records/index.md
new file mode 100644
index 0000000..c958e50
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Records/index.md
@@ -0,0 +1,68 @@
+---
+layout: default
+title: "Records"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Records.cbs]
+-----------------------------
+
+### Records
+
+
+
+
+
+
+
+
+
+
+
+
+ A value of type records(T) contains a map from identifiers to values of
+ type T.
+
+
+
+
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Records.cbs]: Records.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Records/Records.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/References/References.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/References/References.cbs
new file mode 100644
index 0000000..c26c3d2
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/References/References.cbs
@@ -0,0 +1,29 @@
+### References and pointers
+
+[
+ Datatype references
+ Funcon reference
+ Type pointers
+ Funcon pointer-null
+ Funcon dereference
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ references(T) ::= reference(_:T)
+
+
+Datatype
+ pointers(T) ::= pointer-null | { _:references(T) }
+
+
+Funcon
+ dereference(_:pointers(T)) : =>(T)?
+Rule
+ dereference(reference(V:T)) ~> V
+Rule
+ dereference(pointer-null) ~> ( )
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/References/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/References/index.md
new file mode 100644
index 0000000..554c885
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/References/index.md
@@ -0,0 +1,66 @@
+---
+layout: default
+title: "References"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [References.cbs]
+-----------------------------
+
+### References and pointers
+
+
+
+
+
+
+
+
+
+Datatype
+ references(T) ::= reference(_:T)
+
+
+
+Datatype
+ pointers(T) ::= pointer-null | { _:references(T) }
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[References.cbs]: References.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/References/References.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/Sequences.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/Sequences.cbs
new file mode 100644
index 0000000..d3ac43c
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/Sequences.cbs
@@ -0,0 +1,157 @@
+### Sequences of values
+
+[
+ Funcon length
+ Funcon index
+ Funcon is-in
+ Funcon first
+ Funcon second
+ Funcon third
+ Funcon first-n
+ Funcon drop-first-n
+ Funcon reverse
+ Funcon n-of
+ Funcon intersperse
+]
+
+/*
+ Sequences of two or more values are not themselves values, nor is the empty
+ sequence a value. However, sequences can be provided to funcons as arguments,
+ and returned as results. Many operations on composite values can be expressed
+ by extracting their components as sequences, operating on the sequences, then
+ forming the required composite values from the resulting sequences.
+
+ A sequence with elements `X1`, ..., `Xn` is written `X1,...,Xn`.
+ A sequence with a single element `X` is identified with (and written) `X`.
+ An empty sequence is indicated by the absence of a term.
+ Any sequence `X*` can be enclosed in parentheses `(X*)`, e.g.:
+ `( )`, `(1)`, `(1,2,3)`. Superfluous commas are ignored.
+
+ The elements of a type sequence `T1,...,Tn` are the value sequences `V1,...,Vn`
+ where `V1:T1`, ..., `Vn:Tn`. The only element of the empty type sequence `( )`
+ is the empty value sequence `( )`.
+
+ `(T)^N` is equivalent to `T,...,T` with `N` occurrences of `T`.
+ `(T)*` is equivalent to the union of all `(T)^N` for `N`>=0,
+ `(T)+` is equivalent to the union of all `(T)^N` for `N`>=1, and
+ `(T)?` is equivalent to `T | ( )`.
+ The parentheses around `T` above can be omitted when they are not needed for
+ disambiguation.
+
+ (Non-trivial) sequence types are not values, so not included in `types`.
+*/
+
+
+Meta-variables
+ T, T' <: values
+
+
+Funcon
+ length(_:values*) : =>natural-numbers
+/*
+ `length(V*)` gives the number of elements in `V*`.
+*/
+Rule
+ length( ) ~> 0
+Rule
+ length(V:values, V*:values*) ~> natural-successor(length(V*))
+
+
+Funcon
+ is-in(_:values, _:values*) : =>booleans
+Rule
+ is-in(V:values ,V':values, V*:values*) ~> or(is-equal(V, V'), is-in(V, V*))
+Rule
+ is-in(V:values, ( )) ~> false
+
+
+#### Sequence indexing
+
+Funcon
+ index(_:natural-numbers, _:values*) : =>values?
+/*
+ `index(N, V*)` gives the `N`th element of `V*`, if it exists, otherwise `( )`.
+*/
+Rule
+ index(1, V:values, V*:values*) ~> V
+Rule
+ natural-predecessor(N) ~> N'
+ -----------------------------------------------------------------
+ index(N:positive-integers, _:values, V*:values*) ~> index(N', V*)
+Rule
+ index(0, V*:values*) ~> ( )
+Rule
+ index(_:positive-integers, ( )) ~> ( )
+
+
+/* Total indexing funcons: */
+
+Funcon
+ first(_:T, _:values*) : =>T
+Rule
+ first(V:T, V*:values*) ~> V
+
+Funcon
+ second(_:values, _:T, _:values*) : =>T
+Rule
+ second(_:values, V:T, V*:values*) ~> V
+
+Funcon
+ third(_:values, _:values, _:T, _:values*) : =>T
+Rule
+ third(_:values, _:values, V:T, V*:values*) ~> V
+
+
+#### Homogeneous sequences
+
+
+Funcon
+ first-n(_:natural-numbers, _:(T)*) : =>(T)*
+Rule
+ first-n(0, V*:(T)*) ~> ( )
+Rule
+ natural-predecessor(N) ~> N'
+ -----------------------------------------------------------------
+ first-n(N:positive-integers, V:T, V*:(T)*) ~> (V,first-n(N', V*))
+Rule
+ first-n(N:positive-integers, ( )) ~> ( )
+
+
+Funcon
+ drop-first-n(_:natural-numbers, _:(T)*) : =>(T)*
+Rule
+ drop-first-n(0, V*:(T)*) ~> V*
+Rule
+ natural-predecessor(N) ~> N'
+ -----------------------------------------------------------------------
+ drop-first-n(N:positive-integers, _:T, V*:(T)*) ~> drop-first-n(N', V*)
+Rule
+ drop-first-n(N:positive-integers, ( )) ~> ( )
+
+
+Funcon
+ reverse(_:(T)*) : =>(T)*
+Rule
+ reverse( ) ~> ( )
+Rule
+ reverse(V:T, V*:(T)*) ~> (reverse(V*), V)
+
+
+Funcon
+ n-of(N:natural-numbers, V:T) : =>(T)*
+Rule
+ n-of(0, _:T) ~> ( )
+Rule
+ natural-predecessor(N) ~> N'
+ --------------------------------------------------
+ n-of(N:positive-integers, V:T) ~> (V, n-of(N', V))
+
+
+Funcon
+ intersperse(_:T', _:(T)*) : =>(T, (T', T)*)?
+Rule
+ intersperse(_:T', ( )) ~> ( )
+Rule
+ intersperse(_:T', V) ~> V
+Rule
+ intersperse(V':T', V1:T, V2:T, V*:(T)*) ~> (V1, V', intersperse(V', V2, V*))
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/index.md
new file mode 100644
index 0000000..5ff12a7
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/index.md
@@ -0,0 +1,192 @@
+---
+layout: default
+title: "Sequences"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Sequences.cbs]
+-----------------------------
+
+### Sequences of values
+
+
+
+
+
+ Sequences of two or more values are not themselves values, nor is the empty
+ sequence a value. However, sequences can be provided to funcons as arguments,
+ and returned as results. Many operations on composite values can be expressed
+ by extracting their components as sequences, operating on the sequences, then
+ forming the required composite values from the resulting sequences.
+
+ A sequence with elements X1, ..., Xn is written X1,...,Xn.
+ A sequence with a single element X is identified with (and written) X.
+ An empty sequence is indicated by the absence of a term.
+ Any sequence X* can be enclosed in parentheses (X*), e.g.:
+ ( ), (1), (1,2,3). Superfluous commas are ignored.
+
+ The elements of a type sequence T1,...,Tn are the value sequences V1,...,Vn
+ where V1:T1, ..., Vn:Tn. The only element of the empty type sequence ( )
+ is the empty value sequence ( ).
+
+ (T)^N is equivalent to T,...,T with N occurrences of T.
+ (T)* is equivalent to the union of all (T)^N for N>=0,
+ (T)+ is equivalent to the union of all (T)^N for N>=1, and
+ (T)? is equivalent to T | ( ).
+ The parentheses around T above can be omitted when they are not needed for
+ disambiguation.
+
+ (Non-trivial) sequence types are not values, so not included in types.
+
+
+
+Meta-variables
+ T, T′ <: values
+
+
+
+
+
+ length(V*) gives the number of elements in V*.
+
+
+
+
+
+
+
+#### Sequence indexing
+
+
+
+ index(N, V*) gives the Nth element of V*, if it exists, otherwise ( ).
+
+
+
+
+
+ Total indexing funcons:
+
+
+
+
+
+
+
+
+#### Homogeneous sequences
+
+
+
+
+
+
+
+
+
+
+
+Funcon
+ intersperse(_:T′, _:(T)*) : =>(T, (T′, T)*)?
+Rule
+ intersperse(_:T′, ( )) ~> ( )
+Rule
+ intersperse(_:T′, V) ~> V
+Rule
+ intersperse(V′:T′, V1:T, V2:T, V*:(T)*) ~> (V1, V′, intersperse(V′, V2, V*))
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Sequences.cbs]: Sequences.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Sequences/Sequences.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/drop-first-n.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/drop-first-n.config
new file mode 100644
index 0000000..ec857e4
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/drop-first-n.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(tuple(1,2,3,4,5), tuple drop-first-n(0,1,2,3,4,5)))
+ , check-true(is-equal(tuple(2,3,4,5), tuple drop-first-n(1,1,2,3,4,5)))
+ , check-true(is-equal(tuple(3,4,5), tuple drop-first-n(2,1,2,3,4,5)))
+ , check-true(is-equal(tuple(4,5), tuple drop-first-n(3,1,2,3,4,5)))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/first-n.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/first-n.config
new file mode 100644
index 0000000..82fade8
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/first-n.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(tuple(), tuple first-n(0,1,2,3,4,5)))
+ , check-true(is-equal(tuple(1), tuple first-n(1,1,2,3,4,5)))
+ , check-true(is-equal(tuple(1,2), tuple first-n(2,1,2,3,4,5)))
+ , check-true(is-equal(tuple(1,2,3), tuple first-n(3,1,2,3,4,5)))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/first.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/first.config
new file mode 100644
index 0000000..b1f0198
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/first.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(first(1), 1))
+ , check-true(is-equal(first(1,2,3), 1))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/index.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/index.config
new file mode 100644
index 0000000..f7116f7
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/index.config
@@ -0,0 +1,21 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(index(1,1), 1))
+ , check-true(is-equal(index(1,1,2), 1))
+ , check-true(is-equal(index(2,1,2), 2))
+ , check-true(is-equal(index(2,1,2,3), 2))
+ , check-true(not is-value(index(0)))
+ , check-true(not is-value(index(0,1)))
+ , check-true(not is-value(index(0,1,2)))
+ , check-true(not is-value(index(1)))
+ , check-true(not is-value(index(2)))
+ , check-true(not is-value(index(2,1)))
+ , check-true(not is-value(index(3,1,2)))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/intersperse.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/intersperse.config
new file mode 100644
index 0000000..8ba1f31
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/intersperse.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(tuple intersperse(42), tuple( )))
+ , check-true(is-equal(tuple intersperse(42,1), tuple(1)))
+ , check-true(is-equal(tuple intersperse(0,1,2), tuple(1,0,2)))
+ , check-true(is-equal(tuple intersperse(0,1,2,3), tuple(1,0,2,0,3)))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/is-in.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/is-in.config
new file mode 100644
index 0000000..430f440
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/is-in.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term: sequential (
+ check-true(is-in(1,1))
+ , check-true(is-in(1,1,2))
+ , check-true(is-in(2,1,2))
+ , check-true(is-in(3,1,2,3,4,5))
+ , check-true(not is-in(0))
+ , check-true(not is-in(1))
+ , check-true(not is-in(0,1))
+ , check-true(not is-in(3,1,2))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/length.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/length.config
new file mode 100644
index 0000000..6c0ef9a
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/length.config
@@ -0,0 +1,13 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(length( ), 0))
+ , check-true(is-equal(length(1), 1))
+ , check-true(is-equal(length(1,2,3), 3))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/n-of.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/n-of.config
new file mode 100644
index 0000000..748d62e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/n-of.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(tuple n-of(0,42), tuple( )))
+ , check-true(is-equal(tuple n-of(1,2), tuple(2)))
+ , check-true(is-equal(tuple n-of(2,3), tuple(3,3)))
+ , check-true(is-equal(tuple n-of(3,4), tuple(4,4,4)))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/reverse.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/reverse.config
new file mode 100644
index 0000000..d8dd4fd
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/reverse.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(tuple reverse( ), tuple( )))
+ , check-true(is-equal(tuple reverse(1), tuple(1)))
+ , check-true(is-equal(tuple reverse(1,2), tuple(2,1)))
+ , check-true(is-equal(tuple reverse(1,2,3), tuple(3,2,1)))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/second.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/second.config
new file mode 100644
index 0000000..7dea68a
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/second.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(second(1,2), 2))
+ , check-true(is-equal(second(1,2,3), 2))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/third.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/third.config
new file mode 100644
index 0000000..eb0e1aa
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sequences/tests/third.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(third(1,2,3), 3))
+ , check-true(is-equal(third(1,2,3,4), 3))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sets/Sets.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/Sets.cbs
new file mode 100644
index 0000000..a80158f
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/Sets.cbs
@@ -0,0 +1,155 @@
+### Sets
+
+[
+ Type sets
+ Funcon set
+ Funcon set-elements
+ Funcon is-in-set
+ Funcon is-subset
+ Funcon set-insert
+ Funcon set-unite
+ Funcon set-intersect
+ Funcon set-difference
+ Funcon set-size
+ Funcon some-element
+ Funcon element-not-in
+]
+
+
+Meta-variables
+ GT <: ground-values
+
+
+Built-in Type
+ sets(GT)
+/*
+ `sets(GT)` is the type of possibly-empty finite sets `{V1, ..., Vn}`
+ where `V1:GT`, ..., `Vn:GT`.
+*/
+
+
+Built-in Funcon
+ set(_:(GT)*) : =>sets(GT)
+/*
+ The notation `{V1, ..., Vn}` for `set(V1, ..., Vn)` is built-in.
+*/
+Assert
+ {V*:(GT)*} == set(V*)
+/*
+ Note that `set(...)` is not a constructor operation. The order and duplicates
+ of argument values are ignored (e.g., `{1,2,1}` denotes the same set as `{1,2}`
+ and `{2,1}`).
+*/
+
+
+Built-in Funcon
+ set-elements(_:sets(GT)) : =>(GT)*
+/*
+ For each set `S`, the sequence of values `V*` returned by `set-elements(S)`
+ contains each element of `S` just once. The order of the values in `V*` is
+ unspecified, and may vary between sets (e.g., `set-elements{1,2}` could be
+ `(1,2)` and `set-elements{1,2,3}` could be `(3,2,1)`).
+*/
+Assert
+ set(set-elements(S)) == S
+
+
+Built-in Funcon
+ is-in-set(_:GT, _:sets(GT)) : =>booleans
+/*
+ `is-in-set(GV,S)` tests whether `GV` is in the set `S`.
+*/
+Assert
+ is-in-set(GV:GT, { }) == false
+Assert
+ is-in-set(GV:GT, {GV}:sets(GT)) == true
+
+
+Built-in Funcon
+ is-subset(_:sets(GT), _:sets(GT)) : =>booleans
+/*
+ `is-subset(S1,S2)` tests whether `S1` is a subset of `S2`.
+*/
+Assert
+ is-subset({ }, S:sets(GT)) == true
+Assert
+ is-subset(S:sets(GT), S) == true
+
+
+Built-in Funcon
+ set-insert(_:GT, _:sets(GT)) : =>sets(GT)
+/*
+ `set-insert(GV, S)` returns the set union of `{GV}` and `S`.
+*/
+Assert
+ is-in-set(GV:GT, set-insert(GV:GT, S:sets(GT))) == true
+
+
+Built-in Funcon
+ set-unite(_:(sets(GT))*) : =>sets(GT)
+/*
+ `set-unite(...)` unites a sequence of sets.
+*/
+Assert
+ set-unite(S:sets(GT), S) == S
+Assert
+ set-unite(S1:sets(GT), S2:sets(GT)) == set-unite(S2, S1)
+Assert
+ set-unite(S1:sets(GT), set-unite(S2:sets(GT), S3:sets(GT))) ==
+ set-unite(set-unite(S1, S2), S3)
+Assert
+ set-unite(S1:sets(GT), S2:sets(GT), S3:sets(GT)) ==
+ set-unite(S1, set-unite(S2, S3))
+Assert
+ set-unite(S:sets(GT)) == S
+Assert
+ set-unite( ) == { }
+
+
+Built-in Funcon
+ set-intersect(_:(sets(GT))+) : =>sets(GT)
+/*
+ `set-intersect(GT,...)` intersects a non-empty sequence of sets.
+*/
+Assert
+ set-intersect(S:sets(GT), S) == S
+Assert
+ set-intersect(S1:sets(GT), S2:sets(GT)) == set-intersect(S2, S1)
+Assert
+ set-intersect(S1:sets(GT), set-intersect(S2:sets(GT), S3:sets(GT))) ==
+ set-intersect(set-intersect(S1, S2), S3)
+Assert
+ set-intersect(S1:sets(GT), S2:sets(GT), S3:sets(GT)) ==
+ set-intersect(S1, set-intersect(S2, S3))
+Assert
+ set-intersect(S:sets(GT)) == S
+
+
+Built-in Funcon
+ set-difference(_:sets(GT), _:sets(GT)) : =>sets(GT)
+/*
+ `set-difference(S1, S2)` returns the set containing those elements of `S1`
+ that are not in `S2`.
+*/
+
+Built-in Funcon
+ set-size(_:sets(GT)) : =>natural-numbers
+Assert
+ set-size(S:sets(GT)) == length(set-elements(S))
+
+
+Funcon
+ some-element(_:sets(GT)) : =>GT?
+Assert
+ some-element(S:sets(GT)) == index(1, set-elements(S))
+Assert
+ some-element{ } == ( )
+
+
+Built-in Funcon
+ element-not-in(GT:types, _:set(GT)) : =>GT?
+/*
+ `element-not-in(GT, S)` gives an element of the type `GT` not in the set
+ `S`, or `( )` when `S` is empty. When the set of elements of `GT` is infinite,
+ `element-not-in(GT, S)` never gives `( )`.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sets/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/index.md
new file mode 100644
index 0000000..d4553fe
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/index.md
@@ -0,0 +1,198 @@
+---
+layout: default
+title: "Sets"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Sets.cbs]
+-----------------------------
+
+### Sets
+
+
+
+
+
+
+
+
+
+
+
+ sets(GT) is the type of possibly-empty finite sets {V1, ..., Vn}
+ where V1:GT, ..., Vn:GT.
+
+
+
+Built-in Funcon
+ set(_:(GT)*) : =>sets(GT)
+
+ The notation {V1, ..., Vn} for set(V1, ..., Vn) is built-in.
+
+Assert
+ {V*:(GT)*} == set(V*)
+
+
+ Note that set(...) is not a constructor operation. The order and duplicates
+ of argument values are ignored (e.g., {1,2,1} denotes the same set as {1,2}
+ and {2,1}).
+
+
+
+Built-in Funcon
+ set-elements(_:sets(GT)) : =>(GT)*
+
+ For each set S, the sequence of values V* returned by set-elements(S)
+ contains each element of S just once. The order of the values in V* is
+ unspecified, and may vary between sets (e.g., set-elements{1,2} could be
+ (1,2) and set-elements{1,2,3} could be (3,2,1)).
+
+
+
+
+
+
+
+ is-in-set(GV,S) tests whether GV is in the set S.
+
+
+
+
+
+
+
+ is-subset(S1,S2) tests whether S1 is a subset of S2.
+
+
+
+
+
+Built-in Funcon
+ set-insert(_:GT, _:sets(GT)) : =>sets(GT)
+
+ set-insert(GV, S) returns the set union of {GV} and S.
+
+
+
+
+
+Built-in Funcon
+ set-unite(_:(sets(GT))*) : =>sets(GT)
+
+ set-unite(...) unites a sequence of sets.
+
+Assert
+ set-unite(S:sets(GT), S) == S
+Assert
+ set-unite(S1:sets(GT), S2:sets(GT)) == set-unite(S2, S1)
+Assert
+ set-unite(S1:sets(GT), set-unite(S2:sets(GT), S3:sets(GT))) ==
+ set-unite(set-unite(S1, S2), S3)
+Assert
+ set-unite(S1:sets(GT), S2:sets(GT), S3:sets(GT)) ==
+ set-unite(S1, set-unite(S2, S3))
+Assert
+ set-unite(S:sets(GT)) == S
+Assert
+ set-unite( ) == { }
+
+
+
+Built-in Funcon
+ set-intersect(_:(sets(GT))+) : =>sets(GT)
+
+ set-intersect(GT,...) intersects a non-empty sequence of sets.
+
+Assert
+ set-intersect(S:sets(GT), S) == S
+Assert
+ set-intersect(S1:sets(GT), S2:sets(GT)) == set-intersect(S2, S1)
+Assert
+ set-intersect(S1:sets(GT), set-intersect(S2:sets(GT), S3:sets(GT))) ==
+ set-intersect(set-intersect(S1, S2), S3)
+Assert
+ set-intersect(S1:sets(GT), S2:sets(GT), S3:sets(GT)) ==
+ set-intersect(S1, set-intersect(S2, S3))
+Assert
+ set-intersect(S:sets(GT)) == S
+
+
+
+Built-in Funcon
+ set-difference(_:sets(GT), _:sets(GT)) : =>sets(GT)
+
+ set-difference(S1, S2) returns the set containing those elements of S1
+ that are not in S2.
+
+
+
+
+
+
+
+
+
+Built-in Funcon
+ element-not-in(GT:types, _:set(GT)) : =>GT?
+
+ element-not-in(GT, S) gives an element of the type GT not in the set
+ S, or ( ) when S is empty. When the set of elements of GT is infinite,
+ element-not-in(GT, S) never gives ( ).
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Sets.cbs]: Sets.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Sets/Sets.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set-difference.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set-difference.config
new file mode 100644
index 0000000..94d5607
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set-difference.config
@@ -0,0 +1,27 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print set-difference({1},set()),
+ print set-difference(set(),{2}),
+ print set-difference({1},{2}),
+ print set-difference({1,2},{1,2}),
+ print set-difference({1,2},{1}),
+ print set-difference({1,2},set()),
+ print "OK"
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ {1},
+ {},
+ {1},
+ {},
+ {2},
+ {1,2},
+ "OK"
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set-elements.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set-elements.config
new file mode 100644
index 0000000..755bc42
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set-elements.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print tuple(set-elements set( )),
+ print tuple(set-elements {1}),
+ print tuple(set-elements {2,3})
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [tuple(), tuple(1), tuple(2, 3) ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set-unite.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set-unite.config
new file mode 100644
index 0000000..3a76eda
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set-unite.config
@@ -0,0 +1,27 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print set-unite({1},set()),
+ print set-unite(set(),{2}),
+ print set-unite({1},{2}),
+ print set-unite({1}),
+ print set-unite(set()),
+ print set-unite(),
+ print "OK"
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ {1},
+ {2},
+ {1,2},
+ {1},
+ set(),
+ set(),
+ "OK"
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set.config
new file mode 100644
index 0000000..e52e90a
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/set.config
@@ -0,0 +1,21 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print set(),
+ print {1},
+ print {1,2,3},
+ print cast({1,2}, sets(integers))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ set(),
+ {1},
+ {1, 2, 3},
+ {1, 2}
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/some-element.config b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/some-element.config
new file mode 100644
index 0000000..cfc2deb
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Sets/tests/some-element.config
@@ -0,0 +1,15 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print some-element {1},
+ print some-element {1,2},
+ print some-element {1,2,3}
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [1, 1, 1];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Strings/Strings.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Strings/Strings.cbs
new file mode 100644
index 0000000..3cd02da
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Strings/Strings.cbs
@@ -0,0 +1,36 @@
+### Strings
+
+[
+ Type strings
+ Funcon string
+ Funcon string-append
+ Funcon to-string
+]
+
+
+Type
+ strings ~> lists(characters)
+
+
+Funcon
+ string(C*:characters*) : =>strings
+ ~> [C*]
+/*
+ Literal strings are written `"C1...Cn"`.
+ A double-quote or backslash needs to be escaped: `"...\"..."`, `"...\\..."`.
+*/
+
+
+Funcon
+ string-append(S*:strings*) : =>strings
+ ~> list-append(S*)
+
+
+Built-in Funcon
+ to-string(_:ground-values) : =>strings
+/*
+ The strings returned by `to-string(GV)` are unspecified, except that when
+ `GV` is already a string, it is returned unchanged.
+*/
+Assert
+ to-string(S:strings) == S
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Strings/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Strings/index.md
new file mode 100644
index 0000000..7b3ee8e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Strings/index.md
@@ -0,0 +1,75 @@
+---
+layout: default
+title: "Strings"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Strings.cbs]
+-----------------------------
+
+### Strings
+
+
+
+
+
+
+
+
+
+
+
+
+ Literal strings are written "C1...Cn".
+ A double-quote or backslash needs to be escaped: "...\"...", "...\\...".
+
+
+
+
+
+
+
+
+
+ The strings returned by to-string(GV) are unspecified, except that when
+ GV is already a string, it is returned unchanged.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Strings.cbs]: Strings.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Strings/Strings.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Trees/Trees.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/Trees.cbs
new file mode 100644
index 0000000..1b82cb2
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/Trees.cbs
@@ -0,0 +1,94 @@
+### Trees
+
+[
+ Datatype trees
+ Funcon tree
+ Funcon tree-root-value
+ Funcon tree-branch-sequence
+ Funcon single-branching-sequence
+ Funcon forest-root-value-sequence
+ Funcon forest-branch-sequence
+ Funcon forest-value-sequence
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ trees(T) ::= tree( _:T, _:(trees(T))*)
+/*
+ `trees(T)` consists of finitely-branching trees with elements of type `T`.
+ When `V:T`, `tree(V)` is a leaf, and `tree(V,B1,...,Bn)` is a tree with
+ branches `B1`, ..., `Bn`.
+*/
+
+
+Funcon
+ tree-root-value(_:trees(T)) : =>(T)?
+Rule
+ tree-root-value tree(V:T, _*:(trees(T))*) ~> V
+
+
+Funcon
+ tree-branch-sequence(_:trees(T)) : =>(trees(T))*
+Rule
+ tree-branch-sequence tree(_:T, B*:(trees(T))*) ~> B*
+
+
+Funcon
+ single-branching-sequence(_:trees(T)) : =>T+
+/*
+ `single-branching-sequence B ` extracts the values in `B` starting from
+ the root, provided that `B` is at most single-branching; otherwise it fails.
+*/
+Rule
+ single-branching-sequence tree(V:T) ~> V
+Rule
+ single-branching-sequence tree(V:T, B:trees(T))
+ ~> left-to-right( V, single-branching-sequence B)
+Rule
+ single-branching-sequence tree(_:T, _:trees(T), _+:(trees(T))+) ~> fail
+
+
+/*
+ A sequence of trees corresponds to a forest, and the selector funcons
+ on trees `B` extend to forests `B*`:
+*/
+
+Funcon
+ forest-root-value-sequence(_:(trees(T))*) : =>T*
+Rule
+ forest-root-value-sequence(B:trees(T), B*:(trees(T))*)
+ ~>(tree-root-value B , forest-root-value-sequence B*)
+Rule
+ forest-root-value-sequence( ) ~>( )
+
+
+Funcon
+ forest-branch-sequence(_:(trees(T))*) : =>T*
+Rule
+ forest-branch-sequence(B:trees(T), B*:(trees(T))*)
+ ~>(tree-branch-sequence B , forest-branch-sequence B*)
+Rule
+ forest-branch-sequence( ) ~>( )
+
+
+Funcon
+ forest-value-sequence(_:(trees(T))*) : =>T*
+/*
+ `forest-value-sequence B*` provides the values from a left-to-right pre-order
+ depth-first traversal.
+*/
+Rule
+ forest-value-sequence(tree(V:T, B1*:(trees(T))*), B2*:(trees(T))*)
+ ~>(V , forest-value-sequence B1*, forest-value-sequence B2*)
+Rule
+ forest-value-sequence( ) ~>( )
+
+
+/*
+ Other linearizations of trees can be added: breadth-first, right-to-left,
+ C3, etc.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Trees/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/index.md
new file mode 100644
index 0000000..b3c794d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/index.md
@@ -0,0 +1,130 @@
+---
+layout: default
+title: "Trees"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Trees.cbs]
+-----------------------------
+
+### Trees
+
+
+
+
+
+
+
+
+
+Datatype
+ trees(T) ::= tree( _:T, _:(trees(T))*)
+
+
+ trees(T) consists of finitely-branching trees with elements of type T.
+ When V:T, tree(V) is a leaf, and tree(V,B1,...,Bn) is a tree with
+ branches B1, ..., Bn.
+
+
+
+
+
+
+
+Funcon
+ single-branching-sequence(_:trees(T)) : =>T+
+
+ single-branching-sequence B extracts the values in B starting from
+ the root, provided that B is at most single-branching; otherwise it fails.
+
+
+
+
+
+
+ A sequence of trees corresponds to a forest, and the selector funcons
+ on trees B extend to forests B*:
+
+
+
+
+
+
+
+Funcon
+ forest-value-sequence(_:(trees(T))*) : =>T*
+
+ forest-value-sequence B* provides the values from a left-to-right pre-order
+ depth-first traversal.
+
+
+
+
+
+
+ Other linearizations of trees can be added: breadth-first, right-to-left,
+ C3, etc.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Trees.cbs]: Trees.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Trees/Trees.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/forest-branch-sequence.config b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/forest-branch-sequence.config
new file mode 100644
index 0000000..d793322
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/forest-branch-sequence.config
@@ -0,0 +1,20 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print [forest-branch-sequence
+ (tree(1),
+ tree(2,tree(3)),
+ tree(4),
+ tree(5,tree(6),tree(7)))
+ ]
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ [tree(3),tree(6),tree(7)]
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/forest-root-value-sequence.config b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/forest-root-value-sequence.config
new file mode 100644
index 0000000..4bee783
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/forest-root-value-sequence.config
@@ -0,0 +1,20 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print [forest-root-value-sequence
+ (tree(1),
+ tree(2,tree(3)),
+ tree(4),
+ tree(5,tree(6),tree(7)))
+ ]
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ [1,2,4,5]
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/forest-value-sequence.config b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/forest-value-sequence.config
new file mode 100644
index 0000000..5dacfb7
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/forest-value-sequence.config
@@ -0,0 +1,20 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print [forest-value-sequence
+ (tree(1),
+ tree(2,tree(3)),
+ tree(4),
+ tree(5,tree(6),tree(7)))
+ ]
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ [1,2,3,4,5,6,7]
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/single-branching-sequence.config b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/single-branching-sequence.config
new file mode 100644
index 0000000..32f9432
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/single-branching-sequence.config
@@ -0,0 +1,22 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print [single-branching-sequence tree(1)],
+ print [single-branching-sequence tree(1,tree(2,tree(3)))],
+ else(
+ print [single-branching-sequence tree(1,tree(2),tree(3))],
+ print [single-branching-sequence tree(1,tree(2,tree(3,tree(4),tree(5))))],
+ print "OK")
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ [1],
+ [1,2,3],
+ "OK"
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/tree-branch-sequence.config b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/tree-branch-sequence.config
new file mode 100644
index 0000000..20c438d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/tree-branch-sequence.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print tree-branch-sequence
+ tree(1,tree(2,tree(3)),tree(4),tree(5,tree(6),tree(7)))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ tree(2,tree(3)), tree(4), tree(5,tree(6),tree(7))
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/tree-root-value.config b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/tree-root-value.config
new file mode 100644
index 0000000..1f603a8
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/tree-root-value.config
@@ -0,0 +1,16 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print tree-root-value
+ tree(1,tree(2,tree(3)),tree(4),tree(5,tree(6),tree(7)))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ 1
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/tree.config b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/tree.config
new file mode 100644
index 0000000..18af5e9
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Trees/tests/tree.config
@@ -0,0 +1,21 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print tree(1),
+ print tree(1,tree(2,tree(3))),
+ print tree(1,tree(2),tree(3)),
+ print tree(1,tree(2,tree(3)),tree(4),tree(5,tree(6),tree(7)))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ tree(1),
+ tree(1,tree(2,tree(3))),
+ tree(1,tree(2),tree(3)),
+ tree(1,tree(2,tree(3)),tree(4),tree(5,tree(6),tree(7)))
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Tuples/Tuples.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Tuples/Tuples.cbs
new file mode 100644
index 0000000..96612b4
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Tuples/Tuples.cbs
@@ -0,0 +1,47 @@
+### Tuples
+
+[
+ Datatype tuples
+ Funcon tuple-elements
+ Funcon tuple-zip
+]
+
+
+Meta-variables
+ T1, T2 <: values
+ T1+, T2+ <: values+
+ T*, T1*, T2* <: values*
+
+
+Datatype
+ tuples(T*) ::= tuple(_:T*)
+/*
+ `T*` can be any sequence of types, including `( )` and `values*`.
+
+ The values of type `tuples(T1, ..., Tn)` are of the form `tuple(V1, ..., Vn)`
+ with `V1:T1`, ..., `Vn:Tn`.
+*/
+
+
+Funcon
+ tuple-elements(_:tuples(T*)) : =>(T*)
+Rule
+ tuple-elements(tuple(V*:T*)) ~> V*
+
+
+Funcon
+ tuple-zip(_:tuples(values*), _:tuples(values*)) : =>(tuples(values,values))*
+/*
+ `tuple-zip(TV1, TV2)` takes two tuples, and returns the sequence of pairs of
+ their elements, provided that they have the same length. If they have
+ different lengths, the last elements of the longer sequence are ignored.
+*/
+Rule
+ tuple-zip(tuple(V1:T1, V1*:T1*), tuple(V2:T2, V2*:T2*))
+ ~> (tuple(V1, V2), tuple-zip(tuple(V1*), tuple(V2*)))
+Rule
+ tuple-zip(tuple( ), tuple( )) ~> ( )
+Rule
+ tuple-zip(tuple(V1+:T1+), tuple( )) ~> ( )
+Rule
+ tuple-zip(tuple( ), tuple(V2+:T2+)) ~> ( )
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Tuples/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Tuples/index.md
new file mode 100644
index 0000000..c2e5f19
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Tuples/index.md
@@ -0,0 +1,84 @@
+---
+layout: default
+title: "Tuples"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Tuples.cbs]
+-----------------------------
+
+### Tuples
+
+
+
+
+
+
+
+
+
+Datatype
+ tuples(T*) ::= tuple(_:T*)
+
+
+ T* can be any sequence of types, including ( ) and values*.
+
+ The values of type tuples(T1, ..., Tn) are of the form tuple(V1, ..., Vn)
+ with V1:T1, ..., Vn:Tn.
+
+
+
+
+
+
+
+ tuple-zip(TV1, TV2) takes two tuples, and returns the sequence of pairs of
+ their elements, provided that they have the same length. If they have
+ different lengths, the last elements of the longer sequence are ignored.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Tuples.cbs]: Tuples.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Tuples/Tuples.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Tuples/tests/tuple-zip.config b/IBAF-cbs/Funcons-beta/Values/Composite/Tuples/tests/tuple-zip.config
new file mode 100644
index 0000000..172cc09
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Tuples/tests/tuple-zip.config
@@ -0,0 +1,18 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(tuple tuple-zip(tuple( ),tuple( )), tuple( )))
+ , check-true(is-equal(tuple tuple-zip(tuple(1),tuple(2)), tuple(tuple(1,2))))
+ , check-true(is-equal(tuple tuple-zip(tuple(1,3),tuple(2,4)),
+ tuple(tuple(1,2),tuple(3,4))))
+ , check-true(is-equal(tuple tuple-zip(tuple(1,3,5),tuple(2,4,6)),
+ tuple(tuple(1,2),tuple(3,4),tuple(5,6))))
+ , check-true(is-equal(tuple tuple-zip(tuple(1),tuple( )), tuple( )))
+ , check-true(is-equal(tuple tuple-zip(tuple( ),tuple(1)), tuple( )))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Variants/Variants.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Variants/Variants.cbs
new file mode 100644
index 0000000..3938779
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Variants/Variants.cbs
@@ -0,0 +1,32 @@
+### Variants
+
+[
+ Datatype variants
+ Funcon variant
+ Funcon variant-id
+ Funcon variant-value
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ variants(T) ::= variant(_:identifiers, _:T)
+/*
+ A value of type `variants(T)` is a pair formed from an identifier and
+ a value of type `T`.
+*/
+
+
+Funcon
+ variant-id(_:variants(T)) : =>identifiers
+Rule
+ variant-id(variant(I:identifiers, _:T)) ~> I
+
+
+Funcon
+ variant-value(_:variants(T)) : =>T
+Rule
+ variant-value(variant(_:identifiers, V:T)) ~> V
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Variants/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Variants/index.md
new file mode 100644
index 0000000..7808e96
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Variants/index.md
@@ -0,0 +1,67 @@
+---
+layout: default
+title: "Variants"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Variants.cbs]
+-----------------------------
+
+### Variants
+
+
+
+
+
+
+
+
+
+
+
+
+ A value of type variants(T) is a pair formed from an identifier and
+ a value of type T.
+
+
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Variants.cbs]: Variants.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Variants/Variants.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Vectors/Vectors.cbs b/IBAF-cbs/Funcons-beta/Values/Composite/Vectors/Vectors.cbs
new file mode 100644
index 0000000..4469472
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Vectors/Vectors.cbs
@@ -0,0 +1,21 @@
+### Vectors
+
+[
+ Datatype vectors
+ Funcon vector
+ Funcon vector-elements
+]
+
+
+Meta-variables
+ T <: values
+
+
+Datatype
+ vectors(T) ::= vector(_:(T)*)
+
+
+Funcon
+ vector-elements(_:vectors(T)) : =>(T)*
+Rule
+ vector-elements(vector(V*:(T)*)) ~> V*
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Vectors/index.md b/IBAF-cbs/Funcons-beta/Values/Composite/Vectors/index.md
new file mode 100644
index 0000000..2117a5e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Vectors/index.md
@@ -0,0 +1,57 @@
+---
+layout: default
+title: "Vectors"
+parent: Composite
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Vectors.cbs]
+-----------------------------
+
+### Vectors
+
+
+
+
+
+
+
+
+
+Datatype
+ vectors(T) ::= vector(_:(T)*)
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Vectors.cbs]: Vectors.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Composite/Vectors/Vectors.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Composite/Vectors/tests/vector.config b/IBAF-cbs/Funcons-beta/Values/Composite/Vectors/tests/vector.config
new file mode 100644
index 0000000..686a58e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Composite/Vectors/tests/vector.config
@@ -0,0 +1,21 @@
+general {
+ funcon-term:
+ initialise-giving finalise-failing
+ sequential (
+ print vector(),
+ print vector(1,2),
+ print is-in-type(vector(), vectors(integers)),
+ print is-in-type(vector(1,2), vectors(integers))
+ )
+ ;
+}
+
+tests {
+ result-term: null-value;
+ standard-out: [
+ vector(),
+ vector(1,2),
+ true,
+ true
+ ];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/Booleans.cbs b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/Booleans.cbs
new file mode 100644
index 0000000..b2c560e
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/Booleans.cbs
@@ -0,0 +1,87 @@
+### Booleans
+
+[
+ Datatype booleans Alias bools
+ Funcon true
+ Funcon false
+ Funcon not
+ Funcon implies
+ Funcon and
+ Funcon or
+ Funcon exclusive-or Alias xor
+]
+
+
+Datatype
+ booleans ::= true | false
+Alias
+ bools = booleans
+
+
+Funcon
+ not(_:booleans) : =>booleans
+/*
+ `not(B)` is logical negation.
+*/
+Rule
+ not(false) ~> true
+Rule
+ not(true) ~> false
+
+
+Funcon
+ implies(_:booleans, _:booleans) : =>booleans
+/*
+ `implies(B1, B2)` is logical implication.
+*/
+Rule
+ implies(false, false) ~> true
+Rule
+ implies(false, true) ~> true
+Rule
+ implies(true, true) ~> true
+Rule
+ implies(true, false) ~> false
+
+
+Funcon
+ and(_:booleans*) : =>booleans
+/*
+ `and(B, ...)` is logical conjunction of any number of Boolean values.
+*/
+Rule
+ and( ) ~> true
+Rule
+ and(false, _*:booleans*) ~> false
+Rule
+ and(true, B*:booleans*) ~> and(B*)
+
+
+Funcon
+ or(_:booleans*) : =>booleans
+/*
+ `or(B, ...)` is logical disjunction of any number of Boolean values.
+*/
+Rule
+ or( ) ~> false
+Rule
+ or(true, _*:booleans*) ~> true
+Rule
+ or(false, B*:booleans*) ~> or(B*)
+
+
+Funcon
+ exclusive-or(_:booleans, _:booleans) : =>booleans
+Alias
+ xor = exclusive-or
+/*
+ `exclusive-or(B1, B2)` is exclusive disjunction.
+*/
+Rule
+ exclusive-or(false, false) ~> false
+Rule
+ exclusive-or(false, true) ~> true
+Rule
+ exclusive-or(true, false) ~> true
+Rule
+ exclusive-or(true, true) ~> false
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/index.md b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/index.md
new file mode 100644
index 0000000..854a0bd
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/index.md
@@ -0,0 +1,128 @@
+---
+layout: default
+title: "Booleans"
+parent: Primitive
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Booleans.cbs]
+-----------------------------
+
+### Booleans
+
+
+
+
+
+
+Datatype
+ booleans ::= true | false
+Alias
+ bools = booleans
+
+
+
+
+
+ not(B) is logical negation.
+
+
+
+
+
+
+
+ implies(B1, B2) is logical implication.
+
+
+
+
+
+
+
+ and(B, ...) is logical conjunction of any number of Boolean values.
+
+
+
+
+
+
+
+ or(B, ...) is logical disjunction of any number of Boolean values.
+
+
+
+
+
+
+ exclusive-or(B1, B2) is exclusive disjunction.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Booleans.cbs]: Booleans.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Primitive/Booleans/Booleans.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/and.config b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/and.config
new file mode 100644
index 0000000..dce17c8
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/and.config
@@ -0,0 +1,20 @@
+general {
+ funcon-term: sequential (
+ check-true(and( ))
+ , check-true(and(true))
+ , check-true(and(true,true))
+ , check-true(and(true,true,true))
+ , check-true(not and(false))
+ , check-true(not and(false,true))
+ , check-true(not and(true,false))
+ , check-true(not and(false,true,true))
+ , check-true(not and(true,true,false))
+ , check-true(not and(true,true,false,true))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/exclusive-or.config b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/exclusive-or.config
new file mode 100644
index 0000000..5ce76ec
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/exclusive-or.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term: sequential (
+ check-true(exclusive-or(false, true))
+ , check-true(exclusive-or(true, false))
+ , check-true(not exclusive-or(false, false))
+ , check-true(not exclusive-or(true, true))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/implies.config b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/implies.config
new file mode 100644
index 0000000..5345ca5
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/implies.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term: sequential (
+ check-true(implies(false, false))
+ , check-true(implies(false, true))
+ , check-true(implies(true, true))
+ , check-true(not implies(true, false))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/not.config b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/not.config
new file mode 100644
index 0000000..47ae409
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/not.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(not false, true))
+ , check-true(is-equal(not true, false))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/or.config b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/or.config
new file mode 100644
index 0000000..dd88114
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Booleans/tests/or.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term: sequential (
+ check-true(or(true))
+ , check-true(or(true, false))
+ , check-true(or(false, true))
+ , check-true(or(false, false, true))
+ , check-true(or(false, false, true, false))
+ , check-true(not or( ))
+ , check-true(not or(false))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Characters/Characters.cbs b/IBAF-cbs/Funcons-beta/Values/Primitive/Characters/Characters.cbs
new file mode 100644
index 0000000..7d1466a
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Characters/Characters.cbs
@@ -0,0 +1,171 @@
+### Characters
+
+[
+ Type characters Alias chars
+ Datatype unicode-characters Alias unicode-chars
+ Type unicode-points
+ Funcon unicode-character Alias unicode-char
+ Funcon unicode-point Alias unicode
+ Type basic-multilingual-plane-characters Alias bmp-chars
+ Type basic-multilingual-plane-points
+ Type iso-latin-1-characters Alias latin-1-chars
+ Type iso-latin-1-points
+ Type ascii-characters Alias ascii-chars
+ Type ascii-points
+ Funcon ascii-character Alias ascii-char
+ Funcon utf-8
+ Funcon utf-16
+ Funcon utf-32
+ Funcon backspace
+ Funcon horizontal-tab
+ Funcon line-feed
+ Funcon form-feed
+ Funcon carriage-return
+ Funcon double-quote
+ Funcon single-quote
+ Funcon backslash
+]
+
+
+Built-in Type
+ characters <: values
+/*
+ Literal characters can be written `'C'` where `C` is any visible character
+ other than a `single-quote` or `backslash` character, which need to be
+ escaped as `'\''` and `'\\'`.
+*/
+Alias
+ chars = characters
+
+
+#### Unicode character set
+/*
+ The set of Unicode characters and allocated points is open to extension.
+ See https://en.wikipedia.org/wiki/Plane_(Unicode)
+*/
+
+Built-in Datatype
+ unicode-characters <: characters
+Alias
+ unicode-chars = unicode-characters
+Built-in Type
+ unicode-points <: bounded-integers(0, unsigned-bit-vector-maximum(21))
+Built-in Funcon
+ unicode-character(_:unicode-points) : unicode-characters
+Alias
+ unicode-char = unicode-character
+/*
+ The values in `unicode-characters` are the values of
+ `unicode-character(UP:unicode-points)`.
+*/
+Funcon
+ unicode-point(_:unicode-characters) : =>unicode-points
+Alias
+ unicode = unicode-point
+Rule
+ unicode-point(unicode-character(UP:unicode-points)) ~> UP
+
+
+#### Unicode basic multilingual plane
+/*
+ The set of Unicode BMP characters and allocated points is open to extension.
+*/
+
+Built-in Datatype
+ basic-multilingual-plane-characters <: unicode-characters
+Alias
+ bmp-chars = basic-multilingual-plane-characters
+Built-in Type
+ basic-multilingual-plane-points <:
+ bounded-integers(0, unsigned-bit-vector-maximum(17))
+/*
+ The values in `basic-multilingual-plane-characters` are the values of
+ `unicode-character(BMPP:basic-multilingual-plane-points)`.
+*/
+
+
+#### ISO Latin-1 character set
+
+Built-in Datatype
+ iso-latin-1-characters <: basic-multilingual-plane-characters
+Alias
+ latin-1-chars = iso-latin-1-characters
+Type
+ iso-latin-1-points ~> bounded-integers(0, unsigned-bit-vector-maximum(8))
+/*
+ The values in `iso-latin-1-characters` are the values of
+ `unicode-character(ILP:iso-latin-1-points)`.
+*/
+
+
+#### ASCII character set
+
+Built-in Type
+ ascii-characters <: iso-latin-1-characters
+Alias
+ ascii-chars = ascii-characters
+Type
+ ascii-points ~> bounded-integers(0, unsigned-bit-vector-maximum(7))
+/*
+ The values in `ascii-characters` are the values of
+ `unicode-character(AP:ascii-points)`.
+*/
+Funcon
+ ascii-character(_:strings) : =>ascii-characters?
+Alias
+ ascii-char = ascii-character
+/*
+ `ascii-character"C"` takes a string. When it consists of a single ASCII
+ character `C` it gives the character, otherwise `( )`.
+*/
+Rule
+ ascii-character[C:ascii-characters] ~> C
+Rule
+ C : ~ ascii-characters
+ ------------------------------------
+ ascii-character[C:characters] ~> ( )
+Rule
+ length(C*) =/= 1
+ --------------------------------------
+ ascii-character[C*:characters*] ~> ( )
+
+
+#### Character point encodings
+/*
+ See https://en.wikipedia.org/wiki/Character_encoding
+*/
+
+Built-in Funcon
+ utf-8(_:unicode-points) : =>(bytes, (bytes, (bytes, bytes?)? )? )
+Built-in Funcon
+ utf-16(_:unicode-points) : =>(bit-vectors(16), (bit-vectors(16))? )
+Built-in Funcon
+ utf-32(_:unicode-points) : =>bit-vectors(32)
+
+
+#### Control characters
+
+Funcon
+ backspace : =>ascii-characters
+ ~> unicode-character(hexadecimal-natural"0008")
+Funcon
+ horizontal-tab : =>ascii-characters
+ ~> unicode-character(hexadecimal-natural"0009")
+Funcon
+ line-feed : =>ascii-characters
+ ~> unicode-character(hexadecimal-natural"000a")
+Funcon
+ form-feed : =>ascii-characters
+ ~> unicode-character(hexadecimal-natural"000c")
+Funcon
+ carriage-return : =>ascii-characters
+ ~> unicode-character(hexadecimal-natural"000d")
+Funcon
+ double-quote : =>ascii-characters
+ ~> unicode-character(hexadecimal-natural"0022")
+Funcon
+ single-quote : =>ascii-characters
+ ~> unicode-character(hexadecimal-natural"0027")
+Funcon
+ backslash : =>ascii-characters
+ ~> unicode-character(hexadecimal-natural"005c")
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Characters/index.md b/IBAF-cbs/Funcons-beta/Values/Primitive/Characters/index.md
new file mode 100644
index 0000000..f61486b
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Characters/index.md
@@ -0,0 +1,225 @@
+---
+layout: default
+title: "Characters"
+parent: Primitive
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Characters.cbs]
+-----------------------------
+
+### Characters
+
+
+
+
+
+Built-in Type
+ characters <: values
+
+ Literal characters can be written 'C' where C is any visible character
+ other than a single-quote or backslash character, which need to be
+ escaped as '\'' and '\\'.
+
+
+
+
+
+#### Unicode character set
+
+ The set of Unicode characters and allocated points is open to extension.
+ See https://en.wikipedia.org/wiki/Plane_(Unicode)
+
+
+
+
+
+
+
+
+ The values in unicode-characters are the values of
+ unicode-character(UP:unicode-points).
+
+
+
+
+
+
+
+#### Unicode basic multilingual plane
+
+ The set of Unicode BMP characters and allocated points is open to extension.
+
+
+
+
+
+ The values in basic-multilingual-plane-characters are the values of
+ unicode-character(BMPP:basic-multilingual-plane-points).
+
+
+
+#### ISO Latin-1 character set
+
+
+
+
+
+
+
+ The values in iso-latin-1-characters are the values of
+ unicode-character(ILP:iso-latin-1-points).
+
+
+
+#### ASCII character set
+
+
+
+
+
+
+
+ The values in ascii-characters are the values of
+ unicode-character(AP:ascii-points).
+
+
+
+
+ ascii-character"C" takes a string. When it consists of a single ASCII
+ character C it gives the character, otherwise ( ).
+
+
+
+
+
+#### Character point encodings
+
+ See https://en.wikipedia.org/wiki/Character_encoding
+
+
+
+
+
+#### Control characters
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Characters.cbs]: Characters.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Primitive/Characters/Characters.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Floats/Floats.cbs b/IBAF-cbs/Funcons-beta/Values/Primitive/Floats/Floats.cbs
new file mode 100644
index 0000000..4687771
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Floats/Floats.cbs
@@ -0,0 +1,230 @@
+### Floats
+
+[
+ Datatype float-formats
+ Funcon binary32
+ Funcon binary64
+ Funcon binary128
+ Funcon decimal64
+ Funcon decimal128
+ Type floats
+ Funcon float
+ Funcon quiet-not-a-number Alias qNaN
+ Funcon signaling-not-a-number Alias sNaN
+ Funcon positive-infinity Alias pos-inf
+ Funcon negative-infinity Alias neg-inf
+ Funcon float-convert
+ Funcon decimal-float
+ Funcon float-equal
+ Funcon float-is-less
+ Funcon float-is-less-or-equal
+ Funcon float-is-greater
+ Funcon float-is-greater-or-equal
+ Funcon float-negate
+ Funcon float-absolute-value
+ Funcon float-add
+ Funcon float-subtract
+ Funcon float-multiply
+ Funcon float-multiply-add
+ Funcon float-divide
+ Funcon float-remainder
+ Funcon float-sqrt
+ Funcon float-integer-power
+ Funcon float-float-power
+ Funcon float-round-ties-to-even
+ Funcon float-round-ties-to-infinity
+ Funcon float-floor
+ Funcon float-ceiling
+ Funcon float-truncate
+ Funcon float-pi
+ Funcon float-e
+ Funcon float-log
+ Funcon float-log10
+ Funcon float-exp
+ Funcon float-sin
+ Funcon float-cos
+ Funcon float-tan
+ Funcon float-asin
+ Funcon float-acos
+ Funcon float-atan
+ Funcon float-sinh
+ Funcon float-cosh
+ Funcon float-tanh
+ Funcon float-asinh
+ Funcon float-acosh
+ Funcon float-atanh
+ Funcon float-atan2
+]
+
+/*
+ Floating-point numbers according to the IEEE 754 Standard (2008).
+
+ See:
+ - http://doi.org/10.1109/IEEESTD.2008.4610935
+ - https://en.wikipedia.org/wiki/IEEE_754
+*/
+
+Datatype
+ float-formats ::= binary32 | binary64 | binary128 | decimal64 | decimal128
+Built-in Type
+ floats(_:float-formats)
+/*
+ Note that for distinct formats `FF1`, `FF2`, the types `floats(FF1)` and
+ `floats(FF2)` are not necessarily disjoint.
+*/
+
+Built-in Funcon
+ float(FF:float-formats,
+ _:bounded-integers(0, 1), _:natural-numbers, _:integers) : =>floats(FF)
+/*
+ Each finite number is described by three integers:
+ * s = a sign (zero or one),
+ * c = a significand (or 'coefficient'),
+ * q = an exponent.
+ The numerical value of a finite number is (-1)^s * c * b^q
+ where b is the base (2 or 10), also called radix.
+
+ The possible finite values that can be represented in a format
+ are determined by the base b, the number of digits in the significand
+ (precision p), and the exponent parameter emax:
+ * c must be an integer in the range zero through (b^p)-1
+ (e.g., if b=10 and p=7 then c is 0 through 9999999);
+ * q must be an integer such that 1-emax <= q+p-1 <= emax
+ (e.g., if p=7 and emax=96 then q is -101 through 90).
+
+ Note that `float(FF, S, C, Q)` is not a 1-1 operation.
+*/
+
+Built-in Funcon
+ quiet-not-a-number(FF:float-formats) : floats(FF)
+Alias
+ qNaN = quiet-not-a-number
+Built-in Funcon
+ signaling-not-a-number(FF:float-formats) : floats(FF)
+Alias
+ sNaN = signaling-not-a-number
+Built-in Funcon
+ positive-infinity(FF:float-formats) : floats(FF)
+Alias
+ pos-inf = positive-infinity
+Built-in Funcon
+ negative-infinity(FF:float-formats) : floats(FF)
+Alias
+ neg-inf = negative-infinity
+
+
+#### Conversions
+
+Built-in Funcon
+ float-convert(FF1:float-formats,
+ FF2:float-formats, F:floats(FF1)) : =>floats(FF2)
+Built-in Funcon
+ decimal-float(FF:float-formats,
+ _:strings, _:strings, _:strings) : =>floats(FF)
+/*
+ `decimal-float(F, "M", "N", "E")` is an approximation in `floats(FF)` to the
+ value of 'M.N' times 10 to the power 'E', where "M.N" is decimal notation
+ (optionally-signed) for a fixed-point number and "E" is decimal notation
+ (optionally signed) for an integer. When any argument string is invalid,
+ the result is `quiet-not-a-number(F)`.
+*/
+
+
+#### Comparison
+
+Built-in Funcon
+ float-equal(FF:float-formats,
+ _:floats(FF), _:floats(FF)) : =>booleans
+Built-in Funcon
+ float-is-less(FF:float-formats,
+ _:floats(FF), _:floats(FF)) : =>booleans
+Built-in Funcon
+ float-is-less-or-equal(FF:float-formats,
+ _:floats(FF), _:floats(FF)) : =>booleans
+Built-in Funcon
+ float-is-greater(FF:float-formats,
+ _:floats(FF), _:floats(FF)) : =>booleans
+Built-in Funcon
+ float-is-greater-or-equal(FF:float-formats,
+ _:floats(FF), _:floats(FF)) : =>booleans
+
+
+#### Arithmetic
+
+Built-in Funcon
+ float-negate(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-absolute-value(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-add(FF:float-formats, _:floats(FF), _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-subtract(FF:float-formats, _:floats(FF), _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-multiply(FF:float-formats, _:floats(FF), _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-multiply-add(FF:float-formats,
+ _:floats(FF), _:floats(FF), _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-divide(FF:float-formats, _:floats(FF), _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-remainder(FF:float-formats, _:floats(FF), _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-sqrt(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-integer-power(FF:float-formats, _:floats(FF), _:integers) : =>floats(FF)
+Built-in Funcon
+ float-float-power(FF:float-formats, _:floats(FF), _:floats(FF)) : =>floats(FF)
+
+
+#### Rounding
+
+Built-in Funcon
+ float-round-ties-to-even(FF:float-formats, _:floats(FF)) : =>integers
+Built-in Funcon
+ float-round-ties-to-infinity(FF:float-formats, _:floats(FF)) : =>integers
+Built-in Funcon
+ float-floor(FF:float-formats, _:floats(FF)) : =>integers
+Built-in Funcon
+ float-ceiling(FF:float-formats, _:floats(FF)) : =>integers
+Built-in Funcon
+ float-truncate(FF:float-formats, _:floats(FF)) : =>integers
+
+
+#### Miscellaneous
+
+Built-in Funcon
+ float-pi(FF:float-formats) : =>floats(FF)
+Built-in Funcon
+ float-e(FF:float-formats) : =>floats(FF)
+Built-in Funcon
+ float-log(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-log10(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-exp(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-sin(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-cos(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-tan(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-asin(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-acos(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-atan(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-sinh(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-cosh(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-tanh(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-asinh(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-acosh(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-atanh(FF:float-formats, _:floats(FF)) : =>floats(FF)
+Built-in Funcon
+ float-atan2(FF:float-formats, _:floats(FF), _:floats(FF)) : =>floats(FF)
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Floats/index.md b/IBAF-cbs/Funcons-beta/Values/Primitive/Floats/index.md
new file mode 100644
index 0000000..3969d11
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Floats/index.md
@@ -0,0 +1,262 @@
+---
+layout: default
+title: "Floats"
+parent: Primitive
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Floats.cbs]
+-----------------------------
+
+### Floats
+
+
+
+
+
+ Floating-point numbers according to the IEEE 754 Standard (2008).
+
+ See:
+ - http://doi.org/10.1109/IEEESTD.2008.4610935
+ - https://en.wikipedia.org/wiki/IEEE_754
+
+
+Datatype
+ float-formats ::= binary32 | binary64 | binary128 | decimal64 | decimal128
+
+
+ Note that for distinct formats FF1, FF2, the types floats(FF1) and
+ floats(FF2) are not necessarily disjoint.
+
+
+
+
+ Each finite number is described by three integers:
+ * s = a sign (zero or one),
+ * c = a significand (or 'coefficient'),
+ * q = an exponent.
+ The numerical value of a finite number is (-1)^s * c * b^q
+ where b is the base (2 or 10), also called radix.
+
+ The possible finite values that can be represented in a format
+ are determined by the base b, the number of digits in the significand
+ (precision p), and the exponent parameter emax:
+ * c must be an integer in the range zero through (b^p)-1
+ (e.g., if b=10 and p=7 then c is 0 through 9999999);
+ * q must be an integer such that 1-emax <= q+p-1 <= emax
+ (e.g., if p=7 and emax=96 then q is -101 through 90).
+
+ Note that float(FF, S, C, Q) is not a 1-1 operation.
+
+
+
+
+
+
+
+
+
+
+
+#### Conversions
+
+
+
+
+ decimal-float(F, "M", "N", "E") is an approximation in floats(FF) to the
+ value of 'M.N' times 10 to the power 'E', where "M.N" is decimal notation
+ (optionally-signed) for a fixed-point number and "E" is decimal notation
+ (optionally signed) for an integer. When any argument string is invalid,
+ the result is quiet-not-a-number(F).
+
+
+
+#### Comparison
+
+
+
+
+
+
+#### Arithmetic
+
+
+
+
+
+
+
+
+
+
+
+
+#### Rounding
+
+
+
+
+
+
+#### Miscellaneous
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Floats.cbs]: Floats.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Primitive/Floats/Floats.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Integers/Integers.cbs b/IBAF-cbs/Funcons-beta/Values/Primitive/Integers/Integers.cbs
new file mode 100644
index 0000000..ca6e82d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Integers/Integers.cbs
@@ -0,0 +1,230 @@
+### Integers
+
+[
+ Type integers Alias ints
+ Type integers-from Alias from
+ Type integers-up-to Alias up-to
+ Type bounded-integers Alias bounded-ints
+ Type positive-integers Alias pos-ints
+ Type negative-integers Alias neg-ints
+ Type natural-numbers Alias nats
+ Funcon natural-successor Alias nat-succ
+ Funcon natural-predecessor Alias nat-pred
+ Funcon integer-add Alias int-add
+ Funcon integer-subtract Alias int-sub
+ Funcon integer-multiply Alias int-mul
+ Funcon integer-divide Alias int-div
+ Funcon integer-modulo Alias int-mod
+ Funcon integer-power Alias int-pow
+ Funcon integer-absolute-value Alias int-abs
+ Funcon integer-negate Alias int-neg
+ Funcon integer-is-less Alias is-less
+ Funcon integer-is-less-or-equal Alias is-less-or-equal
+ Funcon integer-is-greater Alias is-greater
+ Funcon integer-is-greater-or-equal Alias is-greater-or-equal
+ Funcon binary-natural Alias binary
+ Funcon octal-natural Alias octal
+ Funcon decimal-natural Alias decimal
+ Funcon hexadecimal-natural Alias hexadecimal
+ Funcon integer-sequence
+]
+
+
+Built-in Type
+ integers
+Alias
+ ints = integers
+/*
+ `integers` is the type of unbounded integers. Decimal notation is used to
+ express particular integer values.
+*/
+
+
+#### Subtypes of integers
+
+Built-in Type
+ integers-from(_:integers) <: integers
+Alias
+ from = integers-from
+/*
+ `integers-from(M)` is the subtype of integers greater than or equal to `M`.
+*/
+
+
+Built-in Type
+ integers-up-to(_:integers) <: integers
+Alias
+ up-to = integers-up-to
+/*
+ `integers-up-to(N)` is the subtype of integers less than or equal to `N`.
+*/
+
+
+Type
+ bounded-integers(M:integers, N:integers)
+ ~> integers-from(M) & integers-up-to(N)
+Alias
+ bounded-ints = bounded-integers
+/*
+ `bounded-integers(M,N)` is the subtype of integers from `M` to `N`, inclusive.
+*/
+
+
+Type
+ positive-integers ~> integers-from(1)
+Alias
+ pos-ints = positive-integers
+
+
+Type
+ negative-integers ~> integers-up-to(-1)
+Alias
+ neg-ints = negative-integers
+
+
+#### Natural numbers
+
+Type
+ natural-numbers ~> integers-from(0)
+Alias
+ nats = natural-numbers
+
+
+Built-in Funcon
+ natural-successor(N:natural-numbers) : =>natural-numbers
+Alias
+ nat-succ = natural-successor
+
+
+Built-in Funcon
+ natural-predecessor(_:natural-numbers) : =>natural-numbers?
+Alias
+ nat-pred = natural-predecessor
+Assert
+ natural-predecessor(0) == ( )
+
+
+#### Arithmetic
+
+Built-in Funcon
+ integer-add(_:integers*) : =>integers
+Alias
+ int-add = integer-add
+
+
+Built-in Funcon
+ integer-subtract(_:integers, _:integers) : =>integers
+Alias
+ int-sub = integer-subtract
+
+
+Built-in Funcon
+ integer-multiply(_:integers*) : =>integers
+Alias
+ int-mul = integer-multiply
+
+
+Built-in Funcon
+ integer-divide(_:integers, _:integers) : =>integers?
+Alias
+ int-div = integer-divide
+Assert
+ integer-divide(_:integers, 0) == ( )
+
+
+Built-in Funcon
+ integer-modulo(_:integers, _:integers) : =>integers?
+Alias
+ int-mod = integer-modulo
+Assert
+ integer-modulo(_:integers, 0) == ( )
+
+
+Built-in Funcon
+ integer-power(_:integers, _:natural-numbers) : =>integers
+Alias
+ int-pow = integer-power
+
+Built-in Funcon
+ integer-absolute-value(_:integers) : =>natural-numbers
+Alias
+ int-abs = integer-absolute-value
+
+
+Funcon
+ integer-negate(N:integers) : =>integers
+ ~> integer-subtract(0, N)
+Alias
+ int-neg = integer-negate
+
+
+#### Comparison
+
+Built-in Funcon
+ integer-is-less(_:integers, _:integers) : =>booleans
+Alias
+ is-less = integer-is-less
+
+
+Built-in Funcon
+ integer-is-less-or-equal(_:integers, _:integers) : =>booleans
+Alias
+ is-less-or-equal = integer-is-less-or-equal
+
+
+Built-in Funcon
+ integer-is-greater(_:integers, _:integers) : =>booleans
+Alias
+ is-greater = integer-is-greater
+
+
+Built-in Funcon
+ integer-is-greater-or-equal(_:integers, _:integers) : =>booleans
+Alias
+ is-greater-or-equal = integer-is-greater-or-equal
+
+
+#### Conversion
+
+Built-in Funcon
+ binary-natural(_:strings) : =>natural-numbers?
+Alias
+ binary = binary-natural
+
+
+Built-in Funcon
+ octal-natural(_:strings) : =>natural-numbers?
+Alias
+ octal = octal-natural
+
+
+Built-in Funcon
+ decimal-natural(_:strings) : =>natural-numbers?
+Alias
+ decimal = decimal-natural
+/*
+ Literal natural numbers `N` are equivalent to `decimal-natural"N"`.
+*/
+
+
+Built-in Funcon
+ hexadecimal-natural(_:strings) : =>natural-numbers?
+Alias
+ hexadecimal = hexadecimal-natural
+
+
+Funcon
+ integer-sequence(_:integers, _:integers) : =>integers*
+/*
+ `integer-sequence(M, N)` is the seqeunce of integers from `M` to `N`,
+ except that if `M` is greater than `N`, it is the empty sequence.
+*/
+Rule
+ is-greater(M, N) == false
+ ------------------------------------------------
+ integer-sequence(M:integers, N:integers)
+ ~> (M, integer-sequence(integer-add(M, 1), N))
+Rule
+ is-greater(M, N) == true
+ -----------------------------------------------
+ integer-sequence(M:integers, N:integers) ~> ( )
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Integers/index.md b/IBAF-cbs/Funcons-beta/Values/Primitive/Integers/index.md
new file mode 100644
index 0000000..9341675
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Integers/index.md
@@ -0,0 +1,263 @@
+---
+layout: default
+title: "Integers"
+parent: Primitive
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Integers.cbs]
+-----------------------------
+
+### Integers
+
+
+
+
+
+
+Built-in Type
+ integers
+Alias
+ ints = integers
+
+
+ integers is the type of unbounded integers. Decimal notation is used to
+ express particular integer values.
+
+
+
+#### Subtypes of integers
+
+
+
+
+
+ integers-from(M) is the subtype of integers greater than or equal to M.
+
+
+
+
+ integers-up-to(N) is the subtype of integers less than or equal to N.
+
+
+
+
+ bounded-integers(M,N) is the subtype of integers from M to N, inclusive.
+
+
+
+
+
+
+
+#### Natural numbers
+
+
+
+
+
+
+
+
+
+
+
+
+#### Arithmetic
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+#### Comparison
+
+
+
+
+
+
+
+
+
+
+
+
+#### Conversion
+
+
+
+
+
+
+
+
+
+ Literal natural numbers N are equivalent to decimal-natural"N".
+
+
+
+
+
+
+
+ integer-sequence(M, N) is the seqeunce of integers from M to N,
+ except that if M is greater than N, it is the empty sequence.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Integers.cbs]: Integers.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Primitive/Integers/Integers.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Null/Null.cbs b/IBAF-cbs/Funcons-beta/Values/Primitive/Null/Null.cbs
new file mode 100644
index 0000000..4808465
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Null/Null.cbs
@@ -0,0 +1,15 @@
+### Null
+
+[
+Datatype null-type
+Funcon null-value Alias null
+]
+
+
+Datatype
+ null-type ::= null-value
+Alias
+ null = null-value
+/*
+ The only element of the datatype `null-type` is `null-value`.
+*/
diff --git a/IBAF-cbs/Funcons-beta/Values/Primitive/Null/index.md b/IBAF-cbs/Funcons-beta/Values/Primitive/Null/index.md
new file mode 100644
index 0000000..8012a76
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Primitive/Null/index.md
@@ -0,0 +1,52 @@
+---
+layout: default
+title: "Null"
+parent: Primitive
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Null.cbs]
+-----------------------------
+
+### Null
+
+
+
+
+
+
+Datatype
+ null-type ::= null-value
+Alias
+ null = null-value
+
+
+ The only element of the datatype null-type is null-value.
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Null.cbs]: Null.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Primitive/Null/Null.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Value-Types/Value-Types.cbs b/IBAF-cbs/Funcons-beta/Values/Value-Types/Value-Types.cbs
new file mode 100644
index 0000000..17a6c39
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Value-Types/Value-Types.cbs
@@ -0,0 +1,216 @@
+## Value Types
+
+[
+ Type values Alias vals
+ Type value-types Alias types
+ Type empty-type
+ Funcon is-in-type Alias is
+ Funcon is-value Alias is-val
+ Funcon when-true Alias when
+ Type cast-to-type Alias cast
+ Type ground-values Alias ground-vals
+ Funcon is-equal Alias is-eq
+]
+
+
+### Values
+
+Built-in Type
+ values
+Alias
+ vals = values
+/*
+ The type `values` includes all values provided by CBS.
+
+ Some funcons are declared as value constructors. Values are constructed by
+ applying value constructor funcons to the required arguments.
+
+ Values are immutable and context-independent. Their structure can be
+ inspected using patterns formed from value constructors and variables.
+ Computations can be extracted from values and executed, but the structure
+ of computations cannot be inspected.
+
+ Some types of values and their funcons are declared as built-in, and not
+ further specified in CBS. New types of built-in values can be added to CBS
+ by its developers.
+
+ New algebraic datatypes may be declared by users of CBS. Their values are
+ disjoint from built-in values.
+*/
+
+
+Meta-variables
+ T, T1, T2 <: values
+
+
+### Types
+
+Built-in Type
+ value-types
+Alias
+ types = value-types
+Built-in Type
+ empty-type
+/*
+ A type `T` is a value that represents a set of values.
+
+ The values of type `types` are all the types, including `types` itself.
+
+ The formula ``V : T`` holds when `V` is a value of type `T`, i.e., `V` is in
+ the set represented by the type `T`.
+
+ The formula ``T1 <: T2`` holds when `T1` is a subtype of `T2`, i.e., the set
+ represented by `T1` is a subset of the set represented by `T2`.
+
+ The set of types forms a Boolean algebra with the following operations and
+ constants:
+ * `T1 & T2` (meet/intersection)
+ * `T1 | T2` (join/union)
+ * `~ T` (complement)
+ * `values` (top)
+ * `empty-type` (bottom)
+
+ Subtyping: ``T1 <: T2`` is the partial order defined by the algebra.
+
+ Subsumption: If ``V : T1`` and ``T1 <: T2`` both hold, so does ``V : T2``.
+
+ Indivisibility: For each value `V` and type `T`, either ``V : T`` or
+ ``V : ~T`` holds.
+
+ Universality: ``V : values`` holds for all values `V`.
+
+ Emptiness: ``V : empty-type`` holds for no value `V`.
+
+ 'Type N' declares the name 'N' to refer to a fresh value constructor
+ and includes it as an element of `types`.
+
+ 'Type N ~> T' moreover specifies 'Rule N ~> T', so that 'N' can be used as
+ an abbreviation for the type term 'T'.
+
+ 'Type N <: T' declares the name 'N' to refer to a fresh value constructor
+ in `types`, and asserts 'N <: T'.
+
+ Parametrised type declarations introduce generic (possibly dependent) types,
+ i.e., families of individual types, indexed by types (and by other values).
+ For example, `lists(T)` is parameterised by the type of list elements `T`.
+ Replacing a parameter by `_` denotes the union over all instances of that
+ parameter, e.g., `lists(_)` is the union of all types `lists(T)` with `T:types`.
+
+ Qualified variables `V:T` in terms range over values of type `T`.
+ Qualified variables ``T1<:T2`` in terms range over subtypes `T1` of `T2`.
+*/
+
+
+Funcon
+ is-in-type(V:values, T:types) : =>booleans
+Alias
+ is = is-in-type
+/*
+ `is-in-type(V, T)` tests whether ``V : T`` holds. The value `V` need not be a
+ ground value, but `T` should not require testing any computation types.
+*/
+Rule
+ V : T
+ -------------------------------------
+ is-in-type(V:values, T:types) ~> true
+Rule
+ V : ~ T
+ --------------------------------------
+ is-in-type(V:values, T:types) ~> false
+
+
+### Option types
+
+/*
+ For any value type `T`, the elements of the option type `(T)?` are the
+ elements of `T` together with the empty sequence `( )`, which represents
+ the absence of a value. Option types are a special case of sequence types.
+
+ A funcon whose result type is an option type `(T)?` may compute a value of
+ type `T` or the empty sequence `( )`; the latter represents undefined results
+ of partial operations.
+
+ The parentheses in `(T)?` and `( )` can be omitted when this does not give
+ rise to grouoing ambiguity. Note however that `T?` is a meta-variable ranging
+ over option types, whereas `(T)?` is the option type for the value type `T`.
+*/
+
+
+Funcon
+ is-value(_:values?) : =>booleans
+Alias
+ is-val = is-value
+/*
+ `is-value(V?)` tests whether the optional value `V?` is a value or absent.
+*/
+Rule
+ is-value(_:values) ~> true
+Rule
+ is-value( ) ~> false
+
+
+Funcon
+ when-true(_:booleans, _:T) : =>(T)?
+Alias
+ when = when-true
+/*
+ `when-true(B, V)` gives `V` when `B` is `true`, and `( )` when `B` is `false`.
+*/
+Rule
+ when-true(true, V:values) ~> V
+Rule
+ when-true(false, V:values) ~> ( )
+
+
+Funcon
+ cast-to-type(V:values, T:types) : =>(T)?
+Alias
+ cast = cast-to-type
+/*
+ `cast-to-type(V, T)` gives `V` if it is in `T`, otherwise `( )`.
+*/
+Rule
+ V : T
+ -------------------------------------
+ cast-to-type(V:values, T:types) ~> V
+Rule
+ V : ~ T
+ --------------------------------------
+ cast-to-type(V:values, T:types) ~> ( )
+
+
+### Ground values
+
+Built-in Type
+ ground-values
+Alias
+ ground-vals = ground-values
+/*
+ The elements of `ground-values` are all values that are formed entirely
+ from value-constructors, and thus do not involve computations.
+
+ A type is a subtype of `ground-values` if and only if all its elements are
+ included in `ground-values`.
+*/
+
+
+Funcon
+ is-equal(V:values, W:values) : =>booleans
+Alias
+ is-eq = is-equal
+/*
+ `is-equal(V, W)` returns `true` when `V` and `W` are identical ground values,
+ otherwise `false`.
+*/
+Rule
+ V == W
+ --------------------------------------------------
+ is-equal(V:ground-values, W:ground-values) ~> true
+Rule
+ V =/= W
+ ---------------------------------------------------
+ is-equal(V:ground-values, W:ground-values) ~> false
+Rule
+ is-equal(V:~ground-values, W:values) ~> false
+Rule
+ is-equal(V:values, W:~ground-values) ~> false
diff --git a/IBAF-cbs/Funcons-beta/Values/Value-Types/index.md b/IBAF-cbs/Funcons-beta/Values/Value-Types/index.md
new file mode 100644
index 0000000..136869c
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Value-Types/index.md
@@ -0,0 +1,258 @@
+---
+layout: default
+title: "Value-Types"
+parent: Values
+ancestor: Funcons-beta
+
+---
+
+[Funcons-beta] : [Value-Types.cbs]
+-----------------------------
+
+## Value Types
+
+
+
+
+
+### Values
+
+
+Built-in Type
+ values
+Alias
+ vals = values
+
+
+ The type values includes all values provided by CBS.
+
+ Some funcons are declared as value constructors. Values are constructed by
+ applying value constructor funcons to the required arguments.
+
+ Values are immutable and context-independent. Their structure can be
+ inspected using patterns formed from value constructors and variables.
+ Computations can be extracted from values and executed, but the structure
+ of computations cannot be inspected.
+
+ Some types of values and their funcons are declared as built-in, and not
+ further specified in CBS. New types of built-in values can be added to CBS
+ by its developers.
+
+ New algebraic datatypes may be declared by users of CBS. Their values are
+ disjoint from built-in values.
+
+
+
+Meta-variables
+ T, T1, T2 <: values
+
+
+
+### Types
+
+
+Built-in Type
+ value-types
+Alias
+ types = value-types
+
+Built-in Type
+ empty-type
+
+ A type T is a value that represents a set of values.
+
+ The values of type types are all the types, including types itself.
+
+ The formula V : T holds when V is a value of type T, i.e., V is in
+ the set represented by the type T.
+
+ The formula T1 <: T2 holds when T1 is a subtype of T2, i.e., the set
+ represented by T1 is a subset of the set represented by T2.
+
+ The set of types forms a Boolean algebra with the following operations and
+ constants:
+ * T1 & T2 (meet/intersection)
+ * T1 | T2 (join/union)
+ * ~ T (complement)
+ * values (top)
+ * empty-type (bottom)
+
+ Subtyping: T1 <: T2 is the partial order defined by the algebra.
+
+ Subsumption: If V : T1 and T1 <: T2 both hold, so does V : T2.
+
+ Indivisibility: For each value V and type T, either V : T or
+ V : ~T holds.
+
+ Universality: V : values holds for all values V.
+
+ Emptiness: V : empty-type holds for no value V.
+
+ 'Type N' declares the name 'N' to refer to a fresh value constructor
+ and includes it as an element of types.
+
+ 'Type N ~> T' moreover specifies 'Rule N ~> T', so that 'N' can be used as
+ an abbreviation for the type term 'T'.
+
+ 'Type N <: T' declares the name 'N' to refer to a fresh value constructor
+ in types, and asserts 'N <: T'.
+
+ Parametrised type declarations introduce generic (possibly dependent) types,
+ i.e., families of individual types, indexed by types (and by other values).
+ For example, lists(T) is parameterised by the type of list elements T.
+ Replacing a parameter by _ denotes the union over all instances of that
+ parameter, e.g., lists(_) is the union of all types lists(T) with T:types.
+
+ Qualified variables V:T in terms range over values of type T.
+ Qualified variables T1<:T2 in terms range over subtypes T1 of T2.
+
+
+
+
+ is-in-type(V, T) tests whether V : T holds. The value V need not be a
+ ground value, but T should not require testing any computation types.
+
+
+
+
+
+### Option types
+
+
+ For any value type T, the elements of the option type (T)? are the
+ elements of T together with the empty sequence ( ), which represents
+ the absence of a value. Option types are a special case of sequence types.
+
+ A funcon whose result type is an option type (T)? may compute a value of
+ type T or the empty sequence ( ); the latter represents undefined results
+ of partial operations.
+
+ The parentheses in (T)? and ( ) can be omitted when this does not give
+ rise to grouoing ambiguity. Note however that T? is a meta-variable ranging
+ over option types, whereas (T)? is the option type for the value type T.
+
+
+
+
+ is-value(V?) tests whether the optional value V? is a value or absent.
+
+
+
+
+
+
+ when-true(B, V) gives V when B is true, and ( ) when B is false.
+
+
+
+
+
+
+ cast-to-type(V, T) gives V if it is in T, otherwise ( ).
+
+
+
+
+
+### Ground values
+
+
+Built-in Type
+ ground-values
+Alias
+ ground-vals = ground-values
+
+
+ The elements of ground-values are all values that are formed entirely
+ from value-constructors, and thus do not involve computations.
+
+ A type is a subtype of ground-values if and only if all its elements are
+ included in ground-values.
+
+
+
+
+ is-equal(V, W) returns true when V and W are identical ground values,
+ otherwise false.
+
+
+
+
+
+____
+
+From the [PLanCompS Project] | [CBS-beta issues...] | [Suggest an improvement...]
+
+[Value-Types.cbs]: Value-Types.cbs
+ "CBS SOURCE FILE"
+[Funcons-beta]: /CBS-beta/docs/Funcons-beta
+ "FUNCONS-BETA"
+[Unstable-Funcons-beta]: /CBS-beta/docs/Unstable-Funcons-beta
+ "UNSTABLE-FUNCONS-BETA"
+[Languages-beta]: /CBS-beta/docs/Languages-beta
+ "LANGUAGES-BETA"
+[Unstable-Languages-beta]: /CBS-beta/docs/Unstable-Languages-beta
+ "UNSTABLE-LANGUAGES-BETA"
+[CBS-beta]: /CBS-beta "CBS-BETA"
+[PLanCompS Project]: https://plancomps.github.io
+ "PROGRAMMING LANGUAGE COMPONENTS AND SPECIFICATIONS PROJECT HOME PAGE"
+[CBS-beta issues...]: https://github.com/plancomps/CBS-beta/issues
+ "CBS-BETA ISSUE REPORTS ON GITHUB"
+[Suggest an improvement...]: mailto:plancomps@gmail.com?Subject=CBS-beta%20-%20comment&Body=Re%3A%20CBS-beta%20specification%20at%20Values/Value-Types/Value-Types.cbs%0A%0AComment/Query/Issue/Suggestion%3A%0A%0A%0ASignature%3A%0A
+ "GENERATE AN EMAIL TEMPLATE"
diff --git a/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/cast-to-type.config b/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/cast-to-type.config
new file mode 100644
index 0000000..4b0911d
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/cast-to-type.config
@@ -0,0 +1,14 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(cast-to-type(false,booleans), false))
+ , check-true(is-equal(cast-to-type(false,values), false))
+ , check-true(not is-value(cast-to-type(false, natural-numbers)))
+ , check-true(not is-value(cast-to-type(false, empty-type)))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/is-equal.config b/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/is-equal.config
new file mode 100644
index 0000000..53f207f
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/is-equal.config
@@ -0,0 +1,17 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(false,false))
+ , check-true(is-equal(0,0))
+ , check-true(not is-equal(false, true))
+ , check-true(not is-equal(false, 0))
+ , check-true(not is-equal(abstraction fail, abstraction fail))
+ , check-true(not is-equal(abstraction fail, false))
+ , check-true(not is-equal(false, abstraction fail))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/is-in-type.config b/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/is-in-type.config
new file mode 100644
index 0000000..fd60f6c
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/is-in-type.config
@@ -0,0 +1,30 @@
+general {
+ funcon-term: sequential (
+ check-true(is-in-type(true,booleans))
+ , check-true(is-in-type(0,natural-numbers))
+ , check-true(is-in-type(true,values))
+ , check-true(is-in-type(true,ground-values))
+ , check-true(is-in-type(true,booleans|natural-numbers))
+ , check-true(is-in-type(0,~booleans))
+ , check-true(is-in-type(0,booleans|natural-numbers))
+ , check-true(is-in-type(booleans,value-types))
+ , check-true(is-in-type(value-types,value-types))
+ , check-true(is-in-type(empty-type,value-types))
+ , check-true(is-in-type(ground-values,value-types))
+ , check-true(is-in-type(booleans|natural-numbers,value-types))
+ , check-true(is-in-type(booleans&natural-numbers,value-types))
+ , check-true(is-in-type(~booleans,value-types))
+ , check-true(not is-in-type(0,booleans))
+ , check-true(not is-in-type(true,natural-numbers))
+ , check-true(not is-in-type(true,empty-type))
+ , check-true(not is-in-type(true,booleans&natural-numbers))
+ , check-true(not is-in-type(true,~values))
+ , check-true(not is-in-type(abstraction fail,ground-values))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/is-value.config b/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/is-value.config
new file mode 100644
index 0000000..fb947d4
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/is-value.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term: sequential (
+ check-true(is-value(false))
+ , check-true(not is-value( ))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/when-true.config b/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/when-true.config
new file mode 100644
index 0000000..c6a8639
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/Values/Value-Types/tests/when-true.config
@@ -0,0 +1,12 @@
+general {
+ funcon-term: sequential (
+ check-true(is-equal(when-true(true,0), 0))
+ , check-true(not is-value(when-true(false, 0)))
+ , print "OK"
+ );
+}
+
+tests {
+ result-term : null-value;
+ standard-out : ["OK"];
+}
diff --git a/IBAF-cbs/Funcons-beta/cbs.css b/IBAF-cbs/Funcons-beta/cbs.css
new file mode 100644
index 0000000..0dce603
--- /dev/null
+++ b/IBAF-cbs/Funcons-beta/cbs.css
@@ -0,0 +1,244 @@
+body, i.keyword {
+ color: grey;
+ background-color: white;
+}
+
+a:link {
+ text-decoration: none;
+}
+
+a:visited {
+ text-decoration: none;
+}
+
+a:hover {
+ text-decoration: underline;
+}
+
+a:active {
+ text-decoration: underline;
+}
+
+pre, nav div.buttons {
+ tab-size: 4;
+ padding: 1em 1em 0em 1em;
+ font-family: Consolas, "Lucida Console", Monaco, monospace;
+}
+
+span.name, span.name a, span.comment span.name a {
+ color: darkred;
+ background-color: white;
+}
+
+span.ent-name, span.ent-name a, span.comment span.ent-name a {
+ color: black;
+ background-color: white;
+}
+
+span.syn-name, span.syn-name a, span.comment span.syn-name a {
+ color: green;
+ background-color: white;
+}
+
+i.sem-name, i.sem-name a, span.comment i.sem-name a {
+ color: blue;
+ background-color: white;
+}
+
+i.var, i.var a, sub, sup {
+ color: black;
+}
+
+span.comment, span.comment a:link {
+ color: grey;
+ background-color: white;
+}
+
+span.sectnumtitle a:link {
+ color: black;
+ background-color: white;
+}
+
+/* Body */
+
+body {
+ margin: 1em;
+ padding: 0;
+ font-family: Arial, Helvetica, sans-serif
+}
+
+/* Details */
+
+details pre {
+ margin-top: -2em;
+}
+
+details {
+ margin-bottom: -2em;
+}
+
+summary {
+ outline:none;
+ margin-top: -1em;
+}
+
+summary pre {
+ margin-top: -2em;
+}
+
+/* Header */
+
+header {
+ background-color: #F1F1F1;
+ font-size: 1.2em;
+ padding: 1em;
+ text-align: center;
+}
+
+header div {
+ padding: 0em 1em 0em 0em;
+}
+
+header div.topic {
+ margin-left: 0;
+ margin-right: auto;
+ text-align: left;
+}
+
+header div.title {
+ margin-left: auto;
+ margin-right: auto;
+}
+
+
+/* Footer */
+
+footer {
+ background-color: #F1F1F1;
+ text-align: left;
+ padding: 1.2em;
+}
+
+footer span {
+ padding: 0em 3em 0em 0em;
+ display: inline-block;
+}
+
+footer span a, header div a {
+ background-color: #F1F1F1;
+ color: #3e8e41;
+}
+
+/* Menus */
+
+@media screen {
+
+ pre {
+ margin-left: 1em;
+ }
+
+ /* Style The Dropdown Button */
+ .dropbtn {
+ background-color: #4CAF50;
+ color: white;
+ padding: 0.5em;
+ font-size: 1.2em;
+ border: none;
+ cursor: pointer;
+ }
+
+ /* The container - needed to position the dropdown content */
+ .dropdown {
+ position: fixed;
+ top: 2em;
+ right: 2em;
+ display: inline-block;
+ }
+
+ /* Dropdown Content (Hidden by Default) */
+ .dropdown-content {
+ display: none;
+ position: absolute;
+ right: 0;
+ background-color: #f9f9f9;
+ min-width: 10em;
+ box-shadow: 0em 0.5em 1em 0em rgba(0,0,0,0.2);
+ z-index: 1;
+ }
+
+ /* Links and spans inside the dropdown */
+ .dropdown-content a, .dropdown-content span {
+ color: black;
+ padding: 0.75em 0.75em;
+ text-decoration: none;
+ display: block;
+ }
+
+ /* Change color of dropdown links on hover */
+ .dropdown-content a:hover {background-color: #f1f1f1}
+
+ /* Show the dropdown menu on hover */
+ .dropdown:hover .dropdown-content {
+ display: block;
+ }
+
+ /* Change the background color of the dropdown button when the dropdown content is shown */
+ .dropdown:hover .dropbtn {
+ background-color: #3e8e41;
+ }
+
+ div.buttons {
+ float: right;
+ display: block;
+ text-align: right;
+ font-weight: bold;
+ }
+}
+
+@media print {
+
+ /* Style The Dropdown Button */
+ .dropbtn {
+ display: none;
+ padding: 0.5em;
+ font-size: 1.2em;
+ border: none;
+ cursor: pointer;
+ }
+
+ /* The container
- needed to position the dropdown content */
+ .dropdown {
+ position: fixed;
+ top: 0.5em;
+ right: 0.5em;
+ display: none;
+ }
+
+ /* Dropdown Content (Hidden by Default) */
+ .dropdown-content {
+ display: none;
+ position: absolute;
+ right: 0;
+ background-color: #f9f9f9;
+ min-width: 10em;
+ box-shadow: 0em 0.5em 1em 0em rgba(0,0,0,0.2);
+ z-index: 1;
+ }
+
+ div.buttons {
+ float: right;
+ display: none;
+ text-align: right;
+ font-weight: bold;
+ }
+
+ details > summary {
+ list-style: none;
+ }
+ /* Needed for Chrome? */
+ details > summary::-webkit-details-marker {
+ display: none;
+}
+
+
+}