details: http://hg.nginx.org/njs/rev/d2ab98ea87ad branches: changeset: 254:d2ab98ea87ad user: Igor Sysoev <i...@sysoev.ru> date: Tue Nov 15 17:43:05 2016 +0300 description: Native methods and non-constructor functions must throw TypeError exception if they are called as constructor.
diffstat: njs/njs_builtin.c | 1 + njs/njs_vm.c | 22 +++++++++++++++++----- njs/njs_vm.h | 16 +++------------- njs/test/njs_unit_test.c | 6 ++++++ 4 files changed, 27 insertions(+), 18 deletions(-) diffs (127 lines): diff -r 91640c0405f4 -r d2ab98ea87ad njs/njs_builtin.c --- a/njs/njs_builtin.c Fri Nov 11 18:12:13 2016 +0300 +++ b/njs/njs_builtin.c Tue Nov 15 17:43:05 2016 +0300 @@ -237,6 +237,7 @@ njs_builtin_objects_create(njs_vm_t *vm) for (i = NJS_CONSTRUCTOR_OBJECT; i < NJS_CONSTRUCTOR_MAX; i++) { constructors[i].object.shared = 0; constructors[i].native = 1; + constructors[i].ctor = 1; constructors[i].args_offset = 1; constructors[i].u.native = native_constructors[i].native; constructors[i].args_types[0] = native_constructors[i].args_types[0]; diff -r 91640c0405f4 -r d2ab98ea87ad njs/njs_vm.c --- a/njs/njs_vm.c Fri Nov 11 18:12:13 2016 +0300 +++ b/njs/njs_vm.c Tue Nov 15 17:43:05 2016 +0300 @@ -2152,6 +2152,7 @@ njs_ret_t njs_vmcode_function_frame(njs_vm_t *vm, njs_value_t *value, njs_value_t *nargs) { njs_ret_t ret; + nxt_bool_t ctor; njs_value_t val, *this; njs_object_t *object; njs_function_t *function; @@ -2160,13 +2161,17 @@ njs_vmcode_function_frame(njs_vm_t *vm, if (nxt_fast_path(njs_is_function(value))) { func = (njs_vmcode_function_frame_t *) vm->current; + ctor = func->code.ctor; function = value->data.u.function; if (function->native) { + if (ctor && !function->ctor) { + goto fail; + } + ret = njs_function_native_frame(vm, function, &njs_value_void, - NULL, (uintptr_t) nargs, 0, - func->code.ctor); + NULL, (uintptr_t) nargs, 0, ctor); if (nxt_fast_path(ret == NXT_OK)) { return sizeof(njs_vmcode_function_frame_t); @@ -2175,7 +2180,7 @@ njs_vmcode_function_frame(njs_vm_t *vm, return ret; } - if (func->code.ctor) { + if (ctor) { object = njs_function_new_object(vm, value); if (nxt_slow_path(object == NULL)) { return NXT_ERROR; @@ -2191,7 +2196,7 @@ njs_vmcode_function_frame(njs_vm_t *vm, } ret = njs_function_frame(vm, function, this, NULL, (uintptr_t) nargs, - func->code.ctor); + ctor); if (nxt_fast_path(ret == NXT_OK)) { return sizeof(njs_vmcode_function_frame_t); @@ -2200,6 +2205,8 @@ njs_vmcode_function_frame(njs_vm_t *vm, return ret; } +fail: + vm->exception = &njs_exception_type_error; return NXT_ERROR; @@ -2329,8 +2336,13 @@ njs_vmcode_method_call(njs_vm_t *vm, njs return ret; } + if (method->code.ctor) { + vm->exception = &njs_exception_type_error; + return NXT_ERROR; + } + ret = njs_function_native_frame(vm, function, object, NULL, method->nargs, - 0, method->code.ctor); + 0, 0); if (nxt_fast_path(ret == NXT_OK)) { njs_retain(object); diff -r 91640c0405f4 -r d2ab98ea87ad njs/njs_vm.h --- a/njs/njs_vm.h Fri Nov 11 18:12:13 2016 +0300 +++ b/njs/njs_vm.h Tue Nov 15 17:43:05 2016 +0300 @@ -230,20 +230,10 @@ struct njs_function_s { uint8_t args_types[NJS_ARGS_TYPES_MAX]; uint8_t args_offset; - - /* - * TODO Shared - * When function object is used as value: in assignments, - * as function argument, as property and as object to get properties. - */ + uint8_t continuation_size; -#if (NXT_64BIT) - uint8_t native; - uint8_t continuation_size; -#else - uint8_t native; - uint8_t continuation_size; -#endif + uint8_t native:1; + uint8_t ctor:1; union { njs_function_lambda_t *lambda; diff -r 91640c0405f4 -r d2ab98ea87ad njs/test/njs_unit_test.c --- a/njs/test/njs_unit_test.c Fri Nov 11 18:12:13 2016 +0300 +++ b/njs/test/njs_unit_test.c Tue Nov 15 17:43:05 2016 +0300 @@ -4223,6 +4223,12 @@ static njs_unit_test_t njs_test[] = { nxt_string("var F = function (){}; typeof F.prototype"), nxt_string("object") }, + { nxt_string("new decodeURI('%00')"), + nxt_string("TypeError")}, + + { nxt_string("new ''.toString"), + nxt_string("TypeError")}, + { nxt_string("function F() { return Number }" "var o = new (F())(5);" "typeof o +' '+ o"), _______________________________________________ nginx-devel mailing list nginx-devel@nginx.org http://mailman.nginx.org/mailman/listinfo/nginx-devel