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

Side by Side Diff: src/objects.cc

Issue 22934006: Handlify JSObject::DeepCopy method. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Addressed comments by Toon Verwaest. Created 7 years, 3 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/objects.h ('k') | src/runtime.cc » ('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 2013 the V8 project authors. All rights reserved. 1 // Copyright 2013 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 5594 matching lines...) Expand 10 before | Expand all | Expand 10 after
5605 MaybeObject* maybe_copy = map()->Copy(); 5605 MaybeObject* maybe_copy = map()->Copy();
5606 if (!maybe_copy->To(&new_map)) return maybe_copy; 5606 if (!maybe_copy->To(&new_map)) return maybe_copy;
5607 new_map->set_is_observed(true); 5607 new_map->set_is_observed(true);
5608 } 5608 }
5609 set_map(new_map); 5609 set_map(new_map);
5610 5610
5611 return heap->undefined_value(); 5611 return heap->undefined_value();
5612 } 5612 }
5613 5613
5614 5614
5615 MUST_USE_RESULT MaybeObject* JSObject::DeepCopy(Isolate* isolate) { 5615 // TODO(mstarzinger): Temporary wrapper until handlified.
5616 static Handle<Object> NewStorageFor(Isolate* isolate,
5617 Handle<Object> object,
5618 Representation representation) {
5619 Heap* heap = isolate->heap();
5620 CALL_HEAP_FUNCTION(isolate,
5621 object->AllocateNewStorageFor(heap, representation),
5622 Object);
5623 }
5624
5625
5626 Handle<JSObject> JSObject::Copy(Handle<JSObject> object) {
5627 Isolate* isolate = object->GetIsolate();
5628 CALL_HEAP_FUNCTION(isolate,
5629 isolate->heap()->CopyJSObject(*object), JSObject);
5630 }
5631
5632
5633 Handle<JSObject> JSObject::DeepCopy(Handle<JSObject> object) {
5634 Isolate* isolate = object->GetIsolate();
5616 StackLimitCheck check(isolate); 5635 StackLimitCheck check(isolate);
5617 if (check.HasOverflowed()) return isolate->StackOverflow(); 5636 if (check.HasOverflowed()) {
5618 5637 isolate->StackOverflow();
5619 if (map()->is_deprecated()) { 5638 return Handle<JSObject>::null();
5620 MaybeObject* maybe_failure = MigrateInstance();
5621 if (maybe_failure->IsFailure()) return maybe_failure;
5622 } 5639 }
5623 5640
5624 Heap* heap = isolate->heap(); 5641 if (object->map()->is_deprecated()) {
5625 Object* result; 5642 MigrateInstance(object);
5626 { MaybeObject* maybe_result = heap->CopyJSObject(this);
5627 if (!maybe_result->ToObject(&result)) return maybe_result;
5628 } 5643 }
5629 JSObject* copy = JSObject::cast(result); 5644
5645 Handle<JSObject> copy = Copy(object);
5630 5646
5631 // Deep copy local properties. 5647 // Deep copy local properties.
5632 if (copy->HasFastProperties()) { 5648 if (copy->HasFastProperties()) {
5633 DescriptorArray* descriptors = copy->map()->instance_descriptors(); 5649 Handle<DescriptorArray> descriptors(copy->map()->instance_descriptors());
5634 int limit = copy->map()->NumberOfOwnDescriptors(); 5650 int limit = copy->map()->NumberOfOwnDescriptors();
5635 for (int i = 0; i < limit; i++) { 5651 for (int i = 0; i < limit; i++) {
5636 PropertyDetails details = descriptors->GetDetails(i); 5652 PropertyDetails details = descriptors->GetDetails(i);
5637 if (details.type() != FIELD) continue; 5653 if (details.type() != FIELD) continue;
5638 int index = descriptors->GetFieldIndex(i); 5654 int index = descriptors->GetFieldIndex(i);
5639 Object* value = RawFastPropertyAt(index); 5655 Handle<Object> value(object->RawFastPropertyAt(index), isolate);
5640 if (value->IsJSObject()) { 5656 if (value->IsJSObject()) {
5641 JSObject* js_object = JSObject::cast(value); 5657 value = DeepCopy(Handle<JSObject>::cast(value));
5642 MaybeObject* maybe_copy = js_object->DeepCopy(isolate); 5658 RETURN_IF_EMPTY_HANDLE_VALUE(isolate, value, Handle<JSObject>());
5643 if (!maybe_copy->To(&value)) return maybe_copy;
5644 } else { 5659 } else {
5645 Representation representation = details.representation(); 5660 Representation representation = details.representation();
5646 MaybeObject* maybe_storage = 5661 value = NewStorageFor(isolate, value, representation);
5647 value->AllocateNewStorageFor(heap, representation);
5648 if (!maybe_storage->To(&value)) return maybe_storage;
5649 } 5662 }
5650 copy->FastPropertyAtPut(index, value); 5663 copy->FastPropertyAtPut(index, *value);
5651 } 5664 }
5652 } else { 5665 } else {
5653 { MaybeObject* maybe_result = 5666 Handle<FixedArray> names =
5654 heap->AllocateFixedArray(copy->NumberOfLocalProperties()); 5667 isolate->factory()->NewFixedArray(copy->NumberOfLocalProperties());
5655 if (!maybe_result->ToObject(&result)) return maybe_result; 5668 copy->GetLocalPropertyNames(*names, 0);
5656 }
5657 FixedArray* names = FixedArray::cast(result);
5658 copy->GetLocalPropertyNames(names, 0);
5659 for (int i = 0; i < names->length(); i++) { 5669 for (int i = 0; i < names->length(); i++) {
5660 ASSERT(names->get(i)->IsString()); 5670 ASSERT(names->get(i)->IsString());
5661 String* key_string = String::cast(names->get(i)); 5671 Handle<String> key_string(String::cast(names->get(i)));
5662 PropertyAttributes attributes = 5672 PropertyAttributes attributes =
5663 copy->GetLocalPropertyAttribute(key_string); 5673 copy->GetLocalPropertyAttribute(*key_string);
5664 // Only deep copy fields from the object literal expression. 5674 // Only deep copy fields from the object literal expression.
5665 // In particular, don't try to copy the length attribute of 5675 // In particular, don't try to copy the length attribute of
5666 // an array. 5676 // an array.
5667 if (attributes != NONE) continue; 5677 if (attributes != NONE) continue;
5668 Object* value = 5678 Handle<Object> value(
5669 copy->GetProperty(key_string, &attributes)->ToObjectUnchecked(); 5679 copy->GetProperty(*key_string, &attributes)->ToObjectUnchecked(),
5680 isolate);
5670 if (value->IsJSObject()) { 5681 if (value->IsJSObject()) {
5671 JSObject* js_object = JSObject::cast(value); 5682 Handle<Object> result = DeepCopy(Handle<JSObject>::cast(value));
5672 { MaybeObject* maybe_result = js_object->DeepCopy(isolate); 5683 RETURN_IF_EMPTY_HANDLE_VALUE(isolate, result, Handle<JSObject>());
5673 if (!maybe_result->ToObject(&result)) return maybe_result; 5684 // Creating object copy for literals. No strict mode needed.
5674 } 5685 CHECK_NOT_EMPTY_HANDLE(isolate, SetProperty(
5675 { MaybeObject* maybe_result = 5686 copy, key_string, result, NONE, kNonStrictMode));
5676 // Creating object copy for literals. No strict mode needed.
5677 copy->SetProperty(key_string, result, NONE, kNonStrictMode);
5678 if (!maybe_result->ToObject(&result)) return maybe_result;
5679 }
5680 } 5687 }
5681 } 5688 }
5682 } 5689 }
5683 5690
5684 // Deep copy local elements. 5691 // Deep copy local elements.
5685 // Pixel elements cannot be created using an object literal. 5692 // Pixel elements cannot be created using an object literal.
5686 ASSERT(!copy->HasExternalArrayElements()); 5693 ASSERT(!copy->HasExternalArrayElements());
5687 switch (copy->GetElementsKind()) { 5694 switch (copy->GetElementsKind()) {
5688 case FAST_SMI_ELEMENTS: 5695 case FAST_SMI_ELEMENTS:
5689 case FAST_ELEMENTS: 5696 case FAST_ELEMENTS:
5690 case FAST_HOLEY_SMI_ELEMENTS: 5697 case FAST_HOLEY_SMI_ELEMENTS:
5691 case FAST_HOLEY_ELEMENTS: { 5698 case FAST_HOLEY_ELEMENTS: {
5692 FixedArray* elements = FixedArray::cast(copy->elements()); 5699 Handle<FixedArray> elements(FixedArray::cast(copy->elements()));
5693 if (elements->map() == heap->fixed_cow_array_map()) { 5700 if (elements->map() == isolate->heap()->fixed_cow_array_map()) {
5694 isolate->counters()->cow_arrays_created_runtime()->Increment(); 5701 isolate->counters()->cow_arrays_created_runtime()->Increment();
5695 #ifdef DEBUG 5702 #ifdef DEBUG
5696 for (int i = 0; i < elements->length(); i++) { 5703 for (int i = 0; i < elements->length(); i++) {
5697 ASSERT(!elements->get(i)->IsJSObject()); 5704 ASSERT(!elements->get(i)->IsJSObject());
5698 } 5705 }
5699 #endif 5706 #endif
5700 } else { 5707 } else {
5701 for (int i = 0; i < elements->length(); i++) { 5708 for (int i = 0; i < elements->length(); i++) {
5702 Object* value = elements->get(i); 5709 Handle<Object> value(elements->get(i), isolate);
5703 ASSERT(value->IsSmi() || 5710 ASSERT(value->IsSmi() ||
5704 value->IsTheHole() || 5711 value->IsTheHole() ||
5705 (IsFastObjectElementsKind(copy->GetElementsKind()))); 5712 (IsFastObjectElementsKind(copy->GetElementsKind())));
5706 if (value->IsJSObject()) { 5713 if (value->IsJSObject()) {
5707 JSObject* js_object = JSObject::cast(value); 5714 Handle<Object> result = DeepCopy(Handle<JSObject>::cast(value));
5708 { MaybeObject* maybe_result = js_object->DeepCopy(isolate); 5715 RETURN_IF_EMPTY_HANDLE_VALUE(isolate, result, Handle<JSObject>());
5709 if (!maybe_result->ToObject(&result)) return maybe_result; 5716 elements->set(i, *result);
5710 }
5711 elements->set(i, result);
5712 } 5717 }
5713 } 5718 }
5714 } 5719 }
5715 break; 5720 break;
5716 } 5721 }
5717 case DICTIONARY_ELEMENTS: { 5722 case DICTIONARY_ELEMENTS: {
5718 SeededNumberDictionary* element_dictionary = copy->element_dictionary(); 5723 Handle<SeededNumberDictionary> element_dictionary(
5724 copy->element_dictionary());
5719 int capacity = element_dictionary->Capacity(); 5725 int capacity = element_dictionary->Capacity();
5720 for (int i = 0; i < capacity; i++) { 5726 for (int i = 0; i < capacity; i++) {
5721 Object* k = element_dictionary->KeyAt(i); 5727 Object* k = element_dictionary->KeyAt(i);
5722 if (element_dictionary->IsKey(k)) { 5728 if (element_dictionary->IsKey(k)) {
5723 Object* value = element_dictionary->ValueAt(i); 5729 Handle<Object> value(element_dictionary->ValueAt(i), isolate);
5724 if (value->IsJSObject()) { 5730 if (value->IsJSObject()) {
5725 JSObject* js_object = JSObject::cast(value); 5731 Handle<Object> result = DeepCopy(Handle<JSObject>::cast(value));
5726 { MaybeObject* maybe_result = js_object->DeepCopy(isolate); 5732 RETURN_IF_EMPTY_HANDLE_VALUE(isolate, result, Handle<JSObject>());
5727 if (!maybe_result->ToObject(&result)) return maybe_result; 5733 element_dictionary->ValueAtPut(i, *result);
5728 }
5729 element_dictionary->ValueAtPut(i, result);
5730 } 5734 }
5731 } 5735 }
5732 } 5736 }
5733 break; 5737 break;
5734 } 5738 }
5735 case NON_STRICT_ARGUMENTS_ELEMENTS: 5739 case NON_STRICT_ARGUMENTS_ELEMENTS:
5736 UNIMPLEMENTED(); 5740 UNIMPLEMENTED();
5737 break; 5741 break;
5738 case EXTERNAL_PIXEL_ELEMENTS: 5742 case EXTERNAL_PIXEL_ELEMENTS:
5739 case EXTERNAL_BYTE_ELEMENTS: 5743 case EXTERNAL_BYTE_ELEMENTS:
(...skipping 10237 matching lines...) Expand 10 before | Expand all | Expand 10 after
15977 #define ERROR_MESSAGES_TEXTS(C, T) T, 15981 #define ERROR_MESSAGES_TEXTS(C, T) T,
15978 static const char* error_messages_[] = { 15982 static const char* error_messages_[] = {
15979 ERROR_MESSAGES_LIST(ERROR_MESSAGES_TEXTS) 15983 ERROR_MESSAGES_LIST(ERROR_MESSAGES_TEXTS)
15980 }; 15984 };
15981 #undef ERROR_MESSAGES_TEXTS 15985 #undef ERROR_MESSAGES_TEXTS
15982 return error_messages_[reason]; 15986 return error_messages_[reason];
15983 } 15987 }
15984 15988
15985 15989
15986 } } // namespace v8::internal 15990 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/objects.h ('k') | src/runtime.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698