diff --git a/jerry-main/main-options.c b/jerry-main/main-options.c index f5ffe855b..da10a9532 100644 --- a/jerry-main/main-options.c +++ b/jerry-main/main-options.c @@ -32,6 +32,7 @@ typedef enum OPT_HELP, OPT_VERSION, OPT_MEM_STATS, + OPT_TEST262_OBJECT, OPT_PARSE_ONLY, OPT_SHOW_OP, OPT_SHOW_RE_OP, @@ -60,6 +61,8 @@ static const cli_opt_t main_opts[] = .help = "print tool and library version and exit"), CLI_OPT_DEF (.id = OPT_MEM_STATS, .longopt = "mem-stats", .help = "dump memory statistics"), + CLI_OPT_DEF (.id = OPT_TEST262_OBJECT, .longopt = "test262-object", + .help = "create test262 object"), CLI_OPT_DEF (.id = OPT_PARSE_ONLY, .longopt = "parse-only", .help = "don't execute JS input"), CLI_OPT_DEF (.id = OPT_SHOW_OP, .longopt = "show-opcodes", @@ -180,6 +183,11 @@ main_parse_args (int argc, /**< argc */ } break; } + case OPT_TEST262_OBJECT: + { + arguments_p->option_flags |= OPT_FLAG_TEST262_OBJECT; + break; + } case OPT_PARSE_ONLY: { arguments_p->option_flags |= OPT_FLAG_PARSE_ONLY; diff --git a/jerry-main/main-options.h b/jerry-main/main-options.h index 62a1e12c2..4486e5d12 100644 --- a/jerry-main/main-options.h +++ b/jerry-main/main-options.h @@ -23,12 +23,13 @@ */ typedef enum { - OPT_FLAG_EMPTY = 0, - OPT_FLAG_PARSE_ONLY = (1 << 0), - OPT_FLAG_DEBUG_SERVER = (1 << 1), - OPT_FLAG_WAIT_SOURCE = (1 << 2), - OPT_FLAG_NO_PROMPT = (1 << 3), - OPT_FLAG_USE_STDIN = (1 << 4), + OPT_FLAG_EMPTY = 0, + OPT_FLAG_PARSE_ONLY = (1 << 0), + OPT_FLAG_DEBUG_SERVER = (1 << 1), + OPT_FLAG_WAIT_SOURCE = (1 << 2), + OPT_FLAG_NO_PROMPT = (1 << 3), + OPT_FLAG_USE_STDIN = (1 << 4), + OPT_FLAG_TEST262_OBJECT = (1u << 5), } main_option_flags_t; /** diff --git a/jerry-main/main-utils.c b/jerry-main/main-utils.c index da1d6a6b5..6597cc50e 100644 --- a/jerry-main/main-utils.c +++ b/jerry-main/main-utils.c @@ -44,6 +44,126 @@ main_register_global_function (const char *name_p, /**< name of the function */ jerry_release_value (result_val); } /* main_register_global_function */ +/** + * Register a method for the $262 object. + */ +static void +test262_register_function (jerry_value_t test262_obj, /** $262 object */ + const char *name_p, /**< name of the function */ + jerry_external_handler_t handler_p) /**< function callback */ +{ + jerry_value_t function_name_val = jerry_create_string ((const jerry_char_t *) name_p); + jerry_value_t function_val = jerry_create_external_function (handler_p); + + jerry_value_t result_val = jerry_set_property (test262_obj, function_name_val, function_val); + + jerry_release_value (function_val); + jerry_release_value (function_name_val); + + assert (!jerry_value_is_error (result_val)); + jerry_release_value (result_val); +} /* test262_register_function */ + +/** + * $262.detachArrayBuffer + * + * A function which implements the DetachArrayBuffer abstract operation + * + * @return null value - if success + * value marked with error flag - otherwise + */ +static jerry_value_t +test262_detach_array_buffer (const jerry_value_t func_obj_val, /**< function object */ + const jerry_value_t this_p, /**< this arg */ + const jerry_value_t args_p[], /**< function arguments */ + const jerry_length_t args_cnt) /**< number of function arguments */ +{ + (void) func_obj_val; /* unused */ + (void) this_p; /* unused */ + + if (args_cnt < 1 || !jerry_value_is_arraybuffer (args_p[0])) + { + return jerry_create_error (JERRY_ERROR_TYPE, (jerry_char_t *) "Expected an ArrayBuffer object"); + } + + /* TODO: support the optional 'key' argument */ + + return jerry_detach_arraybuffer (args_p[0]); +} /* test262_detach_array_buffer */ + +/** + * $262.evalScript + * + * A function which accepts a string value as its first argument and executes it + * + * @return completion of the script parsing and execution. + */ +static jerry_value_t +test262_eval_script (const jerry_value_t func_obj_val, /**< function object */ + const jerry_value_t this_p, /**< this arg */ + const jerry_value_t args_p[], /**< function arguments */ + const jerry_length_t args_cnt) /**< number of function arguments */ +{ + (void) func_obj_val; /* unused */ + (void) this_p; /* unused */ + + if (args_cnt < 1 || !jerry_value_is_string (args_p[0])) + { + return jerry_create_error (JERRY_ERROR_TYPE, (jerry_char_t *) "Expected a string"); + } + + jerry_size_t str_size = jerry_get_utf8_string_size (args_p[0]); + jerry_char_t *str_buf_p = malloc (str_size * sizeof (jerry_char_t)); + + if (str_buf_p == NULL || jerry_string_to_utf8_char_buffer (args_p[0], str_buf_p, str_size) != str_size) + { + free (str_buf_p); + return jerry_create_error (JERRY_ERROR_RANGE, (jerry_char_t *) "Internal error"); + } + + jerry_value_t ret_value = jerry_parse (NULL, 0, str_buf_p, str_size, JERRY_PARSE_NO_OPTS); + + if (!jerry_value_is_error (ret_value)) + { + jerry_value_t func_val = ret_value; + ret_value = jerry_run (func_val); + jerry_release_value (func_val); + } + + free (str_buf_p); + + return ret_value; +} /* test262_eval_script */ + +/** + * Init the $262 object + */ +static void +register_test262 (void) +{ + jerry_value_t global_obj = jerry_get_global_object (); + jerry_value_t test262_object = jerry_create_object (); + + test262_register_function (test262_object, "detachArrayBuffer", test262_detach_array_buffer); + test262_register_function (test262_object, "evalScript", test262_eval_script); + test262_register_function (test262_object, "gc", jerryx_handler_gc); + + jerry_value_t prop_name = jerry_create_string ((const jerry_char_t *) "global"); + jerry_value_t result = jerry_set_property (test262_object, prop_name, global_obj); + assert (!jerry_value_is_error (result)); + jerry_release_value (prop_name); + jerry_release_value (result); + prop_name = jerry_create_string ((const jerry_char_t *) "$262"); + result = jerry_set_property (global_obj, prop_name, test262_object); + + jerry_release_value (prop_name); + assert (!jerry_value_is_error (result)); + + jerry_release_value (global_obj); + jerry_release_value (test262_object); + jerry_release_value (result); +} /* register_test262 */ + /** * Inits the engine and the debugger */ @@ -76,7 +196,10 @@ main_init_engine (main_args_t *arguments_p) /** main arguments */ jerryx_debugger_after_connect (protocol && jerryx_debugger_ws_create ()); } } - + if (arguments_p->option_flags & OPT_FLAG_TEST262_OBJECT) + { + register_test262 (); + } main_register_global_function ("assert", jerryx_handler_assert); main_register_global_function ("gc", jerryx_handler_gc); main_register_global_function ("print", jerryx_handler_print); diff --git a/tests/test262-esnext-excludelist.xml b/tests/test262-esnext-excludelist.xml index 469796b4d..67187c072 100644 --- a/tests/test262-esnext-excludelist.xml +++ b/tests/test262-esnext-excludelist.xml @@ -7905,7 +7905,6 @@ features: [async-iteration] https://github.com/tc39/proposal-async-iteration --> - @@ -9528,26 +9527,9 @@ - - - - - - - - - - - - - - - - - @@ -9683,7 +9665,6 @@ - @@ -9845,18 +9826,13 @@ - - - - - @@ -9864,199 +9840,53 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -10065,43 +9895,27 @@ - - - - - - - - - - - - - - - - diff --git a/tools/run-tests.py b/tools/run-tests.py index 32427189c..2c45168f7 100755 --- a/tools/run-tests.py +++ b/tools/run-tests.py @@ -435,7 +435,7 @@ def run_test262_test_suite(options): test_cmd = get_platform_cmd_prefix() + [ settings.TEST262_RUNNER_SCRIPT, - '--engine', get_binary_path(build_dir_path), + '--engine', get_binary_path(build_dir_path) + " --test262-object", '--test-dir', settings.TEST262_TEST_SUITE_DIR ]