#include #pragma comment(lib,"ws2_32") #include #include #include #include "shttpd126.h" #include "api.h" class zsRegPrimitive { public: zsRegPrimitive(const char* name, void* func) { api_add_primitive(name, 0, func); } }; void *g_caller = 0; void input_error(void* caller) { api_runtime_error(caller, "bad arguments"); } static int script_handler(struct shttpd_callback_arg *arg) { void *func = api_get_func(g_caller, (char*)arg->callback_data); arg->n = 0; void *p[1]; p[0] = api_create_user(func, arg, 0, 0, 0); api_call_func(func, 1, p); return arg->n; } static int template_handler(struct shttpd_callback_arg *arg) { void *func = api_get_func(g_caller, (char*)arg->callback_data); void *ret = api_call_func(func, 0, 0); if (!api_is_array(ret)) return 0; char *sub[10] = {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "}; char *key[10] = {"0", "1", "2", "3", "4", "5", "6", "7", "8", "9"}; for (int i = 0; i < 10; i++) { void *p = api_get_array_object(g_caller, ret, key[i]); if (p != 0) sub[i] = (char*)api_get_string(g_caller, p); } char buf[256]; buf[255] = 0; strncpy(buf, user_url(arg->connection)+1, 255); int n = shttpd_template(arg->connection, "Content-Type: text/html\r\n", buf, "KEYWORD0", sub[0], "KEYWORD1", sub[1], "KEYWORD2", sub[2], "KEYWORD3", sub[3], "KEYWORD4", sub[4], "KEYWORD5", sub[5], "KEYWORD6", sub[6], "KEYWORD7", sub[7], "KEYWORD8", sub[8], "KEYWORD9", sub[9], 0); return n; } void* w3_httpd(void *caller, int nargs, void** args) { if (nargs < 1) input_error(caller); g_caller = caller; shttpd_init(NULL); for (int i = 3; i < nargs; i += 3) { const char* url = api_get_string(caller, args[i-2]); void * func = (void*)api_get_string(caller, args[i-1]); int flag = api_get_integer(caller, args[i]); if (flag != 0) shttpd_register_url(url, &template_handler, func); else shttpd_register_url(url, &script_handler, func); } int sock = shttpd_open_port(api_get_integer(caller, args[0])); for (;;) { shttpd_poll(sock, 200); } shttpd_fini(); return 0; } static zsRegPrimitive w3a("httpd", w3_httpd); void* w3_get(void *caller, int nargs, void** args) { if (nargs < 2) input_error(caller); struct shttpd_callback_arg *arg = (struct shttpd_callback_arg*)api_get_ptr(caller, args[0]); const char *p = shttpd_get_var(arg->connection, api_get_string(caller, args[1])); if (!p) return 0; //api_create_null(); return api_create_string(caller, p); } static zsRegPrimitive w3b("w3get", w3_get); void* w3_send(void *caller, int nargs, void** args) { if (nargs < 2) input_error(caller); struct shttpd_callback_arg *arg = (struct shttpd_callback_arg*)api_get_ptr(caller, args[0]); for (int i = 1; i < nargs; i++) { const char *s = api_get_string(caller, args[i]); size_t n = strlen(s); if (n > arg->buflen - arg->n) api_runtime_error(caller, "buffer overflow"); memcpy(arg->buf+arg->n, s, n); arg->n += n; } return 0; } static zsRegPrimitive w3c("w3send", w3_send); void* w3_write(void *caller, int nargs, void** args) { if (nargs < 3) input_error(caller); struct shttpd_callback_arg *arg = (struct shttpd_callback_arg*)api_get_ptr(caller, args[0]); size_t n = api_get_integer(caller, args[2]); if (n > arg->buflen - arg->n) api_runtime_error(caller, "buffer overflow"); memcpy(arg->buf+arg->n, api_get_ptr(caller, args[1]), n); arg->n += n; return 0; } static zsRegPrimitive w3d("w3write", w3_write);