Changeset 53455 in webkit


Ignore:
Timestamp:
Jan 18, 2010 11:00:38 PM (14 years ago)
Author:
ggaren@apple.com
Message:

2010-01-18 Geoffrey Garen <ggaren@apple.com>

Reviewed by Oliver Hunt.

REGRESSION (52082): Crash on worker thread when reloading http://radnan.public.iastate.edu/procedural/
https://bugs.webkit.org/show_bug.cgi?id=33826

This bug was caused by a GC-protected object being destroyed early by
Heap::destroy. Clients of the GC protect APIs (reasonably) expect pointers
to GC-protected memory to be valid.

The solution is to do two passes of tear-down in Heap::destroy. The first
pass tears down all unprotected objects. The second pass ASSERTs that all
previously protected objects are now unprotected, and then tears down
all perviously protected objects. These two passes simulate the two passes
that would have been required to free a protected object during normal GC.


  • API/JSContextRef.cpp: Removed some ASSERTs that have moved into Heap.
  • runtime/Collector.cpp: (JSC::Heap::destroy): Moved ASSERTs to here. (JSC::Heap::freeBlock): Tidied up the use of didShrink by moving its setter to the function that does the shrinking. (JSC::Heap::freeBlocks): Implemented above algorithm. (JSC::Heap::shrinkBlocks): Tidied up the use of didShrink.

2010-01-18 Geoffrey Garen <ggaren@apple.com>

Reviewed by Oliver Hunt.

REGRESSION (52082): Crash on worker thread when reloading http://radnan.public.iastate.edu/procedural/
https://bugs.webkit.org/show_bug.cgi?id=33826

Test: fast/workers/worker-gc2.html

  • bindings/js/WorkerScriptController.cpp: (WebCore::WorkerScriptController::~WorkerScriptController): Removed some ASSERTs that have moved to JavaScriptCore.

2010-01-18 Geoffrey Garen <ggaren@apple.com>

Reviewed by Oliver Hunt.

REGRESSION (52082): Crash on worker thread when reloading http://radnan.public.iastate.edu/procedural/
https://bugs.webkit.org/show_bug.cgi?id=33826


Added a test for this edge case.

  • fast/workers/resources/worker-gc2.js: Added. (Dummy):
  • fast/workers/worker-gc2.html: Added.
Location:
trunk
Files:
2 added
6 edited

Legend:

Unmodified
Added
Removed
  • trunk/JavaScriptCore/API/JSContextRef.cpp

    r52856 r53455  
    128128    if (globalData.refCount() == 2) { // One reference is held by JSGlobalObject, another added by JSGlobalContextRetain().
    129129        // The last reference was released, this is our last chance to collect.
    130         ASSERT(!globalData.heap.protectedObjectCount());
    131         ASSERT(!globalData.heap.isBusy());
    132130        globalData.heap.destroy();
    133131    } else
  • trunk/JavaScriptCore/ChangeLog

    r53454 r53455  
     12010-01-18  Geoffrey Garen  <ggaren@apple.com>
     2
     3        Reviewed by Oliver Hunt.
     4
     5        REGRESSION (52082): Crash on worker thread when reloading http://radnan.public.iastate.edu/procedural/
     6        https://bugs.webkit.org/show_bug.cgi?id=33826
     7
     8        This bug was caused by a GC-protected object being destroyed early by
     9        Heap::destroy. Clients of the GC protect APIs (reasonably) expect pointers
     10        to GC-protected memory to be valid.
     11
     12        The solution is to do two passes of tear-down in Heap::destroy. The first
     13        pass tears down all unprotected objects. The second pass ASSERTs that all
     14        previously protected objects are now unprotected, and then tears down
     15        all perviously protected objects. These two passes simulate the two passes
     16        that would have been required to free a protected object during normal GC.
     17       
     18        * API/JSContextRef.cpp: Removed some ASSERTs that have moved into Heap.
     19
     20        * runtime/Collector.cpp:
     21        (JSC::Heap::destroy): Moved ASSERTs to here.
     22        (JSC::Heap::freeBlock): Tidied up the use of didShrink by moving its
     23        setter to the function that does the shrinking.
     24        (JSC::Heap::freeBlocks): Implemented above algorithm.
     25        (JSC::Heap::shrinkBlocks): Tidied up the use of didShrink.
     26
    1272010-01-18  Gavin Barraclough  <barraclough@apple.com>
    228
  • trunk/JavaScriptCore/runtime/Collector.cpp

    r52791 r53455  
    187187        return;
    188188
     189    ASSERT(!m_globalData->dynamicGlobalObject);
     190    ASSERT(!isBusy());
     191   
    189192    // The global object is not GC protected at this point, so sweeping may delete it
    190193    // (and thus the global data) before other objects that may use the global data.
     
    291294NEVER_INLINE void Heap::freeBlock(size_t block)
    292295{
     296    m_heap.didShrink = true;
     297
    293298    ObjectIterator it(m_heap, block);
    294299    ObjectIterator end(m_heap, block + 1);
     
    330335void Heap::freeBlocks()
    331336{
    332     while (m_heap.usedBlocks)
    333         freeBlock(0);
     337    ProtectCountSet protectedValuesCopy = m_protectedValues;
     338
     339    clearMarkBits();
     340    markProtectedObjects(m_globalData->markStack);
     341
     342    m_heap.nextCell = 0;
     343    m_heap.nextBlock = 0;
     344    DeadObjectIterator it(m_heap, m_heap.nextBlock, m_heap.nextCell);
     345    DeadObjectIterator end(m_heap, m_heap.usedBlocks);
     346    for ( ; it != end; ++it)
     347        (*it)->~JSCell();
     348
     349    ASSERT(!protectedObjectCount());
     350
     351    ProtectCountSet::iterator protectedValuesEnd = protectedValuesCopy.end();
     352    for (ProtectCountSet::iterator protectedValuesIt = protectedValuesCopy.begin(); protectedValuesIt != protectedValuesEnd; ++protectedValuesIt)
     353        protectedValuesIt->first->~JSCell();
     354
     355    for (size_t block = 0; block < m_heap.usedBlocks; ++block)
     356        freeBlockPtr(m_heap.blocks[block]);
     357
    334358    fastFree(m_heap.blocks);
     359
    335360    memset(&m_heap, 0, sizeof(CollectorHeap));
    336361}
     
    441466        if (m_heap.blocks[i]->marked.isEmpty()) {
    442467            freeBlock(i);
    443             m_heap.didShrink = true;
    444468        } else
    445469            ++i;
  • trunk/LayoutTests/ChangeLog

    r53453 r53455  
     12010-01-18  Geoffrey Garen  <ggaren@apple.com>
     2
     3        Reviewed by Oliver Hunt.
     4
     5        REGRESSION (52082): Crash on worker thread when reloading http://radnan.public.iastate.edu/procedural/
     6        https://bugs.webkit.org/show_bug.cgi?id=33826
     7       
     8        Added a test for this edge case.
     9
     10        * fast/workers/resources/worker-gc2.js: Added.
     11        (Dummy):
     12        * fast/workers/worker-gc2.html: Added.
     13
    1142010-01-18  Daniel Bates  <dbates@webkit.org>
    215
  • trunk/WebCore/ChangeLog

    r53452 r53455  
     12010-01-18  Geoffrey Garen  <ggaren@apple.com>
     2
     3        Reviewed by Oliver Hunt.
     4
     5        REGRESSION (52082): Crash on worker thread when reloading http://radnan.public.iastate.edu/procedural/
     6        https://bugs.webkit.org/show_bug.cgi?id=33826
     7
     8        Test: fast/workers/worker-gc2.html
     9
     10        * bindings/js/WorkerScriptController.cpp:
     11        (WebCore::WorkerScriptController::~WorkerScriptController): Removed some
     12        ASSERTs that have moved to JavaScriptCore.
     13
    1142010-01-18  Daniel Bates  <dbates@webkit.org>
    215
  • trunk/WebCore/bindings/js/WorkerScriptController.cpp

    r51512 r53455  
    5959{
    6060    m_workerContextWrapper = 0; // Unprotect the global object.
    61 
    62     ASSERT(!m_globalData->heap.protectedObjectCount());
    63     ASSERT(!m_globalData->heap.isBusy());
    6461    m_globalData->heap.destroy();
    6562}
Note: See TracChangeset for help on using the changeset viewer.