Remove INSTANTIATED_MASK_32_63 internal property type. (#1474)
Furthermore the maximum number of properties is increased to 96. JerryScript-DCO-1.0-Signed-off-by: Zoltan Herczeg zherczeg.u-szeged@partner.samsung.com
This commit is contained in:
@@ -202,11 +202,9 @@ ecma_gc_mark_property (ecma_property_t *property_p) /**< property */
|
||||
{
|
||||
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;
|
||||
}
|
||||
|
||||
default:
|
||||
{
|
||||
JERRY_ASSERT (ECMA_PROPERTY_GET_INTERNAL_PROPERTY_TYPE (property_p) == ECMA_SPECIAL_PROPERTY_DELETED
|
||||
@@ -405,6 +403,26 @@ ecma_gc_sweep (ecma_object_t *object_p) /**< object to free */
|
||||
{
|
||||
ecma_object_type_t object_type = ecma_get_object_type (object_p);
|
||||
|
||||
size_t ext_object_size = sizeof (ecma_extended_object_t);
|
||||
|
||||
if (ecma_get_object_is_builtin (object_p))
|
||||
{
|
||||
uint8_t length_and_bitset_size;
|
||||
|
||||
if (object_type == ECMA_OBJECT_TYPE_CLASS
|
||||
|| object_type == ECMA_OBJECT_TYPE_ARRAY)
|
||||
{
|
||||
ext_object_size = sizeof (ecma_extended_built_in_object_t);
|
||||
length_and_bitset_size = ((ecma_extended_built_in_object_t *) object_p)->built_in.length_and_bitset_size;
|
||||
}
|
||||
else
|
||||
{
|
||||
length_and_bitset_size = ((ecma_extended_object_t *) object_p)->u.built_in.length_and_bitset_size;
|
||||
}
|
||||
|
||||
ext_object_size += (2 * sizeof (uint32_t)) * (length_and_bitset_size >> ECMA_BUILT_IN_BITSET_SHIFT);
|
||||
}
|
||||
|
||||
if (object_type == ECMA_OBJECT_TYPE_CLASS)
|
||||
{
|
||||
ecma_extended_object_t *ext_object_p = (ecma_extended_object_t *) object_p;
|
||||
@@ -461,25 +479,15 @@ ecma_gc_sweep (ecma_object_t *object_p) /**< object to free */
|
||||
}
|
||||
}
|
||||
|
||||
size_t size = (ecma_get_object_is_builtin (object_p) ? sizeof (ecma_extended_built_in_object_t)
|
||||
: sizeof (ecma_extended_object_t));
|
||||
ecma_dealloc_extended_object ((ecma_extended_object_t *) object_p, size);
|
||||
return;
|
||||
}
|
||||
|
||||
if (object_type == ECMA_OBJECT_TYPE_ARRAY)
|
||||
{
|
||||
size_t size = (ecma_get_object_is_builtin (object_p) ? sizeof (ecma_extended_built_in_object_t)
|
||||
: sizeof (ecma_extended_object_t));
|
||||
|
||||
ecma_dealloc_extended_object ((ecma_extended_object_t *) object_p, size);
|
||||
ecma_dealloc_extended_object ((ecma_extended_object_t *) object_p, ext_object_size);
|
||||
return;
|
||||
}
|
||||
|
||||
if (ecma_get_object_is_builtin (object_p)
|
||||
|| object_type == ECMA_OBJECT_TYPE_ARRAY
|
||||
|| object_type == ECMA_OBJECT_TYPE_EXTERNAL_FUNCTION)
|
||||
{
|
||||
ecma_dealloc_extended_object ((ecma_extended_object_t *) object_p, sizeof (ecma_extended_object_t));
|
||||
ecma_dealloc_extended_object ((ecma_extended_object_t *) object_p, ext_object_size);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
@@ -192,7 +192,7 @@ typedef int32_t ecma_integer_value_t;
|
||||
typedef uintptr_t ecma_external_pointer_t;
|
||||
|
||||
/**
|
||||
* Internal properties' identifiers.
|
||||
* Special property identifiers.
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
@@ -204,10 +204,8 @@ typedef enum
|
||||
|
||||
ECMA_INTERNAL_PROPERTY_NATIVE_HANDLE, /**< native handle associated with an object */
|
||||
ECMA_INTERNAL_PROPERTY_FREE_CALLBACK, /**< object's native free callback */
|
||||
ECMA_INTERNAL_PROPERTY_INSTANTIATED_MASK_32_63, /**< Bit-mask of non-instantiated
|
||||
* built-in's properties (bits 32-63) */
|
||||
|
||||
ECMA_INTERNAL_PROPERTY__COUNT /**< Number of internal properties' types */
|
||||
ECMA_SPECIAL_PROPERTY__COUNT /**< Number of special property types */
|
||||
} ecma_internal_property_id_t;
|
||||
|
||||
/**
|
||||
@@ -598,11 +596,17 @@ typedef struct
|
||||
typedef struct
|
||||
{
|
||||
uint8_t id; /**< built-in id */
|
||||
uint8_t length; /**< length for built-in functions */
|
||||
uint8_t length_and_bitset_size; /**< length for built-in functions and
|
||||
* bit set size for all built-ins */
|
||||
uint16_t routine_id; /**< routine id for built-in functions */
|
||||
uint32_t instantiated_bitset; /**< bit set for instantiated properties */
|
||||
uint32_t instantiated_bitset[1]; /**< bit set for instantiated properties */
|
||||
} ecma_built_in_props_t;
|
||||
|
||||
/**
|
||||
* Start position of bit set size in length_and_bitset_size field.
|
||||
*/
|
||||
#define ECMA_BUILT_IN_BITSET_SHIFT 5
|
||||
|
||||
/**
|
||||
* Description of extended ECMA-object.
|
||||
*
|
||||
|
||||
@@ -792,12 +792,6 @@ ecma_free_internal_property (ecma_property_t *property_p) /**< the property */
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case ECMA_INTERNAL_PROPERTY_INSTANTIATED_MASK_32_63: /* an integer (bit-mask) */
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
{
|
||||
JERRY_UNREACHABLE ();
|
||||
|
||||
@@ -54,6 +54,9 @@
|
||||
#undef ROUTINE_ARG_LIST_0
|
||||
#undef ROUTINE_ARG
|
||||
|
||||
/**
|
||||
* List of built-in routine identifiers.
|
||||
*/
|
||||
enum
|
||||
{
|
||||
PASTE (ECMA_ROUTINE_START_, BUILTIN_UNDERSCORED_ID) = ECMA_BUILTIN_ID__COUNT - 1,
|
||||
|
||||
@@ -34,6 +34,46 @@
|
||||
|
||||
static void ecma_instantiate_builtin (ecma_builtin_id_t id);
|
||||
|
||||
/**
|
||||
* Helper definition for ecma_builtin_property_list_references.
|
||||
*/
|
||||
typedef const ecma_builtin_property_descriptor_t *ecma_builtin_property_list_reference_t;
|
||||
|
||||
/**
|
||||
* Property descriptor lists for all built-ins.
|
||||
*/
|
||||
static const ecma_builtin_property_list_reference_t ecma_builtin_property_list_references[] =
|
||||
{
|
||||
#define BUILTIN(builtin_id, \
|
||||
object_type, \
|
||||
object_prototype_builtin_id, \
|
||||
is_extensible, \
|
||||
is_static, \
|
||||
lowercase_name) \
|
||||
ecma_builtin_ ## lowercase_name ## _property_descriptor_list,
|
||||
#include "ecma-builtins.inc.h"
|
||||
};
|
||||
|
||||
/**
|
||||
* Get the number of properties of a built-in object.
|
||||
*
|
||||
* @return the number of properties
|
||||
*/
|
||||
static size_t
|
||||
ecma_builtin_get_property_count (ecma_builtin_id_t builtin_id)
|
||||
{
|
||||
const ecma_builtin_property_descriptor_t *property_list_p = ecma_builtin_property_list_references[builtin_id];
|
||||
|
||||
const ecma_builtin_property_descriptor_t *curr_property_p = property_list_p;
|
||||
|
||||
while (curr_property_p->magic_string_id != LIT_MAGIC_STRING__COUNT)
|
||||
{
|
||||
curr_property_p++;
|
||||
}
|
||||
|
||||
return (size_t) (curr_property_p - property_list_p);
|
||||
} /* ecma_builtin_get_property_count */
|
||||
|
||||
/**
|
||||
* Check if passed object is the instance of specified built-in.
|
||||
*/
|
||||
@@ -109,6 +149,17 @@ ecma_builtin_init_object (ecma_builtin_id_t obj_builtin_id, /**< built-in ID */
|
||||
size_t ext_object_size = (is_extended_built_in ? sizeof (ecma_extended_built_in_object_t)
|
||||
: sizeof (ecma_extended_object_t));
|
||||
|
||||
size_t property_count = ecma_builtin_get_property_count (obj_builtin_id);
|
||||
|
||||
if (property_count > 32)
|
||||
{
|
||||
/* Only 64 extra properties supported at the moment.
|
||||
* This can be extended to 256 later. */
|
||||
JERRY_ASSERT (property_count <= (32 + 64));
|
||||
|
||||
ext_object_size += sizeof (uint32_t) * 2;
|
||||
}
|
||||
|
||||
ecma_object_t *obj_p = ecma_create_object (prototype_obj_p, ext_object_size, obj_type);
|
||||
|
||||
if (!is_extensible)
|
||||
@@ -136,7 +187,20 @@ ecma_builtin_init_object (ecma_builtin_id_t obj_builtin_id, /**< built-in ID */
|
||||
|
||||
built_in_props_p->id = obj_builtin_id;
|
||||
built_in_props_p->routine_id = obj_builtin_id;
|
||||
built_in_props_p->instantiated_bitset = 0;
|
||||
built_in_props_p->instantiated_bitset[0] = 0;
|
||||
|
||||
if (property_count > 32)
|
||||
{
|
||||
built_in_props_p->length_and_bitset_size = 1 << ECMA_BUILT_IN_BITSET_SHIFT;
|
||||
|
||||
uint32_t *instantiated_bitset_p = built_in_props_p->instantiated_bitset;
|
||||
instantiated_bitset_p[1] = 0;
|
||||
instantiated_bitset_p[2] = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
built_in_props_p->length_and_bitset_size = 0;
|
||||
}
|
||||
|
||||
/** Initializing [[PrimitiveValue]] properties of built-in prototype objects */
|
||||
switch (obj_builtin_id)
|
||||
@@ -309,10 +373,25 @@ ecma_builtin_make_function_object_for_routine (ecma_builtin_id_t builtin_id, /**
|
||||
* object's routine property */
|
||||
uint8_t length_prop_value) /**< value of 'length' property */
|
||||
{
|
||||
JERRY_ASSERT (length_prop_value < (1 << ECMA_BUILT_IN_BITSET_SHIFT));
|
||||
|
||||
ecma_object_t *prototype_obj_p = ecma_builtin_get (ECMA_BUILTIN_ID_FUNCTION_PROTOTYPE);
|
||||
|
||||
size_t ext_object_size = sizeof (ecma_extended_object_t);
|
||||
|
||||
size_t property_count = ecma_builtin_get_property_count (builtin_id);
|
||||
|
||||
if (property_count > 32)
|
||||
{
|
||||
/* Only 64 extra properties supported at the moment.
|
||||
* This can be extended to 256 later. */
|
||||
JERRY_ASSERT (property_count <= (32 + 64));
|
||||
|
||||
ext_object_size += sizeof (uint32_t) * 2;
|
||||
}
|
||||
|
||||
ecma_object_t *func_obj_p = ecma_create_object (prototype_obj_p,
|
||||
sizeof (ecma_extended_object_t),
|
||||
ext_object_size,
|
||||
ECMA_OBJECT_TYPE_FUNCTION);
|
||||
|
||||
ecma_deref_object (prototype_obj_p);
|
||||
@@ -323,9 +402,19 @@ ecma_builtin_make_function_object_for_routine (ecma_builtin_id_t builtin_id, /**
|
||||
|
||||
ecma_extended_object_t *ext_func_obj_p = (ecma_extended_object_t *) func_obj_p;
|
||||
ext_func_obj_p->u.built_in.id = builtin_id;
|
||||
ext_func_obj_p->u.built_in.length = length_prop_value;
|
||||
ext_func_obj_p->u.built_in.routine_id = routine_id;
|
||||
ext_func_obj_p->u.built_in.instantiated_bitset = 0;
|
||||
ext_func_obj_p->u.built_in.instantiated_bitset[0] = 0;
|
||||
|
||||
if (property_count > 32)
|
||||
{
|
||||
length_prop_value = (uint8_t) (length_prop_value | (1 << ECMA_BUILT_IN_BITSET_SHIFT));
|
||||
|
||||
uint32_t *instantiated_bitset_p = ext_func_obj_p->u.built_in.instantiated_bitset;
|
||||
instantiated_bitset_p[1] = 0;
|
||||
instantiated_bitset_p[2] = 0;
|
||||
}
|
||||
|
||||
ext_func_obj_p->u.built_in.length_and_bitset_size = length_prop_value;
|
||||
|
||||
return func_obj_p;
|
||||
} /* ecma_builtin_make_function_object_for_routine */
|
||||
@@ -356,20 +445,6 @@ ecma_builtin_make_function_object_for_setter_accessor (ecma_builtin_id_t builtin
|
||||
return ecma_builtin_make_function_object_for_routine (builtin_id, routine_id, 1);
|
||||
} /* ecma_builtin_make_function_object_for_setter_accessor */
|
||||
|
||||
typedef const ecma_builtin_property_descriptor_t *ecma_builtin_property_list_reference_t;
|
||||
|
||||
static const ecma_builtin_property_list_reference_t ecma_builtin_property_list_references[] =
|
||||
{
|
||||
#define BUILTIN(builtin_id, \
|
||||
object_type, \
|
||||
object_prototype_builtin_id, \
|
||||
is_extensible, \
|
||||
is_static, \
|
||||
lowercase_name) \
|
||||
ecma_builtin_ ## lowercase_name ## _property_descriptor_list,
|
||||
#include "ecma-builtins.inc.h"
|
||||
};
|
||||
|
||||
/**
|
||||
* If the property's name is one of built-in properties of the object
|
||||
* that is not instantiated yet, instantiate the property and
|
||||
@@ -404,7 +479,10 @@ ecma_builtin_try_to_instantiate_property (ecma_object_t *object_p, /**< object *
|
||||
&len_prop_p);
|
||||
|
||||
ecma_extended_object_t *ext_obj_p = (ecma_extended_object_t *) object_p;
|
||||
len_prop_value_p->value = ecma_make_integer_value (ext_obj_p->u.built_in.length);
|
||||
|
||||
uint8_t length = ext_obj_p->u.built_in.length_and_bitset_size & ((1 << ECMA_BUILT_IN_BITSET_SHIFT) - 1);
|
||||
|
||||
len_prop_value_p->value = ecma_make_integer_value (length);
|
||||
|
||||
return len_prop_p;
|
||||
}
|
||||
@@ -451,46 +529,17 @@ ecma_builtin_try_to_instantiate_property (ecma_object_t *object_p, /**< object *
|
||||
|
||||
uint32_t index = (uint32_t) (curr_property_p - property_list_p);
|
||||
|
||||
JERRY_ASSERT (index < 64);
|
||||
uint32_t *bitset_p = built_in_props_p->instantiated_bitset + (index >> 5);
|
||||
|
||||
if (likely (index < 32))
|
||||
uint32_t bit_for_index = (uint32_t) (1u << (index & 0x1f));
|
||||
|
||||
if (*bitset_p & bit_for_index)
|
||||
{
|
||||
uint32_t bit_for_index = (uint32_t) 1u << index;
|
||||
|
||||
if (built_in_props_p->instantiated_bitset & bit_for_index)
|
||||
{
|
||||
/* This property was instantiated before. */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
built_in_props_p->instantiated_bitset |= bit_for_index;
|
||||
/* This property was instantiated before. */
|
||||
return NULL;
|
||||
}
|
||||
else
|
||||
{
|
||||
uint32_t bit_for_index = (uint32_t) 1u << (index - 32);
|
||||
ecma_value_t *mask_prop_p = ecma_find_internal_property (object_p,
|
||||
ECMA_INTERNAL_PROPERTY_INSTANTIATED_MASK_32_63);
|
||||
|
||||
uint32_t instantiated_bitset;
|
||||
|
||||
if (mask_prop_p == NULL)
|
||||
{
|
||||
mask_prop_p = ecma_create_internal_property (object_p, ECMA_INTERNAL_PROPERTY_INSTANTIATED_MASK_32_63);
|
||||
instantiated_bitset = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
instantiated_bitset = *mask_prop_p;
|
||||
|
||||
if (instantiated_bitset & bit_for_index)
|
||||
{
|
||||
/* This property was instantiated before. */
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
*mask_prop_p = (instantiated_bitset | bit_for_index);
|
||||
}
|
||||
*bitset_p |= bit_for_index;
|
||||
|
||||
ecma_value_t value = ecma_make_simple_value (ECMA_SIMPLE_VALUE_EMPTY);
|
||||
bool is_accessor = false;
|
||||
@@ -695,50 +744,24 @@ ecma_builtin_list_lazy_property_names (ecma_object_t *object_p, /**< a built-in
|
||||
const ecma_builtin_property_descriptor_t *curr_property_p = ecma_builtin_property_list_references[builtin_id];
|
||||
|
||||
ecma_length_t index = 0;
|
||||
uint32_t instantiated_bitset = built_in_props_p->instantiated_bitset;
|
||||
uint32_t *bitset_p = built_in_props_p->instantiated_bitset;
|
||||
|
||||
ecma_collection_header_t *for_non_enumerable_p = (separate_enumerable ? non_enum_collection_p
|
||||
: main_collection_p);
|
||||
|
||||
while (curr_property_p->magic_string_id != LIT_MAGIC_STRING__COUNT)
|
||||
{
|
||||
JERRY_ASSERT (index < 64);
|
||||
|
||||
if (index == 32)
|
||||
{
|
||||
ecma_value_t *mask_prop_p = ecma_find_internal_property (object_p,
|
||||
ECMA_INTERNAL_PROPERTY_INSTANTIATED_MASK_32_63);
|
||||
|
||||
if (mask_prop_p == NULL)
|
||||
{
|
||||
instantiated_bitset = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
instantiated_bitset = *mask_prop_p;
|
||||
}
|
||||
}
|
||||
|
||||
uint32_t bit_for_index;
|
||||
if (index >= 32)
|
||||
{
|
||||
bit_for_index = (uint32_t) 1u << (index - 32);
|
||||
}
|
||||
else
|
||||
{
|
||||
bit_for_index = (uint32_t) 1u << index;
|
||||
}
|
||||
|
||||
bool was_instantiated = false;
|
||||
|
||||
if (instantiated_bitset & bit_for_index)
|
||||
{
|
||||
was_instantiated = true;
|
||||
bitset_p++;
|
||||
index = 0;
|
||||
}
|
||||
|
||||
ecma_string_t *name_p = ecma_get_magic_string (curr_property_p->magic_string_id);
|
||||
|
||||
if (!was_instantiated || ecma_op_object_has_own_property (object_p, name_p))
|
||||
uint32_t bit_for_index = (uint32_t) 1u << index;
|
||||
|
||||
if (!(*bitset_p & bit_for_index) || ecma_op_object_has_own_property (object_p, name_p))
|
||||
{
|
||||
ecma_append_to_values_collection (for_non_enumerable_p,
|
||||
ecma_make_string_value (name_p),
|
||||
|
||||
Reference in New Issue
Block a user