Decoupling MarkDescriptorArray as much as possible from the ContentArray.
Review URL: https://chromiumcodereview.appspot.com/10417030 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@11683 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
This commit is contained in:
parent
3a2d4c88f4
commit
75f35d3fe1
@ -1872,17 +1872,16 @@ void Marker<T>::MarkDescriptorArray(DescriptorArray* descriptors) {
|
|||||||
if (!base_marker()->MarkObjectAndPush(descriptors)) return;
|
if (!base_marker()->MarkObjectAndPush(descriptors)) return;
|
||||||
FixedArray* contents = FixedArray::cast(
|
FixedArray* contents = FixedArray::cast(
|
||||||
descriptors->get(DescriptorArray::kContentArrayIndex));
|
descriptors->get(DescriptorArray::kContentArrayIndex));
|
||||||
ASSERT(contents->length() >= 2);
|
|
||||||
ASSERT(Marking::IsWhite(Marking::MarkBitFrom(contents)));
|
ASSERT(Marking::IsWhite(Marking::MarkBitFrom(contents)));
|
||||||
base_marker()->MarkObjectWithoutPush(contents);
|
base_marker()->MarkObjectWithoutPush(contents);
|
||||||
|
|
||||||
// Contents contains (value, details) pairs. If the descriptor contains a
|
// If the descriptor contains a transition (value is a Map), we don't mark the
|
||||||
// transition (value is a Map), we don't mark the value as live. It might
|
// value as live. It might be set to the NULL_DESCRIPTOR in
|
||||||
// be set to the NULL_DESCRIPTOR in ClearNonLiveTransitions later.
|
// ClearNonLiveTransitions later.
|
||||||
for (int i = 0; i < contents->length(); i += 2) {
|
for (int i = 0; i < descriptors->number_of_descriptors(); ++i) {
|
||||||
PropertyDetails details(Smi::cast(contents->get(i + 1)));
|
PropertyDetails details(descriptors->GetDetails(i));
|
||||||
|
Object** slot = descriptors->GetValueSlot(i);
|
||||||
|
|
||||||
Object** slot = contents->data_start() + i;
|
|
||||||
if (!(*slot)->IsHeapObject()) continue;
|
if (!(*slot)->IsHeapObject()) continue;
|
||||||
HeapObject* value = HeapObject::cast(*slot);
|
HeapObject* value = HeapObject::cast(*slot);
|
||||||
|
|
||||||
|
@ -1939,6 +1939,12 @@ String* DescriptorArray::GetKey(int descriptor_number) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Object** DescriptorArray::GetValueSlot(int descriptor_number) {
|
||||||
|
ASSERT(descriptor_number < number_of_descriptors());
|
||||||
|
return GetContentArray()->data_start() + ToValueIndex(descriptor_number);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
Object* DescriptorArray::GetValue(int descriptor_number) {
|
Object* DescriptorArray::GetValue(int descriptor_number) {
|
||||||
ASSERT(descriptor_number < number_of_descriptors());
|
ASSERT(descriptor_number < number_of_descriptors());
|
||||||
return GetContentArray()->get(ToValueIndex(descriptor_number));
|
return GetContentArray()->get(ToValueIndex(descriptor_number));
|
||||||
|
@ -6069,7 +6069,10 @@ MaybeObject* DescriptorArray::RemoveTransitions() {
|
|||||||
return new_descriptors;
|
return new_descriptors;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// We need the whiteness witness since sort will reshuffle the entries in the
|
||||||
|
// descriptor array. If the descriptor array were to be black, the shuffling
|
||||||
|
// would move a slot that was already recorded as pointing into an evacuation
|
||||||
|
// candidate. This would result in missing updates upon evacuation.
|
||||||
void DescriptorArray::SortUnchecked(const WhitenessWitness& witness) {
|
void DescriptorArray::SortUnchecked(const WhitenessWitness& witness) {
|
||||||
// In-place heap sort.
|
// In-place heap sort.
|
||||||
int len = number_of_descriptors();
|
int len = number_of_descriptors();
|
||||||
|
@ -2453,6 +2453,7 @@ class DescriptorArray: public FixedArray {
|
|||||||
// Accessors for fetching instance descriptor at descriptor number.
|
// Accessors for fetching instance descriptor at descriptor number.
|
||||||
inline String* GetKey(int descriptor_number);
|
inline String* GetKey(int descriptor_number);
|
||||||
inline Object* GetValue(int descriptor_number);
|
inline Object* GetValue(int descriptor_number);
|
||||||
|
inline Object** GetValueSlot(int descriptor_number);
|
||||||
inline PropertyDetails GetDetails(int descriptor_number);
|
inline PropertyDetails GetDetails(int descriptor_number);
|
||||||
inline PropertyType GetType(int descriptor_number);
|
inline PropertyType GetType(int descriptor_number);
|
||||||
inline int GetFieldIndex(int descriptor_number);
|
inline int GetFieldIndex(int descriptor_number);
|
||||||
@ -2463,6 +2464,14 @@ class DescriptorArray: public FixedArray {
|
|||||||
inline bool IsTransitionOnly(int descriptor_number);
|
inline bool IsTransitionOnly(int descriptor_number);
|
||||||
inline bool IsNullDescriptor(int descriptor_number);
|
inline bool IsNullDescriptor(int descriptor_number);
|
||||||
|
|
||||||
|
// WhitenessWitness is used to prove that a specific descriptor array is white
|
||||||
|
// (unmarked), so incremental write barriers can be skipped because the
|
||||||
|
// marking invariant cannot be broken and slots pointing into evacuation
|
||||||
|
// candidates will be discovered when the object is scanned. A witness is
|
||||||
|
// always stack-allocated right after creating a descriptor array. By
|
||||||
|
// allocating a witness, incremental marking is globally disabled. The witness
|
||||||
|
// is then passed along wherever needed to statically prove that the
|
||||||
|
// descriptor array is known to be white.
|
||||||
class WhitenessWitness {
|
class WhitenessWitness {
|
||||||
public:
|
public:
|
||||||
inline explicit WhitenessWitness(DescriptorArray* array);
|
inline explicit WhitenessWitness(DescriptorArray* array);
|
||||||
|
Loading…
Reference in New Issue
Block a user