Skip to content

Instantly share code, notes, and snippets.

@semmypurewal
Last active January 7, 2019 14:22
Show Gist options
  • Save semmypurewal/cd637669fdc9ec4edfc4ba98927f7748 to your computer and use it in GitHub Desktop.
Save semmypurewal/cd637669fdc9ec4edfc4ba98927f7748 to your computer and use it in GitHub Desktop.
Duktape 'cannot push beyond allocated stack'
#include "duktape/src/duktape.h"
// #include <SDL2/SDL.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
typedef unsigned int Uint32;
const char *js = " \
print('hello from javascript!'); \
var count = 0; \
\
setInterval(function() { \
print('hello from timeout: ' + ++count); \
}, 200); \
";
typedef struct {
duk_context *duk;
Uint32 id;
Uint32 timeout;
} TimeoutContext;
duk_ret_t print(duk_context *ctx);
duk_ret_t set_interval(duk_context *ctx);
Uint32 execute_timeout(Uint32 interval, void *param);
int timeout_id = 0;
void js_error(void *udata, const char *msg) {
fprintf(stderr, "***FATAL: %s\n", (msg ? msg : "no message"));
fflush(stderr);
abort();
}
int main(int argc, char **argv) {
duk_context *c = duk_create_heap(NULL, NULL, NULL, NULL, js_error);
duk_push_c_function(c, &print, DUK_VARARGS);
duk_put_global_string(c, "print");
duk_push_c_function(c, &set_interval, 2);
duk_put_global_string(c, "setInterval");
duk_push_string(c, js);
duk_eval(c);
char ch = getchar();
printf("%c\n", ch);
return 0;
}
duk_ret_t print(duk_context *ctx) {
duk_push_string(ctx, " ");
duk_insert(ctx, 0);
duk_join(ctx, duk_get_top(ctx) - 1);
printf("%s\n", duk_safe_to_string(ctx, -1));
return 0;
}
duk_ret_t set_interval(duk_context *ctx) {
int id = ++timeout_id;
duk_int_t timeout = duk_get_int(ctx, -1);
duk_pop(ctx); // get rid of timeout
duk_push_int(ctx, id);
duk_insert(ctx, -2); // move int below function in stack
duk_push_global_stash(ctx);
duk_insert(ctx, -3); // move stash below args
duk_require_object(ctx, -3);
duk_require_int(ctx, -2);
duk_require_function(ctx, -1);
duk_put_prop(ctx, -3);
TimeoutContext *tc = malloc(sizeof(TimeoutContext));
tc->duk = ctx;
tc->id = id;
tc->timeout = timeout;
// SDL_AddTimer(timeout, execute_timeout, tc);
execute_timeout(timeout, tc);
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment