Improve arguments object (#4145)
- Enhancement: Arguments object properties are now lazy instantiated - Bugfix: Mapped arguments object instantiated properties cannot be lcached - Bugfix: Mapped arguments should be constructed even if 0 formal parameters or arguments are provided - Update: remove 'caller' property of unmapped arguments object JerryScript-DCO-1.0-Signed-off-by: Robert Fancsik frobert@inf.u-szeged.hu
This commit is contained in:
@@ -149,6 +149,36 @@ ecma_deref_object (ecma_object_t *object_p) /**< object */
|
||||
object_p->type_flags_refs = (uint16_t) (object_p->type_flags_refs - ECMA_OBJECT_REF_ONE);
|
||||
} /* ecma_deref_object */
|
||||
|
||||
/**
|
||||
* Mark objects referenced by arguments object
|
||||
*/
|
||||
static void
|
||||
ecma_gc_mark_arguments_object (ecma_extended_object_t *ext_object_p) /**< arguments object */
|
||||
{
|
||||
JERRY_ASSERT (ecma_get_object_type ((ecma_object_t *) ext_object_p) == ECMA_OBJECT_TYPE_PSEUDO_ARRAY);
|
||||
|
||||
ecma_unmapped_arguments_t *arguments_p = (ecma_unmapped_arguments_t *) ext_object_p;
|
||||
ecma_value_t *argv_p = (ecma_value_t *) (arguments_p + 1);
|
||||
|
||||
if (ext_object_p->u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_MAPPED)
|
||||
{
|
||||
ecma_mapped_arguments_t *mapped_arguments_p = (ecma_mapped_arguments_t *) ext_object_p;
|
||||
argv_p = (ecma_value_t *) (mapped_arguments_p + 1);
|
||||
|
||||
ecma_gc_set_object_visited (ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, mapped_arguments_p->lex_env));
|
||||
}
|
||||
|
||||
uint32_t arguments_number = arguments_p->header.u.pseudo_array.u2.arguments_number;
|
||||
|
||||
for (uint32_t i = 0; i < arguments_number; i++)
|
||||
{
|
||||
if (ecma_is_value_object (argv_p[i]))
|
||||
{
|
||||
ecma_gc_set_object_visited (ecma_get_object_from_value (argv_p[i]));
|
||||
}
|
||||
}
|
||||
} /* ecma_gc_mark_arguments_object */
|
||||
|
||||
/**
|
||||
* Mark referenced object from property
|
||||
*/
|
||||
@@ -706,10 +736,7 @@ ecma_gc_mark (ecma_object_t *object_p) /**< object to mark from */
|
||||
{
|
||||
JERRY_ASSERT (ext_object_p->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS);
|
||||
|
||||
ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t,
|
||||
ext_object_p->u.pseudo_array.u2.lex_env_cp);
|
||||
|
||||
ecma_gc_set_object_visited (lex_env_p);
|
||||
ecma_gc_mark_arguments_object (ext_object_p);
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -915,6 +942,49 @@ ecma_gc_free_native_pointer (ecma_property_t *property_p) /**< property */
|
||||
}
|
||||
} /* ecma_gc_free_native_pointer */
|
||||
|
||||
/**
|
||||
* Free specified arguments object.
|
||||
*
|
||||
* @return allocated object's size
|
||||
*/
|
||||
static size_t
|
||||
ecma_free_arguments_object (ecma_extended_object_t *ext_object_p) /**< arguments object */
|
||||
{
|
||||
JERRY_ASSERT (ecma_get_object_type ((ecma_object_t *) ext_object_p) == ECMA_OBJECT_TYPE_PSEUDO_ARRAY);
|
||||
|
||||
size_t object_size = sizeof (ecma_unmapped_arguments_t);
|
||||
|
||||
if (ext_object_p->u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_MAPPED)
|
||||
{
|
||||
ecma_mapped_arguments_t *mapped_arguments_p = (ecma_mapped_arguments_t *) ext_object_p;
|
||||
object_size = sizeof (ecma_mapped_arguments_t);
|
||||
|
||||
#if ENABLED (JERRY_SNAPSHOT_EXEC)
|
||||
if (!(mapped_arguments_p->unmapped.header.u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_STATIC_BYTECODE))
|
||||
#endif /* ENABLED (JERRY_SNAPSHOT_EXEC) */
|
||||
{
|
||||
ecma_compiled_code_t *byte_code_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_compiled_code_t,
|
||||
mapped_arguments_p->u.byte_code);
|
||||
|
||||
ecma_bytecode_deref (byte_code_p);
|
||||
}
|
||||
}
|
||||
|
||||
ecma_value_t *argv_p = (ecma_value_t *) (((uint8_t *) ext_object_p) + object_size);
|
||||
ecma_unmapped_arguments_t *arguments_p = (ecma_unmapped_arguments_t *) ext_object_p;
|
||||
uint32_t arguments_number = arguments_p->header.u.pseudo_array.u2.arguments_number;
|
||||
|
||||
for (uint32_t i = 0; i < arguments_number; i++)
|
||||
{
|
||||
ecma_free_value_if_not_object (argv_p[i]);
|
||||
}
|
||||
|
||||
uint32_t saved_argument_count = JERRY_MAX (arguments_number,
|
||||
arguments_p->header.u.pseudo_array.u1.formal_params_number);
|
||||
|
||||
return object_size + (saved_argument_count * sizeof (ecma_value_t));
|
||||
} /* ecma_free_arguments_object */
|
||||
|
||||
/**
|
||||
* Free specified fast access mode array object.
|
||||
*/
|
||||
@@ -1444,22 +1514,7 @@ ecma_gc_free_object (ecma_object_t *object_p) /**< object to free */
|
||||
{
|
||||
case ECMA_PSEUDO_ARRAY_ARGUMENTS:
|
||||
{
|
||||
JERRY_ASSERT (ext_object_p->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS);
|
||||
|
||||
uint32_t formal_params_number = ext_object_p->u.pseudo_array.u1.length;
|
||||
ecma_value_t *arg_literal_p = (ecma_value_t *) (ext_object_p + 1);
|
||||
|
||||
for (uint32_t i = 0; i < formal_params_number; i++)
|
||||
{
|
||||
if (arg_literal_p[i] != ECMA_VALUE_EMPTY)
|
||||
{
|
||||
ecma_string_t *name_p = ecma_get_string_from_value (arg_literal_p[i]);
|
||||
ecma_deref_ecma_string (name_p);
|
||||
}
|
||||
}
|
||||
|
||||
size_t formal_params_size = formal_params_number * sizeof (ecma_value_t);
|
||||
ext_object_size += formal_params_size;
|
||||
ext_object_size = ecma_free_arguments_object (ext_object_p);
|
||||
break;
|
||||
}
|
||||
#if ENABLED (JERRY_BUILTIN_TYPEDARRAY)
|
||||
|
||||
@@ -215,6 +215,7 @@ enum
|
||||
* or function call argument list */
|
||||
ECMA_VALUE_SYNC_ITERATOR = ECMA_MAKE_VALUE (12), /**< option for ecma_op_get_iterator: sync iterator is requested */
|
||||
ECMA_VALUE_ASYNC_ITERATOR = ECMA_MAKE_VALUE (13), /**< option for ecma_op_get_iterator: async iterator is requested */
|
||||
ECMA_VALUE_INITIALIZED = ECMA_MAKE_VALUE (14), /**< represents initialized mapped arguments formal parameter */
|
||||
};
|
||||
|
||||
#if !ENABLED (JERRY_NUMBER_TYPE_FLOAT64)
|
||||
@@ -648,7 +649,6 @@ typedef enum
|
||||
ECMA_PROPERTY_GET_NO_OPTIONS = 0, /**< no option flags for ecma_op_object_get_property */
|
||||
ECMA_PROPERTY_GET_VALUE = 1u << 0, /**< fill virtual_value field for virtual properties */
|
||||
ECMA_PROPERTY_GET_EXT_REFERENCE = 1u << 1, /**< get extended reference to the property */
|
||||
ECMA_PROPERTY_GET_HAS_OWN_PROP = 1u << 2, /**< internal [[HasOwnProperty]] method */
|
||||
} ecma_property_get_option_bits_t;
|
||||
|
||||
/**
|
||||
@@ -937,13 +937,13 @@ typedef struct
|
||||
* [[IterationKind]] property for %Iterator% */
|
||||
union
|
||||
{
|
||||
uint16_t length; /**< for arguments: length of names */
|
||||
uint16_t formal_params_number; /**< for arguments: formal parameters number */
|
||||
uint16_t class_id; /**< for typedarray: the specific class name id */
|
||||
uint16_t iterator_index; /**< for %Iterator%: [[%Iterator%NextIndex]] property */
|
||||
} u1;
|
||||
union
|
||||
{
|
||||
ecma_value_t lex_env_cp; /**< for arguments: lexical environment */
|
||||
uint32_t arguments_number; /**< for arguments: arguments number */
|
||||
ecma_value_t arraybuffer; /**< for typedarray: internal arraybuffer */
|
||||
ecma_value_t iterated_value; /**< for %Iterator%: [[IteratedObject]] property */
|
||||
ecma_value_t spread_value; /**< for spread object: spreaded element */
|
||||
@@ -2183,6 +2183,45 @@ typedef struct
|
||||
uint32_t lazy_string_named_props; /**< number of lazy instantiated properties */
|
||||
} ecma_property_counter_t;
|
||||
|
||||
/**
|
||||
* Arguments object related status flags
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
ECMA_ARGUMENTS_OBJECT_NO_FLAGS = 0, /* unmapped arguments object */
|
||||
ECMA_ARGUMENTS_OBJECT_MAPPED = (1 << 0), /* mapped arguments object */
|
||||
ECMA_ARGUMENTS_OBJECT_STATIC_BYTECODE = (1 << 1), /* static mapped arguments object */
|
||||
ECMA_ARGUMENTS_OBJECT_CALLEE_INITIALIZED = (1 << 2), /* 'callee' property has been lazy initialized */
|
||||
ECMA_ARGUMENTS_OBJECT_CALLER_INITIALIZED = (1 << 3), /* 'caller' property has been lazy initialized */
|
||||
ECMA_ARGUMENTS_OBJECT_LENGTH_INITIALIZED = (1 << 4), /* 'length' property has been lazy initialized */
|
||||
ECMA_ARGUMENTS_OBJECT_ITERATOR_INITIALIZED = (1 << 5), /* 'Symbol.iterator' property has been lazy initialized */
|
||||
} ecma_arguments_object_flags_t;
|
||||
|
||||
/**
|
||||
* Definition of unmapped arguments object
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
ecma_extended_object_t header; /**< object header */
|
||||
ecma_value_t callee; /**< 'callee' property */
|
||||
} ecma_unmapped_arguments_t;
|
||||
|
||||
/**
|
||||
* Definition of mapped arguments object
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
ecma_unmapped_arguments_t unmapped; /**< unmapped arguments object header */
|
||||
ecma_value_t lex_env; /**< environment reference */
|
||||
union
|
||||
{
|
||||
ecma_value_t byte_code; /**< callee's compiled code */
|
||||
#if ENABLED (JERRY_SNAPSHOT_EXEC)
|
||||
ecma_compiled_code_t *byte_code_p; /**< real byte code pointer */
|
||||
#endif /* ENABLED (JERRY_SNAPSHOT_EXEC) */
|
||||
} u;
|
||||
} ecma_mapped_arguments_t;
|
||||
|
||||
/**
|
||||
* @}
|
||||
* @}
|
||||
|
||||
@@ -1498,23 +1498,6 @@ ecma_bytecode_deref (ecma_compiled_code_t *bytecode_p) /**< byte code pointer */
|
||||
((size_t) bytecode_p->size) << JMEM_ALIGNMENT_LOG);
|
||||
} /* ecma_bytecode_deref */
|
||||
|
||||
#if ENABLED (JERRY_ESNEXT)
|
||||
/**
|
||||
* Get the tagged template collection of the compiled code
|
||||
*
|
||||
* @return pointer to the tagged template collection
|
||||
*/
|
||||
ecma_collection_t *
|
||||
ecma_compiled_code_get_tagged_template_collection (const ecma_compiled_code_t *bytecode_header_p) /**< compiled code */
|
||||
{
|
||||
JERRY_ASSERT (bytecode_header_p != NULL);
|
||||
JERRY_ASSERT (bytecode_header_p->status_flags & CBC_CODE_FLAGS_HAS_TAGGED_LITERALS);
|
||||
|
||||
ecma_value_t *base_p = ecma_compiled_code_resolve_function_name (bytecode_header_p);
|
||||
|
||||
return ECMA_GET_INTERNAL_VALUE_POINTER (ecma_collection_t, base_p[-1]);
|
||||
} /* ecma_compiled_code_get_tagged_template_collection */
|
||||
|
||||
/**
|
||||
* Get the number of formal parameters of the compiled code
|
||||
*
|
||||
@@ -1552,6 +1535,23 @@ ecma_compiled_code_resolve_arguments_start (const ecma_compiled_code_t *bytecode
|
||||
return ((ecma_value_t *) byte_p) - ecma_compiled_code_get_formal_params (bytecode_header_p);
|
||||
} /* ecma_compiled_code_resolve_arguments_start */
|
||||
|
||||
#if ENABLED (JERRY_ESNEXT)
|
||||
/**
|
||||
* Get the tagged template collection of the compiled code
|
||||
*
|
||||
* @return pointer to the tagged template collection
|
||||
*/
|
||||
ecma_collection_t *
|
||||
ecma_compiled_code_get_tagged_template_collection (const ecma_compiled_code_t *bytecode_header_p) /**< compiled code */
|
||||
{
|
||||
JERRY_ASSERT (bytecode_header_p != NULL);
|
||||
JERRY_ASSERT (bytecode_header_p->status_flags & CBC_CODE_FLAGS_HAS_TAGGED_LITERALS);
|
||||
|
||||
ecma_value_t *base_p = ecma_compiled_code_resolve_function_name (bytecode_header_p);
|
||||
|
||||
return ECMA_GET_INTERNAL_VALUE_POINTER (ecma_collection_t, base_p[-1]);
|
||||
} /* ecma_compiled_code_get_tagged_template_collection */
|
||||
|
||||
/**
|
||||
* Resolve the position of the function name of the compiled code
|
||||
*
|
||||
|
||||
@@ -536,12 +536,10 @@ void ecma_raise_error_from_error_reference (ecma_value_t value);
|
||||
|
||||
void ecma_bytecode_ref (ecma_compiled_code_t *bytecode_p);
|
||||
void ecma_bytecode_deref (ecma_compiled_code_t *bytecode_p);
|
||||
#if ENABLED (JERRY_ESNEXT)
|
||||
ecma_collection_t *ecma_compiled_code_get_tagged_template_collection (const ecma_compiled_code_t *bytecode_header_p);
|
||||
#endif /* ENABLED (JERRY_ESNEXT) */
|
||||
#if ENABLED (JERRY_ESNEXT)
|
||||
uint32_t ecma_compiled_code_get_formal_params (const ecma_compiled_code_t *bytecode_p);
|
||||
ecma_value_t *ecma_compiled_code_resolve_arguments_start (const ecma_compiled_code_t *bytecode_header_p);
|
||||
#if ENABLED (JERRY_ESNEXT)
|
||||
ecma_collection_t *ecma_compiled_code_get_tagged_template_collection (const ecma_compiled_code_t *bytecode_header_p);
|
||||
ecma_value_t *ecma_compiled_code_resolve_function_name (const ecma_compiled_code_t *bytecode_header_p);
|
||||
#endif /* ENABLED (JERRY_ESNEXT) */
|
||||
ecma_value_t ecma_get_resource_name (const ecma_compiled_code_t *bytecode_p);
|
||||
|
||||
@@ -0,0 +1,507 @@
|
||||
/* Copyright JS Foundation and other contributors, http://js.foundation
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "ecma-alloc.h"
|
||||
#include "ecma-builtin-helpers.h"
|
||||
#include "ecma-builtins.h"
|
||||
#include "ecma-function-object.h"
|
||||
#include "ecma-gc.h"
|
||||
#include "ecma-globals.h"
|
||||
#include "ecma-helpers.h"
|
||||
#include "ecma-lex-env.h"
|
||||
#include "ecma-objects.h"
|
||||
#include "ecma-arguments-object.h"
|
||||
#include "ecma-objects-general.h"
|
||||
#include "jrt.h"
|
||||
|
||||
/** \addtogroup ecma ECMA
|
||||
* @{
|
||||
*
|
||||
* \addtogroup ecmaargumentsobject ECMA arguments object related routines
|
||||
* @{
|
||||
*/
|
||||
|
||||
/**
|
||||
* Arguments object creation operation.
|
||||
*
|
||||
* See also: ECMA-262 v5, 10.6
|
||||
*/
|
||||
void
|
||||
ecma_op_create_arguments_object (ecma_object_t *func_obj_p, /**< callee function */
|
||||
ecma_object_t *lex_env_p, /**< lexical environment the Arguments
|
||||
* object is created for */
|
||||
vm_frame_ctx_shared_args_t *shared_p) /**< shared context data */
|
||||
{
|
||||
const ecma_compiled_code_t *bytecode_data_p = shared_p->header.bytecode_header_p;
|
||||
uint16_t formal_params_number;
|
||||
|
||||
if (bytecode_data_p->status_flags & CBC_CODE_FLAGS_UINT16_ARGUMENTS)
|
||||
{
|
||||
formal_params_number = ((cbc_uint16_arguments_t *) bytecode_data_p)->argument_end;
|
||||
}
|
||||
else
|
||||
{
|
||||
formal_params_number = ((cbc_uint8_arguments_t *) bytecode_data_p)->argument_end;
|
||||
}
|
||||
|
||||
uint32_t object_size = sizeof (ecma_unmapped_arguments_t);
|
||||
uint32_t saved_arg_count = JERRY_MAX (shared_p->arg_list_len, formal_params_number);
|
||||
uint8_t flags = ECMA_ARGUMENTS_OBJECT_NO_FLAGS;
|
||||
|
||||
if (bytecode_data_p->status_flags & CBC_CODE_FLAGS_MAPPED_ARGUMENTS_NEEDED)
|
||||
{
|
||||
flags = ECMA_ARGUMENTS_OBJECT_MAPPED;
|
||||
object_size = sizeof (ecma_mapped_arguments_t);
|
||||
|
||||
#if ENABLED (JERRY_SNAPSHOT_EXEC)
|
||||
if (bytecode_data_p->status_flags & CBC_CODE_FLAGS_STATIC_FUNCTION)
|
||||
{
|
||||
flags |= ECMA_ARGUMENTS_OBJECT_STATIC_BYTECODE;
|
||||
}
|
||||
#endif /* ENABLED (JERRY_SNAPSHOT_EXEC) */
|
||||
}
|
||||
|
||||
ecma_object_t *obj_p = ecma_create_object (ecma_builtin_get (ECMA_BUILTIN_ID_OBJECT_PROTOTYPE),
|
||||
object_size + (saved_arg_count * sizeof (ecma_value_t)),
|
||||
ECMA_OBJECT_TYPE_PSEUDO_ARRAY);
|
||||
|
||||
ecma_unmapped_arguments_t *arguments_p = (ecma_unmapped_arguments_t *) obj_p;
|
||||
|
||||
arguments_p->header.u.pseudo_array.type = ECMA_PSEUDO_ARRAY_ARGUMENTS;
|
||||
arguments_p->header.u.pseudo_array.extra_info = flags;
|
||||
arguments_p->header.u.pseudo_array.u1.formal_params_number = formal_params_number;
|
||||
arguments_p->header.u.pseudo_array.u2.arguments_number = 0;
|
||||
arguments_p->callee = ecma_make_object_value (func_obj_p);
|
||||
|
||||
ecma_value_t *argv_p = (ecma_value_t *) (((uint8_t *) obj_p) + object_size);
|
||||
|
||||
for (uint32_t i = 0; i < shared_p->arg_list_len; i++)
|
||||
{
|
||||
argv_p[i] = ecma_copy_value_if_not_object (shared_p->arg_list_p[i]);
|
||||
}
|
||||
|
||||
for (uint32_t i = shared_p->arg_list_len; i < saved_arg_count; i++)
|
||||
{
|
||||
argv_p[i] = ECMA_VALUE_INITIALIZED;
|
||||
}
|
||||
|
||||
arguments_p->header.u.pseudo_array.u2.arguments_number = shared_p->arg_list_len;
|
||||
|
||||
if (bytecode_data_p->status_flags & CBC_CODE_FLAGS_MAPPED_ARGUMENTS_NEEDED)
|
||||
{
|
||||
ecma_mapped_arguments_t *mapped_arguments_p = (ecma_mapped_arguments_t *) obj_p;
|
||||
|
||||
ECMA_SET_INTERNAL_VALUE_POINTER (mapped_arguments_p->lex_env, lex_env_p);
|
||||
|
||||
#if ENABLED (JERRY_SNAPSHOT_EXEC)
|
||||
if (flags & ECMA_ARGUMENTS_OBJECT_STATIC_BYTECODE)
|
||||
{
|
||||
mapped_arguments_p->u.byte_code_p = (ecma_compiled_code_t *) bytecode_data_p;
|
||||
}
|
||||
else
|
||||
#endif /* ENABLED (JERRY_SNAPSHOT_EXEC) */
|
||||
{
|
||||
ECMA_SET_INTERNAL_VALUE_POINTER (mapped_arguments_p->u.byte_code, bytecode_data_p);
|
||||
}
|
||||
|
||||
ecma_bytecode_ref ((ecma_compiled_code_t *) bytecode_data_p);
|
||||
|
||||
ecma_value_t *formal_parameter_start_p;
|
||||
formal_parameter_start_p = ecma_compiled_code_resolve_arguments_start ((ecma_compiled_code_t *) bytecode_data_p);
|
||||
|
||||
for (uint32_t i = 0; i < formal_params_number; i++)
|
||||
{
|
||||
/* For legacy (non-strict) argument definition the trailing duplicated arguments cannot be lazy instantiated
|
||||
E.g: function f (a,a,a,a) {} */
|
||||
if (JERRY_UNLIKELY (ecma_is_value_empty (formal_parameter_start_p[i])))
|
||||
{
|
||||
ecma_property_value_t *prop_value_p;
|
||||
ecma_string_t *prop_name_p = ecma_new_ecma_string_from_uint32 (i);
|
||||
|
||||
prop_value_p = ecma_create_named_data_property (obj_p,
|
||||
prop_name_p,
|
||||
ECMA_PROPERTY_CONFIGURABLE_ENUMERABLE_WRITABLE,
|
||||
NULL);
|
||||
|
||||
ecma_deref_ecma_string (prop_name_p);
|
||||
|
||||
prop_value_p->value = argv_p[i];
|
||||
argv_p[i] = ECMA_VALUE_EMPTY;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
uint8_t prop_flags = ((bytecode_data_p->status_flags & CBC_CODE_FLAGS_STRICT_MODE) ? ECMA_PROPERTY_FIXED
|
||||
: ECMA_PROPERTY_FLAG_WRITABLE);
|
||||
|
||||
ecma_property_value_t *prop_value_p;
|
||||
prop_value_p = ecma_create_named_data_property (lex_env_p,
|
||||
ecma_get_magic_string (LIT_MAGIC_STRING_ARGUMENTS),
|
||||
prop_flags,
|
||||
NULL);
|
||||
|
||||
prop_value_p->value = ecma_make_object_value (obj_p);
|
||||
ecma_deref_object (obj_p);
|
||||
} /* ecma_op_create_arguments_object */
|
||||
|
||||
/**
|
||||
* [[DefineOwnProperty]] ecma Arguments object's operation
|
||||
*
|
||||
* See also:
|
||||
* ECMA-262 v5, 8.6.2; ECMA-262 v5, Table 8
|
||||
* ECMA-262 v5, 10.6
|
||||
*
|
||||
* @return ecma value
|
||||
* Returned value must be freed with ecma_free_value
|
||||
*/
|
||||
ecma_value_t
|
||||
ecma_op_arguments_object_define_own_property (ecma_object_t *object_p, /**< the object */
|
||||
ecma_string_t *property_name_p, /**< property name */
|
||||
const ecma_property_descriptor_t *property_desc_p) /**< property
|
||||
* descriptor */
|
||||
{
|
||||
/* 3. */
|
||||
ecma_value_t ret_value = ecma_op_general_object_define_own_property (object_p,
|
||||
property_name_p,
|
||||
property_desc_p);
|
||||
|
||||
if (ECMA_IS_VALUE_ERROR (ret_value)
|
||||
|| !(((ecma_extended_object_t *) object_p)->u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_MAPPED))
|
||||
{
|
||||
return ret_value;
|
||||
}
|
||||
|
||||
ecma_mapped_arguments_t *mapped_arguments_p = (ecma_mapped_arguments_t *) object_p;
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
|
||||
if (index >= mapped_arguments_p->unmapped.header.u.pseudo_array.u1.formal_params_number)
|
||||
{
|
||||
return ret_value;
|
||||
}
|
||||
|
||||
ecma_value_t *argv_p = (ecma_value_t *) (mapped_arguments_p + 1);
|
||||
|
||||
if (!ecma_is_value_empty (argv_p[index]))
|
||||
{
|
||||
if (property_desc_p->flags & (ECMA_PROP_IS_GET_DEFINED | ECMA_PROP_IS_SET_DEFINED))
|
||||
{
|
||||
ecma_free_value_if_not_object (argv_p[index]);
|
||||
argv_p[index] = ECMA_VALUE_EMPTY;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (property_desc_p->flags & ECMA_PROP_IS_VALUE_DEFINED)
|
||||
{
|
||||
ecma_string_t *name_p = ecma_op_arguments_object_get_formal_parameter (mapped_arguments_p, index);
|
||||
ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, mapped_arguments_p->lex_env);
|
||||
|
||||
ecma_value_t completion = ecma_op_set_mutable_binding (lex_env_p,
|
||||
name_p,
|
||||
property_desc_p->value,
|
||||
true);
|
||||
|
||||
JERRY_ASSERT (ecma_is_value_empty (completion));
|
||||
}
|
||||
|
||||
if ((property_desc_p->flags & ECMA_PROP_IS_WRITABLE_DEFINED)
|
||||
&& !(property_desc_p->flags & ECMA_PROP_IS_WRITABLE))
|
||||
{
|
||||
ecma_free_value_if_not_object (argv_p[index]);
|
||||
argv_p[index] = ECMA_VALUE_EMPTY;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ret_value;
|
||||
} /* ecma_op_arguments_object_define_own_property */
|
||||
|
||||
/**
|
||||
* [[Delete]] ecma Arguments object's operation
|
||||
*
|
||||
* See also:
|
||||
* ECMA-262 v5, 8.6.2; ECMA-262 v5, Table 8
|
||||
* ECMA-262 v5, 10.6
|
||||
*
|
||||
* @return ecma value
|
||||
* Returned value must be freed with ecma_free_value
|
||||
*/
|
||||
ecma_value_t
|
||||
ecma_op_arguments_object_delete (ecma_object_t *object_p, /**< the object */
|
||||
ecma_string_t *property_name_p, /**< property name */
|
||||
bool is_throw) /**< flag that controls failure handling */
|
||||
{
|
||||
/* 3. */
|
||||
ecma_value_t ret_value = ecma_op_general_object_delete (object_p, property_name_p, is_throw);
|
||||
|
||||
if (!ecma_is_value_true (ret_value)
|
||||
|| !(((ecma_extended_object_t *) object_p)->u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_MAPPED))
|
||||
{
|
||||
return ret_value;
|
||||
}
|
||||
|
||||
ecma_mapped_arguments_t *mapped_arguments_p = (ecma_mapped_arguments_t *) object_p;
|
||||
ecma_value_t *argv_p = (ecma_value_t *) (mapped_arguments_p + 1);
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
|
||||
if (index < mapped_arguments_p->unmapped.header.u.pseudo_array.u1.formal_params_number)
|
||||
{
|
||||
ecma_free_value_if_not_object (argv_p[index]);
|
||||
argv_p[index] = ECMA_VALUE_EMPTY;
|
||||
}
|
||||
|
||||
return ret_value;
|
||||
} /* ecma_op_arguments_object_delete */
|
||||
|
||||
/**
|
||||
* Try to lazy instantiate the given property of a mapped/unmapped arguments object
|
||||
*
|
||||
* @return pointer property, if one was instantiated,
|
||||
* NULL - otherwise.
|
||||
*/
|
||||
ecma_property_t *
|
||||
ecma_op_arguments_object_try_to_lazy_instantiate_property (ecma_object_t *object_p, /**< object */
|
||||
ecma_string_t *property_name_p) /**< property's name */
|
||||
{
|
||||
JERRY_ASSERT (ecma_get_object_type (object_p) == ECMA_OBJECT_TYPE_PSEUDO_ARRAY);
|
||||
JERRY_ASSERT (((ecma_extended_object_t *) object_p)->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS);
|
||||
|
||||
ecma_unmapped_arguments_t *arguments_p = (ecma_unmapped_arguments_t *) object_p;
|
||||
ecma_value_t *argv_p = (ecma_value_t *) (arguments_p + 1);
|
||||
ecma_property_value_t *prop_value_p;
|
||||
ecma_property_t *prop_p = NULL;
|
||||
uint32_t arguments_number = arguments_p->header.u.pseudo_array.u2.arguments_number;
|
||||
uint8_t flags = arguments_p->header.u.pseudo_array.extra_info;
|
||||
|
||||
if (flags & ECMA_ARGUMENTS_OBJECT_MAPPED)
|
||||
{
|
||||
argv_p = (ecma_value_t *) (((ecma_mapped_arguments_t *) object_p) + 1);
|
||||
}
|
||||
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
|
||||
if (index != ECMA_STRING_NOT_ARRAY_INDEX)
|
||||
{
|
||||
if (index >= arguments_number
|
||||
|| ecma_is_value_empty (argv_p[index])
|
||||
|| argv_p[index] == ECMA_VALUE_INITIALIZED)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
prop_value_p = ecma_create_named_data_property (object_p,
|
||||
property_name_p,
|
||||
ECMA_PROPERTY_CONFIGURABLE_ENUMERABLE_WRITABLE,
|
||||
&prop_p);
|
||||
|
||||
/* Passing the reference */
|
||||
prop_value_p->value = argv_p[index];
|
||||
|
||||
/* Pevent reinitialization */
|
||||
if ((flags & ECMA_ARGUMENTS_OBJECT_MAPPED)
|
||||
&& index < arguments_p->header.u.pseudo_array.u1.formal_params_number)
|
||||
{
|
||||
argv_p[index] = ECMA_VALUE_INITIALIZED;
|
||||
}
|
||||
else
|
||||
{
|
||||
argv_p[index] = ECMA_VALUE_EMPTY;
|
||||
}
|
||||
|
||||
return prop_p;
|
||||
}
|
||||
|
||||
if (property_name_p == ecma_get_magic_string (LIT_MAGIC_STRING_LENGTH)
|
||||
&& !(flags & ECMA_ARGUMENTS_OBJECT_LENGTH_INITIALIZED))
|
||||
{
|
||||
arguments_p->header.u.pseudo_array.extra_info |= ECMA_ARGUMENTS_OBJECT_LENGTH_INITIALIZED;
|
||||
|
||||
prop_value_p = ecma_create_named_data_property (object_p,
|
||||
ecma_get_magic_string (LIT_MAGIC_STRING_LENGTH),
|
||||
ECMA_PROPERTY_CONFIGURABLE_WRITABLE,
|
||||
&prop_p);
|
||||
|
||||
prop_value_p->value = ecma_make_uint32_value (arguments_number);
|
||||
}
|
||||
|
||||
if (property_name_p == ecma_get_magic_string (LIT_MAGIC_STRING_CALLEE)
|
||||
&& !(flags & ECMA_ARGUMENTS_OBJECT_CALLEE_INITIALIZED))
|
||||
{
|
||||
arguments_p->header.u.pseudo_array.extra_info |= ECMA_ARGUMENTS_OBJECT_CALLEE_INITIALIZED;
|
||||
|
||||
if (flags & ECMA_ARGUMENTS_OBJECT_MAPPED)
|
||||
{
|
||||
prop_value_p = ecma_create_named_data_property (object_p,
|
||||
property_name_p,
|
||||
ECMA_PROPERTY_CONFIGURABLE_WRITABLE,
|
||||
&prop_p);
|
||||
|
||||
prop_value_p->value = arguments_p->callee;
|
||||
}
|
||||
else
|
||||
{
|
||||
ecma_object_t *thrower_p = ecma_builtin_get (ECMA_BUILTIN_ID_TYPE_ERROR_THROWER);
|
||||
|
||||
prop_value_p = ecma_create_named_accessor_property (object_p,
|
||||
ecma_get_magic_string (LIT_MAGIC_STRING_CALLEE),
|
||||
thrower_p,
|
||||
thrower_p,
|
||||
ECMA_PROPERTY_FIXED,
|
||||
&prop_p);
|
||||
}
|
||||
return prop_p;
|
||||
}
|
||||
|
||||
#if !ENABLED (JERRY_ESNEXT)
|
||||
if (property_name_p == ecma_get_magic_string (LIT_MAGIC_STRING_CALLER)
|
||||
&& !(arguments_p->header.u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_CALLER_INITIALIZED))
|
||||
{
|
||||
if (arguments_p->header.u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_MAPPED)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
arguments_p->header.u.pseudo_array.extra_info |= ECMA_ARGUMENTS_OBJECT_CALLER_INITIALIZED;
|
||||
|
||||
ecma_object_t *thrower_p = ecma_builtin_get (ECMA_BUILTIN_ID_TYPE_ERROR_THROWER);
|
||||
|
||||
prop_value_p = ecma_create_named_accessor_property (object_p,
|
||||
ecma_get_magic_string (LIT_MAGIC_STRING_CALLER),
|
||||
thrower_p,
|
||||
thrower_p,
|
||||
ECMA_PROPERTY_FIXED,
|
||||
&prop_p);
|
||||
return prop_p;
|
||||
}
|
||||
#else /* ENABLED (JERRY_ESNEXT) */
|
||||
ecma_string_t *symbol_p = ecma_op_get_global_symbol (LIT_GLOBAL_SYMBOL_ITERATOR);
|
||||
|
||||
if (property_name_p == symbol_p
|
||||
&& !(flags & ECMA_ARGUMENTS_OBJECT_ITERATOR_INITIALIZED))
|
||||
{
|
||||
arguments_p->header.u.pseudo_array.extra_info |= ECMA_ARGUMENTS_OBJECT_ITERATOR_INITIALIZED;
|
||||
|
||||
prop_value_p = ecma_create_named_data_property (object_p,
|
||||
symbol_p,
|
||||
ECMA_PROPERTY_CONFIGURABLE_WRITABLE,
|
||||
&prop_p);
|
||||
|
||||
prop_value_p->value = ecma_op_object_get_by_magic_id (ecma_builtin_get (ECMA_BUILTIN_ID_INTRINSIC_OBJECT),
|
||||
LIT_INTERNAL_MAGIC_STRING_ARRAY_PROTOTYPE_VALUES);
|
||||
|
||||
JERRY_ASSERT (ecma_is_value_object (prop_value_p->value));
|
||||
ecma_deref_object (ecma_get_object_from_value (prop_value_p->value));
|
||||
}
|
||||
|
||||
ecma_deref_ecma_string (symbol_p);
|
||||
#endif /* !ENABLED (JERRY_ESNEXT) */
|
||||
|
||||
return prop_p;
|
||||
} /* ecma_op_arguments_object_try_to_lazy_instantiate_property */
|
||||
|
||||
/**
|
||||
* List names of an arguments object's lazy instantiated properties
|
||||
*/
|
||||
void
|
||||
ecma_op_arguments_object_list_lazy_property_names (ecma_object_t *obj_p, /**< arguments object */
|
||||
ecma_collection_t *prop_names_p, /**< prop name collection */
|
||||
ecma_property_counter_t *prop_counter_p) /**< prop counter */
|
||||
{
|
||||
JERRY_ASSERT (ecma_get_object_type (obj_p) == ECMA_OBJECT_TYPE_PSEUDO_ARRAY);
|
||||
JERRY_ASSERT (((ecma_extended_object_t *) obj_p)->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS);
|
||||
|
||||
ecma_unmapped_arguments_t *arguments_p = (ecma_unmapped_arguments_t *) obj_p;
|
||||
|
||||
ecma_value_t *argv_p = (ecma_value_t *) (arguments_p + 1);
|
||||
uint32_t arguments_number = arguments_p->header.u.pseudo_array.u2.arguments_number;
|
||||
uint8_t flags = arguments_p->header.u.pseudo_array.extra_info;
|
||||
|
||||
if (flags & ECMA_ARGUMENTS_OBJECT_MAPPED)
|
||||
{
|
||||
argv_p = (ecma_value_t *) (((ecma_mapped_arguments_t *) obj_p) + 1);
|
||||
}
|
||||
|
||||
for (uint32_t index = 0; index < arguments_number; index++)
|
||||
{
|
||||
if (!ecma_is_value_empty (argv_p[index]))
|
||||
{
|
||||
ecma_string_t *index_string_p = ecma_new_ecma_string_from_uint32 (index);
|
||||
ecma_collection_push_back (prop_names_p, ecma_make_string_value (index_string_p));
|
||||
prop_counter_p->array_index_named_props++;
|
||||
}
|
||||
}
|
||||
|
||||
if (!(flags & ECMA_ARGUMENTS_OBJECT_LENGTH_INITIALIZED))
|
||||
{
|
||||
ecma_collection_push_back (prop_names_p, ecma_make_magic_string_value (LIT_MAGIC_STRING_LENGTH));
|
||||
prop_counter_p->string_named_props++;
|
||||
}
|
||||
|
||||
if (!(flags & ECMA_ARGUMENTS_OBJECT_CALLEE_INITIALIZED))
|
||||
{
|
||||
ecma_collection_push_back (prop_names_p, ecma_make_magic_string_value (LIT_MAGIC_STRING_CALLEE));
|
||||
prop_counter_p->string_named_props++;
|
||||
}
|
||||
|
||||
#if !ENABLED (JERRY_ESNEXT)
|
||||
if (!(flags & (ECMA_ARGUMENTS_OBJECT_CALLER_INITIALIZED | ECMA_ARGUMENTS_OBJECT_MAPPED)))
|
||||
{
|
||||
ecma_collection_push_back (prop_names_p, ecma_make_magic_string_value (LIT_MAGIC_STRING_CALLER));
|
||||
prop_counter_p->string_named_props++;
|
||||
}
|
||||
#else /* ENABLED (JERRY_ESNEXT) */
|
||||
if (!(flags & ECMA_ARGUMENTS_OBJECT_ITERATOR_INITIALIZED))
|
||||
{
|
||||
ecma_string_t *symbol_p = ecma_op_get_global_symbol (LIT_GLOBAL_SYMBOL_ITERATOR);
|
||||
ecma_collection_push_back (prop_names_p, ecma_make_symbol_value (symbol_p));
|
||||
prop_counter_p->symbol_named_props++;
|
||||
}
|
||||
#endif /* !ENABLED (JERRY_ESNEXT) */
|
||||
} /* ecma_op_arguments_object_list_lazy_property_names */
|
||||
|
||||
/**
|
||||
* Get the formal parameter name corresponding to the given property index
|
||||
*
|
||||
* @return pointer to the formal parameter name
|
||||
*/
|
||||
ecma_string_t *
|
||||
ecma_op_arguments_object_get_formal_parameter (ecma_mapped_arguments_t *mapped_arguments_p, /**< mapped arguments
|
||||
* object */
|
||||
uint32_t index) /**< formal parameter index */
|
||||
{
|
||||
JERRY_ASSERT (mapped_arguments_p->unmapped.header.u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_MAPPED);
|
||||
JERRY_ASSERT (index < mapped_arguments_p->unmapped.header.u.pseudo_array.u1.formal_params_number);
|
||||
|
||||
ecma_compiled_code_t *byte_code_p;
|
||||
|
||||
#if ENABLED (JERRY_SNAPSHOT_EXEC)
|
||||
if (mapped_arguments_p->unmapped.header.u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_STATIC_BYTECODE)
|
||||
{
|
||||
byte_code_p = mapped_arguments_p->u.byte_code_p;
|
||||
}
|
||||
else
|
||||
#endif /* ENABLED (JERRY_SNAPSHOT_EXEC) */
|
||||
{
|
||||
byte_code_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_compiled_code_t, mapped_arguments_p->u.byte_code);
|
||||
}
|
||||
|
||||
ecma_value_t *formal_param_names_p = ecma_compiled_code_resolve_arguments_start (byte_code_p);
|
||||
|
||||
return ecma_get_string_from_value (formal_param_names_p[index]);
|
||||
} /* ecma_op_arguments_object_get_formal_parameter */
|
||||
|
||||
/**
|
||||
* @}
|
||||
* @}
|
||||
*/
|
||||
+15
-3
@@ -13,8 +13,8 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef ECMA_OBJECTS_ARGUMENTS_H
|
||||
#define ECMA_OBJECTS_ARGUMENTS_H
|
||||
#ifndef ECMA_ARGUMENTS_OBJECT_H
|
||||
#define ECMA_ARGUMENTS_OBJECT_H
|
||||
|
||||
#include "ecma-globals.h"
|
||||
#include "ecma-helpers.h"
|
||||
@@ -30,4 +30,16 @@ ecma_value_t
|
||||
ecma_op_arguments_object_define_own_property (ecma_object_t *object_p, ecma_string_t *property_name_p,
|
||||
const ecma_property_descriptor_t *property_desc_p);
|
||||
|
||||
#endif /* !ECMA_OBJECTS_ARGUMENTS_H */
|
||||
ecma_property_t *
|
||||
ecma_op_arguments_object_try_to_lazy_instantiate_property (ecma_object_t *object_p,
|
||||
ecma_string_t *property_name_p);
|
||||
|
||||
void
|
||||
ecma_op_arguments_object_list_lazy_property_names (ecma_object_t *obj_p,
|
||||
ecma_collection_t *prop_names_p,
|
||||
ecma_property_counter_t *prop_counter_p);
|
||||
|
||||
ecma_string_t *
|
||||
ecma_op_arguments_object_get_formal_parameter (ecma_mapped_arguments_t *mapped_arguments_p,
|
||||
uint32_t index);
|
||||
#endif /* !ECMA_ARGUMENTS_OBJECT_H */
|
||||
@@ -25,7 +25,7 @@
|
||||
#include "ecma-lex-env.h"
|
||||
#include "ecma-objects.h"
|
||||
#include "ecma-objects-general.h"
|
||||
#include "ecma-objects-arguments.h"
|
||||
#include "ecma-arguments-object.h"
|
||||
#include "ecma-proxy-object.h"
|
||||
#include "ecma-symbol-object.h"
|
||||
#include "jcontext.h"
|
||||
|
||||
@@ -1,358 +0,0 @@
|
||||
/* Copyright JS Foundation and other contributors, http://js.foundation
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "ecma-alloc.h"
|
||||
#include "ecma-builtin-helpers.h"
|
||||
#include "ecma-builtins.h"
|
||||
#include "ecma-function-object.h"
|
||||
#include "ecma-gc.h"
|
||||
#include "ecma-globals.h"
|
||||
#include "ecma-helpers.h"
|
||||
#include "ecma-lex-env.h"
|
||||
#include "ecma-objects.h"
|
||||
#include "ecma-objects-arguments.h"
|
||||
#include "ecma-objects-general.h"
|
||||
|
||||
#include "jrt.h"
|
||||
|
||||
/** \addtogroup ecma ECMA
|
||||
* @{
|
||||
*
|
||||
* \addtogroup ecmafunctionobject ECMA Function object related routines
|
||||
* @{
|
||||
*/
|
||||
|
||||
/**
|
||||
* Arguments object creation operation.
|
||||
*
|
||||
* See also: ECMA-262 v5, 10.6
|
||||
*/
|
||||
void
|
||||
ecma_op_create_arguments_object (ecma_object_t *func_obj_p, /**< callee function */
|
||||
ecma_object_t *lex_env_p, /**< lexical environment the Arguments
|
||||
object is created for */
|
||||
vm_frame_ctx_shared_args_t *shared_p) /**< shared context dta */
|
||||
{
|
||||
const ecma_compiled_code_t *bytecode_data_p = shared_p->header.bytecode_header_p;
|
||||
bool is_strict = (bytecode_data_p->status_flags & CBC_CODE_FLAGS_STRICT_MODE) != 0;
|
||||
|
||||
uint32_t formal_params_number;
|
||||
|
||||
if (bytecode_data_p->status_flags & CBC_CODE_FLAGS_UINT16_ARGUMENTS)
|
||||
{
|
||||
cbc_uint16_arguments_t *args_p = (cbc_uint16_arguments_t *) bytecode_data_p;
|
||||
|
||||
formal_params_number = args_p->argument_end;
|
||||
}
|
||||
else
|
||||
{
|
||||
cbc_uint8_arguments_t *args_p = (cbc_uint8_arguments_t *) bytecode_data_p;
|
||||
|
||||
formal_params_number = args_p->argument_end;
|
||||
}
|
||||
|
||||
ecma_object_t *prototype_p = ecma_builtin_get (ECMA_BUILTIN_ID_OBJECT_PROTOTYPE);
|
||||
ecma_object_t *obj_p;
|
||||
uint32_t arguments_number = shared_p->arg_list_len;
|
||||
|
||||
if ((bytecode_data_p->status_flags & CBC_CODE_FLAGS_MAPPED_ARGUMENTS_NEEDED)
|
||||
&& arguments_number > 0
|
||||
&& formal_params_number > 0)
|
||||
{
|
||||
size_t formal_params_size = formal_params_number * sizeof (ecma_value_t);
|
||||
|
||||
obj_p = ecma_create_object (prototype_p,
|
||||
sizeof (ecma_extended_object_t) + formal_params_size,
|
||||
ECMA_OBJECT_TYPE_PSEUDO_ARRAY);
|
||||
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) obj_p;
|
||||
|
||||
ext_object_p->u.pseudo_array.type = ECMA_PSEUDO_ARRAY_ARGUMENTS;
|
||||
|
||||
ECMA_SET_INTERNAL_VALUE_POINTER (ext_object_p->u.pseudo_array.u2.lex_env_cp, lex_env_p);
|
||||
|
||||
ext_object_p->u.pseudo_array.u1.length = (uint16_t) formal_params_number;
|
||||
|
||||
ecma_value_t *arg_literal_p = (ecma_value_t *) (ext_object_p + 1);
|
||||
|
||||
uint8_t *byte_p = (uint8_t *) bytecode_data_p;
|
||||
byte_p += ((size_t) bytecode_data_p->size) << JMEM_ALIGNMENT_LOG;
|
||||
byte_p -= formal_params_size;
|
||||
|
||||
memcpy (arg_literal_p, byte_p, formal_params_size);
|
||||
|
||||
for (uint32_t i = 0; i < formal_params_number; i++)
|
||||
{
|
||||
if (arg_literal_p[i] != ECMA_VALUE_EMPTY)
|
||||
{
|
||||
ecma_string_t *name_p = ecma_get_string_from_value (arg_literal_p[i]);
|
||||
ecma_ref_ecma_string (name_p);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
obj_p = ecma_create_object (prototype_p, sizeof (ecma_extended_object_t), ECMA_OBJECT_TYPE_CLASS);
|
||||
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) obj_p;
|
||||
ext_object_p->u.class_prop.class_id = LIT_MAGIC_STRING_ARGUMENTS_UL;
|
||||
}
|
||||
|
||||
ecma_property_value_t *prop_value_p;
|
||||
|
||||
/* 11.a, 11.b */
|
||||
for (uint32_t index = 0;
|
||||
index < arguments_number;
|
||||
index++)
|
||||
{
|
||||
ecma_string_t *index_string_p = ecma_new_ecma_string_from_uint32 (index);
|
||||
|
||||
prop_value_p = ecma_create_named_data_property (obj_p,
|
||||
index_string_p,
|
||||
ECMA_PROPERTY_CONFIGURABLE_ENUMERABLE_WRITABLE,
|
||||
NULL);
|
||||
|
||||
const ecma_value_t *arguments_list_p = shared_p->arg_list_p;
|
||||
prop_value_p->value = ecma_copy_value_if_not_object (arguments_list_p[index]);
|
||||
|
||||
ecma_deref_ecma_string (index_string_p);
|
||||
}
|
||||
|
||||
/* 7. */
|
||||
prop_value_p = ecma_create_named_data_property (obj_p,
|
||||
ecma_get_magic_string (LIT_MAGIC_STRING_LENGTH),
|
||||
ECMA_PROPERTY_CONFIGURABLE_WRITABLE,
|
||||
NULL);
|
||||
|
||||
prop_value_p->value = ecma_make_uint32_value (arguments_number);
|
||||
|
||||
ecma_property_descriptor_t prop_desc = ecma_make_empty_property_descriptor ();
|
||||
|
||||
#if ENABLED (JERRY_ESNEXT)
|
||||
/* ECMAScript v6, 9.4.4.6.7, 9.4.4.7.22 */
|
||||
ecma_string_t *symbol_p = ecma_op_get_global_symbol (LIT_GLOBAL_SYMBOL_ITERATOR);
|
||||
|
||||
prop_value_p = ecma_create_named_data_property (obj_p,
|
||||
symbol_p,
|
||||
ECMA_PROPERTY_CONFIGURABLE_WRITABLE,
|
||||
NULL);
|
||||
ecma_deref_ecma_string (symbol_p);
|
||||
prop_value_p->value = ecma_op_object_get_by_magic_id (ecma_builtin_get (ECMA_BUILTIN_ID_INTRINSIC_OBJECT),
|
||||
LIT_INTERNAL_MAGIC_STRING_ARRAY_PROTOTYPE_VALUES);
|
||||
|
||||
JERRY_ASSERT (ecma_is_value_object (prop_value_p->value));
|
||||
ecma_deref_object (ecma_get_object_from_value (prop_value_p->value));
|
||||
#endif /* ENABLED (JERRY_ESNEXT) */
|
||||
|
||||
/* 13. */
|
||||
if (!is_strict)
|
||||
{
|
||||
prop_value_p = ecma_create_named_data_property (obj_p,
|
||||
ecma_get_magic_string (LIT_MAGIC_STRING_CALLEE),
|
||||
ECMA_PROPERTY_CONFIGURABLE_WRITABLE,
|
||||
NULL);
|
||||
|
||||
prop_value_p->value = ecma_make_object_value (func_obj_p);
|
||||
}
|
||||
else
|
||||
{
|
||||
ecma_object_t *thrower_p = ecma_builtin_get (ECMA_BUILTIN_ID_TYPE_ERROR_THROWER);
|
||||
|
||||
/* 14. */
|
||||
prop_desc = ecma_make_empty_property_descriptor ();
|
||||
{
|
||||
prop_desc.flags = (ECMA_PROP_IS_GET_DEFINED
|
||||
| ECMA_PROP_IS_SET_DEFINED
|
||||
| ECMA_PROP_IS_ENUMERABLE_DEFINED
|
||||
| ECMA_PROP_IS_CONFIGURABLE_DEFINED);
|
||||
}
|
||||
prop_desc.set_p = thrower_p;
|
||||
prop_desc.get_p = thrower_p;
|
||||
|
||||
ecma_value_t completion = ecma_op_object_define_own_property (obj_p,
|
||||
ecma_get_magic_string (LIT_MAGIC_STRING_CALLEE),
|
||||
&prop_desc);
|
||||
|
||||
JERRY_ASSERT (ecma_is_value_true (completion));
|
||||
|
||||
completion = ecma_op_object_define_own_property (obj_p,
|
||||
ecma_get_magic_string (LIT_MAGIC_STRING_CALLER),
|
||||
&prop_desc);
|
||||
JERRY_ASSERT (ecma_is_value_true (completion));
|
||||
}
|
||||
|
||||
ecma_string_t *arguments_string_p = ecma_get_magic_string (LIT_MAGIC_STRING_ARGUMENTS);
|
||||
|
||||
if (is_strict)
|
||||
{
|
||||
ecma_op_create_immutable_binding (lex_env_p,
|
||||
arguments_string_p,
|
||||
ecma_make_object_value (obj_p));
|
||||
}
|
||||
else
|
||||
{
|
||||
ecma_value_t completion = ecma_op_create_mutable_binding (lex_env_p,
|
||||
arguments_string_p,
|
||||
false);
|
||||
JERRY_ASSERT (ecma_is_value_empty (completion));
|
||||
|
||||
completion = ecma_op_set_mutable_binding (lex_env_p,
|
||||
arguments_string_p,
|
||||
ecma_make_object_value (obj_p),
|
||||
false);
|
||||
|
||||
JERRY_ASSERT (ecma_is_value_empty (completion));
|
||||
}
|
||||
|
||||
ecma_deref_object (obj_p);
|
||||
} /* ecma_op_create_arguments_object */
|
||||
|
||||
/**
|
||||
* [[DefineOwnProperty]] ecma Arguments object's operation
|
||||
*
|
||||
* See also:
|
||||
* ECMA-262 v5, 8.6.2; ECMA-262 v5, Table 8
|
||||
* ECMA-262 v5, 10.6
|
||||
*
|
||||
* @return ecma value
|
||||
* Returned value must be freed with ecma_free_value
|
||||
*/
|
||||
ecma_value_t
|
||||
ecma_op_arguments_object_define_own_property (ecma_object_t *object_p, /**< the object */
|
||||
ecma_string_t *property_name_p, /**< property name */
|
||||
const ecma_property_descriptor_t *property_desc_p) /**< property
|
||||
* descriptor */
|
||||
{
|
||||
/* 3. */
|
||||
ecma_value_t ret_value = ecma_op_general_object_define_own_property (object_p,
|
||||
property_name_p,
|
||||
property_desc_p);
|
||||
|
||||
if (ECMA_IS_VALUE_ERROR (ret_value))
|
||||
{
|
||||
return ret_value;
|
||||
}
|
||||
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
|
||||
if (index == ECMA_STRING_NOT_ARRAY_INDEX)
|
||||
{
|
||||
return ret_value;
|
||||
}
|
||||
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) object_p;
|
||||
|
||||
if (index >= ext_object_p->u.pseudo_array.u1.length)
|
||||
{
|
||||
return ret_value;
|
||||
}
|
||||
|
||||
ecma_value_t *arg_literal_p = (ecma_value_t *) (ext_object_p + 1);
|
||||
|
||||
if (arg_literal_p[index] == ECMA_VALUE_EMPTY)
|
||||
{
|
||||
return ret_value;
|
||||
}
|
||||
|
||||
ecma_string_t *name_p = ecma_get_string_from_value (arg_literal_p[index]);
|
||||
|
||||
if (property_desc_p->flags & (ECMA_PROP_IS_GET_DEFINED | ECMA_PROP_IS_SET_DEFINED))
|
||||
{
|
||||
ecma_deref_ecma_string (name_p);
|
||||
arg_literal_p[index] = ECMA_VALUE_EMPTY;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (property_desc_p->flags & ECMA_PROP_IS_VALUE_DEFINED)
|
||||
{
|
||||
/* emulating execution of function described by MakeArgSetter */
|
||||
ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t,
|
||||
ext_object_p->u.pseudo_array.u2.lex_env_cp);
|
||||
|
||||
ecma_value_t completion = ecma_op_set_mutable_binding (lex_env_p,
|
||||
name_p,
|
||||
property_desc_p->value,
|
||||
true);
|
||||
|
||||
JERRY_ASSERT (ecma_is_value_empty (completion));
|
||||
}
|
||||
|
||||
if ((property_desc_p->flags & ECMA_PROP_IS_WRITABLE_DEFINED)
|
||||
&& !(property_desc_p->flags & ECMA_PROP_IS_WRITABLE))
|
||||
{
|
||||
ecma_deref_ecma_string (name_p);
|
||||
arg_literal_p[index] = ECMA_VALUE_EMPTY;
|
||||
}
|
||||
}
|
||||
|
||||
return ret_value;
|
||||
} /* ecma_op_arguments_object_define_own_property */
|
||||
|
||||
/**
|
||||
* [[Delete]] ecma Arguments object's operation
|
||||
*
|
||||
* See also:
|
||||
* ECMA-262 v5, 8.6.2; ECMA-262 v5, Table 8
|
||||
* ECMA-262 v5, 10.6
|
||||
*
|
||||
* @return ecma value
|
||||
* Returned value must be freed with ecma_free_value
|
||||
*/
|
||||
ecma_value_t
|
||||
ecma_op_arguments_object_delete (ecma_object_t *object_p, /**< the object */
|
||||
ecma_string_t *property_name_p, /**< property name */
|
||||
bool is_throw) /**< flag that controls failure handling */
|
||||
{
|
||||
/* 3. */
|
||||
ecma_value_t ret_value = ecma_op_general_object_delete (object_p, property_name_p, is_throw);
|
||||
|
||||
if (ECMA_IS_VALUE_ERROR (ret_value))
|
||||
{
|
||||
return ret_value;
|
||||
}
|
||||
|
||||
JERRY_ASSERT (ecma_is_value_boolean (ret_value));
|
||||
|
||||
if (ecma_is_value_true (ret_value))
|
||||
{
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
|
||||
if (index != ECMA_STRING_NOT_ARRAY_INDEX)
|
||||
{
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) object_p;
|
||||
|
||||
if (index < ext_object_p->u.pseudo_array.u1.length)
|
||||
{
|
||||
ecma_value_t *arg_literal_p = (ecma_value_t *) (ext_object_p + 1);
|
||||
|
||||
if (arg_literal_p[index] != ECMA_VALUE_EMPTY)
|
||||
{
|
||||
ecma_string_t *name_p = ecma_get_string_from_value (arg_literal_p[index]);
|
||||
ecma_deref_ecma_string (name_p);
|
||||
arg_literal_p[index] = ECMA_VALUE_EMPTY;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ret_value = ECMA_VALUE_TRUE;
|
||||
}
|
||||
|
||||
return ret_value;
|
||||
} /* ecma_op_arguments_object_delete */
|
||||
|
||||
/**
|
||||
* @}
|
||||
* @}
|
||||
*/
|
||||
@@ -22,8 +22,9 @@
|
||||
#include "ecma-helpers.h"
|
||||
#include "ecma-function-object.h"
|
||||
#include "ecma-lex-env.h"
|
||||
#include "ecma-lcache.h"
|
||||
#include "ecma-string-object.h"
|
||||
#include "ecma-objects-arguments.h"
|
||||
#include "ecma-arguments-object.h"
|
||||
#include "ecma-objects-general.h"
|
||||
#include "ecma-objects.h"
|
||||
#include "ecma-proxy-object.h"
|
||||
@@ -80,7 +81,6 @@ ecma_op_object_get_own_property (ecma_object_t *object_p, /**< the object */
|
||||
#endif /* ENABLED (JERRY_BUILTIN_PROXY) */
|
||||
JERRY_ASSERT (property_name_p != NULL);
|
||||
JERRY_ASSERT (options == ECMA_PROPERTY_GET_NO_OPTIONS
|
||||
|| options == ECMA_PROPERTY_GET_HAS_OWN_PROP
|
||||
|| property_ref_p != NULL);
|
||||
|
||||
ecma_object_type_t type = ecma_get_object_type (object_p);
|
||||
@@ -256,46 +256,67 @@ ecma_op_object_get_own_property (ecma_object_t *object_p, /**< the object */
|
||||
property_p = ecma_builtin_try_to_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
}
|
||||
else if (type == ECMA_OBJECT_TYPE_FUNCTION)
|
||||
else
|
||||
{
|
||||
#if !ENABLED (JERRY_ESNEXT)
|
||||
if (ecma_string_is_length (property_name_p))
|
||||
switch (type)
|
||||
{
|
||||
if (options & ECMA_PROPERTY_GET_VALUE)
|
||||
case ECMA_OBJECT_TYPE_FUNCTION:
|
||||
{
|
||||
/* Get length virtual property. */
|
||||
ecma_extended_object_t *ext_func_p = (ecma_extended_object_t *) object_p;
|
||||
const ecma_compiled_code_t *bytecode_data_p = ecma_op_function_get_compiled_code (ext_func_p);
|
||||
|
||||
uint32_t len;
|
||||
if (bytecode_data_p->status_flags & CBC_CODE_FLAGS_UINT16_ARGUMENTS)
|
||||
#if !ENABLED (JERRY_ESNEXT)
|
||||
if (ecma_string_is_length (property_name_p))
|
||||
{
|
||||
cbc_uint16_arguments_t *args_p = (cbc_uint16_arguments_t *) bytecode_data_p;
|
||||
len = args_p->argument_end;
|
||||
}
|
||||
else
|
||||
{
|
||||
cbc_uint8_arguments_t *args_p = (cbc_uint8_arguments_t *) bytecode_data_p;
|
||||
len = args_p->argument_end;
|
||||
}
|
||||
if (options & ECMA_PROPERTY_GET_VALUE)
|
||||
{
|
||||
/* Get length virtual property. */
|
||||
ecma_extended_object_t *ext_func_p = (ecma_extended_object_t *) object_p;
|
||||
const ecma_compiled_code_t *bytecode_data_p = ecma_op_function_get_compiled_code (ext_func_p);
|
||||
|
||||
property_ref_p->virtual_value = ecma_make_uint32_value (len);
|
||||
uint32_t len;
|
||||
if (bytecode_data_p->status_flags & CBC_CODE_FLAGS_UINT16_ARGUMENTS)
|
||||
{
|
||||
cbc_uint16_arguments_t *args_p = (cbc_uint16_arguments_t *) bytecode_data_p;
|
||||
len = args_p->argument_end;
|
||||
}
|
||||
else
|
||||
{
|
||||
cbc_uint8_arguments_t *args_p = (cbc_uint8_arguments_t *) bytecode_data_p;
|
||||
len = args_p->argument_end;
|
||||
}
|
||||
|
||||
property_ref_p->virtual_value = ecma_make_uint32_value (len);
|
||||
}
|
||||
|
||||
return ECMA_PROPERTY_TYPE_VIRTUAL;
|
||||
}
|
||||
#endif /* !ENABLED (JERRY_ESNEXT) */
|
||||
|
||||
/* Get prototype physical property. */
|
||||
property_p = ecma_op_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
break;
|
||||
}
|
||||
case ECMA_OBJECT_TYPE_NATIVE_FUNCTION:
|
||||
{
|
||||
property_p = ecma_op_external_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
break;
|
||||
}
|
||||
case ECMA_OBJECT_TYPE_BOUND_FUNCTION:
|
||||
{
|
||||
property_p = ecma_op_bound_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
break;
|
||||
}
|
||||
case ECMA_OBJECT_TYPE_PSEUDO_ARRAY:
|
||||
{
|
||||
if (((ecma_extended_object_t *) object_p)->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS)
|
||||
{
|
||||
property_p = ecma_op_arguments_object_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
return ECMA_PROPERTY_TYPE_VIRTUAL;
|
||||
}
|
||||
#endif /* !ENABLED (JERRY_ESNEXT) */
|
||||
|
||||
/* Get prototype physical property. */
|
||||
property_p = ecma_op_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
else if (type == ECMA_OBJECT_TYPE_NATIVE_FUNCTION)
|
||||
{
|
||||
property_p = ecma_op_external_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
else if (type == ECMA_OBJECT_TYPE_BOUND_FUNCTION)
|
||||
{
|
||||
property_p = ecma_op_bound_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
|
||||
if (property_p == NULL)
|
||||
@@ -304,36 +325,47 @@ ecma_op_object_get_own_property (ecma_object_t *object_p, /**< the object */
|
||||
}
|
||||
}
|
||||
else if (type == ECMA_OBJECT_TYPE_PSEUDO_ARRAY
|
||||
&& (options & ECMA_PROPERTY_GET_HAS_OWN_PROP))
|
||||
&& ((ecma_extended_object_t *) object_p)->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS
|
||||
&& (((ecma_extended_object_t *) object_p)->u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_MAPPED))
|
||||
{
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) object_p;
|
||||
|
||||
if (ext_object_p->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS)
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
|
||||
if (index < ext_object_p->u.pseudo_array.u1.formal_params_number)
|
||||
{
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
ecma_mapped_arguments_t *mapped_arguments_p = (ecma_mapped_arguments_t *) ext_object_p;
|
||||
|
||||
if (index != ECMA_STRING_NOT_ARRAY_INDEX
|
||||
&& index < ext_object_p->u.pseudo_array.u1.length)
|
||||
ecma_value_t *argv_p = (ecma_value_t *) (mapped_arguments_p + 1);
|
||||
|
||||
if (!ecma_is_value_empty (argv_p[index]))
|
||||
{
|
||||
ecma_value_t *arg_Literal_p = (ecma_value_t *) (ext_object_p + 1);
|
||||
|
||||
if (arg_Literal_p[index] != ECMA_VALUE_EMPTY)
|
||||
#if ENABLED (JERRY_LCACHE)
|
||||
/* Mapped arguments initialized properties MUST not be lcached */
|
||||
if (ecma_is_property_lcached (property_p))
|
||||
{
|
||||
ecma_string_t *arg_name_p = ecma_get_string_from_value (arg_Literal_p[index]);
|
||||
jmem_cpointer_t prop_name_cp;
|
||||
|
||||
ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t,
|
||||
ext_object_p->u.pseudo_array.u2.lex_env_cp);
|
||||
|
||||
JERRY_ASSERT (lex_env_p != NULL
|
||||
&& ecma_is_lexical_environment (lex_env_p));
|
||||
|
||||
ecma_value_t binding_value = ecma_op_get_binding_value (lex_env_p, arg_name_p, true);
|
||||
|
||||
ecma_named_data_property_assign_value (object_p,
|
||||
ECMA_PROPERTY_VALUE_PTR (property_p),
|
||||
binding_value);
|
||||
ecma_free_value (binding_value);
|
||||
if (JERRY_UNLIKELY (ECMA_IS_DIRECT_STRING (property_name_p)))
|
||||
{
|
||||
prop_name_cp = (jmem_cpointer_t) ECMA_GET_DIRECT_STRING_VALUE (property_name_p);
|
||||
}
|
||||
else
|
||||
{
|
||||
ECMA_SET_NON_NULL_POINTER (prop_name_cp, property_name_p);
|
||||
}
|
||||
ecma_lcache_invalidate (object_p, prop_name_cp, property_p);
|
||||
}
|
||||
#endif /* ENABLED (JERRY_LCACHE) */
|
||||
ecma_string_t *name_p = ecma_op_arguments_object_get_formal_parameter (mapped_arguments_p, index);
|
||||
ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, mapped_arguments_p->lex_env);
|
||||
|
||||
ecma_value_t binding_value = ecma_op_get_binding_value (lex_env_p, name_p, true);
|
||||
|
||||
ecma_named_data_property_assign_value (object_p,
|
||||
ECMA_PROPERTY_VALUE_PTR (property_p),
|
||||
binding_value);
|
||||
ecma_free_value (binding_value);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -480,26 +512,23 @@ ecma_op_object_find_own (ecma_value_t base_value, /**< base value */
|
||||
{
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) object_p;
|
||||
|
||||
if (ext_object_p->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS)
|
||||
if (ext_object_p->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS
|
||||
&& ext_object_p->u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_MAPPED)
|
||||
{
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
|
||||
if (index != ECMA_STRING_NOT_ARRAY_INDEX
|
||||
&& index < ext_object_p->u.pseudo_array.u1.length)
|
||||
if (index < ext_object_p->u.pseudo_array.u1.formal_params_number)
|
||||
{
|
||||
ecma_value_t *arg_Literal_p = (ecma_value_t *) (ext_object_p + 1);
|
||||
ecma_mapped_arguments_t *mapped_arguments_p = (ecma_mapped_arguments_t *) ext_object_p;
|
||||
|
||||
if (arg_Literal_p[index] != ECMA_VALUE_EMPTY)
|
||||
ecma_value_t *argv_p = (ecma_value_t *) (mapped_arguments_p + 1);
|
||||
|
||||
if (!ecma_is_value_empty (argv_p[index]))
|
||||
{
|
||||
ecma_string_t *arg_name_p = ecma_get_string_from_value (arg_Literal_p[index]);
|
||||
ecma_string_t *name_p = ecma_op_arguments_object_get_formal_parameter (mapped_arguments_p, index);
|
||||
ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, mapped_arguments_p->lex_env);
|
||||
|
||||
ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t,
|
||||
ext_object_p->u.pseudo_array.u2.lex_env_cp);
|
||||
|
||||
JERRY_ASSERT (lex_env_p != NULL
|
||||
&& ecma_is_lexical_environment (lex_env_p));
|
||||
|
||||
return ecma_op_get_binding_value (lex_env_p, arg_name_p, true);
|
||||
return ecma_op_get_binding_value (lex_env_p, name_p, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -572,41 +601,62 @@ ecma_op_object_find_own (ecma_value_t base_value, /**< base value */
|
||||
property_p = ecma_builtin_try_to_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
}
|
||||
else if (type == ECMA_OBJECT_TYPE_FUNCTION)
|
||||
else
|
||||
{
|
||||
#if !ENABLED (JERRY_ESNEXT)
|
||||
if (ecma_string_is_length (property_name_p))
|
||||
switch (type)
|
||||
{
|
||||
/* Get length virtual property. */
|
||||
ecma_extended_object_t *ext_func_p = (ecma_extended_object_t *) object_p;
|
||||
const ecma_compiled_code_t *bytecode_data_p = ecma_op_function_get_compiled_code (ext_func_p);
|
||||
|
||||
uint32_t len;
|
||||
if (bytecode_data_p->status_flags & CBC_CODE_FLAGS_UINT16_ARGUMENTS)
|
||||
case ECMA_OBJECT_TYPE_FUNCTION:
|
||||
{
|
||||
cbc_uint16_arguments_t *args_p = (cbc_uint16_arguments_t *) bytecode_data_p;
|
||||
len = args_p->argument_end;
|
||||
}
|
||||
else
|
||||
{
|
||||
cbc_uint8_arguments_t *args_p = (cbc_uint8_arguments_t *) bytecode_data_p;
|
||||
len = args_p->argument_end;
|
||||
}
|
||||
#if !ENABLED (JERRY_ESNEXT)
|
||||
if (ecma_string_is_length (property_name_p))
|
||||
{
|
||||
/* Get length virtual property. */
|
||||
ecma_extended_object_t *ext_func_p = (ecma_extended_object_t *) object_p;
|
||||
const ecma_compiled_code_t *bytecode_data_p = ecma_op_function_get_compiled_code (ext_func_p);
|
||||
|
||||
return ecma_make_uint32_value (len);
|
||||
}
|
||||
uint32_t len;
|
||||
if (bytecode_data_p->status_flags & CBC_CODE_FLAGS_UINT16_ARGUMENTS)
|
||||
{
|
||||
cbc_uint16_arguments_t *args_p = (cbc_uint16_arguments_t *) bytecode_data_p;
|
||||
len = args_p->argument_end;
|
||||
}
|
||||
else
|
||||
{
|
||||
cbc_uint8_arguments_t *args_p = (cbc_uint8_arguments_t *) bytecode_data_p;
|
||||
len = args_p->argument_end;
|
||||
}
|
||||
|
||||
return ecma_make_uint32_value (len);
|
||||
}
|
||||
#endif /* !ENABLED (JERRY_ESNEXT) */
|
||||
|
||||
/* Get prototype physical property. */
|
||||
property_p = ecma_op_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
else if (type == ECMA_OBJECT_TYPE_NATIVE_FUNCTION)
|
||||
{
|
||||
property_p = ecma_op_external_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
else if (type == ECMA_OBJECT_TYPE_BOUND_FUNCTION)
|
||||
{
|
||||
property_p = ecma_op_bound_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
/* Get prototype physical property. */
|
||||
property_p = ecma_op_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
break;
|
||||
}
|
||||
case ECMA_OBJECT_TYPE_NATIVE_FUNCTION:
|
||||
{
|
||||
property_p = ecma_op_external_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
break;
|
||||
}
|
||||
case ECMA_OBJECT_TYPE_BOUND_FUNCTION:
|
||||
{
|
||||
property_p = ecma_op_bound_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
break;
|
||||
}
|
||||
case ECMA_OBJECT_TYPE_PSEUDO_ARRAY:
|
||||
{
|
||||
if (((ecma_extended_object_t *) object_p)->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS)
|
||||
{
|
||||
property_p = ecma_op_arguments_object_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (property_p == NULL)
|
||||
@@ -1207,26 +1257,22 @@ ecma_op_object_put_with_receiver (ecma_object_t *object_p, /**< the object */
|
||||
{
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) object_p;
|
||||
|
||||
if (ext_object_p->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS)
|
||||
if (ext_object_p->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS
|
||||
&& (ext_object_p->u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_MAPPED))
|
||||
{
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
|
||||
if (index != ECMA_STRING_NOT_ARRAY_INDEX
|
||||
&& index < ext_object_p->u.pseudo_array.u1.length)
|
||||
if (index < ext_object_p->u.pseudo_array.u1.formal_params_number)
|
||||
{
|
||||
ecma_value_t *arg_Literal_p = (ecma_value_t *) (ext_object_p + 1);
|
||||
ecma_mapped_arguments_t *mapped_arguments_p = (ecma_mapped_arguments_t *) ext_object_p;
|
||||
|
||||
if (arg_Literal_p[index] != ECMA_VALUE_EMPTY)
|
||||
ecma_value_t *argv_p = (ecma_value_t *) (mapped_arguments_p + 1);
|
||||
|
||||
if (!ecma_is_value_empty (argv_p[index]))
|
||||
{
|
||||
ecma_string_t *arg_name_p = ecma_get_string_from_value (arg_Literal_p[index]);
|
||||
|
||||
ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t,
|
||||
ext_object_p->u.pseudo_array.u2.lex_env_cp);
|
||||
|
||||
JERRY_ASSERT (lex_env_p != NULL
|
||||
&& ecma_is_lexical_environment (lex_env_p));
|
||||
|
||||
ecma_op_set_mutable_binding (lex_env_p, arg_name_p, value, true);
|
||||
ecma_string_t *name_p = ecma_op_arguments_object_get_formal_parameter (mapped_arguments_p, index);
|
||||
ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, mapped_arguments_p->lex_env);
|
||||
ecma_op_set_mutable_binding (lex_env_p, name_p, value, true);
|
||||
return ECMA_VALUE_TRUE;
|
||||
}
|
||||
}
|
||||
@@ -1282,27 +1328,6 @@ ecma_op_object_put_with_receiver (ecma_object_t *object_p, /**< the object */
|
||||
|
||||
if (property_p == NULL)
|
||||
{
|
||||
if (type == ECMA_OBJECT_TYPE_CLASS)
|
||||
{
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) object_p;
|
||||
|
||||
if (ext_object_p->u.class_prop.class_id == LIT_MAGIC_STRING_STRING_UL)
|
||||
{
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
|
||||
if (index != ECMA_STRING_NOT_ARRAY_INDEX)
|
||||
{
|
||||
ecma_value_t prim_value_p = ext_object_p->u.class_prop.u.value;
|
||||
ecma_string_t *prim_value_str_p = ecma_get_string_from_value (prim_value_p);
|
||||
|
||||
if (index < ecma_string_get_length (prim_value_str_p))
|
||||
{
|
||||
return ecma_reject (is_throw);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (ecma_get_object_is_builtin (object_p))
|
||||
{
|
||||
if (type == ECMA_OBJECT_TYPE_FUNCTION && ecma_builtin_function_is_routine (object_p))
|
||||
@@ -1320,32 +1345,74 @@ ecma_op_object_put_with_receiver (ecma_object_t *object_p, /**< the object */
|
||||
property_p = ecma_builtin_try_to_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
}
|
||||
else if (type == ECMA_OBJECT_TYPE_FUNCTION)
|
||||
else
|
||||
{
|
||||
#if ENABLED (JERRY_ESNEXT)
|
||||
/* Uninitialized 'length' property is non-writable (ECMA-262 v6, 19.2.4.1) */
|
||||
if ((ecma_string_is_length (property_name_p))
|
||||
&& (!ECMA_GET_FIRST_BIT_FROM_POINTER_TAG (((ecma_extended_object_t *) object_p)->u.function.scope_cp)))
|
||||
switch (type)
|
||||
{
|
||||
return ecma_reject (is_throw);
|
||||
}
|
||||
#else /* !ENABLED (JERRY_ESNEXT) */
|
||||
if (ecma_string_is_length (property_name_p))
|
||||
{
|
||||
return ecma_reject (is_throw);
|
||||
}
|
||||
#endif /* ENABLED (JERRY_ESNEXT) */
|
||||
case ECMA_OBJECT_TYPE_CLASS:
|
||||
{
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) object_p;
|
||||
|
||||
/* Get prototype physical property. */
|
||||
property_p = ecma_op_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
else if (type == ECMA_OBJECT_TYPE_NATIVE_FUNCTION)
|
||||
{
|
||||
property_p = ecma_op_external_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
else if (type == ECMA_OBJECT_TYPE_BOUND_FUNCTION)
|
||||
{
|
||||
property_p = ecma_op_bound_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
if (ext_object_p->u.class_prop.class_id == LIT_MAGIC_STRING_STRING_UL)
|
||||
{
|
||||
uint32_t index = ecma_string_get_array_index (property_name_p);
|
||||
|
||||
if (index != ECMA_STRING_NOT_ARRAY_INDEX)
|
||||
{
|
||||
ecma_value_t prim_value_p = ext_object_p->u.class_prop.u.value;
|
||||
ecma_string_t *prim_value_str_p = ecma_get_string_from_value (prim_value_p);
|
||||
|
||||
if (index < ecma_string_get_length (prim_value_str_p))
|
||||
{
|
||||
return ecma_reject (is_throw);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case ECMA_OBJECT_TYPE_FUNCTION:
|
||||
{
|
||||
#if ENABLED (JERRY_ESNEXT)
|
||||
/* Uninitialized 'length' property is non-writable (ECMA-262 v6, 19.2.4.1) */
|
||||
if ((ecma_string_is_length (property_name_p))
|
||||
&& (!ECMA_GET_FIRST_BIT_FROM_POINTER_TAG (((ecma_extended_object_t *) object_p)->u.function.scope_cp)))
|
||||
{
|
||||
return ecma_reject (is_throw);
|
||||
}
|
||||
#else /* !ENABLED (JERRY_ESNEXT) */
|
||||
if (ecma_string_is_length (property_name_p))
|
||||
{
|
||||
return ecma_reject (is_throw);
|
||||
}
|
||||
#endif /* ENABLED (JERRY_ESNEXT) */
|
||||
|
||||
/* Get prototype physical property. */
|
||||
property_p = ecma_op_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
break;
|
||||
}
|
||||
case ECMA_OBJECT_TYPE_NATIVE_FUNCTION:
|
||||
{
|
||||
property_p = ecma_op_external_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
break;
|
||||
}
|
||||
case ECMA_OBJECT_TYPE_BOUND_FUNCTION:
|
||||
{
|
||||
property_p = ecma_op_bound_function_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
break;
|
||||
}
|
||||
case ECMA_OBJECT_TYPE_PSEUDO_ARRAY:
|
||||
{
|
||||
if (((ecma_extended_object_t *) object_p)->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS)
|
||||
{
|
||||
property_p = ecma_op_arguments_object_try_to_lazy_instantiate_property (object_p, property_name_p);
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1440,7 +1507,8 @@ ecma_op_object_put_with_receiver (ecma_object_t *object_p, /**< the object */
|
||||
{
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) object_p;
|
||||
|
||||
if (ext_object_p->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS)
|
||||
if (ext_object_p->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS
|
||||
&& ext_object_p->u.pseudo_array.extra_info & ECMA_ARGUMENTS_OBJECT_MAPPED)
|
||||
{
|
||||
return ecma_builtin_helper_def_prop (object_p,
|
||||
property_name_p,
|
||||
@@ -2057,6 +2125,10 @@ ecma_object_list_lazy_property_names (ecma_object_t *obj_p, /**< object */
|
||||
{
|
||||
case ECMA_OBJECT_TYPE_PSEUDO_ARRAY:
|
||||
{
|
||||
if (((ecma_extended_object_t *) obj_p)->u.pseudo_array.type == ECMA_PSEUDO_ARRAY_ARGUMENTS)
|
||||
{
|
||||
ecma_op_arguments_object_list_lazy_property_names (obj_p, prop_names_p, prop_counter_p);
|
||||
}
|
||||
#if ENABLED (JERRY_BUILTIN_TYPEDARRAY)
|
||||
if (ecma_object_is_typedarray (obj_p))
|
||||
{
|
||||
@@ -3052,7 +3124,7 @@ ecma_op_ordinary_object_has_own_property (ecma_object_t *object_p, /**< the obje
|
||||
ecma_property_t property = ecma_op_object_get_own_property (object_p,
|
||||
property_name_p,
|
||||
NULL,
|
||||
ECMA_PROPERTY_GET_HAS_OWN_PROP);
|
||||
ECMA_PROPERTY_GET_NO_OPTIONS);
|
||||
|
||||
return property != ECMA_PROPERTY_TYPE_NOT_FOUND && property != ECMA_PROPERTY_TYPE_NOT_FOUND_AND_STOP;
|
||||
} /* ecma_op_ordinary_object_has_own_property */
|
||||
|
||||
@@ -120,7 +120,6 @@ fn_expr = function (a, b, c)
|
||||
}
|
||||
}
|
||||
|
||||
check_type_error_for_property (arguments, 'caller');
|
||||
check_type_error_for_property (arguments, 'callee');
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,21 @@
|
||||
// Copyright JS Foundation and other contributors, http://js.foundation
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
function f(a, b, c)
|
||||
{
|
||||
'use strict';
|
||||
assert(!Object.hasOwnProperty(arguments,'caller'));
|
||||
}
|
||||
|
||||
f(1, 2, 3);
|
||||
@@ -0,0 +1,26 @@
|
||||
// Copyright JS Foundation and other contributors, http://js.foundation
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
function f(a, b, c)
|
||||
{
|
||||
'use strict';
|
||||
try {
|
||||
arguments['caller'];
|
||||
assert(false);
|
||||
} catch (e) {
|
||||
assert(e instanceof TypeError);
|
||||
}
|
||||
}
|
||||
|
||||
f(1, 2, 3);
|
||||
@@ -243,14 +243,6 @@
|
||||
<test id="intl402/String/prototype/toLocaleUpperCase/special_casing_Turkish.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/10.6-13-a-2.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/10.6-13-a-3.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-2.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-4.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-delete-2.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-delete-4.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-nonwritable-3.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-nonwritable-4.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-strict-delete-2.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-strict-delete-4.js"><reason></reason></test>
|
||||
<test id="language/asi/S7.9_A5.7_T1.js"><reason></reason></test>
|
||||
<test id="language/block-scope/syntax/redeclaration-in-block/attempt-to-redeclare-function-declaration-with-function-declaration.js"><reason>No longer a SyntaxError in ES11</reason></test>
|
||||
<test id="language/default-parameters/function-length.js"><reason></reason></test>
|
||||
@@ -344,4 +336,11 @@
|
||||
<test id="built-ins/RegExp/prototype/ignoreCase/15.10.7.3-1.js"><reason>RegExp accessors should no longer throw when called on the RegExp prototype</reason></test>
|
||||
<test id="built-ins/RegExp/prototype/multiline/15.10.7.4-1.js"><reason>RegExp accessors should no longer throw when called on the RegExp prototype</reason></test>
|
||||
<test id="built-ins/RegExp/prototype/source/15.10.7.1-1.js"><reason>RegExp accessors should no longer throw when called on the RegExp prototype</reason></test>
|
||||
<test id="language/arguments-object/10.6-13-b-1-s.js"><reason>ES11: arguments object no longer has caller property</reason></test>
|
||||
<test id="language/arguments-object/10.6-13-b-2-s.js"><reason>ES11: arguments object no longer has caller property</reason></test>
|
||||
<test id="language/arguments-object/10.6-13-b-3-s.js"><reason>ES11: arguments object no longer has caller property</reason></test>
|
||||
<test id="language/arguments-object/10.6-14-1-s.js"><reason>ES11: arguments object no longer has caller property</reason></test>
|
||||
<test id="language/arguments-object/10.6-14-b-1-s.js"><reason>ES11: arguments object no longer has caller property</reason></test>
|
||||
<test id="language/arguments-object/10.6-14-b-4-s.js"><reason>ES11: arguments object no longer has caller property</reason></test>
|
||||
<test id="language/statements/class/strict-mode/arguments-caller.js"><reason>ES11: arguments object no longer has caller property</reason></test>
|
||||
</excludeList>
|
||||
|
||||
@@ -1583,7 +1583,6 @@
|
||||
<test id="built-ins/Symbol/unscopables/cross-realm.js"><reason></reason></test>
|
||||
<test id="built-ins/ThrowTypeError/distinct-cross-realm.js"><reason></reason></test>
|
||||
<test id="built-ins/ThrowTypeError/name.js"><reason></reason></test>
|
||||
<test id="built-ins/ThrowTypeError/unique-per-realm-non-simple.js"><reason></reason></test>
|
||||
<test id="built-ins/TypedArray/from/arylk-get-length-error.js"><reason></reason></test>
|
||||
<test id="built-ins/TypedArray/from/arylk-to-length-error.js"><reason></reason></test>
|
||||
<test id="built-ins/TypedArray/from/iter-access-error.js"><reason></reason></test>
|
||||
@@ -2867,23 +2866,6 @@
|
||||
<test id="intl402/supportedLocalesOf-unicode-extensions-ignored.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/10.6-13-a-2.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/10.6-13-a-3.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/arguments-caller.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-2.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-4.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-delete-2.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-delete-4.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-nonwritable-3.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-nonwritable-4.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-strict-delete-2.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/mapped-arguments-nonconfigurable-strict-delete-4.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/nonconfigurable-descriptors-basic.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/nonconfigurable-descriptors-set-value-by-arguments.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/nonconfigurable-descriptors-set-value-with-define-property.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/nonconfigurable-descriptors-with-param-assign.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/nonconfigurable-nonenumerable-nonwritable-descriptors-set-by-arguments.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/nonconfigurable-nonenumerable-nonwritable-descriptors-set-by-param.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/nonconfigurable-nonwritable-descriptors-set-by-arguments.js"><reason></reason></test>
|
||||
<test id="language/arguments-object/mapped/nonconfigurable-nonwritable-descriptors-set-by-param.js"><reason></reason></test>
|
||||
<test id="language/block-scope/syntax/redeclaration/async-function-name-redeclaration-attempt-with-async-function.js"><reason></reason></test>
|
||||
<test id="language/block-scope/syntax/redeclaration/async-function-name-redeclaration-attempt-with-async-generator.js"><reason></reason></test>
|
||||
<test id="language/block-scope/syntax/redeclaration/async-function-name-redeclaration-attempt-with-function.js"><reason></reason></test>
|
||||
|
||||
Reference in New Issue
Block a user