mirror of
https://github.com/jerryscript-project/jerryscript.git
synced 2025-12-15 16:29:21 +00:00
Improve ecma_string_t descriptor (#3016)
This patch introduces several changes conntect to ecma-strings: - Extend the size of the reference counter to 28 bytes from 13 - Extend the size of the string hash to 32 bytes from 16 to use the extact FNV-1a hash - Introduce ECMA_STATIC_STRING_FLAG to reduce the number of string ref/derefs for static strings. - Introduce ECMA_STRING_CONTAINER_ASCII_STRING to store run-time allocated ASCII strings more efficiently - Remove ECMA_STRING_CONTAINER_LIT_NUMBER to half the storage size of the parsing time allocated floating point numbers - Rework the global number storage, to store only the floating point numbers - Optimize the lookup in the global number/string/symbol tables via reduce the number of NULL checks during decompressing the next element pointers - Reduce the code duplication in ecma_concat_ecma_strings and ecma_append_chars_to_string - Improve ecma_string_get_char with optional arguments to make it more reusable. JerryScript-DCO-1.0-Signed-off-by: Robert Fancsik frobert@inf.u-szeged.hu
This commit is contained in:
parent
f0578b2c25
commit
c6a4a86257
@ -24,9 +24,6 @@ JERRY_STATIC_ASSERT (sizeof (ecma_property_value_t) == sizeof (ecma_value_t),
|
||||
JERRY_STATIC_ASSERT (((sizeof (ecma_property_value_t) - 1) & sizeof (ecma_property_value_t)) == 0,
|
||||
size_of_ecma_property_value_t_must_be_power_of_2);
|
||||
|
||||
JERRY_STATIC_ASSERT (sizeof (ecma_string_t) == sizeof (uint64_t),
|
||||
size_of_ecma_string_t_must_be_less_than_or_equal_to_8_bytes);
|
||||
|
||||
JERRY_STATIC_ASSERT (sizeof (ecma_extended_object_t) - sizeof (ecma_object_t) <= sizeof (uint64_t),
|
||||
size_of_ecma_extended_object_part_must_be_less_than_or_equal_to_8_bytes);
|
||||
|
||||
@ -155,7 +152,35 @@ ecma_dealloc_string (ecma_string_t *string_p) /**< string to be freed */
|
||||
} /* ecma_dealloc_string */
|
||||
|
||||
/**
|
||||
* Allocate memory for string with character data
|
||||
* Allocate memory for extended ecma-string descriptor
|
||||
*
|
||||
* @return pointer to allocated memory
|
||||
*/
|
||||
inline ecma_extended_string_t * JERRY_ATTR_ALWAYS_INLINE
|
||||
ecma_alloc_extended_string (void)
|
||||
{
|
||||
#if ENABLED (JERRY_MEM_STATS)
|
||||
jmem_stats_allocate_string_bytes (sizeof (ecma_extended_string_t));
|
||||
#endif /* ENABLED (JERRY_MEM_STATS) */
|
||||
|
||||
return (ecma_extended_string_t *) jmem_heap_alloc_block (sizeof (ecma_extended_string_t));
|
||||
} /* ecma_alloc_extended_string */
|
||||
|
||||
/**
|
||||
* Dealloc memory from extended ecma-string descriptor
|
||||
*/
|
||||
inline void JERRY_ATTR_ALWAYS_INLINE
|
||||
ecma_dealloc_extended_string (ecma_extended_string_t *ext_string_p) /**< extended string to be freed */
|
||||
{
|
||||
#if ENABLED (JERRY_MEM_STATS)
|
||||
jmem_stats_free_string_bytes (sizeof (ecma_extended_string_t));
|
||||
#endif /* ENABLED (JERRY_MEM_STATS) */
|
||||
|
||||
jmem_heap_free_block (ext_string_p, sizeof (ecma_extended_string_t));
|
||||
} /* ecma_dealloc_extended_string */
|
||||
|
||||
/**
|
||||
* Allocate memory for an string with character data
|
||||
*
|
||||
* @return pointer to allocated memory
|
||||
*/
|
||||
|
||||
@ -73,6 +73,18 @@ ecma_string_t *ecma_alloc_string (void);
|
||||
*/
|
||||
void ecma_dealloc_string (ecma_string_t *string_p);
|
||||
|
||||
/**
|
||||
* Allocate memory for extended ecma-string descriptor
|
||||
*
|
||||
* @return pointer to allocated memory
|
||||
*/
|
||||
ecma_extended_string_t *ecma_alloc_extended_string (void);
|
||||
|
||||
/**
|
||||
* Dealloc memory from extended ecma-string descriptor
|
||||
*/
|
||||
void ecma_dealloc_extended_string (ecma_extended_string_t *string_p);
|
||||
|
||||
/**
|
||||
* Allocate memory for string with character data
|
||||
*
|
||||
|
||||
@ -266,7 +266,7 @@ ecma_gc_mark_container_object (ecma_object_t *object_p) /**< object */
|
||||
|
||||
if (ECMA_STRING_GET_CONTAINER (prop_name_p) == ECMA_STRING_CONTAINER_MAP_KEY)
|
||||
{
|
||||
ecma_value_t key_arg = prop_name_p->u.value;
|
||||
ecma_value_t key_arg = ((ecma_extended_string_t *) prop_name_p)->u.value;
|
||||
|
||||
if (ecma_is_value_object (key_arg))
|
||||
{
|
||||
|
||||
@ -1330,9 +1330,6 @@ typedef enum
|
||||
#define ECMA_GET_DIRECT_STRING_VALUE(string_p) \
|
||||
(((uintptr_t) (string_p)) >> ECMA_DIRECT_STRING_SHIFT)
|
||||
|
||||
/**
|
||||
* Identifier for ecma-string's actual data container
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
ECMA_STRING_CONTAINER_HEAP_UTF8_STRING, /**< actual data is on the heap as an utf-8 (cesu8) string
|
||||
@ -1341,17 +1338,15 @@ typedef enum
|
||||
* maximum size is 2^32. */
|
||||
ECMA_STRING_CONTAINER_UINT32_IN_DESC, /**< actual data is UInt32-represeneted Number
|
||||
stored locally in the string's descriptor */
|
||||
ECMA_STRING_CONTAINER_HEAP_ASCII_STRING, /**< actual data is on the heap as an ASCII string
|
||||
* maximum size is 2^16. */
|
||||
ECMA_STRING_CONTAINER_MAGIC_STRING_EX, /**< the ecma-string is equal to one of external magic strings */
|
||||
|
||||
ECMA_STRING_CONTAINER_SYMBOL, /**< the ecma-string is a symbol */
|
||||
|
||||
ECMA_STRING_CONTAINER_MAP_KEY, /**< the ecma-string is a map key string */
|
||||
|
||||
ECMA_STRING_LITERAL_NUMBER, /**< a literal number which is used solely by the literal storage
|
||||
* so no string processing function supports this type except
|
||||
* the ecma_deref_ecma_string function. */
|
||||
|
||||
ECMA_STRING_CONTAINER__MAX = ECMA_STRING_LITERAL_NUMBER /**< maximum value */
|
||||
ECMA_STRING_CONTAINER__MAX = ECMA_STRING_CONTAINER_MAP_KEY /**< maximum value */
|
||||
} ecma_string_container_t;
|
||||
|
||||
/**
|
||||
@ -1362,12 +1357,29 @@ typedef enum
|
||||
/**
|
||||
* Value for increasing or decreasing the reference counter.
|
||||
*/
|
||||
#define ECMA_STRING_REF_ONE (1u << 3)
|
||||
#define ECMA_STRING_REF_ONE (1u << 4)
|
||||
|
||||
/**
|
||||
* Maximum value of the reference counter (8191).
|
||||
* Maximum value of the reference counter (4294967280).
|
||||
*/
|
||||
#define ECMA_STRING_MAX_REF (0x1fffu << 3)
|
||||
#define ECMA_STRING_MAX_REF (0xFFFFFFF0)
|
||||
|
||||
/**
|
||||
* Flag that identifies that the string is static which means it is stored in JERRY_CONTEXT (string_list_cp)
|
||||
*/
|
||||
#define ECMA_STATIC_STRING_FLAG (1 << 3)
|
||||
|
||||
/**
|
||||
* Set an ecma-string as static string
|
||||
*/
|
||||
#define ECMA_SET_STRING_AS_STATIC(string_p) \
|
||||
(string_p)->refs_and_container |= ECMA_STATIC_STRING_FLAG
|
||||
|
||||
/**
|
||||
* Checks whether the ecma-string is static string
|
||||
*/
|
||||
#define ECMA_STRING_IS_STATIC(string_p) \
|
||||
((string_p)->refs_and_container & ECMA_STATIC_STRING_FLAG)
|
||||
|
||||
/**
|
||||
* Returns with the container type of a string.
|
||||
@ -1379,7 +1391,7 @@ typedef enum
|
||||
* Checks whether the reference counter is 1.
|
||||
*/
|
||||
#define ECMA_STRING_IS_REF_EQUALS_TO_ONE(string_desc_p) \
|
||||
(((string_desc_p)->refs_and_container >> 3) == 1)
|
||||
(((string_desc_p)->refs_and_container >> 4) == 1)
|
||||
|
||||
/**
|
||||
* ECMA string-value descriptor
|
||||
@ -1387,43 +1399,79 @@ typedef enum
|
||||
typedef struct
|
||||
{
|
||||
/** Reference counter for the string */
|
||||
uint16_t refs_and_container;
|
||||
|
||||
/** Hash of the string (calculated from two last characters of the string) */
|
||||
lit_string_hash_t hash;
|
||||
uint32_t refs_and_container;
|
||||
|
||||
/**
|
||||
* Actual data or identifier of it's place in container (depending on 'container' field)
|
||||
*/
|
||||
union
|
||||
{
|
||||
/**
|
||||
* Actual data of an utf-8 string type
|
||||
*/
|
||||
struct
|
||||
{
|
||||
uint16_t size; /**< size of this utf-8 string in bytes */
|
||||
uint16_t length; /**< length of this utf-8 string in characters */
|
||||
} utf8_string;
|
||||
|
||||
lit_utf8_size_t long_utf8_string_size; /**< size of this long utf-8 string in bytes */
|
||||
uint32_t uint32_number; /**< uint32-represented number placed locally in the descriptor */
|
||||
lit_string_hash_t hash; /**< hash of the ASCII/UTF8 string */
|
||||
uint32_t magic_string_ex_id; /**< identifier of an external magic string (lit_magic_string_ex_id_t) */
|
||||
ecma_value_t lit_number; /**< number (see ECMA_STRING_LITERAL_NUMBER) */
|
||||
uint32_t common_uint32_field; /**< for zeroing and comparison in some cases */
|
||||
ecma_value_t symbol_descriptor; /**< symbol descriptor string-value */
|
||||
ecma_value_t value; /**< original key value corresponds to the map key string */
|
||||
uint32_t uint32_number; /**< uint32-represented number placed locally in the descriptor */
|
||||
} u;
|
||||
} ecma_string_t;
|
||||
|
||||
/**
|
||||
* Long ECMA string-value descriptor
|
||||
* ECMA ASCII string-value descriptor
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
ecma_string_t header; /**< string header */
|
||||
lit_utf8_size_t long_utf8_string_length; /**< length of this long utf-8 string in bytes */
|
||||
} ecma_long_string_t;
|
||||
uint16_t size; /**< size of this ASCII string in bytes */
|
||||
} ecma_ascii_string_t;
|
||||
|
||||
/**
|
||||
* ECMA long UTF8 string-value descriptor
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
ecma_string_t header; /**< string header */
|
||||
uint16_t size; /**< size of this utf-8 string in bytes */
|
||||
uint16_t length; /**< length of this utf-8 string in bytes */
|
||||
} ecma_utf8_string_t;
|
||||
|
||||
/**
|
||||
* ECMA UTF8 string-value descriptor
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
ecma_string_t header; /**< string header */
|
||||
lit_utf8_size_t size; /**< size of this long utf-8 string in bytes */
|
||||
lit_utf8_size_t length; /**< length of this long utf-8 string in bytes */
|
||||
} ecma_long_utf8_string_t;
|
||||
|
||||
/**
|
||||
* Get the start position of the string buffer of an ecma ASCII string
|
||||
*/
|
||||
#define ECMA_ASCII_STRING_GET_BUFFER(string_p) \
|
||||
((lit_utf8_byte_t *) ((lit_utf8_byte_t *) (string_p) + sizeof (ecma_ascii_string_t)))
|
||||
|
||||
/**
|
||||
* Get the start position of the string buffer of an ecma UTF8 string
|
||||
*/
|
||||
#define ECMA_UTF8_STRING_GET_BUFFER(string_p) \
|
||||
((lit_utf8_byte_t *) ((lit_utf8_byte_t *) (string_p) + sizeof (ecma_utf8_string_t)))
|
||||
|
||||
/**
|
||||
* Get the start position of the string buffer of an ecma long UTF8 string
|
||||
*/
|
||||
#define ECMA_LONG_UTF8_STRING_GET_BUFFER(string_p) \
|
||||
((lit_utf8_byte_t *) ((lit_utf8_byte_t *) (string_p) + sizeof (ecma_long_utf8_string_t)))
|
||||
|
||||
/**
|
||||
* ECMA extended string-value descriptor
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
ecma_string_t header; /**< string header */
|
||||
|
||||
union
|
||||
{
|
||||
ecma_value_t symbol_descriptor; /**< symbol descriptor string-value */
|
||||
ecma_value_t value; /**< original key value corresponds to the map key string */
|
||||
} u;
|
||||
} ecma_extended_string_t;
|
||||
|
||||
/**
|
||||
* String builder header
|
||||
@ -1437,13 +1485,13 @@ typedef struct
|
||||
* Get pointer to the beginning of the stored string in the string builder
|
||||
*/
|
||||
#define ECMA_STRINGBUILDER_STRING_PTR(header_p) \
|
||||
((lit_utf8_byte_t *) (((ecma_string_t *) header_p) + 1))
|
||||
((lit_utf8_byte_t *) (((lit_utf8_byte_t *) header_p) + sizeof (ecma_ascii_string_t)))
|
||||
|
||||
/**
|
||||
* Get the size of the stored string in the string builder
|
||||
*/
|
||||
#define ECMA_STRINGBUILDER_STRING_SIZE(header_p) \
|
||||
((lit_utf8_size_t) (header_p->current_size - sizeof (ecma_string_t)))
|
||||
((lit_utf8_size_t) (header_p->current_size - sizeof (ecma_ascii_string_t)))
|
||||
|
||||
/**
|
||||
* String builder handle
|
||||
@ -1507,6 +1555,15 @@ typedef struct
|
||||
jmem_cpointer_t values[ECMA_LIT_STORAGE_VALUE_COUNT]; /**< list of values */
|
||||
} ecma_lit_storage_item_t;
|
||||
|
||||
/**
|
||||
* Number storage item
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
jmem_cpointer_t next_cp; /**< cpointer ot next item */
|
||||
jmem_cpointer_t values[ECMA_LIT_STORAGE_VALUE_COUNT]; /**< list of values */
|
||||
} ecma_number_storage_item_t;
|
||||
|
||||
#if ENABLED (JERRY_LCACHE)
|
||||
/**
|
||||
* Container of an LCache entry identifier
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@ -459,6 +459,17 @@ ecma_create_float_number (ecma_number_t ecma_number) /**< value of the float num
|
||||
return ecma_pointer_to_ecma_value (ecma_num_p) | ECMA_TYPE_FLOAT;
|
||||
} /* ecma_create_float_number */
|
||||
|
||||
/**
|
||||
* Encode float number without checks.
|
||||
*
|
||||
* @return ecma-value
|
||||
*/
|
||||
ecma_value_t
|
||||
ecma_make_float_value (ecma_number_t *ecma_num_p) /**< pointer to the float number */
|
||||
{
|
||||
return ecma_pointer_to_ecma_value (ecma_num_p) | ECMA_TYPE_FLOAT;
|
||||
} /* ecma_make_float_value */
|
||||
|
||||
/**
|
||||
* Create a new NaN value.
|
||||
*
|
||||
@ -696,6 +707,19 @@ ecma_get_float_from_value (ecma_value_t value) /**< ecma value */
|
||||
return *(ecma_number_t *) ecma_get_pointer_from_ecma_value (value);
|
||||
} /* ecma_get_float_from_value */
|
||||
|
||||
/**
|
||||
* Get floating point value pointer from an ecma value
|
||||
*
|
||||
* @return floating point value
|
||||
*/
|
||||
inline ecma_number_t * JERRY_ATTR_PURE JERRY_ATTR_ALWAYS_INLINE
|
||||
ecma_get_pointer_from_float_value (ecma_value_t value) /**< ecma value */
|
||||
{
|
||||
JERRY_ASSERT (ecma_get_value_type_field (value) == ECMA_TYPE_FLOAT);
|
||||
|
||||
return (ecma_number_t *) ecma_get_pointer_from_ecma_value (value);
|
||||
} /* ecma_get_pointer_from_float_value */
|
||||
|
||||
/**
|
||||
* Get floating point value from an ecma value
|
||||
*
|
||||
|
||||
@ -50,11 +50,17 @@
|
||||
*/
|
||||
#define ECMA_SET_POINTER(field, non_compressed_pointer) JMEM_CP_SET_POINTER (field, non_compressed_pointer)
|
||||
|
||||
/**
|
||||
* Status flags for ecma_string_get_chars function
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
ECMA_STRING_FLAG_EMPTY = 0,
|
||||
ECMA_STRING_FLAG_IS_ASCII,
|
||||
ECMA_STRING_FLAG_MUST_BE_FREED
|
||||
ECMA_STRING_FLAG_EMPTY = 0, /**< No options are provided. */
|
||||
ECMA_STRING_FLAG_IS_ASCII = (1 << 0), /**< The string contains only ASCII characters. */
|
||||
ECMA_STRING_FLAG_REHASH_NEEDED = (1 << 1), /**< The hash of the string must be recalculated.
|
||||
* For more details see ecma_append_chars_to_string */
|
||||
ECMA_STRING_FLAG_IS_UINT32 = (1 << 2), /**< The string repesents an UINT32 number */
|
||||
ECMA_STRING_FLAG_MUST_BE_FREED = (1 << 3), /**< The returned buffer must be freed */
|
||||
} ecma_string_flag_t;
|
||||
|
||||
/**
|
||||
@ -65,7 +71,11 @@ typedef enum
|
||||
utf8_str_size) /**< [out] output buffer size */ \
|
||||
lit_utf8_size_t utf8_str_size; \
|
||||
uint8_t utf8_ptr ## flags = ECMA_STRING_FLAG_EMPTY; \
|
||||
const lit_utf8_byte_t *utf8_ptr = ecma_string_get_chars (ecma_str_ptr, &utf8_str_size, &utf8_ptr ## flags);
|
||||
const lit_utf8_byte_t *utf8_ptr = ecma_string_get_chars (ecma_str_ptr, \
|
||||
&utf8_str_size, \
|
||||
NULL, \
|
||||
NULL, \
|
||||
&utf8_ptr ## flags);
|
||||
|
||||
/**
|
||||
* Free the cesu-8 string buffer allocated by 'ECMA_STRING_TO_UTF8_STRING'
|
||||
@ -181,6 +191,7 @@ void ecma_check_value_type_is_spec_defined (ecma_value_t value);
|
||||
ecma_value_t JERRY_ATTR_CONST ecma_make_boolean_value (bool boolean_value);
|
||||
ecma_value_t JERRY_ATTR_CONST ecma_make_integer_value (ecma_integer_value_t integer_value);
|
||||
ecma_value_t ecma_make_nan_value (void);
|
||||
ecma_value_t ecma_make_float_value (ecma_number_t *ecma_num_p);
|
||||
ecma_value_t ecma_make_number_value (ecma_number_t ecma_number);
|
||||
ecma_value_t ecma_make_int32_value (int32_t int32_number);
|
||||
ecma_value_t ecma_make_uint32_value (uint32_t uint32_number);
|
||||
@ -195,6 +206,7 @@ ecma_value_t JERRY_ATTR_PURE ecma_make_error_reference_value (const ecma_error_r
|
||||
ecma_value_t JERRY_ATTR_PURE ecma_make_pointer_value (const void *any_p);
|
||||
ecma_integer_value_t JERRY_ATTR_CONST ecma_get_integer_from_value (ecma_value_t value);
|
||||
ecma_number_t JERRY_ATTR_PURE ecma_get_float_from_value (ecma_value_t value);
|
||||
ecma_number_t * ecma_get_pointer_from_float_value (ecma_value_t value);
|
||||
ecma_number_t JERRY_ATTR_PURE ecma_get_number_from_value (ecma_value_t value);
|
||||
ecma_string_t JERRY_ATTR_PURE *ecma_get_string_from_value (ecma_value_t value);
|
||||
#if ENABLED (JERRY_ES2015_BUILTIN_SYMBOL)
|
||||
@ -246,6 +258,7 @@ ecma_string_t *ecma_concat_ecma_strings (ecma_string_t *string1_p, ecma_string_t
|
||||
ecma_string_t *ecma_append_magic_string_to_string (ecma_string_t *string1_p, lit_magic_string_id_t string2_id);
|
||||
void ecma_ref_ecma_string (ecma_string_t *string_p);
|
||||
void ecma_deref_ecma_string (ecma_string_t *string_p);
|
||||
void ecma_destroy_ecma_string (ecma_string_t *string_p);
|
||||
ecma_number_t ecma_string_to_number (const ecma_string_t *str_p);
|
||||
uint32_t ecma_string_get_array_index (const ecma_string_t *str_p);
|
||||
|
||||
@ -271,7 +284,11 @@ ecma_substring_copy_to_utf8_buffer (const ecma_string_t *string_desc_p,
|
||||
lit_utf8_size_t buffer_size);
|
||||
void ecma_string_to_utf8_bytes (const ecma_string_t *string_desc_p, lit_utf8_byte_t *buffer_p,
|
||||
lit_utf8_size_t buffer_size);
|
||||
const lit_utf8_byte_t *ecma_string_get_chars (const ecma_string_t *string_p, lit_utf8_size_t *size_p, uint8_t *flags_p);
|
||||
const lit_utf8_byte_t *ecma_string_get_chars (const ecma_string_t *string_p,
|
||||
lit_utf8_size_t *size_p,
|
||||
lit_utf8_size_t *length_p,
|
||||
lit_utf8_byte_t *uint32_buff_p,
|
||||
uint8_t *flags_p);
|
||||
bool ecma_compare_ecma_string_to_magic_id (const ecma_string_t *string_p, lit_magic_string_id_t id);
|
||||
bool ecma_string_is_empty (const ecma_string_t *string_p);
|
||||
bool ecma_string_is_length (const ecma_string_t *string_p);
|
||||
|
||||
@ -25,14 +25,46 @@
|
||||
* @{
|
||||
*/
|
||||
|
||||
#if ENABLED (JERRY_ES2015_BUILTIN_SYMBOL)
|
||||
/**
|
||||
* Free symbol list
|
||||
*/
|
||||
static void
|
||||
ecma_free_symbol_list (jmem_cpointer_t symbol_list_cp) /**< symbol list */
|
||||
{
|
||||
while (symbol_list_cp != JMEM_CP_NULL)
|
||||
{
|
||||
ecma_lit_storage_item_t *symbol_list_p = JMEM_CP_GET_NON_NULL_POINTER (ecma_lit_storage_item_t, symbol_list_cp);
|
||||
|
||||
for (int i = 0; i < ECMA_LIT_STORAGE_VALUE_COUNT; i++)
|
||||
{
|
||||
if (symbol_list_p->values[i] != JMEM_CP_NULL)
|
||||
{
|
||||
ecma_string_t *string_p = JMEM_CP_GET_NON_NULL_POINTER (ecma_string_t,
|
||||
symbol_list_p->values[i]);
|
||||
|
||||
JERRY_ASSERT (ECMA_STRING_IS_REF_EQUALS_TO_ONE (string_p));
|
||||
ecma_deref_ecma_string (string_p);
|
||||
}
|
||||
}
|
||||
|
||||
jmem_cpointer_t next_item_cp = symbol_list_p->next_cp;
|
||||
jmem_pools_free (symbol_list_p, sizeof (ecma_lit_storage_item_t));
|
||||
symbol_list_cp = next_item_cp;
|
||||
}
|
||||
} /* ecma_free_symbol_list */
|
||||
#endif /* ENABLED (JERRY_ES2015_BUILTIN_SYMBOL) */
|
||||
|
||||
/**
|
||||
* Free string list
|
||||
*/
|
||||
static void
|
||||
ecma_free_string_list (ecma_lit_storage_item_t *string_list_p) /**< string list */
|
||||
ecma_free_string_list (jmem_cpointer_t string_list_cp) /**< string list */
|
||||
{
|
||||
while (string_list_p != NULL)
|
||||
while (string_list_cp != JMEM_CP_NULL)
|
||||
{
|
||||
ecma_lit_storage_item_t *string_list_p = JMEM_CP_GET_NON_NULL_POINTER (ecma_lit_storage_item_t, string_list_cp);
|
||||
|
||||
for (int i = 0; i < ECMA_LIT_STORAGE_VALUE_COUNT; i++)
|
||||
{
|
||||
if (string_list_p->values[i] != JMEM_CP_NULL)
|
||||
@ -41,16 +73,42 @@ ecma_free_string_list (ecma_lit_storage_item_t *string_list_p) /**< string list
|
||||
string_list_p->values[i]);
|
||||
|
||||
JERRY_ASSERT (ECMA_STRING_IS_REF_EQUALS_TO_ONE (string_p));
|
||||
ecma_deref_ecma_string (string_p);
|
||||
ecma_destroy_ecma_string (string_p);
|
||||
}
|
||||
}
|
||||
|
||||
ecma_lit_storage_item_t *prev_item = string_list_p;
|
||||
string_list_p = JMEM_CP_GET_POINTER (ecma_lit_storage_item_t, string_list_p->next_cp);
|
||||
jmem_pools_free (prev_item, sizeof (ecma_lit_storage_item_t));
|
||||
jmem_cpointer_t next_item_cp = string_list_p->next_cp;
|
||||
jmem_pools_free (string_list_p, sizeof (ecma_lit_storage_item_t));
|
||||
string_list_cp = next_item_cp;
|
||||
}
|
||||
} /* ecma_free_string_list */
|
||||
|
||||
/**
|
||||
* Free number list
|
||||
*/
|
||||
static void
|
||||
ecma_free_number_list (jmem_cpointer_t number_list_cp) /**< string list */
|
||||
{
|
||||
while (number_list_cp != JMEM_CP_NULL)
|
||||
{
|
||||
ecma_number_storage_item_t *number_list_p = JMEM_CP_GET_NON_NULL_POINTER (ecma_number_storage_item_t,
|
||||
number_list_cp);
|
||||
|
||||
for (int i = 0; i < ECMA_LIT_STORAGE_VALUE_COUNT; i++)
|
||||
{
|
||||
if (number_list_p->values[i] != JMEM_CP_NULL)
|
||||
{
|
||||
ecma_number_t *num_p = JMEM_CP_GET_NON_NULL_POINTER (ecma_number_t, number_list_p->values[i]);
|
||||
ecma_dealloc_number (num_p);
|
||||
}
|
||||
}
|
||||
|
||||
jmem_cpointer_t next_item_cp = number_list_p->next_cp;
|
||||
jmem_pools_free (number_list_p, sizeof (ecma_number_storage_item_t));
|
||||
number_list_cp = next_item_cp;
|
||||
}
|
||||
} /* ecma_free_number_list */
|
||||
|
||||
/**
|
||||
* Finalize literal storage
|
||||
*/
|
||||
@ -58,10 +116,10 @@ void
|
||||
ecma_finalize_lit_storage (void)
|
||||
{
|
||||
#if ENABLED (JERRY_ES2015_BUILTIN_SYMBOL)
|
||||
ecma_free_string_list (JERRY_CONTEXT (symbol_list_first_p));
|
||||
ecma_free_symbol_list (JERRY_CONTEXT (symbol_list_first_cp));
|
||||
#endif /* ENABLED (JERRY_ES2015_BUILTIN_SYMBOL) */
|
||||
ecma_free_string_list (JERRY_CONTEXT (string_list_first_p));
|
||||
ecma_free_string_list (JERRY_CONTEXT (number_list_first_p));
|
||||
ecma_free_string_list (JERRY_CONTEXT (string_list_first_cp));
|
||||
ecma_free_number_list (JERRY_CONTEXT (number_list_first_cp));
|
||||
} /* ecma_finalize_lit_storage */
|
||||
|
||||
/**
|
||||
@ -80,11 +138,13 @@ ecma_find_or_create_literal_string (const lit_utf8_byte_t *chars_p, /**< string
|
||||
return ecma_make_string_value (string_p);
|
||||
}
|
||||
|
||||
ecma_lit_storage_item_t *string_list_p = JERRY_CONTEXT (string_list_first_p);
|
||||
jmem_cpointer_t string_list_cp = JERRY_CONTEXT (string_list_first_cp);
|
||||
jmem_cpointer_t *empty_cpointer_p = NULL;
|
||||
|
||||
while (string_list_p != NULL)
|
||||
while (string_list_cp != JMEM_CP_NULL)
|
||||
{
|
||||
ecma_lit_storage_item_t *string_list_p = JMEM_CP_GET_NON_NULL_POINTER (ecma_lit_storage_item_t, string_list_cp);
|
||||
|
||||
for (int i = 0; i < ECMA_LIT_STORAGE_VALUE_COUNT; i++)
|
||||
{
|
||||
if (string_list_p->values[i] == JMEM_CP_NULL)
|
||||
@ -108,9 +168,10 @@ ecma_find_or_create_literal_string (const lit_utf8_byte_t *chars_p, /**< string
|
||||
}
|
||||
}
|
||||
|
||||
string_list_p = JMEM_CP_GET_POINTER (ecma_lit_storage_item_t, string_list_p->next_cp);
|
||||
string_list_cp = string_list_p->next_cp;
|
||||
}
|
||||
|
||||
ECMA_SET_STRING_AS_STATIC (string_p);
|
||||
jmem_cpointer_t result;
|
||||
JMEM_CP_SET_NON_NULL_POINTER (result, string_p);
|
||||
|
||||
@ -129,8 +190,8 @@ ecma_find_or_create_literal_string (const lit_utf8_byte_t *chars_p, /**< string
|
||||
new_item_p->values[i] = JMEM_CP_NULL;
|
||||
}
|
||||
|
||||
JMEM_CP_SET_POINTER (new_item_p->next_cp, JERRY_CONTEXT (string_list_first_p));
|
||||
JERRY_CONTEXT (string_list_first_p) = new_item_p;
|
||||
new_item_p->next_cp = JERRY_CONTEXT (string_list_first_cp);
|
||||
JMEM_CP_SET_NON_NULL_POINTER (JERRY_CONTEXT (string_list_first_cp), new_item_p);
|
||||
|
||||
return ecma_make_string_value (string_p);
|
||||
} /* ecma_find_or_create_literal_string */
|
||||
@ -152,11 +213,14 @@ ecma_find_or_create_literal_number (ecma_number_t number_arg) /**< number to be
|
||||
|
||||
JERRY_ASSERT (ecma_is_value_float_number (num));
|
||||
|
||||
ecma_lit_storage_item_t *number_list_p = JERRY_CONTEXT (number_list_first_p);
|
||||
jmem_cpointer_t number_list_cp = JERRY_CONTEXT (number_list_first_cp);
|
||||
jmem_cpointer_t *empty_cpointer_p = NULL;
|
||||
|
||||
while (number_list_p != NULL)
|
||||
while (number_list_cp != JMEM_CP_NULL)
|
||||
{
|
||||
ecma_number_storage_item_t *number_list_p = JMEM_CP_GET_NON_NULL_POINTER (ecma_number_storage_item_t,
|
||||
number_list_cp);
|
||||
|
||||
for (int i = 0; i < ECMA_LIT_STORAGE_VALUE_COUNT; i++)
|
||||
{
|
||||
if (number_list_p->values[i] == JMEM_CP_NULL)
|
||||
@ -168,29 +232,24 @@ ecma_find_or_create_literal_number (ecma_number_t number_arg) /**< number to be
|
||||
}
|
||||
else
|
||||
{
|
||||
ecma_string_t *value_p = JMEM_CP_GET_NON_NULL_POINTER (ecma_string_t,
|
||||
number_list_p->values[i]);
|
||||
ecma_number_t *number_p = JMEM_CP_GET_NON_NULL_POINTER (ecma_number_t,
|
||||
number_list_p->values[i]);
|
||||
|
||||
JERRY_ASSERT (ECMA_STRING_GET_CONTAINER (value_p) == ECMA_STRING_LITERAL_NUMBER);
|
||||
JERRY_ASSERT (ecma_is_value_float_number (value_p->u.lit_number));
|
||||
|
||||
if (ecma_get_float_from_value (value_p->u.lit_number) == number_arg)
|
||||
if (*number_p == number_arg)
|
||||
{
|
||||
ecma_free_value (num);
|
||||
return value_p->u.lit_number;
|
||||
return ecma_make_float_value (number_p);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
number_list_p = JMEM_CP_GET_POINTER (ecma_lit_storage_item_t, number_list_p->next_cp);
|
||||
number_list_cp = number_list_p->next_cp;
|
||||
}
|
||||
|
||||
ecma_string_t *string_p = ecma_alloc_string ();
|
||||
string_p->refs_and_container = ECMA_STRING_REF_ONE | ECMA_STRING_LITERAL_NUMBER;
|
||||
string_p->u.lit_number = num;
|
||||
ecma_number_t *num_p = ecma_get_pointer_from_float_value (num);
|
||||
|
||||
jmem_cpointer_t result;
|
||||
JMEM_CP_SET_NON_NULL_POINTER (result, string_p);
|
||||
JMEM_CP_SET_NON_NULL_POINTER (result, num_p);
|
||||
|
||||
if (empty_cpointer_p != NULL)
|
||||
{
|
||||
@ -198,8 +257,8 @@ ecma_find_or_create_literal_number (ecma_number_t number_arg) /**< number to be
|
||||
return num;
|
||||
}
|
||||
|
||||
ecma_lit_storage_item_t *new_item_p;
|
||||
new_item_p = (ecma_lit_storage_item_t *) jmem_pools_alloc (sizeof (ecma_lit_storage_item_t));
|
||||
ecma_number_storage_item_t *new_item_p;
|
||||
new_item_p = (ecma_number_storage_item_t *) jmem_pools_alloc (sizeof (ecma_number_storage_item_t));
|
||||
|
||||
new_item_p->values[0] = result;
|
||||
for (int i = 1; i < ECMA_LIT_STORAGE_VALUE_COUNT; i++)
|
||||
@ -207,8 +266,8 @@ ecma_find_or_create_literal_number (ecma_number_t number_arg) /**< number to be
|
||||
new_item_p->values[i] = JMEM_CP_NULL;
|
||||
}
|
||||
|
||||
JMEM_CP_SET_POINTER (new_item_p->next_cp, JERRY_CONTEXT (number_list_first_p));
|
||||
JERRY_CONTEXT (number_list_first_p) = new_item_p;
|
||||
new_item_p->next_cp = JERRY_CONTEXT (number_list_first_cp);
|
||||
JMEM_CP_SET_NON_NULL_POINTER (JERRY_CONTEXT (number_list_first_cp), new_item_p);
|
||||
|
||||
return num;
|
||||
} /* ecma_find_or_create_literal_number */
|
||||
|
||||
@ -102,11 +102,14 @@ ecma_builtin_symbol_for_helper (ecma_value_t value_to_find) /**< symbol or ecma-
|
||||
string_p = ecma_get_symbol_from_value (value_to_find);
|
||||
}
|
||||
|
||||
ecma_lit_storage_item_t *symbol_list_p = JERRY_CONTEXT (symbol_list_first_p);
|
||||
jmem_cpointer_t symbol_list_cp = JERRY_CONTEXT (symbol_list_first_cp);
|
||||
jmem_cpointer_t *empty_cpointer_p = NULL;
|
||||
|
||||
while (symbol_list_p != NULL)
|
||||
while (symbol_list_cp != JMEM_CP_NULL)
|
||||
{
|
||||
ecma_lit_storage_item_t *symbol_list_p = JMEM_CP_GET_NON_NULL_POINTER (ecma_lit_storage_item_t,
|
||||
symbol_list_cp);
|
||||
|
||||
for (int i = 0; i < ECMA_LIT_STORAGE_VALUE_COUNT; i++)
|
||||
{
|
||||
if (symbol_list_p->values[i] != JMEM_CP_NULL)
|
||||
@ -145,7 +148,7 @@ ecma_builtin_symbol_for_helper (ecma_value_t value_to_find) /**< symbol or ecma-
|
||||
}
|
||||
}
|
||||
|
||||
symbol_list_p = JMEM_CP_GET_POINTER (ecma_lit_storage_item_t, symbol_list_p->next_cp);
|
||||
symbol_list_cp = symbol_list_p->next_cp;
|
||||
}
|
||||
|
||||
if (!is_for)
|
||||
@ -175,8 +178,8 @@ ecma_builtin_symbol_for_helper (ecma_value_t value_to_find) /**< symbol or ecma-
|
||||
new_item_p->values[i] = JMEM_CP_NULL;
|
||||
}
|
||||
|
||||
JMEM_CP_SET_POINTER (new_item_p->next_cp, JERRY_CONTEXT (symbol_list_first_p));
|
||||
JERRY_CONTEXT (symbol_list_first_p) = new_item_p;
|
||||
new_item_p->next_cp = JERRY_CONTEXT (symbol_list_first_cp);
|
||||
JMEM_CP_SET_NON_NULL_POINTER (JERRY_CONTEXT (symbol_list_first_cp), new_item_p);
|
||||
|
||||
return ecma_copy_value (ecma_make_symbol_value (new_symbol_p));
|
||||
} /* ecma_builtin_symbol_for_helper */
|
||||
|
||||
@ -659,9 +659,9 @@ ecma_builtin_try_to_instantiate_property (ecma_object_t *object_p, /**< object *
|
||||
#if ENABLED (JERRY_ES2015_BUILTIN_SYMBOL)
|
||||
if (JERRY_UNLIKELY (ecma_prop_name_is_symbol (string_p)))
|
||||
{
|
||||
if (string_p->hash & ECMA_GLOBAL_SYMBOL_FLAG)
|
||||
if (string_p->u.hash & ECMA_GLOBAL_SYMBOL_FLAG)
|
||||
{
|
||||
magic_string_id = (string_p->hash >> ECMA_GLOBAL_SYMBOL_SHIFT);
|
||||
magic_string_id = (string_p->u.hash >> ECMA_GLOBAL_SYMBOL_SHIFT);
|
||||
}
|
||||
}
|
||||
#endif /* ENABLED (JERRY_ES2015_BUILTIN_SYMBOL) */
|
||||
@ -802,7 +802,7 @@ ecma_builtin_try_to_instantiate_property (ecma_object_t *object_p, /**< object *
|
||||
|
||||
ecma_string_t *symbol_p = ecma_new_symbol_from_descriptor_string (symbol_desc_value);
|
||||
lit_magic_string_id_t symbol_id = (lit_magic_string_id_t) curr_property_p->value;
|
||||
symbol_p->hash = (uint16_t) ((symbol_id << ECMA_GLOBAL_SYMBOL_SHIFT) | ECMA_GLOBAL_SYMBOL_FLAG);
|
||||
symbol_p->u.hash = (uint16_t) ((symbol_id << ECMA_GLOBAL_SYMBOL_SHIFT) | ECMA_GLOBAL_SYMBOL_FLAG);
|
||||
|
||||
value = ecma_make_symbol_value (symbol_p);
|
||||
break;
|
||||
|
||||
@ -476,7 +476,7 @@ ecma_op_container_foreach (ecma_value_t this_arg, /**< this argument */
|
||||
}
|
||||
else if (ecma_prop_name_is_map_key (prop_name_p))
|
||||
{
|
||||
key_arg = prop_name_p->u.value;
|
||||
key_arg = ((ecma_extended_string_t *) prop_name_p)->u.value;
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -730,7 +730,7 @@ ecma_op_container_iterator_next (ecma_value_t this_val, /**< this argument */
|
||||
}
|
||||
else if (ecma_prop_name_is_map_key (prop_name_p))
|
||||
{
|
||||
key_arg = prop_name_p->u.value;
|
||||
key_arg = ((ecma_extended_string_t *) prop_name_p)->u.value;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
@ -111,7 +111,7 @@ ecma_get_symbol_description (ecma_string_t *symbol_p) /**< ecma-symbol */
|
||||
JERRY_ASSERT (symbol_p != NULL);
|
||||
JERRY_ASSERT (ecma_prop_name_is_symbol (symbol_p));
|
||||
|
||||
return ecma_get_string_from_value (symbol_p->u.symbol_descriptor);
|
||||
return ecma_get_string_from_value (((ecma_extended_string_t *) symbol_p)->u.symbol_descriptor);
|
||||
} /* ecma_get_symbol_description */
|
||||
|
||||
/**
|
||||
|
||||
@ -136,11 +136,11 @@ struct jerry_context_t
|
||||
#endif /* ENABLED (JERRY_CPOINTER_32_BIT) */
|
||||
const lit_utf8_byte_t * const *lit_magic_string_ex_array; /**< array of external magic strings */
|
||||
const lit_utf8_size_t *lit_magic_string_ex_sizes; /**< external magic string lengths */
|
||||
ecma_lit_storage_item_t *string_list_first_p; /**< first item of the literal string list */
|
||||
jmem_cpointer_t string_list_first_cp; /**< first item of the literal string list */
|
||||
#if ENABLED (JERRY_ES2015_BUILTIN_SYMBOL)
|
||||
ecma_lit_storage_item_t *symbol_list_first_p; /**< first item of the global symbol list */
|
||||
jmem_cpointer_t symbol_list_first_cp; /**< first item of the global symbol list */
|
||||
#endif /* ENABLED (JERRY_ES2015_BUILTIN_SYMBOL) */
|
||||
ecma_lit_storage_item_t *number_list_first_p; /**< first item of the literal number list */
|
||||
jmem_cpointer_t number_list_first_cp; /**< first item of the literal number list */
|
||||
jmem_cpointer_t ecma_global_lex_env_cp; /**< global lexical environment */
|
||||
|
||||
#if ENABLED (JERRY_ES2015_MODULE_SYSTEM)
|
||||
|
||||
@ -121,16 +121,11 @@ typedef uint32_t lit_code_point_t;
|
||||
/**
|
||||
* ECMA string hash
|
||||
*/
|
||||
typedef uint16_t lit_string_hash_t;
|
||||
typedef uint32_t lit_string_hash_t;
|
||||
|
||||
/**
|
||||
* Maximum value of ECMA string hash + 1
|
||||
*
|
||||
* Note:
|
||||
* On ARM, this constant can be encoded as an immediate value
|
||||
* while 0xffffu cannot be. Hence using this constant reduces
|
||||
* binary size and improves performance.
|
||||
* Maximum value of ECMA string hash
|
||||
*/
|
||||
#define LIT_STRING_HASH_LIMIT 0x10000u
|
||||
#define LIT_STRING_HASH_LIMIT UINT32_MAX
|
||||
|
||||
#endif /* !LIT_GLOBALS_H */
|
||||
|
||||
@ -275,6 +275,8 @@ parser_module_context_init (void)
|
||||
|
||||
const lit_utf8_byte_t *path_str_chars_p = ecma_string_get_chars (path_str_p,
|
||||
&path_str_size,
|
||||
NULL,
|
||||
NULL,
|
||||
&flags);
|
||||
|
||||
ecma_string_t *path_p = ecma_module_create_normalized_path (path_str_chars_p,
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user