shithub: sl

Download patch

ref: 538d930befd24d2f826bb4586bd7117d201d2be5
parent: 5765093ba41599b90e9b4b32ac885cff9e9f8262
author: Sigrid Solveig Haflínudóttir <sigrid@ftrv.se>
date: Thu Feb 27 00:08:53 EST 2025

apply_cl: move call setup to the op itself

--- a/src/flisp.c
+++ b/src/flisp.c
@@ -841,23 +841,14 @@
 static value_t
 apply_cl(int nargs)
 {
-	value_t *top_frame = FL(curr_frame);
+	value_t *top_frame = FL(curr_frame), *bp, *ipd;
 	register value_t *sp = FL(sp);
+	const uint8_t *ip;
 	bool tail;
 	int n;
 
-apply_cl_top:;
-	value_t *bp = sp-nargs;
-	function_t *fn = (function_t*)ptr(bp[-1]);
-	const uint8_t *ip = cvalue_data(fn->bcode);
-	assert(!ismanaged((uintptr_t)ip));
+	goto apply_func;
 
-	*sp++ = fn->env;
-	*sp++ = (value_t)FL(curr_frame);
-	*sp++ = nargs;
-	value_t *ipd = sp++;
-	FL(curr_frame) = sp;
-
 #if defined(COMPUTED_GOTO)
 #pragma GCC diagnostic push
 #pragma GCC diagnostic ignored "-Wpedantic"
@@ -876,9 +867,8 @@
 #undef NEXT_OP
 #pragma GCC diagnostic pop
 #else /* just a usual (portable) switch/case */
-	uint8_t op = *ip++;
 	while(1){
-		switch(op){
+		switch(*ip++){
 #define NEXT_OP break
 #define LABEL(x) x
 #define OP(x) case x:
@@ -887,7 +877,6 @@
 #undef LABEL
 #undef NEXT_OP
 		}
-		op = *ip++;
 	}
 #endif
 }
--- a/src/vm.inc
+++ b/src/vm.inc
@@ -7,7 +7,7 @@
 )
 
 OP(OP_LOADA0)
-	*sp++ = *bp;
+	*sp++ = bp[0];
 	NEXT_OP;
 
 OP(OP_CALL) {
@@ -32,14 +32,25 @@
 	value_t v = sp[-n-1];
 	if(tag(v) == TAG_FUNCTION){
 		if(v > (N_BUILTINS<<3)){
+			nargs = n;
 			if(tail){
 				FL(curr_frame) = (value_t*)FL(curr_frame)[-3];
 				for(fixnum_t s = -1; s < (fixnum_t)n; s++)
 					bp[s] = sp[s-n];
 				sp = bp+n;
+			}else{
+LABEL(apply_func):
+				bp = sp-nargs;
 			}
-			nargs = n;
-			goto apply_cl_top;
+			function_t *fn = (function_t*)ptr(bp[-1]);
+			ip = cvalue_data(fn->bcode);
+			assert(!ismanaged((uintptr_t)ip));
+			*sp++ = fn->env;
+			*sp++ = (value_t)FL(curr_frame);
+			*sp++ = nargs;
+			ipd = sp++;
+			FL(curr_frame) = sp;
+			NEXT_OP;
 		}
 		int i = uintval(v);
 		assert(isbuiltin(v));