From f2105fbd96e6cc9500b3da82e335e7bc830f7115 Mon Sep 17 00:00:00 2001 From: Nat Quayle Nelson Date: Fri, 14 Nov 2025 16:45:06 -0600 Subject: [PATCH] Make (apply...) work in interp2 --- src/kiss/KissInterp2.kiss | 1 + src/kiss/Macros.hx | 61 +----------------------------------- src/kiss/PortableMacros.hx | 63 ++++++++++++++++++++++++++++++++++++++ 3 files changed, 65 insertions(+), 60 deletions(-) diff --git a/src/kiss/KissInterp2.kiss b/src/kiss/KissInterp2.kiss index c7791c6..1f614f2 100644 --- a/src/kiss/KissInterp2.kiss +++ b/src/kiss/KissInterp2.kiss @@ -24,6 +24,7 @@ =>"Std" Std =>"the" ->[_ v] v =>"Math" Math + =>"Reflect" Reflect ]) (prop &mut :kiss.List> localScopes []) diff --git a/src/kiss/Macros.hx b/src/kiss/Macros.hx index e2957a8..26a723c 100644 --- a/src/kiss/Macros.hx +++ b/src/kiss/Macros.hx @@ -81,67 +81,8 @@ class Macros { destructiveVersion("*", "*="); destructiveVersion("/", "/="); - var opAliases = [ - // These shouldn't be ident aliases because they are common variable names - "min" => "Prelude.min", - "max" => "Prelude.max", - // These might not be common, but playing it safe: - "iHalf" => "Prelude.iHalf", - "iThird" => "Prelude.iThird", - "iFourth" => "Prelude.iFourth", - "iFifth" => "Prelude.iFifth", - "iSixth" => "Prelude.iSixth", - "iSeventh" => "Prelude.iSeventh", - "iEighth" => "Prelude.iEighth", - "iNinth" => "Prelude.iNinth", - "iTenth" => "Prelude.iTenth", - "fHalf" => "Prelude.fHalf", - "fThird" => "Prelude.fThird", - "fFourth" => "Prelude.fFourth", - "fFifth" => "Prelude.fFifth", - "fSixth" => "Prelude.fSixth", - "fSeventh" => "Prelude.fSeventh", - "fEighth" => "Prelude.fEighth", - "fNinth" => "Prelude.fNinth", - "fTenth" => "Prelude.fTenth", - // These can't be ident aliases because they would supercede the typed call macros that wrap them: - "zip" => "Prelude.zipThrow", - "zipThrow" => "Prelude.zipThrow", - "zipKeep" => "Prelude.zipKeep", - "zipDrop" => "Prelude.zipDrop", - "concat" => "Prelude.concat", - "intersect" => "Prelude.intersect", - "and" => "Prelude.and", - "or" => "Prelude.or" - ]; k.doc("apply", 2, 2, '(apply )' ); - macros["apply"] = (wholeExp:ReaderExp, exps:Array, k) -> { - var b = wholeExp.expBuilder(); - var isSafe = false; - var callOn = switch (exps[0].def) { - case FieldExp(field, exp, safe): - isSafe = safe; - exp; - default: - b.symbol("null"); - }; - var func = switch (exps[0].def) { - case Symbol(func) if (opAliases.exists(func)): - b.symbol(opAliases[func]); - default: - exps[0]; - }; - var args = exps[1]; - var exp = b.call( - b.symbol("Reflect.callMethod"), [ - callOn, func, args - ]); - - if (isSafe) - exp = b.callSymbol("when", [callOn, exp]); - - exp; - }; + macros["apply"] = wrapPortable(PortableMacros.apply); function prepareForConditional(i:KissInterp, k:KissState) { i.variables.set("kissFile", k.file); diff --git a/src/kiss/PortableMacros.hx b/src/kiss/PortableMacros.hx index 268940c..58a7078 100644 --- a/src/kiss/PortableMacros.hx +++ b/src/kiss/PortableMacros.hx @@ -15,9 +15,72 @@ class PortableMacros { m["/="] = destructiveVersion("/"); m["when"] = bodyIf("if", false); m["unless"] = bodyIf("if", true); + m["apply"] = apply; + return m; } + static var opAliases = [ + // These shouldn't be ident aliases because they are common variable names + "min" => "Prelude.min", + "max" => "Prelude.max", + // These might not be common, but playing it safe: + "iHalf" => "Prelude.iHalf", + "iThird" => "Prelude.iThird", + "iFourth" => "Prelude.iFourth", + "iFifth" => "Prelude.iFifth", + "iSixth" => "Prelude.iSixth", + "iSeventh" => "Prelude.iSeventh", + "iEighth" => "Prelude.iEighth", + "iNinth" => "Prelude.iNinth", + "iTenth" => "Prelude.iTenth", + "fHalf" => "Prelude.fHalf", + "fThird" => "Prelude.fThird", + "fFourth" => "Prelude.fFourth", + "fFifth" => "Prelude.fFifth", + "fSixth" => "Prelude.fSixth", + "fSeventh" => "Prelude.fSeventh", + "fEighth" => "Prelude.fEighth", + "fNinth" => "Prelude.fNinth", + "fTenth" => "Prelude.fTenth", + // These can't be ident aliases because they would supercede the typed call macros that wrap them: + "zip" => "Prelude.zipThrow", + "zipThrow" => "Prelude.zipThrow", + "zipKeep" => "Prelude.zipKeep", + "zipDrop" => "Prelude.zipDrop", + "concat" => "Prelude.concat", + "intersect" => "Prelude.intersect", + "and" => "Prelude.and", + "or" => "Prelude.or" + ]; + public static function apply(wholeExp:ReaderExp, exps:Array) { + var b = wholeExp.expBuilder(); + var isSafe = false; + var callOn = switch (exps[0].def) { + case FieldExp(field, exp, safe): + isSafe = safe; + exp; + default: + b.symbol("null"); + }; + var func = switch (exps[0].def) { + case Symbol(func) if (opAliases.exists(func)): + b.symbol(opAliases[func]); + default: + exps[0]; + }; + var args = exps[1]; + var exp = b.call( + b.symbol("Reflect.callMethod"), [ + callOn, func, args + ]); + + if (isSafe) + exp = b.callSymbol("when", [callOn, exp]); + + return exp; + } + public static function destructiveVersion(op:String) { return (wholeExp:ReaderExp, exps:Array) -> { var b = wholeExp.expBuilder();