summaryrefslogtreecommitdiffstats
path: root/execute.c
diff options
context:
space:
mode:
authorStephen Dolan <mu@netsoc.tcd.ie>2013-06-22 23:27:16 +0100
committerStephen Dolan <mu@netsoc.tcd.ie>2013-06-22 23:27:16 +0100
commit1c9e03f8009be4ff6d4e79f5399c476e13caca45 (patch)
tree4140d45fe414f8f3dcb356cbb4e3f8d529118ee7 /execute.c
parent5d9ec838051c3451a59f9aa70eecde5c238a201c (diff)
parent7af88962eea41fd25b483f1e4ef750bfd8a999e8 (diff)
Merge branch 'header-cleanup' into libjq
Conflicts: Makefile.am
Diffstat (limited to 'execute.c')
-rw-r--r--execute.c25
1 files changed, 20 insertions, 5 deletions
diff --git a/execute.c b/execute.c
index 423b133a..4b05d793 100644
--- a/execute.c
+++ b/execute.c
@@ -4,7 +4,6 @@
#include <stdint.h>
#include "exec_stack.h"
-#include "opcode.h"
#include "bytecode.h"
#include "jv_alloc.h"
@@ -240,6 +239,8 @@ static void jq_reset(jq_state *jq) {
}
+
+
void print_error(jv value) {
assert(!jv_is_valid(value));
jv msg = jv_invalid_get_msg(value);
@@ -600,12 +601,26 @@ jv jq_next(jq_state *jq) {
case CALL_BUILTIN: {
int nargs = *pc++;
jv top = stack_pop(jq);
- cfunc_input[0] = top;
+ jv* in = cfunc_input;
+ in[0] = top;
for (int i = 1; i < nargs; i++) {
- cfunc_input[i] = stack_pop(jq);
+ in[i] = stack_pop(jq);
}
- struct cfunction* func = &frame_current(jq)->bc->globals->cfunctions[*pc++];
- top = cfunction_invoke(func, cfunc_input);
+ struct cfunction* function = &frame_current(jq)->bc->globals->cfunctions[*pc++];
+ typedef jv (*func_1)(jv);
+ typedef jv (*func_2)(jv,jv);
+ typedef jv (*func_3)(jv,jv,jv);
+ typedef jv (*func_4)(jv,jv,jv,jv);
+ typedef jv (*func_5)(jv,jv,jv,jv,jv);
+ switch (function->nargs) {
+ case 1: top = ((func_1)function->fptr)(in[0]); break;
+ case 2: top = ((func_2)function->fptr)(in[0], in[1]); break;
+ case 3: top = ((func_3)function->fptr)(in[0], in[1], in[2]); break;
+ case 4: top = ((func_4)function->fptr)(in[0], in[1], in[2], in[3]); break;
+ case 5: top = ((func_5)function->fptr)(in[0], in[1], in[2], in[3], in[4]); break;
+ default: return jv_invalid_with_msg(jv_string("Function takes too many arguments"));
+ }
+
if (jv_is_valid(top)) {
stack_push(jq, top);
} else {