diff --git a/jerry-core/ecma/base/ecma-globals.h b/jerry-core/ecma/base/ecma-globals.h index 0c8273217..47f70cfa0 100644 --- a/jerry-core/ecma/base/ecma-globals.h +++ b/jerry-core/ecma/base/ecma-globals.h @@ -2180,7 +2180,8 @@ typedef struct uint32_t array_index_named_props; /**< number of array index named properties */ uint32_t string_named_props; /**< number of string named properties */ uint32_t symbol_named_props; /**< number of symbol named properties */ - uint32_t lazy_string_named_props; /**< number of lazy instantiated properties */ + uint32_t lazy_string_named_props; /**< number of lazy instantiated string properties */ + uint32_t lazy_symbol_named_props; /**< number of lazy instantiated symbol properties */ } ecma_property_counter_t; /** diff --git a/jerry-core/ecma/builtin-objects/ecma-builtins.c b/jerry-core/ecma/builtin-objects/ecma-builtins.c index a41303073..a15253d31 100644 --- a/jerry-core/ecma/builtin-objects/ecma-builtins.c +++ b/jerry-core/ecma/builtin-objects/ecma-builtins.c @@ -1114,24 +1114,38 @@ ecma_builtin_list_lazy_property_names (ecma_object_t *object_p, /**< a built-in index = 0; } -#if ENABLED (JERRY_ESNEXT) - /* Builtin symbol properties are internal magic strings which must not be listed */ - if (curr_property_p->magic_string_id > LIT_NON_INTERNAL_MAGIC_STRING__COUNT) - { - curr_property_p++; - continue; - } -#endif /* ENABLED (JERRY_ESNEXT) */ - - ecma_string_t *name_p = ecma_get_magic_string ((lit_magic_string_id_t) curr_property_p->magic_string_id); - uint32_t bit_for_index = (uint32_t) 1u << index; - if (!(*bitset_p & bit_for_index) || ecma_op_ordinary_object_has_own_property (object_p, name_p)) + if (curr_property_p->magic_string_id > LIT_NON_INTERNAL_MAGIC_STRING__COUNT) { - ecma_value_t name = ecma_make_magic_string_value ((lit_magic_string_id_t) curr_property_p->magic_string_id); - ecma_collection_push_back (prop_names_p, name); - prop_counter_p->string_named_props++; +#if ENABLED (JERRY_ESNEXT) + if (LIT_IS_GLOBAL_SYMBOL (curr_property_p->magic_string_id)) + { + ecma_string_t *name_p = ecma_op_get_global_symbol (curr_property_p->magic_string_id); + + if (!(*bitset_p & bit_for_index) || ecma_op_ordinary_object_has_own_property (object_p, name_p)) + { + ecma_value_t name = ecma_make_symbol_value (name_p); + ecma_collection_push_back (prop_names_p, name); + prop_counter_p->symbol_named_props++; + } + else + { + ecma_deref_ecma_string (name_p); + } + } +#endif /* ENABLED (JERRY_ESNEXT) */ + } + else + { + ecma_string_t *name_p = ecma_get_magic_string ((lit_magic_string_id_t) curr_property_p->magic_string_id); + + if (!(*bitset_p & bit_for_index) || ecma_op_ordinary_object_has_own_property (object_p, name_p)) + { + ecma_value_t name = ecma_make_magic_string_value ((lit_magic_string_id_t) curr_property_p->magic_string_id); + ecma_collection_push_back (prop_names_p, name); + prop_counter_p->string_named_props++; + } } curr_property_p++; diff --git a/jerry-core/ecma/operations/ecma-objects.c b/jerry-core/ecma/operations/ecma-objects.c index 44cda7cd9..9aa2813f8 100644 --- a/jerry-core/ecma/operations/ecma-objects.c +++ b/jerry-core/ecma/operations/ecma-objects.c @@ -2185,9 +2185,12 @@ static void ecma_object_sort_property_names (ecma_collection_t *prop_names_p, /**< prop name collection */ ecma_property_counter_t *prop_counter) /**< prop counter */ { - uint32_t lazy_prop_name_count = (uint32_t) (prop_counter->lazy_string_named_props); - uint32_t string_name_pos = prop_counter->string_named_props; + uint32_t lazy_string_prop_name_count = prop_counter->lazy_string_named_props; +#if ENABLED (JERRY_ESNEXT) + uint32_t lazy_symbol_prop_name_count = prop_counter->lazy_symbol_named_props; +#endif /* ENABLED (JERRY_ESNEXT) */ + uint32_t string_name_pos = prop_counter->string_named_props; #if ENABLED (JERRY_ESNEXT) uint32_t symbol_name_pos = prop_counter->symbol_named_props; #endif /* ENABLED (JERRY_ESNEXT) */ @@ -2206,6 +2209,9 @@ ecma_object_sort_property_names (ecma_collection_t *prop_names_p, /**< prop name uint32_t array_index_name_pos = 0; uint32_t lazy_string_name_pos = 0; +#if ENABLED (JERRY_ESNEXT) + uint32_t lazy_symbol_name_pos = 0; +#endif /* ENABLED (JERRY_ESNEXT) */ for (uint32_t i = 0; i < prop_names_p->item_count; i++) { @@ -2253,7 +2259,14 @@ ecma_object_sort_property_names (ecma_collection_t *prop_names_p, /**< prop name JERRY_ASSERT (symbol_name_pos > 0); JERRY_ASSERT (symbol_name_pos <= prop_counter->symbol_named_props); - symbol_names_p[--symbol_name_pos] = prop_name; + if (i < lazy_symbol_prop_name_count) + { + symbol_names_p[lazy_symbol_name_pos++] = prop_name; + } + else + { + symbol_names_p[--symbol_name_pos] = prop_name; + } } #endif /* ENABLED (JERRY_ESNEXT) */ /* sort string named properties in creation order */ @@ -2262,7 +2275,7 @@ ecma_object_sort_property_names (ecma_collection_t *prop_names_p, /**< prop name JERRY_ASSERT (string_name_pos > 0); JERRY_ASSERT (string_name_pos <= prop_counter->string_named_props); - if (i < lazy_prop_name_count) + if (i < lazy_string_prop_name_count) { string_names_p[lazy_string_name_pos++] = prop_name; } @@ -2311,11 +2324,12 @@ ecma_op_object_own_property_keys (ecma_object_t *obj_p) /**< object */ } ecma_collection_t *prop_names_p = ecma_new_collection (); - ecma_property_counter_t prop_counter = {0, 0, 0, 0}; + ecma_property_counter_t prop_counter = {0, 0, 0, 0, 0}; ecma_object_list_lazy_property_names (obj_p, prop_names_p, &prop_counter); - prop_counter.lazy_string_named_props = prop_names_p->item_count; + prop_counter.lazy_string_named_props = prop_names_p->item_count - prop_counter.symbol_named_props; + prop_counter.lazy_symbol_named_props = prop_counter.symbol_named_props; jmem_cpointer_t prop_iter_cp = obj_p->u1.property_list_cp; @@ -2375,6 +2389,10 @@ ecma_op_object_own_property_keys (ecma_object_t *obj_p) /**< object */ ecma_collection_push_back (prop_names_p, ecma_make_prop_name_value (name_p)); } + else + { + ecma_deref_ecma_string (name_p); + } } } diff --git a/tests/jerry/es.next/map.js b/tests/jerry/es.next/map.js index 078760048..7727a4719 100644 --- a/tests/jerry/es.next/map.js +++ b/tests/jerry/es.next/map.js @@ -157,3 +157,5 @@ map.forEach(function (value, key) { assert(k === Infinity); assert(map.get(+0) === "foo"); + +[Symbol.iterator, Symbol.toStringTag].forEach(e => assert (Reflect.ownKeys(Map.prototype).includes(e))); diff --git a/tests/jerry/es.next/set.js b/tests/jerry/es.next/set.js index 46bbd0ae7..8d2338432 100644 --- a/tests/jerry/es.next/set.js +++ b/tests/jerry/es.next/set.js @@ -136,3 +136,5 @@ set.forEach(function (value) { assert(k === Infinity); assert(set.has(+0) === true); + +[Symbol.iterator, Symbol.toStringTag].forEach(e => assert (Reflect.ownKeys(Set.prototype).includes(e))); diff --git a/tests/jerry/es.next/weakmap.js b/tests/jerry/es.next/weakmap.js index d842872ef..ef5679046 100644 --- a/tests/jerry/es.next/weakmap.js +++ b/tests/jerry/es.next/weakmap.js @@ -182,3 +182,5 @@ try { } catch (e) { assert (e === "abrupt set getter"); } + +[Symbol.toStringTag].forEach(e => assert (Reflect.ownKeys(WeakMap.prototype).includes(e))); diff --git a/tests/jerry/es.next/weakset.js b/tests/jerry/es.next/weakset.js index d026d1ad0..8e42369e1 100644 --- a/tests/jerry/es.next/weakset.js +++ b/tests/jerry/es.next/weakset.js @@ -166,3 +166,5 @@ try { } catch (e) { assert (e === "abrupt add getter"); } + +[Symbol.toStringTag].forEach(e => assert (Reflect.ownKeys(WeakSet.prototype).includes(e)));