1414 */
1515
1616#include " ecma-alloc.h"
17- #include " ecma-builtins.h"
1817#include " ecma-conversion.h"
19- #include " ecma-exceptions.h"
2018#include " ecma-gc.h"
21- #include " ecma-globals.h"
22- #include " ecma-helpers.h"
23- #include " ecma-objects.h"
2419#include " ecma-function-object.h"
20+ #include " ecma-lex-env.h"
2521#include " ecma-try-catch-macro.h"
26- #include " jrt.h"
22+ #include " serializer.h"
23+ #include " parser.h"
2724
2825#define ECMA_BUILTINS_INTERNAL
2926#include " ecma-builtins-internal.h"
@@ -59,6 +56,9 @@ ecma_builtin_function_dispatch_call (const ecma_value_t *arguments_list_p, /**<
5956/* *
6057 * Handle calling [[Construct]] of built-in Function object
6158 *
59+ * See also:
60+ * ECMA-262 v5, 15.3.
61+ *
6262 * @return completion-value
6363 */
6464ecma_completion_value_t
@@ -67,7 +67,127 @@ ecma_builtin_function_dispatch_construct (const ecma_value_t *arguments_list_p,
6767{
6868 JERRY_ASSERT (arguments_list_len == 0 || arguments_list_p != NULL );
6969
70- ECMA_BUILTIN_CP_UNIMPLEMENTED (arguments_list_p, arguments_list_len);
70+ ecma_completion_value_t ret_value = ecma_make_empty_completion_value ();
71+
72+ /* Last string, if any, is the function's body, and the rest, if any - are the function's parameter names */
73+ MEM_DEFINE_LOCAL_ARRAY (string_params_p,
74+ arguments_list_len == 0 ? 1 : arguments_list_len,
75+ ecma_string_t *);
76+ uint32_t params_count;
77+
78+ size_t zt_strings_buffer_size;
79+
80+ if (arguments_list_len == 0 )
81+ {
82+ /* 3. */
83+ string_params_p[0 ] = ecma_new_ecma_string_from_magic_string_id (ECMA_MAGIC_STRING__EMPTY);
84+ zt_strings_buffer_size = sizeof (ecma_char_t );
85+ params_count = 1 ;
86+ }
87+ else
88+ {
89+ /* 4., 5., 6. */
90+ zt_strings_buffer_size = 0 ;
91+
92+ params_count = 0 ;
93+ while (params_count < arguments_list_len
94+ && ecma_is_completion_value_empty (ret_value))
95+ {
96+ ECMA_TRY_CATCH (str_arg_value,
97+ ecma_op_to_string (arguments_list_p[params_count]),
98+ ret_value);
99+
100+ string_params_p[params_count] = ecma_copy_or_ref_ecma_string (ecma_get_string_from_value (str_arg_value));
101+ zt_strings_buffer_size += ((size_t ) ecma_string_get_length (string_params_p[params_count]) +
102+ sizeof (ecma_char_t ));
103+ params_count++;
104+
105+ ECMA_FINALIZE (str_arg_value);
106+ }
107+ }
108+
109+ if (ecma_is_completion_value_empty (ret_value))
110+ {
111+ JERRY_ASSERT (params_count >= 1 );
112+
113+ MEM_DEFINE_LOCAL_ARRAY (zt_string_params_p,
114+ params_count,
115+ ecma_char_t *);
116+ MEM_DEFINE_LOCAL_ARRAY (zt_string_buffer_p,
117+ zt_strings_buffer_size,
118+ ecma_char_t );
119+
120+ ssize_t zt_string_buffer_pos = 0 ;
121+ for (uint32_t i = 0 ; i < params_count; i++)
122+ {
123+ ssize_t sz = ecma_string_to_zt_string (string_params_p[i],
124+ &zt_string_buffer_p[zt_string_buffer_pos],
125+ (ssize_t ) zt_strings_buffer_size - zt_string_buffer_pos);
126+ JERRY_ASSERT (sz > 0 );
127+
128+ zt_string_params_p[i] = zt_string_buffer_p + zt_string_buffer_pos;
129+
130+ zt_string_buffer_pos += sz;
131+ }
132+
133+ parser_init ();
134+
135+ /*
136+ * FIXME:
137+ * Handle syntax errors
138+ */
139+ parser_parse_new_function ((const char **) zt_string_params_p, params_count);
140+ const opcode_t * opcodes_p = (const opcode_t *) serializer_get_bytecode ();
141+ serializer_print_opcodes ();
142+ parser_free ();
143+
144+ bool is_strict = false ;
145+ bool do_instantiate_arguments_object = true ;
146+
147+ opcode_scope_code_flags_t scope_flags = vm_get_scope_flags (opcodes_p,
148+ 0 );
149+
150+ if (scope_flags & OPCODE_SCOPE_CODE_FLAGS_STRICT)
151+ {
152+ is_strict = true ;
153+ }
154+
155+ if ((scope_flags & OPCODE_SCOPE_CODE_FLAGS_NOT_REF_ARGUMENTS_IDENTIFIER)
156+ && (scope_flags & OPCODE_SCOPE_CODE_FLAGS_NOT_REF_EVAL_IDENTIFIER))
157+ {
158+ /* the code doesn't use 'arguments' identifier
159+ * and doesn't perform direct call to eval,
160+ * so Arguments object can't be referenced */
161+ do_instantiate_arguments_object = false ;
162+ }
163+
164+ /* 11. */
165+ ecma_object_t *glob_lex_env_p = ecma_get_global_environment ();
166+
167+ ecma_object_t *func_obj_p = ecma_op_create_function_object (params_count > 1u ? string_params_p : NULL ,
168+ (ecma_length_t ) (params_count - 1u ),
169+ glob_lex_env_p,
170+ is_strict,
171+ do_instantiate_arguments_object,
172+ opcodes_p,
173+ 1 );
174+
175+ ecma_deref_object (glob_lex_env_p);
176+
177+ ret_value = ecma_make_normal_completion_value (ecma_make_object_value (func_obj_p));
178+
179+ MEM_FINALIZE_LOCAL_ARRAY (zt_string_buffer_p);
180+ MEM_FINALIZE_LOCAL_ARRAY (zt_string_params_p);
181+ }
182+
183+ for (uint32_t i = 0 ; i < params_count; i++)
184+ {
185+ ecma_deref_ecma_string (string_params_p[i]);
186+ }
187+
188+ MEM_FINALIZE_LOCAL_ARRAY (string_params_p);
189+
190+ return ret_value;
71191} /* ecma_builtin_function_dispatch_construct */
72192
73193/* *
0 commit comments