/** * The Date.prototype object's 'setTime' routine * * See also: * ECMA-262 v5, 15.9.5.27 * * @return ecma value * Returned value must be freed with ecma_free_value. */ static ecma_value_t ecma_builtin_date_prototype_set_time (ecma_value_t this_arg, /**< this argument */ ecma_value_t time) /**< time */ { ecma_value_t ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_EMPTY); if (!ecma_is_value_object (this_arg) || ecma_object_get_class_name (ecma_get_object_from_value (this_arg)) != LIT_MAGIC_STRING_DATE_UL) { ret_value = ecma_raise_type_error (ECMA_ERR_MSG ("Incompatible type")); } else { /* 1. */ ECMA_OP_TO_NUMBER_TRY_CATCH (t, time, ret_value); ecma_number_t *value_p = ecma_alloc_number (); *value_p = ecma_date_time_clip (t); /* 2. */ ecma_object_t *obj_p = ecma_get_object_from_value (this_arg); ecma_property_t *prim_prop_p = ecma_get_internal_property (obj_p, ECMA_INTERNAL_PROPERTY_PRIMITIVE_NUMBER_VALUE); ecma_number_t *prim_value_num_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_number_t, ecma_get_internal_property_value (prim_prop_p)); *prim_value_num_p = *value_p; /* 3. */ ret_value = ecma_make_number_value (value_p); ECMA_OP_TO_NUMBER_FINALIZE (t); } return ret_value; } /* ecma_builtin_date_prototype_set_time */
/** * The Number.prototype object's 'valueOf' routine * * See also: * ECMA-262 v5, 15.7.4.4 * * @return ecma value * Returned value must be freed with ecma_free_value. */ static ecma_value_t ecma_builtin_number_prototype_object_value_of (ecma_value_t this_arg) /**< this argument */ { if (ecma_is_value_number (this_arg)) { return ecma_copy_value (this_arg); } else if (ecma_is_value_object (this_arg)) { ecma_object_t *obj_p = ecma_get_object_from_value (this_arg); if (ecma_object_get_class_name (obj_p) == LIT_MAGIC_STRING_NUMBER_UL) { ecma_property_t *prim_value_prop_p = ecma_get_internal_property (obj_p, ECMA_INTERNAL_PROPERTY_PRIMITIVE_NUMBER_VALUE); ecma_number_t *prim_value_num_p; prim_value_num_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_number_t, ecma_get_internal_property_value (prim_value_prop_p)); ecma_number_t *ret_num_p = ecma_alloc_number (); *ret_num_p = *prim_value_num_p; return ecma_make_number_value (ret_num_p); } } return ecma_raise_type_error (ECMA_ERR_MSG ("")); } /* ecma_builtin_number_prototype_object_value_of */
/** * [[GetOwnProperty]] 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_property_t * ecma_op_arguments_object_get_own_property (ecma_object_t *obj_p, /**< the object */ ecma_string_t *property_name_p) /**< property name */ { // 1. ecma_property_t *desc_p = ecma_op_general_object_get_own_property (obj_p, property_name_p); // 2. if (desc_p == NULL) { return desc_p; } // 3. ecma_property_t *map_prop_p = ecma_get_internal_property (obj_p, ECMA_INTERNAL_PROPERTY_PARAMETERS_MAP); ecma_object_t *map_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, ECMA_PROPERTY_VALUE_PTR (map_prop_p)->value); // 4. ecma_property_t *mapped_prop_p = ecma_op_object_get_own_property (map_p, property_name_p); // 5. if (mapped_prop_p != NULL) { // a. ecma_value_t completion = ecma_arguments_get_mapped_arg_value (map_p, mapped_prop_p); ecma_named_data_property_assign_value (obj_p, desc_p, completion); ecma_free_value (completion); } // 6. return desc_p; } /* ecma_op_arguments_object_get_own_property */
/** * [[Get]] 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_get (ecma_object_t *obj_p, /**< the object */ ecma_string_t *property_name_p) /**< property name */ { // 1. ecma_property_t *map_prop_p = ecma_get_internal_property (obj_p, ECMA_INTERNAL_PROPERTY_PARAMETERS_MAP); ecma_object_t *map_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, ECMA_PROPERTY_VALUE_PTR (map_prop_p)->value); // 2. ecma_property_t *mapped_prop_p = ecma_op_object_get_own_property (map_p, property_name_p); // 3. if (mapped_prop_p == NULL) { /* We don't check for 'caller' (item 3.b) here, because the 'caller' property is defined as non-configurable and it's get/set are set to [[ThrowTypeError]] object */ return ecma_op_general_object_get (obj_p, property_name_p); } else { // 4. return ecma_arguments_get_mapped_arg_value (map_p, mapped_prop_p); } } /* ecma_op_arguments_object_get */
/** * Get value of function's argument mapped to index of Arguments object. * * Note: * The procedure emulates execution of function described by MakeArgGetter * * @return ecma value * Returned value must be freed with ecma_free_value */ void ecma_arguments_update_mapped_arg_value (ecma_object_t *object_p, /**< the object */ ecma_string_t *property_name_p, /**< property name */ ecma_property_t *property_p) /**< property value */ { ecma_value_t *map_prop_p = ecma_get_internal_property (object_p, ECMA_INTERNAL_PROPERTY_PARAMETERS_MAP); ecma_object_t *map_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, *map_prop_p); ecma_value_t arg_name = ecma_op_object_find (map_p, property_name_p); if (!ecma_is_value_found (arg_name)) { return; } ecma_value_t *scope_prop_p = ecma_get_internal_property (map_p, ECMA_INTERNAL_PROPERTY_SCOPE); ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, *scope_prop_p); JERRY_ASSERT (lex_env_p != NULL && ecma_is_lexical_environment (lex_env_p)); ecma_string_t *arg_name_p = ecma_get_string_from_value (arg_name); ecma_value_t value = ecma_op_get_binding_value (lex_env_p, arg_name_p, true); ecma_deref_ecma_string (arg_name_p); JERRY_ASSERT (!ECMA_IS_VALUE_ERROR (value)); ecma_named_data_property_assign_value (object_p, property_p, value); ecma_free_value (value); /* These properties cannot be cached. This is a temporary * workaround until the property management is fully rewritten. */ if (ecma_is_property_lcached (property_p)) { ecma_lcache_invalidate (object_p, property_name_p, property_p); } } /* ecma_arguments_update_mapped_arg_value */
/** * The Date.prototype object's 'getTime' routine * * See also: * ECMA-262 v5, 15.9.5.9 * * @return ecma value * Returned value must be freed with ecma_free_value. */ static ecma_value_t ecma_builtin_date_prototype_get_time (ecma_value_t this_arg) /**< this argument */ { if (ecma_is_value_object (this_arg)) { ecma_object_t *obj_p = ecma_get_object_from_value (this_arg); if (ecma_object_get_class_name (obj_p) == LIT_MAGIC_STRING_DATE_UL) { ecma_value_t *date_prop_p = ecma_get_internal_property (obj_p, ECMA_INTERNAL_PROPERTY_DATE_FLOAT); ecma_number_t *date_num_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_number_t, *date_prop_p); return ecma_make_number_value (*date_num_p); } } return ecma_raise_type_error (ECMA_ERR_MSG ("")); } /* ecma_builtin_date_prototype_get_time */
/** * [[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 *obj_p, /**< the object */ ecma_string_t *property_name_p, /**< property name */ bool is_throw) /**< flag that controls failure handling */ { // 1. ecma_property_t *map_prop_p = ecma_get_internal_property (obj_p, ECMA_INTERNAL_PROPERTY_PARAMETERS_MAP); ecma_object_t *map_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, ECMA_PROPERTY_VALUE_PTR (map_prop_p)->value); // 2. ecma_property_t *mapped_prop_p = ecma_op_object_get_own_property (map_p, property_name_p); // 3. ecma_value_t ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_EMPTY); ECMA_TRY_CATCH (delete_in_args_ret, ecma_op_general_object_delete (obj_p, property_name_p, is_throw), ret_value); if (ecma_is_value_true (delete_in_args_ret)) { if (mapped_prop_p != NULL) { ecma_value_t delete_in_map_completion = ecma_op_object_delete (map_p, property_name_p, false); JERRY_ASSERT (ecma_is_value_true (delete_in_map_completion)); } ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_TRUE); } else { JERRY_ASSERT (ecma_is_value_boolean (delete_in_args_ret)); ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_FALSE); } ECMA_FINALIZE (delete_in_args_ret); return ret_value; } /* ecma_op_arguments_object_delete */
/** * Get value of function's argument mapped to index of Arguments object. * * Note: * The procedure emulates execution of function described by MakeArgGetter * * @return ecma value * Returned value must be freed with ecma_free_value */ static ecma_value_t ecma_arguments_get_mapped_arg_value (ecma_object_t *map_p, /**< [[ParametersMap]] object */ ecma_property_t *arg_name_prop_p) /**< property of [[ParametersMap]] corresponding to index and value equal to mapped argument's name */ { ecma_property_t *scope_prop_p = ecma_get_internal_property (map_p, ECMA_INTERNAL_PROPERTY_SCOPE); ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, ECMA_PROPERTY_VALUE_PTR (scope_prop_p)->value); JERRY_ASSERT (lex_env_p != NULL && ecma_is_lexical_environment (lex_env_p)); ecma_value_t arg_name_prop_value = ecma_get_named_data_property_value (arg_name_prop_p); ecma_string_t *arg_name_p = ecma_get_string_from_value (arg_name_prop_value); ecma_value_t completion = ecma_op_get_binding_value (lex_env_p, arg_name_p, true); JERRY_ASSERT (!ECMA_IS_VALUE_ERROR (completion)); return completion; } /* ecma_arguments_get_mapped_arg_value */
/** * The Date.prototype object's 'toDateString' routine * * See also: * ECMA-262 v5, 15.9.5.3 * * @return ecma value * Returned value must be freed with ecma_free_value. */ static ecma_value_t ecma_builtin_date_prototype_to_date_string (ecma_value_t this_arg) /**< this argument */ { ecma_value_t ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_EMPTY); if (!ecma_is_value_object (this_arg) || ecma_object_get_class_name (ecma_get_object_from_value (this_arg)) != LIT_MAGIC_STRING_DATE_UL) { ret_value = ecma_raise_type_error (ECMA_ERR_MSG ("Incompatible type")); } else { ECMA_TRY_CATCH (obj_this, ecma_op_to_object (this_arg), ret_value); ecma_object_t *obj_p = ecma_get_object_from_value (obj_this); ecma_property_t *prim_prop_p = ecma_get_internal_property (obj_p, ECMA_INTERNAL_PROPERTY_PRIMITIVE_NUMBER_VALUE); ecma_number_t *prim_value_num_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_number_t, ecma_get_internal_property_value (prim_prop_p)); if (ecma_number_is_nan (*prim_value_num_p)) { ecma_string_t *magic_str_p = ecma_get_magic_string (LIT_MAGIC_STRING_INVALID_DATE_UL); ret_value = ecma_make_string_value (magic_str_p); } else { ret_value = ecma_date_value_to_date_string (*prim_value_num_p); } ECMA_FINALIZE (obj_this); } return ret_value; } /* ecma_builtin_date_prototype_to_date_string */
/** * Free specified object */ void ecma_gc_sweep (ecma_object_t *object_p) /**< object to free */ { JERRY_ASSERT (object_p != NULL && !ecma_gc_is_object_visited (object_p) && object_p->type_flags_refs < ECMA_OBJECT_REF_ONE); if (!ecma_is_lexical_environment (object_p)) { /* if the object provides free callback, invoke it with handle stored in the object */ ecma_external_pointer_t freecb_p; ecma_external_pointer_t native_p; bool is_retrieved = ecma_get_external_pointer_value (object_p, ECMA_INTERNAL_PROPERTY_FREE_CALLBACK, &freecb_p); if (is_retrieved && ((jerry_object_free_callback_t) freecb_p) != NULL) { is_retrieved = ecma_get_external_pointer_value (object_p, ECMA_INTERNAL_PROPERTY_NATIVE_HANDLE, &native_p); JERRY_ASSERT (is_retrieved); jerry_dispatch_object_free_callback (freecb_p, native_p); } } if (!ecma_is_lexical_environment (object_p) || ecma_get_lex_env_type (object_p) == ECMA_LEXICAL_ENVIRONMENT_DECLARATIVE) { ecma_property_header_t *prop_iter_p = ecma_get_property_list (object_p); if (prop_iter_p != NULL && ECMA_PROPERTY_GET_TYPE (prop_iter_p->types[0]) == ECMA_PROPERTY_TYPE_HASHMAP) { ecma_property_hashmap_free (object_p); prop_iter_p = ecma_get_property_list (object_p); } while (prop_iter_p != NULL) { JERRY_ASSERT (ECMA_PROPERTY_IS_PROPERTY_PAIR (prop_iter_p)); /* Both cannot be deleted. */ JERRY_ASSERT (prop_iter_p->types[0] != ECMA_PROPERTY_TYPE_DELETED || prop_iter_p->types[1] != ECMA_PROPERTY_TYPE_DELETED); ecma_property_pair_t *prop_pair_p = (ecma_property_pair_t *) prop_iter_p; for (int i = 0; i < ECMA_PROPERTY_PAIR_ITEM_COUNT; i++) { if (prop_iter_p->types[i] != ECMA_PROPERTY_TYPE_DELETED) { ecma_string_t *name_p = ECMA_GET_POINTER (ecma_string_t, prop_pair_p->names_cp[i]); ecma_free_property (object_p, name_p, prop_iter_p->types + i); if (name_p != NULL) { ecma_deref_ecma_string (name_p); } } } /* Both must be deleted. */ JERRY_ASSERT (prop_iter_p->types[0] == ECMA_PROPERTY_TYPE_DELETED && prop_iter_p->types[1] == ECMA_PROPERTY_TYPE_DELETED); prop_iter_p = ECMA_GET_POINTER (ecma_property_header_t, prop_iter_p->next_property_cp); ecma_dealloc_property_pair (prop_pair_p); } } JERRY_ASSERT (JERRY_CONTEXT (ecma_gc_objects_number) > 0); JERRY_CONTEXT (ecma_gc_objects_number)--; if (!ecma_is_lexical_environment (object_p)) { if (ecma_get_object_is_builtin (object_p) || ecma_get_object_type (object_p) == ECMA_OBJECT_TYPE_EXTERNAL_FUNCTION) { ecma_dealloc_extended_object ((ecma_extended_object_t *) object_p); return; } if (ecma_get_object_type (object_p) == ECMA_OBJECT_TYPE_FUNCTION) { /* Function with byte-code (not a built-in function). */ ecma_extended_object_t *ext_func_p = (ecma_extended_object_t *) object_p; ecma_bytecode_deref (ECMA_GET_INTERNAL_VALUE_POINTER (ecma_compiled_code_t, ext_func_p->u.function.bytecode_cp)); ecma_dealloc_extended_object (ext_func_p); return; } } ecma_dealloc_object (object_p); } /* ecma_gc_sweep */
/** * Mark referenced object from property */ static void ecma_gc_mark_property (ecma_property_t *property_p) /**< property */ { switch (ECMA_PROPERTY_GET_TYPE (*property_p)) { case ECMA_PROPERTY_TYPE_NAMEDDATA: { ecma_value_t value = ECMA_PROPERTY_VALUE_PTR (property_p)->value; if (ecma_is_value_object (value)) { ecma_object_t *value_obj_p = ecma_get_object_from_value (value); ecma_gc_set_object_visited (value_obj_p, true); } break; } case ECMA_PROPERTY_TYPE_NAMEDACCESSOR: { ecma_property_value_t *prop_value_p = ECMA_PROPERTY_VALUE_PTR (property_p); ecma_object_t *getter_obj_p = ecma_get_named_accessor_property_getter (prop_value_p); ecma_object_t *setter_obj_p = ecma_get_named_accessor_property_setter (prop_value_p); if (getter_obj_p != NULL) { ecma_gc_set_object_visited (getter_obj_p, true); } if (setter_obj_p != NULL) { ecma_gc_set_object_visited (setter_obj_p, true); } break; } case ECMA_PROPERTY_TYPE_INTERNAL: { uint32_t property_value = ECMA_PROPERTY_VALUE_PTR (property_p)->value; switch (ECMA_PROPERTY_GET_INTERNAL_PROPERTY_TYPE (property_p)) { case ECMA_INTERNAL_PROPERTY_ECMA_VALUE: /* an ecma_value_t except object */ case ECMA_INTERNAL_PROPERTY_DATE_FLOAT: /* pointer to a ecma_number_t */ case ECMA_INTERNAL_PROPERTY_CLASS: /* an enum */ case ECMA_INTERNAL_PROPERTY_REGEXP_BYTECODE: /* pointer to a regexp bytecode array */ case ECMA_INTERNAL_PROPERTY_NATIVE_HANDLE: /* an external pointer */ case ECMA_INTERNAL_PROPERTY_FREE_CALLBACK: /* an object's native free callback */ case ECMA_INTERNAL_PROPERTY_INSTANTIATED_MASK_32_63: /* an integer (bit-mask) */ { break; } case ECMA_INTERNAL_PROPERTY_BOUND_FUNCTION_BOUND_THIS: /* an ecma value */ { if (ecma_is_value_object (property_value)) { ecma_object_t *obj_p = ecma_get_object_from_value (property_value); ecma_gc_set_object_visited (obj_p, true); } break; } case ECMA_INTERNAL_PROPERTY_BOUND_FUNCTION_BOUND_ARGS: /* a collection of ecma values */ { ecma_collection_header_t *bound_arg_list_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_collection_header_t, property_value); ecma_collection_iterator_t bound_args_iterator; ecma_collection_iterator_init (&bound_args_iterator, bound_arg_list_p); for (ecma_length_t i = 0; i < bound_arg_list_p->unit_number; i++) { bool is_moved = ecma_collection_iterator_next (&bound_args_iterator); JERRY_ASSERT (is_moved); if (ecma_is_value_object (*bound_args_iterator.current_value_p)) { ecma_object_t *obj_p = ecma_get_object_from_value (*bound_args_iterator.current_value_p); ecma_gc_set_object_visited (obj_p, true); } } break; } case ECMA_INTERNAL_PROPERTY_BOUND_FUNCTION_TARGET_FUNCTION: /* an object */ case ECMA_INTERNAL_PROPERTY_SCOPE: /* a lexical environment */ case ECMA_INTERNAL_PROPERTY_PARAMETERS_MAP: /* an object */ { ecma_object_t *obj_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, property_value); ecma_gc_set_object_visited (obj_p, true); break; } case ECMA_INTERNAL_PROPERTY__COUNT: /* not a real internal property type, * but number of the real internal property types */ { JERRY_UNREACHABLE (); break; } } break; } default: { JERRY_UNREACHABLE (); break; } } } /* ecma_gc_mark_property */
/** * Mark objects as visited starting from specified object as root */ void ecma_gc_mark (ecma_object_t *object_p) /**< object to mark from */ { JERRY_ASSERT (object_p != NULL); JERRY_ASSERT (ecma_gc_is_object_visited (object_p)); bool traverse_properties = true; if (ecma_is_lexical_environment (object_p)) { ecma_object_t *lex_env_p = ecma_get_lex_env_outer_reference (object_p); if (lex_env_p != NULL) { ecma_gc_set_object_visited (lex_env_p, true); } if (ecma_get_lex_env_type (object_p) != ECMA_LEXICAL_ENVIRONMENT_DECLARATIVE) { ecma_object_t *binding_object_p = ecma_get_lex_env_binding_object (object_p); ecma_gc_set_object_visited (binding_object_p, true); traverse_properties = false; } } else { ecma_object_t *proto_p = ecma_get_object_prototype (object_p); if (proto_p != NULL) { ecma_gc_set_object_visited (proto_p, true); } if (!ecma_get_object_is_builtin (object_p) && ecma_get_object_type (object_p) == ECMA_OBJECT_TYPE_FUNCTION) { ecma_extended_object_t *ext_func_p = (ecma_extended_object_t *) object_p; ecma_object_t *scope_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, ext_func_p->u.function.scope_cp); ecma_gc_set_object_visited (scope_p, true); } } if (traverse_properties) { ecma_property_header_t *prop_iter_p = ecma_get_property_list (object_p); if (prop_iter_p != NULL && ECMA_PROPERTY_GET_TYPE (prop_iter_p->types[0]) == ECMA_PROPERTY_TYPE_HASHMAP) { prop_iter_p = ECMA_GET_POINTER (ecma_property_header_t, prop_iter_p->next_property_cp); } while (prop_iter_p != NULL) { JERRY_ASSERT (ECMA_PROPERTY_IS_PROPERTY_PAIR (prop_iter_p)); if (prop_iter_p->types[0] != ECMA_PROPERTY_TYPE_DELETED) { ecma_gc_mark_property (prop_iter_p->types + 0); } if (prop_iter_p->types[1] != ECMA_PROPERTY_TYPE_DELETED) { ecma_gc_mark_property (prop_iter_p->types + 1); } prop_iter_p = ECMA_GET_POINTER (ecma_property_header_t, prop_iter_p->next_property_cp); } } } /* ecma_gc_mark */
/** * Dispatch set date functions * * @return ecma value * Returned value must be freed with ecma_free_value. */ static ecma_value_t ecma_builtin_date_prototype_dispatch_set (uint16_t builtin_routine_id, /**< built-in wide routine * identifier */ ecma_extended_object_t *ext_object_p, /**< date extended object */ ecma_number_t date_num, /**< date converted to number */ const ecma_value_t arguments_list[], /**< list of arguments * passed to routine */ ecma_length_t arguments_number) /**< length of arguments' list */ { ecma_number_t converted_number[4]; ecma_length_t conversions = 0; /* If the first argument is not specified, it is always converted to NaN. */ converted_number[0] = ecma_number_make_nan (); switch (builtin_routine_id) { #ifndef CONFIG_DISABLE_ANNEXB_BUILTIN case ECMA_DATE_PROTOTYPE_SET_YEAR: #endif /* !CONFIG_DISABLE_ANNEXB_BUILTIN */ case ECMA_DATE_PROTOTYPE_SET_DATE: case ECMA_DATE_PROTOTYPE_SET_UTC_DATE: case ECMA_DATE_PROTOTYPE_SET_UTC_MILLISECONDS: case ECMA_DATE_PROTOTYPE_SET_MILLISECONDS: { conversions = 1; break; } case ECMA_DATE_PROTOTYPE_SET_MONTH: case ECMA_DATE_PROTOTYPE_SET_UTC_MONTH: case ECMA_DATE_PROTOTYPE_SET_UTC_SECONDS: case ECMA_DATE_PROTOTYPE_SET_SECONDS: { conversions = 2; break; } case ECMA_DATE_PROTOTYPE_SET_FULL_YEAR: case ECMA_DATE_PROTOTYPE_SET_UTC_FULL_YEAR: case ECMA_DATE_PROTOTYPE_SET_MINUTES: case ECMA_DATE_PROTOTYPE_SET_UTC_MINUTES: { conversions = 3; break; } default: { JERRY_ASSERT (builtin_routine_id == ECMA_DATE_PROTOTYPE_SET_HOURS || builtin_routine_id == ECMA_DATE_PROTOTYPE_SET_UTC_HOURS); conversions = 4; break; } } if (conversions > arguments_number) { conversions = arguments_number; } for (ecma_length_t i = 0; i < conversions; i++) { ecma_value_t value = ecma_op_to_number (arguments_list[i]); if (ECMA_IS_VALUE_ERROR (value)) { return value; } converted_number[i] = ecma_get_number_from_value (value); ecma_free_value (value); } ecma_number_t day_part; ecma_number_t time_part; if (builtin_routine_id <= ECMA_DATE_PROTOTYPE_SET_UTC_DATE) { if (ecma_number_is_nan (date_num)) { if (ECMA_DATE_PROTOTYPE_IS_SET_YEAR_ROUTINE (builtin_routine_id)) { date_num = ECMA_NUMBER_ZERO; } else { return ecma_make_number_value (date_num); } } time_part = ecma_date_time_within_day (date_num); ecma_number_t year = ecma_date_year_from_time (date_num); ecma_number_t month = ecma_date_month_from_time (date_num); ecma_number_t day = ecma_date_date_from_time (date_num); switch (builtin_routine_id) { case ECMA_DATE_PROTOTYPE_SET_FULL_YEAR: case ECMA_DATE_PROTOTYPE_SET_UTC_FULL_YEAR: { year = converted_number[0]; if (conversions >= 2) { month = converted_number[1]; } if (conversions >= 3) { day = converted_number[2]; } break; } #ifndef CONFIG_DISABLE_ANNEXB_BUILTIN case ECMA_DATE_PROTOTYPE_SET_YEAR: { year = converted_number[0]; if (year >= 0 && year <= 99) { year += 1900; } break; } #endif /* !CONFIG_DISABLE_ANNEXB_BUILTIN */ case ECMA_DATE_PROTOTYPE_SET_MONTH: case ECMA_DATE_PROTOTYPE_SET_UTC_MONTH: { month = converted_number[0]; if (conversions >= 2) { day = converted_number[1]; } break; } default: { JERRY_ASSERT (builtin_routine_id == ECMA_DATE_PROTOTYPE_SET_DATE || builtin_routine_id == ECMA_DATE_PROTOTYPE_SET_UTC_DATE); day = converted_number[0]; break; } } day_part = ecma_date_make_day (year, month, day); #ifndef CONFIG_DISABLE_ANNEXB_BUILTIN if (builtin_routine_id == ECMA_DATE_PROTOTYPE_SET_YEAR) { builtin_routine_id = ECMA_DATE_PROTOTYPE_SET_UTC_YEAR; if (ecma_number_is_nan (converted_number[0])) { day_part = 0; time_part = converted_number[0]; } } #endif /* !CONFIG_DISABLE_ANNEXB_BUILTIN */ } else { if (ecma_number_is_nan (date_num)) { return ecma_make_number_value (date_num); } day_part = ecma_date_day (date_num); ecma_number_t hour = ecma_date_hour_from_time (date_num); ecma_number_t min = ecma_date_min_from_time (date_num); ecma_number_t sec = ecma_date_sec_from_time (date_num); ecma_number_t ms = ecma_date_ms_from_time (date_num); switch (builtin_routine_id) { case ECMA_DATE_PROTOTYPE_SET_HOURS: case ECMA_DATE_PROTOTYPE_SET_UTC_HOURS: { hour = converted_number[0]; if (conversions >= 2) { min = converted_number[1]; } if (conversions >= 3) { sec = converted_number[2]; } if (conversions >= 4) { ms = converted_number[3]; } break; } case ECMA_DATE_PROTOTYPE_SET_MINUTES: case ECMA_DATE_PROTOTYPE_SET_UTC_MINUTES: { min = converted_number[0]; if (conversions >= 2) { sec = converted_number[1]; } if (conversions >= 3) { ms = converted_number[2]; } break; } case ECMA_DATE_PROTOTYPE_SET_UTC_SECONDS: case ECMA_DATE_PROTOTYPE_SET_SECONDS: { sec = converted_number[0]; if (conversions >= 2) { ms = converted_number[1]; } break; } default: { JERRY_ASSERT (builtin_routine_id == ECMA_DATE_PROTOTYPE_SET_UTC_MILLISECONDS || builtin_routine_id == ECMA_DATE_PROTOTYPE_SET_MILLISECONDS); ms = converted_number[0]; break; } } time_part = ecma_date_make_time (hour, min, sec, ms); } bool is_utc = BUILTIN_DATE_FUNCTION_IS_UTC (builtin_routine_id); ecma_number_t full_date = ecma_date_make_date (day_part, time_part); if (!is_utc) { full_date = ecma_date_utc (full_date); } full_date = ecma_date_time_clip (full_date); *ECMA_GET_INTERNAL_VALUE_POINTER (ecma_number_t, ext_object_p->u.class_prop.u.value) = full_date; return ecma_make_number_value (full_date); } /* ecma_builtin_date_prototype_dispatch_set */
/** * Dispatcher of the built-in's routines * * @return ecma value * Returned value must be freed with ecma_free_value. */ ecma_value_t ecma_builtin_date_prototype_dispatch_routine (uint16_t builtin_routine_id, /**< built-in wide routine * identifier */ ecma_value_t this_arg, /**< 'this' argument value */ const ecma_value_t arguments_list[], /**< list of arguments * passed to routine */ ecma_length_t arguments_number) /**< length of arguments' list */ { if (JERRY_UNLIKELY (builtin_routine_id == ECMA_DATE_PROTOTYPE_TO_JSON)) { return ecma_builtin_date_prototype_to_json (this_arg); } if (!ecma_is_value_object (this_arg) || !ecma_object_class_is (ecma_get_object_from_value (this_arg), LIT_MAGIC_STRING_DATE_UL)) { return ecma_raise_type_error (ECMA_ERR_MSG ("Date object expected")); } ecma_object_t *object_p = ecma_get_object_from_value (this_arg); ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) object_p; ecma_number_t *prim_value_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_number_t, ext_object_p->u.class_prop.u.value); if (builtin_routine_id == ECMA_DATE_PROTOTYPE_GET_TIME) { return ecma_make_number_value (*prim_value_p); } if (builtin_routine_id == ECMA_DATE_PROTOTYPE_SET_TIME) { ecma_value_t time = (arguments_number >= 1 ? arguments_list[0] : ECMA_VALUE_UNDEFINED); ecma_value_t ret_value = ECMA_VALUE_EMPTY; /* 1. */ ECMA_OP_TO_NUMBER_TRY_CATCH (time_num, time, ret_value); *prim_value_p = ecma_date_time_clip (time_num); ret_value = ecma_make_number_value (time_num); ECMA_OP_TO_NUMBER_FINALIZE (time_num); return ret_value; } if (builtin_routine_id <= ECMA_DATE_PROTOTYPE_SET_UTC_MILLISECONDS) { ecma_number_t this_num = *prim_value_p; if (!BUILTIN_DATE_FUNCTION_IS_UTC (builtin_routine_id)) { this_num += ecma_date_local_time_zone (this_num); } if (builtin_routine_id <= ECMA_DATE_PROTOTYPE_GET_UTC_TIMEZONE_OFFSET) { return ecma_builtin_date_prototype_dispatch_get (builtin_routine_id, this_num); } return ecma_builtin_date_prototype_dispatch_set (builtin_routine_id, ext_object_p, this_num, arguments_list, arguments_number); } if (builtin_routine_id == ECMA_DATE_PROTOTYPE_TO_ISO_STRING) { if (ecma_number_is_nan (*prim_value_p) || ecma_number_is_infinity (*prim_value_p)) { return ecma_raise_range_error (ECMA_ERR_MSG ("Date must be a finite number.")); } return ecma_date_value_to_iso_string (*prim_value_p); } if (ecma_number_is_nan (*prim_value_p)) { return ecma_make_magic_string_value (LIT_MAGIC_STRING_INVALID_DATE_UL); } switch (builtin_routine_id) { case ECMA_DATE_PROTOTYPE_TO_STRING: { return ecma_date_value_to_string (*prim_value_p); } case ECMA_DATE_PROTOTYPE_TO_DATE_STRING: { return ecma_date_value_to_date_string (*prim_value_p); } case ECMA_DATE_PROTOTYPE_TO_TIME_STRING: { return ecma_date_value_to_time_string (*prim_value_p); } default: { JERRY_ASSERT (builtin_routine_id == ECMA_DATE_PROTOTYPE_TO_UTC_STRING); return ecma_date_value_to_utc_string (*prim_value_p); } } } /* ecma_builtin_date_prototype_dispatch_routine */
/** * [[Call]] implementation for Function objects, * created through 13.2 (ECMA_OBJECT_TYPE_FUNCTION) * or 15.3.4.5 (ECMA_OBJECT_TYPE_BOUND_FUNCTION), * and for built-in Function objects * from section 15 (ECMA_OBJECT_TYPE_FUNCTION). * * @return ecma value * Returned value must be freed with ecma_free_value */ ecma_value_t ecma_op_function_call (ecma_object_t *func_obj_p, /**< Function object */ ecma_value_t this_arg_value, /**< 'this' argument's value */ const ecma_value_t *arguments_list_p, /**< arguments list */ ecma_length_t arguments_list_len) /**< length of arguments list */ { JERRY_ASSERT (func_obj_p != NULL && !ecma_is_lexical_environment (func_obj_p)); JERRY_ASSERT (ecma_op_is_callable (ecma_make_object_value (func_obj_p))); ecma_value_t ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_EMPTY); if (ecma_get_object_type (func_obj_p) == ECMA_OBJECT_TYPE_FUNCTION) { if (unlikely (ecma_get_object_is_builtin (func_obj_p))) { ret_value = ecma_builtin_dispatch_call (func_obj_p, this_arg_value, arguments_list_p, arguments_list_len); } else { /* Entering Function Code (ECMA-262 v5, 10.4.3) */ ecma_extended_object_t *ext_func_p = (ecma_extended_object_t *) func_obj_p; ecma_object_t *scope_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, ext_func_p->u.function.scope_cp); // 8. ecma_value_t this_binding; bool is_strict; bool is_no_lex_env; const ecma_compiled_code_t *bytecode_data_p; bytecode_data_p = ECMA_GET_INTERNAL_VALUE_POINTER (const ecma_compiled_code_t, ext_func_p->u.function.bytecode_cp); is_strict = (bytecode_data_p->status_flags & CBC_CODE_FLAGS_STRICT_MODE) ? true : false; is_no_lex_env = (bytecode_data_p->status_flags & CBC_CODE_FLAGS_LEXICAL_ENV_NOT_NEEDED) ? true : false; // 1. if (is_strict) { this_binding = ecma_copy_value (this_arg_value); } else if (ecma_is_value_undefined (this_arg_value) || ecma_is_value_null (this_arg_value)) { // 2. this_binding = ecma_make_object_value (ecma_builtin_get (ECMA_BUILTIN_ID_GLOBAL)); } else { // 3., 4. this_binding = ecma_op_to_object (this_arg_value); JERRY_ASSERT (!ECMA_IS_VALUE_ERROR (this_binding)); } // 5. ecma_object_t *local_env_p; if (is_no_lex_env) { local_env_p = scope_p; } else { local_env_p = ecma_create_decl_lex_env (scope_p); if (bytecode_data_p->status_flags & CBC_CODE_FLAGS_ARGUMENTS_NEEDED) { ecma_op_create_arguments_object (func_obj_p, local_env_p, arguments_list_p, arguments_list_len, bytecode_data_p); } } ret_value = vm_run (bytecode_data_p, this_binding, local_env_p, false, arguments_list_p, arguments_list_len); if (!is_no_lex_env) { ecma_deref_object (local_env_p); } ecma_free_value (this_binding); } } else if (ecma_get_object_type (func_obj_p) == ECMA_OBJECT_TYPE_EXTERNAL_FUNCTION)
/** * [[Call]] implementation for Function objects, * created through 13.2 (ECMA_OBJECT_TYPE_FUNCTION) * or 15.3.4.5 (ECMA_OBJECT_TYPE_BOUND_FUNCTION), * and for built-in Function objects * from section 15 (ECMA_OBJECT_TYPE_FUNCTION). * * @return ecma value * Returned value must be freed with ecma_free_value */ ecma_value_t ecma_op_function_has_instance (ecma_object_t *func_obj_p, /**< Function object */ ecma_value_t value) /**< argument 'V' */ { JERRY_ASSERT (func_obj_p != NULL && !ecma_is_lexical_environment (func_obj_p)); ecma_value_t ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_EMPTY); if (ecma_get_object_type (func_obj_p) == ECMA_OBJECT_TYPE_FUNCTION) { if (ecma_get_object_is_builtin (func_obj_p) && ecma_builtin_function_is_routine (func_obj_p)) { return ecma_raise_type_error (ECMA_ERR_MSG ("Function parameter cannot be built-in a function.")); } if (!ecma_is_value_object (value)) { return ecma_make_simple_value (ECMA_SIMPLE_VALUE_FALSE); } ecma_object_t *v_obj_p = ecma_get_object_from_value (value); ecma_string_t *prototype_magic_string_p = ecma_get_magic_string (LIT_MAGIC_STRING_PROTOTYPE); ECMA_TRY_CATCH (prototype_obj_value, ecma_op_object_get (func_obj_p, prototype_magic_string_p), ret_value); if (!ecma_is_value_object (prototype_obj_value)) { ret_value = ecma_raise_type_error (ECMA_ERR_MSG ("Expected an object.")); } else { ecma_object_t *prototype_obj_p = ecma_get_object_from_value (prototype_obj_value); JERRY_ASSERT (prototype_obj_p != NULL); do { v_obj_p = ecma_get_object_prototype (v_obj_p); if (v_obj_p == NULL) { ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_FALSE); break; } else if (v_obj_p == prototype_obj_p) { ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_TRUE); break; } } while (true); } ECMA_FINALIZE (prototype_obj_value); ecma_deref_ecma_string (prototype_magic_string_p); } else if (ecma_get_object_type (func_obj_p) == ECMA_OBJECT_TYPE_EXTERNAL_FUNCTION) { ret_value = ecma_raise_type_error (ECMA_ERR_MSG ("Expected a function.")); } else { JERRY_ASSERT (ecma_get_object_type (func_obj_p) == ECMA_OBJECT_TYPE_BOUND_FUNCTION); /* 1. */ ecma_extended_object_t *ext_function_p = (ecma_extended_object_t *) func_obj_p; ecma_object_t *target_func_obj_p; target_func_obj_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, ext_function_p->u.bound_function.target_function); /* 3. */ ret_value = ecma_op_object_has_instance (target_func_obj_p, value); } return ret_value; } /* ecma_op_function_has_instance */
/** * The RegExp.prototype object's 'compile' routine * * See also: * ECMA-262 v5, B.2.5.1 * * @return undefined - if compiled successfully * error ecma value - otherwise * * Returned value must be freed with ecma_free_value. */ static ecma_value_t ecma_builtin_regexp_prototype_compile (ecma_value_t this_arg, /**< this argument */ ecma_value_t pattern_arg, /**< pattern or RegExp object */ ecma_value_t flags_arg) /**< flags */ { ecma_value_t ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_EMPTY); if (!ecma_is_value_object (this_arg) || ecma_object_get_class_name (ecma_get_object_from_value (this_arg)) != LIT_MAGIC_STRING_REGEXP_UL) { ret_value = ecma_raise_type_error (ECMA_ERR_MSG ("Incomplete RegExp type")); } else { ecma_string_t *pattern_string_p = NULL; uint16_t flags = 0; if (ecma_is_value_object (pattern_arg) && ecma_object_get_class_name (ecma_get_object_from_value (pattern_arg)) == LIT_MAGIC_STRING_REGEXP_UL) { if (!ecma_is_value_undefined (flags_arg)) { ret_value = ecma_raise_type_error (ECMA_ERR_MSG ("Invalid argument of RegExp compile.")); } else { /* Compile from existing RegExp pbject. */ ecma_object_t *target_p = ecma_get_object_from_value (pattern_arg); /* Get source. */ ecma_string_t *magic_string_p = ecma_get_magic_string (LIT_MAGIC_STRING_SOURCE); ecma_property_t *prop_p = ecma_op_object_get_property (target_p, magic_string_p); pattern_string_p = ecma_get_string_from_value (ecma_get_named_data_property_value (prop_p)); ecma_deref_ecma_string (magic_string_p); /* Get flags. */ magic_string_p = ecma_get_magic_string (LIT_MAGIC_STRING_GLOBAL); prop_p = ecma_op_object_get_property (target_p, magic_string_p); if (ecma_is_value_true (ecma_get_named_data_property_value (prop_p))) { flags |= RE_FLAG_GLOBAL; } ecma_deref_ecma_string (magic_string_p); magic_string_p = ecma_get_magic_string (LIT_MAGIC_STRING_IGNORECASE_UL); prop_p = ecma_op_object_get_property (target_p, magic_string_p); if (ecma_is_value_true (ecma_get_named_data_property_value (prop_p))) { flags |= RE_FLAG_IGNORE_CASE; } ecma_deref_ecma_string (magic_string_p); magic_string_p = ecma_get_magic_string (LIT_MAGIC_STRING_MULTILINE); prop_p = ecma_op_object_get_property (target_p, magic_string_p); if (ecma_is_value_true (ecma_get_named_data_property_value (prop_p))) { flags |= RE_FLAG_MULTILINE; } ecma_deref_ecma_string (magic_string_p); ECMA_TRY_CATCH (obj_this, ecma_op_to_object (this_arg), ret_value); ecma_object_t *this_obj_p = ecma_get_object_from_value (obj_this); /* Get bytecode property. */ ecma_property_t *bc_prop_p = ecma_get_internal_property (this_obj_p, ECMA_INTERNAL_PROPERTY_REGEXP_BYTECODE); /* TODO: We currently have to re-compile the bytecode, because * we can't copy it without knowing its length. */ const re_compiled_code_t *new_bc_p = NULL; ecma_value_t bc_comp = re_compile_bytecode (&new_bc_p, pattern_string_p, flags); /* Should always succeed, since we're compiling from a source that has been compiled previously. */ JERRY_ASSERT (ecma_is_value_empty (bc_comp)); re_compiled_code_t *old_bc_p = ECMA_GET_INTERNAL_VALUE_POINTER (re_compiled_code_t, ecma_get_internal_property_value (bc_prop_p)); if (old_bc_p != NULL) { /* Free the old bytecode */ ecma_bytecode_deref ((ecma_compiled_code_t *) old_bc_p); } ECMA_SET_INTERNAL_VALUE_POINTER (ECMA_PROPERTY_VALUE_PTR (bc_prop_p)->value, new_bc_p); re_initialize_props (this_obj_p, pattern_string_p, flags); ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_UNDEFINED); ECMA_FINALIZE (obj_this); } } else { /* Get source string. */ if (!ecma_is_value_undefined (pattern_arg)) { ECMA_TRY_CATCH (regexp_str_value, ecma_op_to_string (pattern_arg), ret_value); if (ecma_string_is_empty (ecma_get_string_from_value (regexp_str_value))) { pattern_string_p = ecma_get_magic_string (LIT_MAGIC_STRING_EMPTY_NON_CAPTURE_GROUP); } else { pattern_string_p = ecma_get_string_from_value (regexp_str_value); ecma_ref_ecma_string (pattern_string_p); } ECMA_FINALIZE (regexp_str_value); } else { pattern_string_p = ecma_get_magic_string (LIT_MAGIC_STRING_EMPTY_NON_CAPTURE_GROUP); } /* Parse flags. */ if (ecma_is_value_empty (ret_value) && !ecma_is_value_undefined (flags_arg)) { ECMA_TRY_CATCH (flags_str_value, ecma_op_to_string (flags_arg), ret_value); ECMA_TRY_CATCH (flags_dummy, re_parse_regexp_flags (ecma_get_string_from_value (flags_str_value), &flags), ret_value); ECMA_FINALIZE (flags_dummy); ECMA_FINALIZE (flags_str_value); } if (ecma_is_value_empty (ret_value)) { ECMA_TRY_CATCH (obj_this, ecma_op_to_object (this_arg), ret_value); ecma_object_t *this_obj_p = ecma_get_object_from_value (obj_this); ecma_property_t *bc_prop_p = ecma_get_internal_property (this_obj_p, ECMA_INTERNAL_PROPERTY_REGEXP_BYTECODE); /* Try to compile bytecode from new source. */ const re_compiled_code_t *new_bc_p = NULL; ECMA_TRY_CATCH (bc_dummy, re_compile_bytecode (&new_bc_p, pattern_string_p, flags), ret_value); re_compiled_code_t *old_bc_p = ECMA_GET_INTERNAL_VALUE_POINTER (re_compiled_code_t, ecma_get_internal_property_value (bc_prop_p)); if (old_bc_p != NULL) { /* Free the old bytecode */ ecma_bytecode_deref ((ecma_compiled_code_t *) old_bc_p); } ECMA_SET_INTERNAL_VALUE_POINTER (ECMA_PROPERTY_VALUE_PTR (bc_prop_p)->value, new_bc_p); re_initialize_props (this_obj_p, pattern_string_p, flags); ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_UNDEFINED); ECMA_FINALIZE (bc_dummy); ECMA_FINALIZE (obj_this); } if (pattern_string_p != NULL) { ecma_deref_ecma_string (pattern_string_p); } } } return ret_value; } /* ecma_builtin_regexp_prototype_compile */
/** * [[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 *obj_p, /**< the object */ ecma_string_t *property_name_p, /**< property name */ const ecma_property_descriptor_t *property_desc_p, /**< property * descriptor */ bool is_throw) /**< flag that controls failure handling */ { // 1. ecma_property_t *map_prop_p = ecma_get_internal_property (obj_p, ECMA_INTERNAL_PROPERTY_PARAMETERS_MAP); ecma_object_t *map_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, ECMA_PROPERTY_VALUE_PTR (map_prop_p)->value); // 2. ecma_property_t *mapped_prop_p = ecma_op_object_get_own_property (map_p, property_name_p); // 3. ecma_value_t ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_EMPTY); ECMA_TRY_CATCH (defined, ecma_op_general_object_define_own_property (obj_p, property_name_p, property_desc_p, is_throw), ret_value); // 5. if (mapped_prop_p != NULL) { // a. if (property_desc_p->is_get_defined || property_desc_p->is_set_defined) { ecma_value_t completion = ecma_op_object_delete (map_p, property_name_p, false); JERRY_ASSERT (ecma_is_value_true (completion)); // 6. ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_TRUE); } else { // b. ecma_value_t completion = ecma_make_simple_value (ECMA_SIMPLE_VALUE_EMPTY); // i. if (property_desc_p->is_value_defined) { /* emulating execution of function described by MakeArgSetter */ ecma_property_t *scope_prop_p = ecma_get_internal_property (map_p, ECMA_INTERNAL_PROPERTY_SCOPE); ecma_object_t *lex_env_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_object_t, ECMA_PROPERTY_VALUE_PTR (scope_prop_p)->value); ecma_property_t *mapped_prop_p = ecma_op_object_get_own_property (map_p, property_name_p); ecma_value_t arg_name_prop_value = ecma_get_named_data_property_value (mapped_prop_p); ecma_string_t *arg_name_p = ecma_get_string_from_value (arg_name_prop_value); completion = ecma_op_set_mutable_binding (lex_env_p, arg_name_p, property_desc_p->value, true); JERRY_ASSERT (ecma_is_value_empty (completion)); } // ii. if (property_desc_p->is_writable_defined && !property_desc_p->is_writable) { completion = ecma_op_object_delete (map_p, property_name_p, false); JERRY_ASSERT (ecma_is_value_true (completion)); } // 6. ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_TRUE); } } else { ret_value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_TRUE); } ECMA_FINALIZE (defined); return ret_value; } /* ecma_op_arguments_object_define_own_property */
/** * Free the internal property and values it references. */ static void ecma_free_internal_property (ecma_property_t *property_p) /**< the property */ { JERRY_ASSERT (property_p != NULL && ECMA_PROPERTY_GET_TYPE (property_p) == ECMA_PROPERTY_TYPE_INTERNAL); uint32_t property_value = ECMA_PROPERTY_VALUE_PTR (property_p)->value; switch (ECMA_PROPERTY_GET_INTERNAL_PROPERTY_TYPE (property_p)) { case ECMA_INTERNAL_PROPERTY_ECMA_VALUE: /* ecma-value property except object */ { JERRY_ASSERT (!ecma_is_value_object (property_value)); ecma_free_value (property_value); break; } case ECMA_INTERNAL_PROPERTY_DATE_FLOAT: /* pointer to a ecma_number_t */ { ecma_number_t *num_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_number_t, property_value); ecma_dealloc_number (num_p); break; } case ECMA_INTERNAL_PROPERTY_NATIVE_CODE: /* an external pointer */ case ECMA_INTERNAL_PROPERTY_NATIVE_HANDLE: /* an external pointer */ case ECMA_INTERNAL_PROPERTY_FREE_CALLBACK: /* an external pointer */ { ecma_free_external_pointer_in_property (property_p); break; } case ECMA_INTERNAL_PROPERTY_SCOPE: /* a lexical environment */ case ECMA_INTERNAL_PROPERTY_PARAMETERS_MAP: /* an object */ case ECMA_INTERNAL_PROPERTY_CLASS: /* an enum */ case ECMA_INTERNAL_PROPERTY_BUILT_IN_ID: /* an integer */ case ECMA_INTERNAL_PROPERTY_BUILT_IN_ROUTINE_DESC: /* an integer */ case ECMA_INTERNAL_PROPERTY_NON_INSTANTIATED_BUILT_IN_MASK_0_31: /* an integer (bit-mask) */ case ECMA_INTERNAL_PROPERTY_NON_INSTANTIATED_BUILT_IN_MASK_32_63: /* an integer (bit-mask) */ case ECMA_INTERNAL_PROPERTY_BOUND_FUNCTION_TARGET_FUNCTION: { break; } case ECMA_INTERNAL_PROPERTY_BOUND_FUNCTION_BOUND_THIS: { ecma_free_value_if_not_object (property_value); break; } case ECMA_INTERNAL_PROPERTY_BOUND_FUNCTION_BOUND_ARGS: { if (property_value != ECMA_NULL_POINTER) { ecma_free_values_collection (ECMA_GET_INTERNAL_VALUE_POINTER (ecma_collection_header_t, property_value), false); } break; } case ECMA_INTERNAL_PROPERTY__COUNT: /* not a real internal property type, * but number of the real internal property types */ { JERRY_UNREACHABLE (); break; } case ECMA_INTERNAL_PROPERTY_CODE_BYTECODE: /* compressed pointer to a bytecode array */ { ecma_bytecode_deref (ECMA_GET_INTERNAL_VALUE_POINTER (ecma_compiled_code_t, property_value)); break; } case ECMA_INTERNAL_PROPERTY_REGEXP_BYTECODE: /* compressed pointer to a regexp bytecode array */ { ecma_compiled_code_t *bytecode_p = ECMA_GET_INTERNAL_VALUE_POINTER (ecma_compiled_code_t, property_value); if (bytecode_p != NULL) { ecma_bytecode_deref (bytecode_p); } break; } } } /* ecma_free_internal_property */