Browse Source

Update to Duktape 2.2.0

bel2125 7 năm trước cách đây
mục cha
commit
7cafb40440
3 tập tin đã thay đổi với 103 bổ sung28 xóa
  1. 14 1
      Makefile
  2. 9 1
      resources/Makefile.in-duktape
  3. 80 26
      src/mod_duktape.inl

+ 14 - 1
Makefile

@@ -92,6 +92,11 @@ ifdef WITH_ALL
   #WITH_CPP is not defined, ALL means only real features, not wrappers
 endif
 
+# Use Lua?
+ifdef WITH_LUA_VERSION
+  WITH_LUA = 1
+endif
+
 ifdef WITH_LUA_SHARED
   WITH_LUA = 1
 endif
@@ -106,10 +111,15 @@ ifdef WITH_LUA
   include resources/Makefile.in-lua
 endif
 
+# Use Duktape?
 ifdef WITH_SSJS
   WITH_DUKTAPE = 1
 endif
 
+ifdef WITH_DUKTAPE_VERSION
+  WITH_DUKTAPE = 1
+endif
+
 ifdef WITH_DUKTAPE_SHARED
   WITH_DUKTAPE = 1
 endif
@@ -118,6 +128,7 @@ ifdef WITH_DUKTAPE
   include resources/Makefile.in-duktape
 endif
 
+# Use zlib?
 ifdef WITH_COMPRESSION
   WITH_ZLIB = 1
 endif
@@ -126,6 +137,7 @@ ifdef WITH_ZLIB
   LIBS += -lz
 endif
 
+# Other features
 ifdef WITH_EXPERIMENTAL
   CFLAGS += -DMG_EXPERIMENTAL_INTERFACES
 endif
@@ -148,6 +160,7 @@ ifdef WITH_SERVER_STATS
   CFLAGS += -DUSE_SERVER_STATS
 endif
 
+# File names
 ifdef CONFIG_FILE
   CFLAGS += -DCONFIG_FILE=\"$(CONFIG_FILE)\"
 endif
@@ -216,7 +229,7 @@ help:
 	@echo "   WITH_LUA_VERSION=502  build with Lua 5.2.x (501 for Lua 5.1.x to 503 for 5.3.x)"
 	@echo "   WITH_DUKTAPE=1        build with Duktape support; include as static library"
 	@echo "   WITH_DUKTAPE_SHARED=1 build with Duktape support; use libduktape1.3.so"
-#	@echo "   WITH_DUKTAPE_VERSION=103 build with Duktape 1.3.x"
+	@echo "   WITH_DUKTAPE_VERSION=108 build with Duktape 1.8.x"
 	@echo "   WITH_DEBUG=1          build with GDB debug support"
 	@echo "   WITH_IPV6=1           with IPV6 support"
 	@echo "   WITH_WEBSOCKET=1      build with web socket support"

+ 9 - 1
resources/Makefile.in-duktape

@@ -9,7 +9,7 @@ ifndef WITH_DUKTAPE
 endif
 
 # Duktape default version is 1.5.2 (105)
-WITH_DUKTAPE_VERSION ?= 105
+WITH_DUKTAPE_VERSION ?= 202
 DUKTAPE_VERSION_KNOWN = 0
 
 # Select src and header according to the Duktape version
@@ -37,6 +37,14 @@ ifeq ($(WITH_DUKTAPE_VERSION), 201)
   DUKTAPE_VERSION_KNOWN = 1
 endif
 
+ifeq ($(WITH_DUKTAPE_VERSION), 202)
+  $(info Duktape: Using version 2.2.0)
+  DUKTAPE_DIR = src/third_party/duktape-2.2.0/src
+  DUKTAPE_SHARED_LIB_FLAG = -lduktape2.2
+  DUKTAPE_CFLAGS = -DDUKTAPE_VERSION_MAKEFILE=202
+  DUKTAPE_VERSION_KNOWN = 1
+endif
+
 ifneq ($(DUKTAPE_VERSION_KNOWN), 1)
   $(error Duktape: Unknwon version - $(WITH_DUKTAPE_VERSION))
 endif

+ 80 - 26
src/mod_duktape.inl

@@ -40,7 +40,6 @@ mg_duk_mem_free(void *udata, void *ptr)
 	mg_free(ptr);
 }
 
-
 static void
 mg_duk_fatal_handler(duk_context *duk_ctx, duk_errcode_t code, const char *msg)
 {
@@ -56,6 +55,56 @@ mg_duk_fatal_handler(duk_context *duk_ctx, duk_errcode_t code, const char *msg)
 	mg_cry_internal(conn, "JavaScript fatal (%u): %s", (unsigned)code, msg);
 }
 
+#if DUK_VERSION >= 20000L
+/* Dropped from interface */
+duk_int_t duk_peval_file(duk_context *duk_ctx, const char *script);
+
+static void
+mg_duk_v2_fatal(void *udata, const char *msg)
+{
+	; /* TODO: How to get "conn" without duk_ctx */
+}
+
+static void
+push_file_as_string(duk_context *ctx, const char *filename)
+{
+	FILE *f;
+	struct stat fst;
+	void *buf;
+	size_t len;
+
+	if (0 != stat(filename, &fst)) {
+		duk_push_undefined(ctx);
+		return;
+	}
+
+	f = fopen(filename, "rb");
+	if (!f) {
+		duk_push_undefined(ctx);
+		return;
+	}
+
+	buf = mg_malloc(fst.st_size);
+	if (!f) {
+		fclose(f);
+		duk_push_undefined(ctx);
+		return;
+	}
+
+	len = fread(buf, 1, fst.st_size, f);
+	fclose(f);
+
+	duk_push_lstring(ctx, (const char *)buf, (duk_size_t)len);
+	mg_free(buf);
+}
+
+duk_int_t
+duk_peval_file(duk_context *duk_ctx, const char *script)
+{
+	push_file_as_string(duk_ctx, script);
+	return duk_peval(duk_ctx);
+}
+#endif
 
 static duk_ret_t
 duk_itf_write(duk_context *duk_ctx)
@@ -76,10 +125,9 @@ duk_itf_write(duk_context *duk_ctx)
 
 	if (!conn) {
 		duk_error(duk_ctx,
-		          DUK_ERR_INTERNAL_ERROR,
+		          DUK_ERR_ERROR,
 		          "function not available without connection object");
-		/* probably never reached, but satisfies static code analysis */
-		return DUK_RET_INTERNAL_ERROR;
+		return DUK_RET_ERROR;
 	}
 
 	ret = mg_write(conn, val, len);
@@ -96,16 +144,15 @@ duk_itf_read(duk_context *duk_ctx)
 	char buf[1024];
 	int len;
 
-	duk_push_global_stash(duk_ctx);
+	duk_push_current_function(duk_ctx);
 	duk_get_prop_string(duk_ctx, -1, civetweb_conn_id);
 	conn = (struct mg_connection *)duk_to_pointer(duk_ctx, -1);
 
 	if (!conn) {
 		duk_error(duk_ctx,
-		          DUK_ERR_INTERNAL_ERROR,
+		          DUK_ERR_ERROR,
 		          "function not available without connection object");
-		/* probably never reached, but satisfies static code analysis */
-		return DUK_RET_INTERNAL_ERROR;
+		return DUK_RET_ERROR;
 	}
 
 	len = mg_read(conn, buf, sizeof(buf));
@@ -118,7 +165,7 @@ duk_itf_read(duk_context *duk_ctx)
 static duk_ret_t
 duk_itf_getoption(duk_context *duk_ctx)
 {
-	struct mg_connection *cv_conn;
+	struct mg_connection *conn;
 	const char *ret;
 	int optidx;
 	duk_size_t len = 0;
@@ -126,19 +173,18 @@ duk_itf_getoption(duk_context *duk_ctx)
 
 	duk_push_current_function(duk_ctx);
 	duk_get_prop_string(duk_ctx, -1, civetweb_conn_id);
-	cv_conn = (struct mg_connection *)duk_to_pointer(duk_ctx, -1);
+	conn = (struct mg_connection *)duk_to_pointer(duk_ctx, -1);
 
-	if (!cv_conn) {
+	if (!conn) {
 		duk_error(duk_ctx,
-		          DUK_ERR_INTERNAL_ERROR,
-		          "function not available without connection object");
-		/* probably never reached, but satisfies static code analysis */
-		return DUK_RET_INTERNAL_ERROR;
+		          DUK_ERR_ERROR,
+		          "function not available without context object");
+		return DUK_RET_ERROR;
 	}
 
 	optidx = get_option_index(val);
 	if (optidx >= 0) {
-		ret = cv_conn->dom_ctx->config[optidx];
+		ret = conn->dom_ctx->config[optidx];
 	} else {
 		ret = NULL;
 	}
@@ -165,7 +211,12 @@ mg_exec_duktape_script(struct mg_connection *conn, const char *script_name)
 	                          mg_duk_mem_realloc,
 	                          mg_duk_mem_free,
 	                          (void *)conn->phys_ctx,
-	                          mg_duk_fatal_handler);
+#if DUK_VERSION >= 20000L
+	                          mg_duk_v2_fatal
+#else
+	                          mg_duk_fatal_handler
+#endif
+	                          );
 	if (!duk_ctx) {
 		mg_cry_internal(conn, "%s", "Failed to create a Duktape heap.");
 		goto exec_duktape_finished;
@@ -175,16 +226,19 @@ mg_exec_duktape_script(struct mg_connection *conn, const char *script_name)
 	duk_push_global_object(duk_ctx);
 	duk_push_object(duk_ctx); /* create a new table/object ("conn") */
 
+	/* add function conn.write */
 	duk_push_c_function(duk_ctx, duk_itf_write, 1 /* 1 = nargs */);
 	duk_push_pointer(duk_ctx, (void *)conn);
 	duk_put_prop_string(duk_ctx, -2, civetweb_conn_id);
-	duk_put_prop_string(duk_ctx, -2, "write"); /* add function conn.write */
+	duk_put_prop_string(duk_ctx, -2, "write");
 
+	/* add function conn.read */
 	duk_push_c_function(duk_ctx, duk_itf_read, 0 /* 0 = nargs */);
 	duk_push_pointer(duk_ctx, (void *)conn);
 	duk_put_prop_string(duk_ctx, -2, civetweb_conn_id);
-	duk_put_prop_string(duk_ctx, -2, "read"); /* add function conn.read */
+	duk_put_prop_string(duk_ctx, -2, "read");
 
+	/* add request_method object */
 	duk_push_string(duk_ctx, conn->request_info.request_method);
 	duk_put_prop_string(duk_ctx,
 	                    -2,
@@ -232,14 +286,14 @@ mg_exec_duktape_script(struct mg_connection *conn, const char *script_name)
 	duk_push_string(duk_ctx, script_name);
 	duk_put_prop_string(duk_ctx, -2, "script_name");
 
-	if (conn->phys_ctx != NULL) {
-		duk_push_c_function(duk_ctx, duk_itf_getoption, 1 /* 1 = nargs */);
-		duk_push_pointer(duk_ctx, (void *)(conn->phys_ctx));
-		duk_put_prop_string(duk_ctx, -2, civetweb_ctx_id);
-		duk_put_prop_string(duk_ctx,
-		                    -2,
-		                    "getoption"); /* add function conn.write */
+	/* add function civetweb.getoption */
+	duk_push_c_function(duk_ctx, duk_itf_getoption, 1 /* 1 = nargs */);
+	duk_push_pointer(duk_ctx, (void *)conn);
+	duk_put_prop_string(duk_ctx, -2, civetweb_conn_id);
+	duk_put_prop_string(duk_ctx, -2, "getoption");
 
+	if (conn->phys_ctx != NULL) {
+		/* add system name */
 		if (conn->phys_ctx->systemName != NULL) {
 			duk_push_string(duk_ctx, conn->phys_ctx->systemName);
 			duk_put_prop_string(duk_ctx, -2, "system");