diff options
Diffstat (limited to 'starts/meaning-vm/level-2')
-rw-r--r-- | starts/meaning-vm/level-2/baseref.hpp | 6 | ||||
-rw-r--r-- | starts/meaning-vm/level-2/funcs.cpp | 22 | ||||
-rw-r--r-- | starts/meaning-vm/level-2/funcs.hpp | 1 | ||||
-rw-r--r-- | starts/meaning-vm/level-2/sugar.hpp | 2 |
4 files changed, 29 insertions, 2 deletions
diff --git a/starts/meaning-vm/level-2/baseref.hpp b/starts/meaning-vm/level-2/baseref.hpp index c66d1a7..8fbcc91 100644 --- a/starts/meaning-vm/level-2/baseref.hpp +++ b/starts/meaning-vm/level-2/baseref.hpp @@ -20,7 +20,11 @@ struct baseref : public level1::baseref<ref> static ref & context() { return level2::context(); } template <typename... Refs> - ref operator()(Refs... args) { return level2::dohabit(self, {args.ptr()...}); } + ref operator()(ref first, Refs... rest) { return level2::dohabit(self, {first, rest...}); } + template <typename... Pairs> + ref operator()(std::initializer_list<ref> first, Pairs... rest) { return level2::dohabit(self, {first, rest...}); } + + ref operator()() { return level2::dohabit(self); } }; } diff --git a/starts/meaning-vm/level-2/funcs.cpp b/starts/meaning-vm/level-2/funcs.cpp index 11b3184..e4fc090 100644 --- a/starts/meaning-vm/level-2/funcs.cpp +++ b/starts/meaning-vm/level-2/funcs.cpp @@ -60,5 +60,27 @@ ref dohabit(ref habit, std::initializer_list<ref> args) return nothing; } +ref dohabit(ref habit, std::initializer_list<std::initializer_list<ref>> pairs) +{ + using namespace concepts; + // TODO: subcontexts or call instances + ref ctx = ref::context(); + for (auto pair : pairs) { + auto second = pair.begin(); ++ second; + ctx.link(pair.begin(), second); + } + habit.fun<ref>()(ctx); + for (auto pair : pairs) { + auto second = pair.begin(); ++ second; + ctx.unlink(pair.begin(), second); + } + if (ctx.linked(result)) { + ref ret = ctx.get(result); + ctx.unlink(result, ret); + return ret; + } + return nothing; +} + } } diff --git a/starts/meaning-vm/level-2/funcs.hpp b/starts/meaning-vm/level-2/funcs.hpp index 2a92bfd..85e1af8 100644 --- a/starts/meaning-vm/level-2/funcs.hpp +++ b/starts/meaning-vm/level-2/funcs.hpp @@ -11,6 +11,7 @@ namespace level2 { ref & context(); ref makehabit(ref name, std::initializer_list<ref> argnames, std::function<void(ref)> code); ref dohabit(ref habit, std::initializer_list<ref> args); +ref dohabit(ref habit, std::initializer_list<std::initializer_list<ref>> args = {}); } } diff --git a/starts/meaning-vm/level-2/sugar.hpp b/starts/meaning-vm/level-2/sugar.hpp index 5b3b150..b44b282 100644 --- a/starts/meaning-vm/level-2/sugar.hpp +++ b/starts/meaning-vm/level-2/sugar.hpp @@ -35,7 +35,7 @@ ref result("nothing"); (void)result; \ _macro_call(_macro_for_each_parens, _macro_habit_set_posarg, _macro_habit_set_posarg _macro_comma_remove_parens(argnametoklist)); \ __VA_ARGS__ \ - if (result != ref("nothing")) { ctx.link(ref("result"), result); } + if (result != ref("nothing")) { ctx.link(ref("result"), result); } \ }); #define _macro_habit_argnameref(name, tok) \ ref(#name) |