From 2159b470d7f375275009a3e231f65ed53dd862c1 Mon Sep 17 00:00:00 2001 From: "jkummerow@chromium.org" Date: Mon, 25 Mar 2013 15:18:52 +0000 Subject: [PATCH] Fix crash involving zombie maps escaping from the JSON parser's underground lab Zapping is required since transition arrays contain weak references to maps: At the end of a GC cycle, ClearNonLiveTransitions removes references to dead maps from transition arrays. If a marked transition array with weak (dead) references is replaced by another transition array before the end of the GC cycle, dead references are not removed from the replaced transition array. If the replaced transition array is kept alive by a handle, marking will crash when trying to mark the first reference to a dead map. Review URL: https://codereview.chromium.org/12987013 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@14063 ce2b1a6d-e550-0410-aec6-3dcde31c8c00 --- src/objects-inl.h | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/src/objects-inl.h b/src/objects-inl.h index b2bad48d4a..2bed396aa2 100644 --- a/src/objects-inl.h +++ b/src/objects-inl.h @@ -1490,7 +1490,7 @@ MaybeObject* JSObject::AddFastPropertyUsingMap(Map* map) { bool JSObject::TryTransitionToField(Handle object, Handle key) { if (!object->map()->HasTransitionArray()) return false; - Handle transitions(object->map()->transitions()); + TransitionArray* transitions = object->map()->transitions(); int transition = transitions->Search(*key); if (transition == TransitionArray::kNotFound) return false; PropertyDetails target_details = transitions->GetTargetDetails(transition); @@ -4128,9 +4128,12 @@ TransitionArray* Map::transitions() { void Map::set_transitions(TransitionArray* transition_array, WriteBarrierMode mode) { - // In release mode, only run this code if verify_heap is on. - if (Heap::ShouldZapGarbage() && HasTransitionArray()) { - CHECK(transitions() != transition_array); + // Transition arrays are not shared. When one is replaced, it should not + // keep referenced objects alive, so we zap it. + // When there is another reference to the array somewhere (e.g. a handle), + // not zapping turns from a waste of memory into a source of crashes. + if (HasTransitionArray()) { + ASSERT(transitions() != transition_array); ZapTransitions(); }