OLD | NEW |
---|---|
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "src/elements.h" | 5 #include "src/elements.h" |
6 | 6 |
7 #include "src/arguments.h" | 7 #include "src/arguments.h" |
8 #include "src/conversions.h" | 8 #include "src/conversions.h" |
9 #include "src/factory.h" | 9 #include "src/factory.h" |
10 #include "src/messages.h" | 10 #include "src/messages.h" |
(...skipping 817 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
828 // intentionally to avoid ArrayConcat() builtin performance degradation. | 828 // intentionally to avoid ArrayConcat() builtin performance degradation. |
829 // | 829 // |
830 // Details: The idea is that allocations actually happen only in case of | 830 // Details: The idea is that allocations actually happen only in case of |
831 // copying from object with fast double elements to object with object | 831 // copying from object with fast double elements to object with object |
832 // elements. In all the other cases there are no allocations performed and | 832 // elements. In all the other cases there are no allocations performed and |
833 // handle creation causes noticeable performance degradation of the builtin. | 833 // handle creation causes noticeable performance degradation of the builtin. |
834 ElementsAccessorSubclass::CopyElementsImpl( | 834 ElementsAccessorSubclass::CopyElementsImpl( |
835 from, from_start, *to, from_kind, to_start, packed_size, copy_size); | 835 from, from_start, *to, from_kind, to_start, packed_size, copy_size); |
836 } | 836 } |
837 | 837 |
838 Maybe<bool> CollectValuesOrEntries(Isolate* isolate, Handle<JSObject> object, | |
839 Handle<FixedArray> values_or_entries, | |
840 bool get_entries, int* nof_items, | |
841 PropertyFilter filter) { | |
842 return ElementsAccessorSubclass::CollectValuesOrEntriesImpl( | |
843 isolate, object, values_or_entries, get_entries, nof_items, filter); | |
844 } | |
845 | |
846 static Maybe<bool> CollectValuesOrEntriesImpl( | |
847 Isolate* isolate, Handle<JSObject> object, | |
848 Handle<FixedArray> values_or_entries, bool get_entries, int* nof_items, | |
849 PropertyFilter filter) { | |
850 int count = 0; | |
851 KeyAccumulator accumulator(isolate, OWN_ONLY, ALL_PROPERTIES); | |
852 accumulator.NextPrototype(); | |
853 ElementsAccessorSubclass::CollectElementIndicesImpl( | |
854 object, handle(object->elements(), isolate), &accumulator, kMaxUInt32, | |
855 ALL_PROPERTIES, 0); | |
856 Handle<FixedArray> keys = accumulator.GetKeys(); | |
857 | |
858 for (int i = 0; i < keys->length(); ++i) { | |
859 Handle<Object> key(keys->get(i), isolate); | |
860 Handle<Object> value; | |
861 uint32_t index; | |
862 if (!key->ToUint32(&index)) continue; | |
863 | |
864 uint32_t entry = ElementsAccessorSubclass::GetEntryForIndexImpl( | |
865 *object, object->elements(), index, filter); | |
866 if (entry == kMaxUInt32) continue; | |
867 | |
868 PropertyDetails details = | |
869 ElementsAccessorSubclass::GetDetailsImpl(*object, entry); | |
870 | |
871 if (details.kind() == kData) { | |
872 value = ElementsAccessorSubclass::GetImpl(object, entry); | |
873 } else { | |
874 LookupIterator it(isolate, object, index, LookupIterator::OWN); | |
875 ASSIGN_RETURN_ON_EXCEPTION_VALUE( | |
876 isolate, value, Object::GetProperty(&it), Nothing<bool>()); | |
877 } | |
878 if (get_entries) { | |
879 value = MakeEntryPair(isolate, index, value); | |
880 } | |
881 values_or_entries->set(count++, *value); | |
882 } | |
883 | |
884 *nof_items = count; | |
885 return Just(true); | |
886 } | |
887 | |
838 void CollectElementIndices(Handle<JSObject> object, | 888 void CollectElementIndices(Handle<JSObject> object, |
839 Handle<FixedArrayBase> backing_store, | 889 Handle<FixedArrayBase> backing_store, |
840 KeyAccumulator* keys, uint32_t range, | 890 KeyAccumulator* keys, uint32_t range, |
841 PropertyFilter filter, uint32_t offset) final { | 891 PropertyFilter filter, uint32_t offset) final { |
842 ElementsAccessorSubclass::CollectElementIndicesImpl( | 892 ElementsAccessorSubclass::CollectElementIndicesImpl( |
843 object, backing_store, keys, range, filter, offset); | 893 object, backing_store, keys, range, filter, offset); |
844 } | 894 } |
845 | 895 |
846 static void CollectElementIndicesImpl(Handle<JSObject> object, | 896 static void CollectElementIndicesImpl(Handle<JSObject> object, |
847 Handle<FixedArrayBase> backing_store, | 897 Handle<FixedArrayBase> backing_store, |
(...skipping 917 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1765 TYPED_ARRAYS(TYPED_ARRAY_CASE) | 1815 TYPED_ARRAYS(TYPED_ARRAY_CASE) |
1766 #undef TYPED_ARRAY_CASE | 1816 #undef TYPED_ARRAY_CASE |
1767 // This function is currently only used for JSArrays with non-zero | 1817 // This function is currently only used for JSArrays with non-zero |
1768 // length. | 1818 // length. |
1769 UNREACHABLE(); | 1819 UNREACHABLE(); |
1770 break; | 1820 break; |
1771 case NO_ELEMENTS: | 1821 case NO_ELEMENTS: |
1772 break; // Nothing to do. | 1822 break; // Nothing to do. |
1773 } | 1823 } |
1774 } | 1824 } |
1825 | |
1826 static Maybe<bool> CollectValuesOrEntriesImpl( | |
1827 Isolate* isolate, Handle<JSObject> object, | |
1828 Handle<FixedArray> values_or_entries, bool get_entries, int* nof_items, | |
1829 PropertyFilter filter) { | |
1830 int count = 0; | |
1831 Handle<FixedArray> elements(FixedArray::cast(object->elements())); | |
1832 for (uint32_t index = 0; index < elements->length(); ++index) { | |
1833 Handle<Object> value(elements->get(index), isolate); | |
1834 if (value->IsTheHole()) continue; | |
1835 if (get_entries) { | |
1836 value = MakeEntryPair(isolate, index, value); | |
1837 } | |
1838 values_or_entries->set(count++, *value); | |
1839 } | |
1840 *nof_items = count; | |
1841 return Just(true); | |
Camillo Bruni
2016/03/15 17:59:52
I think you can combine the FixedArray and FixedDo
caitp (gmail)
2016/03/15 18:24:30
Done
| |
1842 } | |
1775 }; | 1843 }; |
1776 | 1844 |
1777 | 1845 |
1778 class FastPackedSmiElementsAccessor | 1846 class FastPackedSmiElementsAccessor |
1779 : public FastSmiOrObjectElementsAccessor< | 1847 : public FastSmiOrObjectElementsAccessor< |
1780 FastPackedSmiElementsAccessor, | 1848 FastPackedSmiElementsAccessor, |
1781 ElementsKindTraits<FAST_SMI_ELEMENTS> > { | 1849 ElementsKindTraits<FAST_SMI_ELEMENTS> > { |
1782 public: | 1850 public: |
1783 explicit FastPackedSmiElementsAccessor(const char* name) | 1851 explicit FastPackedSmiElementsAccessor(const char* name) |
1784 : FastSmiOrObjectElementsAccessor< | 1852 : FastSmiOrObjectElementsAccessor< |
(...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1914 case NO_ELEMENTS: | 1982 case NO_ELEMENTS: |
1915 #define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) case TYPE##_ELEMENTS: | 1983 #define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) case TYPE##_ELEMENTS: |
1916 TYPED_ARRAYS(TYPED_ARRAY_CASE) | 1984 TYPED_ARRAYS(TYPED_ARRAY_CASE) |
1917 #undef TYPED_ARRAY_CASE | 1985 #undef TYPED_ARRAY_CASE |
1918 // This function is currently only used for JSArrays with non-zero | 1986 // This function is currently only used for JSArrays with non-zero |
1919 // length. | 1987 // length. |
1920 UNREACHABLE(); | 1988 UNREACHABLE(); |
1921 break; | 1989 break; |
1922 } | 1990 } |
1923 } | 1991 } |
1992 | |
1993 static Maybe<bool> CollectValuesOrEntriesImpl( | |
1994 Isolate* isolate, Handle<JSObject> object, | |
1995 Handle<FixedArray> values_or_entries, bool get_entries, int* nof_items, | |
1996 PropertyFilter filter) { | |
1997 int count = 0; | |
1998 Handle<FixedDoubleArray> elements( | |
1999 FixedDoubleArray::cast(object->elements())); | |
2000 for (uint32_t index = 0; index < elements->length(); ++index) { | |
2001 if (elements->is_the_hole(index)) continue; | |
2002 Handle<Object> value = FixedDoubleArray::get(*elements, index, isolate); | |
2003 if (get_entries) { | |
2004 value = MakeEntryPair(isolate, index, value); | |
2005 } | |
2006 values_or_entries->set(count++, *value); | |
2007 } | |
2008 *nof_items = count; | |
2009 return Just(true); | |
2010 } | |
1924 }; | 2011 }; |
1925 | 2012 |
1926 | 2013 |
1927 class FastPackedDoubleElementsAccessor | 2014 class FastPackedDoubleElementsAccessor |
1928 : public FastDoubleElementsAccessor< | 2015 : public FastDoubleElementsAccessor< |
1929 FastPackedDoubleElementsAccessor, | 2016 FastPackedDoubleElementsAccessor, |
1930 ElementsKindTraits<FAST_DOUBLE_ELEMENTS> > { | 2017 ElementsKindTraits<FAST_DOUBLE_ELEMENTS> > { |
1931 public: | 2018 public: |
1932 explicit FastPackedDoubleElementsAccessor(const char* name) | 2019 explicit FastPackedDoubleElementsAccessor(const char* name) |
1933 : FastDoubleElementsAccessor< | 2020 : FastDoubleElementsAccessor< |
(...skipping 99 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2033 static void AddElementsToKeyAccumulatorImpl(Handle<JSObject> receiver, | 2120 static void AddElementsToKeyAccumulatorImpl(Handle<JSObject> receiver, |
2034 KeyAccumulator* accumulator, | 2121 KeyAccumulator* accumulator, |
2035 AddKeyConversion convert) { | 2122 AddKeyConversion convert) { |
2036 Handle<FixedArrayBase> elements(receiver->elements()); | 2123 Handle<FixedArrayBase> elements(receiver->elements()); |
2037 uint32_t length = AccessorClass::GetCapacityImpl(*receiver, *elements); | 2124 uint32_t length = AccessorClass::GetCapacityImpl(*receiver, *elements); |
2038 for (uint32_t i = 0; i < length; i++) { | 2125 for (uint32_t i = 0; i < length; i++) { |
2039 Handle<Object> value = AccessorClass::GetImpl(*elements, i); | 2126 Handle<Object> value = AccessorClass::GetImpl(*elements, i); |
2040 accumulator->AddKey(value, convert); | 2127 accumulator->AddKey(value, convert); |
2041 } | 2128 } |
2042 } | 2129 } |
2130 | |
2131 static Maybe<bool> CollectValuesOrEntriesImpl( | |
2132 Isolate* isolate, Handle<JSObject> object, | |
2133 Handle<FixedArray> values_or_entries, bool get_entries, int* nof_items, | |
2134 PropertyFilter filter) { | |
2135 int count = 0; | |
2136 if ((filter & ONLY_CONFIGURABLE) == 0) { | |
2137 Handle<FixedArrayBase> elements(object->elements()); | |
2138 uint32_t length = AccessorClass::GetCapacityImpl(*object, *elements); | |
2139 for (uint32_t index = 0; index < length; ++index) { | |
2140 Handle<Object> value = AccessorClass::GetImpl(*elements, index); | |
2141 if (get_entries) { | |
2142 value = MakeEntryPair(isolate, index, value); | |
2143 } | |
2144 values_or_entries->set(count++, *value); | |
2145 } | |
2146 } | |
2147 *nof_items = count; | |
2148 return Just(true); | |
2149 } | |
2043 }; | 2150 }; |
2044 | 2151 |
2045 | 2152 |
2046 | 2153 |
2047 #define FIXED_ELEMENTS_ACCESSOR(Type, type, TYPE, ctype, size) \ | 2154 #define FIXED_ELEMENTS_ACCESSOR(Type, type, TYPE, ctype, size) \ |
2048 typedef TypedElementsAccessor<TYPE##_ELEMENTS > \ | 2155 typedef TypedElementsAccessor<TYPE##_ELEMENTS > \ |
2049 Fixed##Type##ElementsAccessor; | 2156 Fixed##Type##ElementsAccessor; |
2050 | 2157 |
2051 TYPED_ARRAYS(FIXED_ELEMENTS_ACCESSOR) | 2158 TYPED_ARRAYS(FIXED_ELEMENTS_ACCESSOR) |
2052 #undef FIXED_ELEMENTS_ACCESSOR | 2159 #undef FIXED_ELEMENTS_ACCESSOR |
(...skipping 770 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2823 } | 2930 } |
2824 } | 2931 } |
2825 | 2932 |
2826 DCHECK(j == result_len); | 2933 DCHECK(j == result_len); |
2827 return result_array; | 2934 return result_array; |
2828 } | 2935 } |
2829 | 2936 |
2830 ElementsAccessor** ElementsAccessor::elements_accessors_ = NULL; | 2937 ElementsAccessor** ElementsAccessor::elements_accessors_ = NULL; |
2831 } // namespace internal | 2938 } // namespace internal |
2832 } // namespace v8 | 2939 } // namespace v8 |
OLD | NEW |