[njs] Introduced njs_function_native_call().
Dmitry Volyntsev
xeioex at nginx.com
Thu Jan 10 13:08:39 UTC 2019
details: https://hg.nginx.org/njs/rev/045ba10db769
branches:
changeset: 716:045ba10db769
user: hongzhidao <hongzhidao at gmail.com>
date: Mon Jan 07 22:14:17 2019 +0800
description:
Introduced njs_function_native_call().
diffstat:
njs/njs_function.c | 92 ++++++++++++++++++++++++++++++++++
njs/njs_function.h | 4 +
njs/njs_vm.c | 140 ++++++----------------------------------------------
3 files changed, 113 insertions(+), 123 deletions(-)
diffs (304 lines):
diff -r 0e7fc17f6071 -r 045ba10db769 njs/njs_function.c
--- a/njs/njs_function.c Mon Jan 07 17:42:00 2019 +0800
+++ b/njs/njs_function.c Mon Jan 07 22:14:17 2019 +0800
@@ -531,6 +531,98 @@ njs_function_call(njs_vm_t *vm, njs_inde
}
+njs_ret_t
+njs_function_native_call(njs_vm_t *vm, njs_function_native_t native,
+ njs_value_t *args, nxt_uint_t nargs, njs_index_t retval)
+{
+ njs_ret_t ret;
+ njs_value_t *value;
+ njs_function_t *function;
+ njs_native_frame_t *frame;
+
+ ret = native(vm, args, nargs, retval);
+
+ /*
+ * A native method can return:
+ * NXT_OK on method success;
+ * NJS_APPLIED by Function.apply() and Function.call();
+ * NXT_AGAIN to postpone nJSVM processing;
+ * NXT_ERROR.
+ *
+ * The callee arguments must be preserved
+ * for NJS_APPLIED and NXT_AGAIN cases.
+ */
+ if (ret == NXT_OK) {
+ frame = vm->top_frame;
+
+ vm->top_frame = njs_function_previous_frame(frame);
+ njs_function_frame_free(vm, frame);
+
+ /*
+ * If a retval is in a callee arguments scope it
+ * must be in the previous callee arguments scope.
+ */
+ args = vm->top_frame->arguments;
+ function = vm->top_frame->function;
+
+ if (function != NULL) {
+ args += function->args_offset;
+ }
+
+ vm->scopes[NJS_SCOPE_CALLEE_ARGUMENTS] = args;
+
+ if (!frame->skip) {
+ value = njs_vmcode_operand(vm, retval);
+ /*
+ * GC: value external/internal++ depending
+ * on vm->retval and retval type
+ */
+ *value = vm->retval;
+ }
+
+ return NXT_OK;
+ }
+
+ return ret;
+}
+
+
+njs_native_frame_t *
+njs_function_previous_frame(njs_native_frame_t *frame)
+{
+ njs_native_frame_t *previous;
+
+ do {
+ previous = frame->previous;
+ frame = previous;
+
+ } while (frame->skip);
+
+ return frame;
+}
+
+
+void
+njs_function_frame_free(njs_vm_t *vm, njs_native_frame_t *frame)
+{
+ njs_native_frame_t *previous;
+
+ do {
+ previous = frame->previous;
+
+ /* GC: free frame->local, etc. */
+
+ if (frame->size != 0) {
+ vm->stack_size -= frame->size;
+ nxt_mem_cache_free(vm->mem_cache_pool, frame);
+ }
+
+ frame = previous;
+
+ } while (frame->skip);
+}
+
+
/*
* The "prototype" property of user defined functions is created on
* demand in private hash of the functions by the "prototype" getter.
diff -r 0e7fc17f6071 -r 045ba10db769 njs/njs_function.h
--- a/njs/njs_function.h Mon Jan 07 17:42:00 2019 +0800
+++ b/njs/njs_function.h Mon Jan 07 22:14:17 2019 +0800
@@ -171,6 +171,10 @@ njs_ret_t njs_function_frame(njs_vm_t *v
const njs_value_t *this, const njs_value_t *args, nxt_uint_t nargs,
nxt_bool_t ctor);
njs_ret_t njs_function_call(njs_vm_t *vm, njs_index_t retval, size_t advance);
+njs_ret_t njs_function_native_call(njs_vm_t *vm, njs_function_native_t native,
+ njs_value_t *args, nxt_uint_t nargs, njs_index_t retval);
+njs_native_frame_t *njs_function_previous_frame(njs_native_frame_t *frame);
+void njs_function_frame_free(njs_vm_t *vm, njs_native_frame_t *frame);
extern const njs_object_init_t njs_function_constructor_init;
extern const njs_object_init_t njs_function_prototype_init;
diff -r 0e7fc17f6071 -r 045ba10db769 njs/njs_vm.c
--- a/njs/njs_vm.c Mon Jan 07 17:42:00 2019 +0800
+++ b/njs/njs_vm.c Mon Jan 07 22:14:17 2019 +0800
@@ -36,10 +36,6 @@ static void njs_vm_scopes_restore(njs_vm
njs_native_frame_t *previous);
static njs_ret_t njs_vmcode_continuation(njs_vm_t *vm, njs_value_t *invld1,
njs_value_t *invld2);
-static njs_native_frame_t *
- njs_function_previous_frame(njs_native_frame_t *frame);
-static void njs_function_frame_free(njs_vm_t *vm,
- njs_native_frame_t *frame);
static void njs_vm_trap(njs_vm_t *vm, njs_trap_t trap, njs_value_t *value1,
njs_value_t *value2);
@@ -2064,52 +2060,19 @@ njs_vmcode_function_call(njs_vm_t *vm, n
return 0;
}
- ret = function->u.native(vm, args, nargs, (njs_index_t) retval);
-
- /*
- * A native method can return:
- * NXT_OK on method success;
- * NJS_APPLIED by Function.apply() and Function.call();
- * NXT_AGAIN to postpone nJSVM processing;
- * NXT_ERROR.
- *
- * The callee arguments must be preserved
- * for NJS_APPLIED and NXT_AGAIN cases.
- */
- if (ret == NXT_OK) {
- frame = vm->top_frame;
-
- vm->top_frame = njs_function_previous_frame(frame);
- njs_function_frame_free(vm, frame);
-
- /*
- * If a retval is in a callee arguments scope it
- * must be in the previous callee arguments scope.
- */
- args = vm->top_frame->arguments;
- function = vm->top_frame->function;
-
- if (function != NULL) {
- args += function->args_offset;
- }
-
- vm->scopes[NJS_SCOPE_CALLEE_ARGUMENTS] = args;
-
- retval = njs_vmcode_operand(vm, retval);
- /*
- * GC: value external/internal++ depending
- * on vm->retval and retval type
- */
- *retval = vm->retval;
-
- ret = sizeof(njs_vmcode_function_call_t);
-
- } else if (ret == NJS_APPLIED) {
- /* A user-defined method has been prepared to run. */
- ret = 0;
+ ret = njs_function_native_call(vm, function->u.native, args, nargs,
+ (njs_index_t) retval);
+
+ switch (ret) {
+ case NXT_OK:
+ return sizeof(njs_vmcode_function_call_t);
+
+ case NJS_APPLIED:
+ return 0;
+
+ default:
+ return ret;
}
-
- return ret;
}
@@ -2467,60 +2430,27 @@ static njs_ret_t
njs_vmcode_continuation(njs_vm_t *vm, njs_value_t *invld1, njs_value_t *invld2)
{
njs_ret_t ret;
- nxt_bool_t skip;
- njs_value_t *args, *retval;
- njs_function_t *function;
njs_native_frame_t *frame;
njs_continuation_t *cont;
cont = njs_vm_continuation(vm);
frame = vm->top_frame;
- args = frame->arguments;
if (cont->args_types != NULL) {
- ret = njs_normalize_args(vm, args, cont->args_types, frame->nargs);
+ ret = njs_normalize_args(vm, frame->arguments, cont->args_types,
+ frame->nargs);
if (ret != NJS_OK) {
return ret;
}
}
- ret = cont->function(vm, args, frame->nargs, cont->retval);
+ ret = njs_function_native_call(vm, cont->function, frame->arguments,
+ frame->nargs, cont->retval);
switch (ret) {
-
case NXT_OK:
-
- frame = vm->top_frame;
- skip = frame->skip;
-
- vm->top_frame = njs_function_previous_frame(frame);
-
- /*
- * If a retval is in a callee arguments scope it
- * must be in the previous callee arguments scope.
- */
- args = vm->top_frame->arguments;
- function = vm->top_frame->function;
-
- if (function != NULL) {
- args += function->args_offset;
- }
-
- vm->scopes[NJS_SCOPE_CALLEE_ARGUMENTS] = args;
-
- if (!skip) {
- retval = njs_vmcode_operand(vm, cont->retval);
- /*
- * GC: value external/internal++ depending
- * on vm->retval and retval type
- */
- *retval = vm->retval;
- }
-
vm->current = cont->return_address;
- (void) njs_function_frame_free(vm, frame);
-
- return 0;
+ /* Fall through. */
case NJS_APPLIED:
return 0;
@@ -2531,42 +2461,6 @@ njs_vmcode_continuation(njs_vm_t *vm, nj
}
-static njs_native_frame_t *
-njs_function_previous_frame(njs_native_frame_t *frame)
-{
- njs_native_frame_t *previous;
-
- do {
- previous = frame->previous;
- frame = previous;
-
- } while (frame->skip);
-
- return frame;
-}
-
-
-static void
-njs_function_frame_free(njs_vm_t *vm, njs_native_frame_t *frame)
-{
- njs_native_frame_t *previous;
-
- do {
- previous = frame->previous;
-
- /* GC: free frame->local, etc. */
-
- if (frame->size != 0) {
- vm->stack_size -= frame->size;
- nxt_mem_cache_free(vm->mem_cache_pool, frame);
- }
-
- frame = previous;
-
- } while (frame->skip);
-}
-
-
njs_ret_t
njs_vmcode_stop(njs_vm_t *vm, njs_value_t *invld, njs_value_t *retval)
{
More information about the nginx-devel
mailing list