about summary refs log tree commit diff
path: root/boot/tests/transpile/closure_nested.cskt
diff options
context:
space:
mode:
authorMel <mel@rnrd.eu>2026-05-28 01:17:32 +0200
committerMel <mel@rnrd.eu>2026-05-28 01:17:32 +0200
commita5b24e3eedc8bd48de99cfb90abb3bececa5d29f (patch)
tree8268e61906adde451f010dfe73241841edbec453 /boot/tests/transpile/closure_nested.cskt
parent351433f3f7dc3f1051a9875402502663fe8a0be8 (diff)
downloadcatskill-a5b24e3eedc8bd48de99cfb90abb3bececa5d29f.tar.zst
catskill-a5b24e3eedc8bd48de99cfb90abb3bececa5d29f.zip
Add tests for function value passing and capturing closure behavior
Signed-off-by: Mel <mel@rnrd.eu>
Diffstat (limited to 'boot/tests/transpile/closure_nested.cskt')
-rw-r--r--boot/tests/transpile/closure_nested.cskt58
1 files changed, 58 insertions, 0 deletions
diff --git a/boot/tests/transpile/closure_nested.cskt b/boot/tests/transpile/closure_nested.cskt
new file mode 100644
index 0000000..ac913b7
--- /dev/null
+++ b/boot/tests/transpile/closure_nested.cskt
@@ -0,0 +1,58 @@
+support for multi-level closures, and capturing through them.
+when a closure captures a local which is multiple function levels
+away from it, the capture should cascade to every single closure
+between the capturer and the capturee.
+when the closure state is created, the captured local needs
+to be accessed via the state structure of the parent closure,
+and not via a simple reference as usual.
+
+<<<
+
+main = fun () {
+    var a int = 1
+    var outer fun (x int) int = fun (x int) int {
+        var b int = 10
+        var inner fun (y int) int = fun (y int) int {
+            return a + b + x + y
+        }
+        return inner(100)
+    }
+    var r int = outer(1000)
+}
+
+>>>
+
+#include "core.c"
+struct __cat_type_0 {
+    void* state;
+    integer (*call)(void* state, integer);
+};
+struct __cat_type_1;
+struct __cat_type_2;
+struct __cat_type_1 {
+    integer* a;
+    integer* b;
+    integer* x;
+};
+struct __cat_type_2 {
+    integer* a;
+};
+void catskill_main(void);
+integer __cat_lambda_0(void* state_void, integer x);
+integer __cat_lambda_1(void* state_void, integer y);
+void catskill_main(void) {
+    integer a = 1;
+    struct __cat_type_0 outer = (struct __cat_type_0){ .state = &(struct __cat_type_2){ .a = &a }, .call = __cat_lambda_0 };
+    integer r = outer.call(outer.state, 1000);
+}
+integer __cat_lambda_0(void* state_void, integer x) {
+    struct __cat_type_2* state = state_void;
+    integer b = 10;
+    struct __cat_type_0 inner = (struct __cat_type_0){ .state = &(struct __cat_type_1){ .a = state->a, .b = &b, .x = &x }, .call = __cat_lambda_1 };
+    return inner.call(inner.state, 100);
+}
+integer __cat_lambda_1(void* state_void, integer y) {
+    struct __cat_type_1* state = state_void;
+    return (*state->a) + (*state->b) + (*state->x) + y;
+}
+#include "runtime.c"