Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(354)

Side by Side Diff: src/elements.cc

Issue 204603003: ElementsAccessor::SetLength() handlified. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Created 6 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/elements.h ('k') | src/objects.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 142 matching lines...) Expand 10 before | Expand all | Expand 10 after
153 if (element->IsSmi() && element == key) return true; 153 if (element->IsSmi() && element == key) return true;
154 if (element->IsString() && 154 if (element->IsString() &&
155 key->IsString() && String::cast(element)->Equals(String::cast(key))) { 155 key->IsString() && String::cast(element)->Equals(String::cast(key))) {
156 return true; 156 return true;
157 } 157 }
158 } 158 }
159 return false; 159 return false;
160 } 160 }
161 161
162 162
163 static Failure* ThrowArrayLengthRangeError(Heap* heap) { 163 static Handle<Object> ThrowArrayLengthRangeError(Isolate* isolate) {
164 HandleScope scope(heap->isolate()); 164 isolate->Throw(
165 return heap->isolate()->Throw( 165 *isolate->factory()->NewRangeError("invalid_array_length",
166 *heap->isolate()->factory()->NewRangeError("invalid_array_length", 166 HandleVector<Object>(NULL, 0)));
167 HandleVector<Object>(NULL, 0))); 167 return Handle<Object>();
168 } 168 }
169 169
170 170
171 static void CopyObjectToObjectElements(FixedArrayBase* from_base, 171 static void CopyObjectToObjectElements(FixedArrayBase* from_base,
172 ElementsKind from_kind, 172 ElementsKind from_kind,
173 uint32_t from_start, 173 uint32_t from_start,
174 FixedArrayBase* to_base, 174 FixedArrayBase* to_base,
175 ElementsKind to_kind, 175 ElementsKind to_kind,
176 uint32_t to_start, 176 uint32_t to_start,
177 int raw_copy_size) { 177 int raw_copy_size) {
(...skipping 552 matching lines...) Expand 10 before | Expand all | Expand 10 after
730 } 730 }
731 731
732 MUST_USE_RESULT static AccessorPair* GetAccessorPairImpl( 732 MUST_USE_RESULT static AccessorPair* GetAccessorPairImpl(
733 Object* receiver, 733 Object* receiver,
734 JSObject* obj, 734 JSObject* obj,
735 uint32_t key, 735 uint32_t key,
736 FixedArrayBase* backing_store) { 736 FixedArrayBase* backing_store) {
737 return NULL; 737 return NULL;
738 } 738 }
739 739
740 // TODO(ishell): Temporary wrapper until handlified.
741 MUST_USE_RESULT virtual Handle<Object> SetLength( 740 MUST_USE_RESULT virtual Handle<Object> SetLength(
742 Handle<JSArray> array, 741 Handle<JSArray> array,
743 Handle<Object> length) { 742 Handle<Object> length) {
744 CALL_HEAP_FUNCTION(array->GetIsolate(), 743 Isolate* isolate = array->GetIsolate();
745 SetLength(*array, *length), 744 return ElementsAccessorSubclass::SetLengthImpl(
746 Object); 745 array, length, handle(array->elements(), isolate));
747 } 746 }
748 747
749 MUST_USE_RESULT virtual MaybeObject* SetLength(JSArray* array, 748 MUST_USE_RESULT static Handle<Object> SetLengthImpl(
750 Object* length) { 749 Handle<JSObject> obj,
751 return ElementsAccessorSubclass::SetLengthImpl( 750 Handle<Object> length,
752 array, length, array->elements()); 751 Handle<FixedArrayBase> backing_store);
753 }
754
755 MUST_USE_RESULT static MaybeObject* SetLengthImpl(
756 JSObject* obj,
757 Object* length,
758 FixedArrayBase* backing_store);
759 752
760 MUST_USE_RESULT virtual MaybeObject* SetCapacityAndLength( 753 MUST_USE_RESULT virtual MaybeObject* SetCapacityAndLength(
761 JSArray* array, 754 JSArray* array,
762 int capacity, 755 int capacity,
763 int length) { 756 int length) {
764 return ElementsAccessorSubclass::SetFastElementsCapacityAndLength( 757 return ElementsAccessorSubclass::SetFastElementsCapacityAndLength(
765 array, 758 array,
766 capacity, 759 capacity,
767 length); 760 length);
768 } 761 }
(...skipping 218 matching lines...) Expand 10 before | Expand all | Expand 10 after
987 SetFastElementsCapacityAndLength(array, new_capacity, length); 980 SetFastElementsCapacityAndLength(array, new_capacity, length);
988 if (result->IsFailure()) return result; 981 if (result->IsFailure()) return result;
989 array->ValidateElements(); 982 array->ValidateElements();
990 return length_object; 983 return length_object;
991 } 984 }
992 985
993 // Request conversion to slow elements. 986 // Request conversion to slow elements.
994 return array->GetHeap()->undefined_value(); 987 return array->GetHeap()->undefined_value();
995 } 988 }
996 989
990 // TODO(ishell): Temporary wrapper until handlified.
991 static Handle<Object> SetLengthWithoutNormalize(
992 Handle<FixedArrayBase> backing_store,
993 Handle<JSArray> array,
994 Handle<Object> length_object,
995 uint32_t length) {
996 CALL_HEAP_FUNCTION(array->GetIsolate(),
997 SetLengthWithoutNormalize(
998 *backing_store, *array, *length_object, length),
999 Object);
1000 }
1001
997 static MaybeObject* DeleteCommon(JSObject* obj, 1002 static MaybeObject* DeleteCommon(JSObject* obj,
998 uint32_t key, 1003 uint32_t key,
999 JSReceiver::DeleteMode mode) { 1004 JSReceiver::DeleteMode mode) {
1000 ASSERT(obj->HasFastSmiOrObjectElements() || 1005 ASSERT(obj->HasFastSmiOrObjectElements() ||
1001 obj->HasFastDoubleElements() || 1006 obj->HasFastDoubleElements() ||
1002 obj->HasFastArgumentsElements()); 1007 obj->HasFastArgumentsElements());
1003 Heap* heap = obj->GetHeap(); 1008 Heap* heap = obj->GetHeap();
1004 Object* elements = obj->elements(); 1009 Object* elements = obj->elements();
1005 if (elements == heap->empty_fixed_array()) { 1010 if (elements == heap->empty_fixed_array()) {
1006 return heap->true_value(); 1011 return heap->true_value();
(...skipping 368 matching lines...) Expand 10 before | Expand all | Expand 10 after
1375 MUST_USE_RESULT static PropertyType GetTypeImpl( 1380 MUST_USE_RESULT static PropertyType GetTypeImpl(
1376 Object* receiver, 1381 Object* receiver,
1377 JSObject* obj, 1382 JSObject* obj,
1378 uint32_t key, 1383 uint32_t key,
1379 FixedArrayBase* backing_store) { 1384 FixedArrayBase* backing_store) {
1380 return 1385 return
1381 key < AccessorClass::GetCapacityImpl(backing_store) 1386 key < AccessorClass::GetCapacityImpl(backing_store)
1382 ? FIELD : NONEXISTENT; 1387 ? FIELD : NONEXISTENT;
1383 } 1388 }
1384 1389
1385 MUST_USE_RESULT static MaybeObject* SetLengthImpl( 1390 MUST_USE_RESULT static Handle<Object> SetLengthImpl(
1386 JSObject* obj, 1391 Handle<JSObject> obj,
1387 Object* length, 1392 Handle<Object> length,
1388 FixedArrayBase* backing_store) { 1393 Handle<FixedArrayBase> backing_store) {
1389 // External arrays do not support changing their length. 1394 // External arrays do not support changing their length.
1390 UNREACHABLE(); 1395 UNREACHABLE();
1391 return obj; 1396 return obj;
1392 } 1397 }
1393 1398
1394 MUST_USE_RESULT virtual MaybeObject* Delete(JSObject* obj, 1399 MUST_USE_RESULT virtual MaybeObject* Delete(JSObject* obj,
1395 uint32_t key, 1400 uint32_t key,
1396 JSReceiver::DeleteMode mode) { 1401 JSReceiver::DeleteMode mode) {
1397 // External arrays always ignore deletes. 1402 // External arrays always ignore deletes.
1398 return obj->GetHeap()->true_value(); 1403 return obj->GetHeap()->true_value();
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after
1486 } 1491 }
1487 } 1492 }
1488 } 1493 }
1489 1494
1490 // Update the number of elements. 1495 // Update the number of elements.
1491 dict->ElementsRemoved(removed_entries); 1496 dict->ElementsRemoved(removed_entries);
1492 } 1497 }
1493 return length_object; 1498 return length_object;
1494 } 1499 }
1495 1500
1501 // TODO(ishell): Temporary wrapper until handlified.
1502 MUST_USE_RESULT static Handle<Object> SetLengthWithoutNormalize(
1503 Handle<FixedArrayBase> store,
1504 Handle<JSArray> array,
1505 Handle<Object> length_object,
1506 uint32_t length) {
1507 CALL_HEAP_FUNCTION(array->GetIsolate(),
1508 SetLengthWithoutNormalize(
1509 *store, *array, *length_object, length),
1510 Object);
1511 }
1512
1496 MUST_USE_RESULT static MaybeObject* DeleteCommon( 1513 MUST_USE_RESULT static MaybeObject* DeleteCommon(
1497 JSObject* obj, 1514 JSObject* obj,
1498 uint32_t key, 1515 uint32_t key,
1499 JSReceiver::DeleteMode mode) { 1516 JSReceiver::DeleteMode mode) {
1500 Isolate* isolate = obj->GetIsolate(); 1517 Isolate* isolate = obj->GetIsolate();
1501 Heap* heap = isolate->heap(); 1518 Heap* heap = isolate->heap();
1502 FixedArray* backing_store = FixedArray::cast(obj->elements()); 1519 FixedArray* backing_store = FixedArray::cast(obj->elements());
1503 bool is_arguments = 1520 bool is_arguments =
1504 (obj->GetElementsKind() == SLOPPY_ARGUMENTS_ELEMENTS); 1521 (obj->GetElementsKind() == SLOPPY_ARGUMENTS_ELEMENTS);
1505 if (is_arguments) { 1522 if (is_arguments) {
(...skipping 223 matching lines...) Expand 10 before | Expand all | Expand 10 after
1729 if (!probe->IsTheHole()) { 1746 if (!probe->IsTheHole()) {
1730 return NULL; 1747 return NULL;
1731 } else { 1748 } else {
1732 // If not aliased, check the arguments. 1749 // If not aliased, check the arguments.
1733 FixedArray* arguments = FixedArray::cast(parameter_map->get(1)); 1750 FixedArray* arguments = FixedArray::cast(parameter_map->get(1));
1734 return ElementsAccessor::ForArray(arguments)->GetAccessorPair( 1751 return ElementsAccessor::ForArray(arguments)->GetAccessorPair(
1735 receiver, obj, key, arguments); 1752 receiver, obj, key, arguments);
1736 } 1753 }
1737 } 1754 }
1738 1755
1739 MUST_USE_RESULT static MaybeObject* SetLengthImpl( 1756 MUST_USE_RESULT static Handle<Object> SetLengthImpl(
1740 JSObject* obj, 1757 Handle<JSObject> obj,
1741 Object* length, 1758 Handle<Object> length,
1742 FixedArrayBase* parameter_map) { 1759 Handle<FixedArrayBase> parameter_map) {
1743 // TODO(mstarzinger): This was never implemented but will be used once we 1760 // TODO(mstarzinger): This was never implemented but will be used once we
1744 // correctly implement [[DefineOwnProperty]] on arrays. 1761 // correctly implement [[DefineOwnProperty]] on arrays.
1745 UNIMPLEMENTED(); 1762 UNIMPLEMENTED();
1746 return obj; 1763 return obj;
1747 } 1764 }
1748 1765
1749 MUST_USE_RESULT virtual MaybeObject* Delete(JSObject* obj, 1766 MUST_USE_RESULT virtual MaybeObject* Delete(JSObject* obj,
1750 uint32_t key, 1767 uint32_t key,
1751 JSReceiver::DeleteMode mode) { 1768 JSReceiver::DeleteMode mode) {
1752 FixedArray* parameter_map = FixedArray::cast(obj->elements()); 1769 FixedArray* parameter_map = FixedArray::cast(obj->elements());
(...skipping 91 matching lines...) Expand 10 before | Expand all | Expand 10 after
1844 1861
1845 void ElementsAccessor::TearDown() { 1862 void ElementsAccessor::TearDown() {
1846 #define ACCESSOR_DELETE(Class, Kind, Store) delete elements_accessors_[Kind]; 1863 #define ACCESSOR_DELETE(Class, Kind, Store) delete elements_accessors_[Kind];
1847 ELEMENTS_LIST(ACCESSOR_DELETE) 1864 ELEMENTS_LIST(ACCESSOR_DELETE)
1848 #undef ACCESSOR_DELETE 1865 #undef ACCESSOR_DELETE
1849 elements_accessors_ = NULL; 1866 elements_accessors_ = NULL;
1850 } 1867 }
1851 1868
1852 1869
1853 template <typename ElementsAccessorSubclass, typename ElementsKindTraits> 1870 template <typename ElementsAccessorSubclass, typename ElementsKindTraits>
1854 MUST_USE_RESULT MaybeObject* ElementsAccessorBase<ElementsAccessorSubclass, 1871 MUST_USE_RESULT Handle<Object> ElementsAccessorBase<ElementsAccessorSubclass,
1855 ElementsKindTraits>:: 1872 ElementsKindTraits>::
1856 SetLengthImpl(JSObject* obj, 1873 SetLengthImpl(Handle<JSObject> obj,
1857 Object* length, 1874 Handle<Object> length,
1858 FixedArrayBase* backing_store) { 1875 Handle<FixedArrayBase> backing_store) {
1859 JSArray* array = JSArray::cast(obj); 1876 Isolate* isolate = obj->GetIsolate();
1877 Handle<JSArray> array = Handle<JSArray>::cast(obj);
1860 1878
1861 // Fast case: The new length fits into a Smi. 1879 // Fast case: The new length fits into a Smi.
1862 MaybeObject* maybe_smi_length = length->ToSmi(); 1880 Handle<Object> smi_length = Object::ToSmi(isolate, length);
1863 Object* smi_length = Smi::FromInt(0); 1881
1864 if (maybe_smi_length->ToObject(&smi_length) && smi_length->IsSmi()) { 1882 if (!smi_length.is_null() && smi_length->IsSmi()) {
1865 const int value = Smi::cast(smi_length)->value(); 1883 const int value = Handle<Smi>::cast(smi_length)->value();
1866 if (value >= 0) { 1884 if (value >= 0) {
1867 Object* new_length; 1885 Handle<Object> new_length = ElementsAccessorSubclass::
1868 MaybeObject* result = ElementsAccessorSubclass::
1869 SetLengthWithoutNormalize(backing_store, array, smi_length, value); 1886 SetLengthWithoutNormalize(backing_store, array, smi_length, value);
1870 if (!result->ToObject(&new_length)) return result; 1887 RETURN_IF_EMPTY_HANDLE_VALUE(isolate, new_length, new_length);
1888
1871 // even though the proposed length was a smi, new_length could 1889 // even though the proposed length was a smi, new_length could
1872 // still be a heap number because SetLengthWithoutNormalize doesn't 1890 // still be a heap number because SetLengthWithoutNormalize doesn't
1873 // allow the array length property to drop below the index of 1891 // allow the array length property to drop below the index of
1874 // non-deletable elements. 1892 // non-deletable elements.
1875 ASSERT(new_length->IsSmi() || new_length->IsHeapNumber() || 1893 ASSERT(new_length->IsSmi() || new_length->IsHeapNumber() ||
1876 new_length->IsUndefined()); 1894 new_length->IsUndefined());
1877 if (new_length->IsSmi()) { 1895 if (new_length->IsSmi()) {
1878 array->set_length(Smi::cast(new_length)); 1896 array->set_length(*Handle<Smi>::cast(new_length));
1879 return array; 1897 return array;
1880 } else if (new_length->IsHeapNumber()) { 1898 } else if (new_length->IsHeapNumber()) {
1881 array->set_length(new_length); 1899 array->set_length(*new_length);
1882 return array; 1900 return array;
1883 } 1901 }
1884 } else { 1902 } else {
1885 return ThrowArrayLengthRangeError(array->GetHeap()); 1903 return ThrowArrayLengthRangeError(isolate);
1886 } 1904 }
1887 } 1905 }
1888 1906
1889 // Slow case: The new length does not fit into a Smi or conversion 1907 // Slow case: The new length does not fit into a Smi or conversion
1890 // to slow elements is needed for other reasons. 1908 // to slow elements is needed for other reasons.
1891 if (length->IsNumber()) { 1909 if (length->IsNumber()) {
1892 uint32_t value; 1910 uint32_t value;
1893 if (length->ToArrayIndex(&value)) { 1911 if (length->ToArrayIndex(&value)) {
1894 SeededNumberDictionary* dictionary; 1912 Handle<SeededNumberDictionary> dictionary =
1895 MaybeObject* maybe_object = array->NormalizeElements(); 1913 JSObject::NormalizeElements(array);
1896 if (!maybe_object->To(&dictionary)) return maybe_object; 1914 RETURN_IF_EMPTY_HANDLE_VALUE(isolate, dictionary, dictionary);
1897 Object* new_length; 1915
1898 MaybeObject* result = DictionaryElementsAccessor:: 1916 Handle<Object> new_length = DictionaryElementsAccessor::
1899 SetLengthWithoutNormalize(dictionary, array, length, value); 1917 SetLengthWithoutNormalize(dictionary, array, length, value);
1900 if (!result->ToObject(&new_length)) return result; 1918 RETURN_IF_EMPTY_HANDLE_VALUE(isolate, new_length, new_length);
1919
1901 ASSERT(new_length->IsNumber()); 1920 ASSERT(new_length->IsNumber());
1902 array->set_length(new_length); 1921 array->set_length(*new_length);
1903 return array; 1922 return array;
1904 } else { 1923 } else {
1905 return ThrowArrayLengthRangeError(array->GetHeap()); 1924 return ThrowArrayLengthRangeError(isolate);
1906 } 1925 }
1907 } 1926 }
1908 1927
1928 Factory* factory = isolate->factory();
1909 // Fall-back case: The new length is not a number so make the array 1929 // Fall-back case: The new length is not a number so make the array
1910 // size one and set only element to length. 1930 // size one and set only element to length.
1911 FixedArray* new_backing_store; 1931 Handle<FixedArray> new_backing_store = factory->NewFixedArray(1);
1912 MaybeObject* maybe_obj = array->GetHeap()->AllocateFixedArray(1); 1932 new_backing_store->set(0, *length);
1913 if (!maybe_obj->To(&new_backing_store)) return maybe_obj; 1933 factory->SetContent(array, new_backing_store);
1914 new_backing_store->set(0, length);
1915 { MaybeObject* result = array->SetContent(new_backing_store);
1916 if (result->IsFailure()) return result;
1917 }
1918 return array; 1934 return array;
1919 } 1935 }
1920 1936
1921 1937
1922 Handle<Object> ArrayConstructInitializeElements(Handle<JSArray> array, 1938 Handle<Object> ArrayConstructInitializeElements(Handle<JSArray> array,
1923 Arguments* args) { 1939 Arguments* args) {
1924 // Optimize the case where there is one argument and the argument is a 1940 // Optimize the case where there is one argument and the argument is a
1925 // small smi. 1941 // small smi.
1926 if (args->length() == 1) { 1942 if (args->length() == 1) {
1927 Handle<Object> obj = args->at<Object>(0); 1943 Handle<Object> obj = args->at<Object>(0);
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after
2005 UNREACHABLE(); 2021 UNREACHABLE();
2006 break; 2022 break;
2007 } 2023 }
2008 2024
2009 array->set_elements(*elms); 2025 array->set_elements(*elms);
2010 array->set_length(Smi::FromInt(number_of_elements)); 2026 array->set_length(Smi::FromInt(number_of_elements));
2011 return array; 2027 return array;
2012 } 2028 }
2013 2029
2014 } } // namespace v8::internal 2030 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/elements.h ('k') | src/objects.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698