Commit 49961d11 authored by bmeurer@chromium.org's avatar bmeurer@chromium.org

Handlify DescriptorArray::Merge().

R=svenpanne@chromium.org

Review URL: https://codereview.chromium.org/169363002

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@20339 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
parent bd353dc3
...@@ -2726,8 +2726,8 @@ Handle<Map> Map::GeneralizeRepresentation(Handle<Map> old_map, ...@@ -2726,8 +2726,8 @@ Handle<Map> Map::GeneralizeRepresentation(Handle<Map> old_map,
} }
Handle<DescriptorArray> new_descriptors = DescriptorArray::Merge( Handle<DescriptorArray> new_descriptors = DescriptorArray::Merge(
updated_descriptors, verbatim, valid, descriptors, modify_index, updated, verbatim, valid, descriptors, modify_index,
store_mode, old_descriptors); store_mode, old_map);
ASSERT(store_mode == ALLOW_AS_CONSTANT || ASSERT(store_mode == ALLOW_AS_CONSTANT ||
new_descriptors->GetDetails(modify_index).type() == FIELD); new_descriptors->GetDetails(modify_index).type() == FIELD);
...@@ -7969,97 +7969,89 @@ void DescriptorArray::CopyFrom(int dst_index, ...@@ -7969,97 +7969,89 @@ void DescriptorArray::CopyFrom(int dst_index,
} }
Handle<DescriptorArray> DescriptorArray::Merge(Handle<DescriptorArray> desc, // Creates a new descriptor array by merging the descriptor array of |right_map|
int verbatim, // into the (at least partly) updated descriptor array of |left_map|.
int valid,
int new_size,
int modify_index,
StoreMode store_mode,
Handle<DescriptorArray> other) {
CALL_HEAP_FUNCTION(desc->GetIsolate(),
desc->Merge(verbatim, valid, new_size, modify_index,
store_mode, *other),
DescriptorArray);
}
// Generalize the |other| descriptor array by merging it into the (at least
// partly) updated |this| descriptor array.
// The method merges two descriptor array in three parts. Both descriptor arrays // The method merges two descriptor array in three parts. Both descriptor arrays
// are identical up to |verbatim|. They also overlap in keys up to |valid|. // are identical up to |verbatim|. They also overlap in keys up to |valid|.
// Between |verbatim| and |valid|, the resulting descriptor type as well as the // Between |verbatim| and |valid|, the resulting descriptor type as well as the
// representation are generalized from both |this| and |other|. Beyond |valid|, // representation are generalized from both |left_map| and |right_map|. Beyond
// the descriptors are copied verbatim from |other| up to |new_size|. // |valid|, the descriptors are copied verbatim from |right_map| up to
// In case of incompatible types, the type and representation of |other| is // |new_size|.
// In case of incompatible types, the type and representation of |right_map| is
// used. // used.
MaybeObject* DescriptorArray::Merge(int verbatim, Handle<DescriptorArray> DescriptorArray::Merge(Handle<Map> left_map,
int verbatim,
int valid, int valid,
int new_size, int new_size,
int modify_index, int modify_index,
StoreMode store_mode, StoreMode store_mode,
DescriptorArray* other) { Handle<Map> right_map) {
ASSERT(verbatim <= valid); ASSERT(verbatim <= valid);
ASSERT(valid <= new_size); ASSERT(valid <= new_size);
DescriptorArray* result;
// Allocate a new descriptor array large enough to hold the required // Allocate a new descriptor array large enough to hold the required
// descriptors, with minimally the exact same size as this descriptor array. // descriptors, with minimally the exact same size as this descriptor array.
MaybeObject* maybe_descriptors = DescriptorArray::Allocate( Factory* factory = left_map->GetIsolate()->factory();
GetIsolate(), new_size, Handle<DescriptorArray> left(left_map->instance_descriptors());
Max(new_size, other->number_of_descriptors()) - new_size); Handle<DescriptorArray> right(right_map->instance_descriptors());
if (!maybe_descriptors->To(&result)) return maybe_descriptors; Handle<DescriptorArray> result = factory->NewDescriptorArray(
ASSERT(result->length() > length() || new_size, Max(new_size, right->number_of_descriptors()) - new_size);
ASSERT(result->length() > left->length() ||
result->NumberOfSlackDescriptors() > 0 || result->NumberOfSlackDescriptors() > 0 ||
result->number_of_descriptors() == other->number_of_descriptors()); result->number_of_descriptors() == right->number_of_descriptors());
ASSERT(result->number_of_descriptors() == new_size); ASSERT(result->number_of_descriptors() == new_size);
DescriptorArray::WhitenessWitness witness(result);
int descriptor; int descriptor;
// 0 -> |verbatim| // 0 -> |verbatim|
int current_offset = 0; int current_offset = 0;
for (descriptor = 0; descriptor < verbatim; descriptor++) { for (descriptor = 0; descriptor < verbatim; descriptor++) {
if (GetDetails(descriptor).type() == FIELD) current_offset++; if (left->GetDetails(descriptor).type() == FIELD) current_offset++;
result->CopyFrom(descriptor, other, descriptor, witness); Descriptor d(right->GetKey(descriptor),
right->GetValue(descriptor),
right->GetDetails(descriptor));
result->Set(descriptor, &d);
} }
// |verbatim| -> |valid| // |verbatim| -> |valid|
for (; descriptor < valid; descriptor++) { for (; descriptor < valid; descriptor++) {
Name* key = GetKey(descriptor); PropertyDetails left_details = left->GetDetails(descriptor);
PropertyDetails details = GetDetails(descriptor); PropertyDetails right_details = right->GetDetails(descriptor);
PropertyDetails other_details = other->GetDetails(descriptor); if (left_details.type() == FIELD || right_details.type() == FIELD ||
if (details.type() == FIELD || other_details.type() == FIELD ||
(store_mode == FORCE_FIELD && descriptor == modify_index) || (store_mode == FORCE_FIELD && descriptor == modify_index) ||
(details.type() == CONSTANT && (left_details.type() == CONSTANT &&
other_details.type() == CONSTANT && right_details.type() == CONSTANT &&
GetValue(descriptor) != other->GetValue(descriptor))) { left->GetValue(descriptor) != right->GetValue(descriptor))) {
Representation representation = Representation representation = left_details.representation().generalize(
details.representation().generalize(other_details.representation()); right_details.representation());
FieldDescriptor d(key, FieldDescriptor d(left->GetKey(descriptor),
current_offset++, current_offset++,
other_details.attributes(), right_details.attributes(),
representation); representation);
result->Set(descriptor, &d, witness); result->Set(descriptor, &d);
} else { } else {
result->CopyFrom(descriptor, other, descriptor, witness); Descriptor d(right->GetKey(descriptor),
right->GetValue(descriptor),
right_details);
result->Set(descriptor, &d);
} }
} }
// |valid| -> |new_size| // |valid| -> |new_size|
for (; descriptor < new_size; descriptor++) { for (; descriptor < new_size; descriptor++) {
PropertyDetails details = other->GetDetails(descriptor); PropertyDetails right_details = right->GetDetails(descriptor);
if (details.type() == FIELD || if (right_details.type() == FIELD ||
(store_mode == FORCE_FIELD && descriptor == modify_index)) { (store_mode == FORCE_FIELD && descriptor == modify_index)) {
Name* key = other->GetKey(descriptor); FieldDescriptor d(right->GetKey(descriptor),
FieldDescriptor d(key,
current_offset++, current_offset++,
details.attributes(), right_details.attributes(),
details.representation()); right_details.representation());
result->Set(descriptor, &d, witness); result->Set(descriptor, &d);
} else { } else {
result->CopyFrom(descriptor, other, descriptor, witness); Descriptor d(right->GetKey(descriptor),
right->GetValue(descriptor),
right_details);
result->Set(descriptor, &d);
} }
} }
......
...@@ -3439,19 +3439,14 @@ class DescriptorArray: public FixedArray { ...@@ -3439,19 +3439,14 @@ class DescriptorArray: public FixedArray {
DescriptorArray* src, DescriptorArray* src,
int src_index, int src_index,
const WhitenessWitness&); const WhitenessWitness&);
static Handle<DescriptorArray> Merge(Handle<DescriptorArray> desc, static Handle<DescriptorArray> Merge(Handle<Map> left_map,
int verbatim, int verbatim,
int valid, int valid,
int new_size, int new_size,
int modify_index, int modify_index,
StoreMode store_mode, StoreMode store_mode,
Handle<DescriptorArray> other); Handle<Map> right_map)
MUST_USE_RESULT MaybeObject* Merge(int verbatim, V8_WARN_UNUSED_RESULT;
int valid,
int new_size,
int modify_index,
StoreMode store_mode,
DescriptorArray* other);
bool IsMoreGeneralThan(int verbatim, bool IsMoreGeneralThan(int verbatim,
int valid, int valid,
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment