Gcstress bug fix: Transition arrays may get smaller during gc.

R=verwaest@chromium.org

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

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@20694 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
This commit is contained in:
mvstanton@chromium.org 2014-04-11 14:25:00 +00:00
parent ac659f3882
commit 1a8f611e42
3 changed files with 18 additions and 10 deletions

View File

@ -4987,8 +4987,7 @@ static void EnsureHasTransitionArray(Handle<Map> map) {
transitions = TransitionArray::Allocate(map->GetIsolate(), 0); transitions = TransitionArray::Allocate(map->GetIsolate(), 0);
transitions->set_back_pointer_storage(map->GetBackPointer()); transitions->set_back_pointer_storage(map->GetBackPointer());
} else if (!map->transitions()->IsFullTransitionArray()) { } else if (!map->transitions()->IsFullTransitionArray()) {
transitions = TransitionArray::ExtendToFullTransitionArray( transitions = TransitionArray::ExtendToFullTransitionArray(map);
handle(map->transitions()));
} else { } else {
return; return;
} }

View File

@ -86,17 +86,24 @@ Handle<TransitionArray> TransitionArray::NewWith(Handle<Map> map,
Handle<TransitionArray> TransitionArray::ExtendToFullTransitionArray( Handle<TransitionArray> TransitionArray::ExtendToFullTransitionArray(
Handle<TransitionArray> array) { Handle<Map> containing_map) {
ASSERT(!array->IsFullTransitionArray()); ASSERT(!containing_map->transitions()->IsFullTransitionArray());
int nof = array->number_of_transitions(); int nof = containing_map->transitions()->number_of_transitions();
Handle<TransitionArray> result = Allocate(array->GetIsolate(), nof);
if (nof == 1) { // A transition array may shrink during GC.
Handle<TransitionArray> result = Allocate(containing_map->GetIsolate(), nof);
DisallowHeapAllocation no_gc;
int new_nof = containing_map->transitions()->number_of_transitions();
if (new_nof != nof) {
ASSERT(new_nof == 0);
result->Shrink(ToKeyIndex(0));
} else if (nof == 1) {
result->NoIncrementalWriteBarrierCopyFrom( result->NoIncrementalWriteBarrierCopyFrom(
*array, kSimpleTransitionIndex, 0); containing_map->transitions(), kSimpleTransitionIndex, 0);
} }
result->set_back_pointer_storage(array->back_pointer_storage()); result->set_back_pointer_storage(
containing_map->transitions()->back_pointer_storage());
return result; return result;
} }

View File

@ -95,8 +95,10 @@ class TransitionArray: public FixedArray {
inline int number_of_entries() { return number_of_transitions(); } inline int number_of_entries() { return number_of_transitions(); }
// Creates a FullTransitionArray from a SimpleTransitionArray in
// containing_map.
static Handle<TransitionArray> ExtendToFullTransitionArray( static Handle<TransitionArray> ExtendToFullTransitionArray(
Handle<TransitionArray> array); Handle<Map> containing_map);
// Create a transition array, copying from the owning map if it already has // Create a transition array, copying from the owning map if it already has
// one, otherwise creating a new one according to flag. // one, otherwise creating a new one according to flag.