]>
git.saurik.com Git - apple/javascriptcore.git/blob - runtime/GCActivityCallback.cpp
   2  * Copyright (C) 2010 Apple Inc. All rights reserved. 
   4  * Redistribution and use in source and binary forms, with or without 
   5  * modification, are permitted provided that the following conditions 
   8  * 1.  Redistributions of source code must retain the above copyright 
   9  *     notice, this list of conditions and the following disclaimer.  
  10  * 2.  Redistributions in binary form must reproduce the above copyright 
  11  *     notice, this list of conditions and the following disclaimer in the 
  12  *     documentation and/or other materials provided with the distribution.  
  13  * 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of 
  14  *     its contributors may be used to endorse or promote products derived 
  15  *     from this software without specific prior written permission.  
  17  * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY 
  18  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 
  19  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 
  20  * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY 
  21  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 
  22  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 
  23  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 
  24  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 
  25  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 
  26  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
  30 #include "GCActivityCallback.h" 
  38 #include <wtf/RetainPtr.h> 
  39 #include <wtf/WTFThreadData.h> 
  42 #include <wtf/MainThread.h> 
  47 #if USE(CF) || PLATFORM(QT) || PLATFORM(EFL) 
  50     bool GCActivityCallback::s_shouldCreateGCTimer 
= true; 
  51 #endif // PLATFORM(IOS) 
  53 const double gcTimeSlicePerMB 
= 0.01; // Percentage of CPU time we will spend to reclaim 1 MB 
  54 const double maxGCTimeSlice 
= 0.05; // The maximum amount of CPU time we want to use for opportunistic timer-triggered collections. 
  55 const double timerSlop 
= 2.0; // Fudge factor to avoid performance cost of resetting timer. 
  56 const double pagingTimeOut 
= 0.1; // Time in seconds to allow opportunistic timer to iterate over all blocks to see if the Heap is paged out. 
  57 const double hour 
= 60 * 60; 
  60 DefaultGCActivityCallback::DefaultGCActivityCallback(Heap
* heap
) 
  61     : GCActivityCallback(heap
->vm(), CFRunLoopGetCurrent()) 
  66 DefaultGCActivityCallback::DefaultGCActivityCallback(Heap
* heap
, CFRunLoopRef runLoop
) 
  67     : GCActivityCallback(heap
->vm(), runLoop
) 
  72 DefaultGCActivityCallback::DefaultGCActivityCallback(Heap
* heap
) 
  73     : GCActivityCallback(heap
->vm()) 
  78 DefaultGCActivityCallback::DefaultGCActivityCallback(Heap
* heap
) 
  79     : GCActivityCallback(heap
->vm(), WTF::isMainThread()) 
  85 void DefaultGCActivityCallback::doWork() 
  87     Heap
* heap 
= &m_vm
->heap
; 
  91     APIEntryShim 
shim(m_vm
); 
  93     double startTime 
= WTF::monotonicallyIncreasingTime(); 
  94     if (heap
->isPagedOut(startTime 
+ pagingTimeOut
)) { 
  95         heap
->activityCallback()->cancel(); 
  96         heap
->increaseLastGCLength(pagingTimeOut
); 
 100     heap
->collect(Heap::DoNotSweep
); 
 104 void DefaultGCActivityCallback::scheduleTimer(double newDelay
) 
 106     if (newDelay 
* timerSlop 
> m_delay
) 
 108     double delta 
= m_delay 
- newDelay
; 
 110     CFRunLoopTimerSetNextFireDate(m_timer
.get(), CFRunLoopTimerGetNextFireDate(m_timer
.get()) - delta
); 
 113 void DefaultGCActivityCallback::cancelTimer() 
 116     CFRunLoopTimerSetNextFireDate(m_timer
.get(), CFAbsoluteTimeGetCurrent() + s_decade
); 
 120 void DefaultGCActivityCallback::scheduleTimer(double newDelay
) 
 122     if (newDelay 
* timerSlop 
> m_delay
) 
 125     m_timer
.start(newDelay 
* 1000, this); 
 128 void DefaultGCActivityCallback::cancelTimer() 
 134 void DefaultGCActivityCallback::scheduleTimer(double newDelay
) 
 136     if (newDelay 
* timerSlop 
> m_delay
) 
 143     m_timer 
= add(newDelay
, this); 
 146 void DefaultGCActivityCallback::cancelTimer() 
 153 void DefaultGCActivityCallback::didAllocate(size_t bytes
) 
 159     ASSERT(WTF::isMainThread()); 
 162     // The first byte allocated in an allocation cycle will report 0 bytes to didAllocate.  
 163     // We pretend it's one byte so that we don't ignore this allocation entirely. 
 166     Heap
* heap 
= static_cast<Heap
*>(&m_vm
->heap
); 
 167     double gcTimeSlice 
= std::min((static_cast<double>(bytes
) / MB
) * gcTimeSlicePerMB
, maxGCTimeSlice
); 
 168     double newDelay 
= heap
->lastGCLength() / gcTimeSlice
; 
 169     scheduleTimer(newDelay
); 
 172 void DefaultGCActivityCallback::willCollect() 
 177 void DefaultGCActivityCallback::cancel() 
 184 DefaultGCActivityCallback::DefaultGCActivityCallback(Heap
* heap
) 
 185     : GCActivityCallback(heap
->vm()) 
 189 void DefaultGCActivityCallback::doWork() 
 193 void DefaultGCActivityCallback::didAllocate(size_t) 
 197 void DefaultGCActivityCallback::willCollect() 
 201 void DefaultGCActivityCallback::cancel()