Changeset 188100 in webkit


Ignore:
Timestamp:
Aug 6, 2015 5:49:54 PM (9 years ago)
Author:
fpizlo@apple.com
Message:

Lightweight locks should be adaptive
https://bugs.webkit.org/show_bug.cgi?id=147545

Reviewed by Geoffrey Garen.

Source/JavaScriptCore:

  • heap/CopiedBlock.h:

(JSC::CopiedBlock::workListLock):

  • heap/CopiedBlockInlines.h:

(JSC::CopiedBlock::shouldReportLiveBytes):
(JSC::CopiedBlock::reportLiveBytes):

  • heap/CopiedSpace.h:

(JSC::CopiedSpace::CopiedGeneration::CopiedGeneration):

  • heap/CopiedSpaceInlines.h:

(JSC::CopiedSpace::recycleEvacuatedBlock):

  • heap/GCThreadSharedData.h:

(JSC::GCThreadSharedData::getNextBlocksToCopy):

  • heap/ListableHandler.h:

(JSC::ListableHandler::List::addThreadSafe):
(JSC::ListableHandler::List::addNotThreadSafe):

  • heap/SlotVisitorInlines.h:

(JSC::SlotVisitor::copyLater):

  • runtime/TypeProfilerLog.h:

Source/WebCore:

No new tests because no new behavior.

  • bindings/objc/WebScriptObject.mm:

(WebCore::getJSWrapper):
(WebCore::addJSWrapper):
(WebCore::removeJSWrapper):
(WebCore::removeJSWrapperIfRetainCountOne):

  • platform/ios/wak/WAKWindow.mm:

(-[WAKWindow setExposedScrollViewRect:]):
(-[WAKWindow exposedScrollViewRect]):

Source/WebKit2:

  • WebProcess/WebPage/EventDispatcher.cpp:

(WebKit::EventDispatcher::clearQueuedTouchEventsForPage):
(WebKit::EventDispatcher::getQueuedTouchEventsForPage):
(WebKit::EventDispatcher::touchEvent):
(WebKit::EventDispatcher::dispatchTouchEvents):

  • WebProcess/WebPage/EventDispatcher.h:
  • WebProcess/WebPage/ViewUpdateDispatcher.cpp:

(WebKit::ViewUpdateDispatcher::visibleContentRectUpdate):
(WebKit::ViewUpdateDispatcher::dispatchVisibleContentRectUpdate):

  • WebProcess/WebPage/ViewUpdateDispatcher.h:

Source/WTF:

A common idiom in WebKit is to use spinlocks. We use them because the lock acquisition
overhead is lower than system locks and because they take dramatically less space than system
locks. The speed and space advantages of spinlocks can be astonishing: an uncontended spinlock
acquire is up to 10x faster and under microcontention - short critical section with two or
more threads taking turns - spinlocks are up to 100x faster. Spinlocks take only 1 byte or 4
bytes depending on the flavor, while system locks take 64 bytes or more. Clearly, WebKit
should continue to avoid system locks - they are just far too slow and far too big.

But there is a problem with this idiom. System lock implementations will sleep a thread when
it attempts to acquire a lock that is held, while spinlocks will cause the thread to burn CPU.
In WebKit spinlocks, the thread will repeatedly call sched_yield(). This is awesome for
microcontention, but awful when the lock will not be released for a while. In fact, when
critical sections take tens of microseconds or more, the CPU time cost of our spinlocks is
almost 100x more than the CPU time cost of a system lock. This case doesn't arise too
frequently in our current uses of spinlocks, but that's probably because right now there are
places where we make a conscious decision to use system locks - even though they use more
memory and are slower - because we don't want to waste CPU cycles when a thread has to wait a
while to acquire the lock.

The solution is to just implement a modern adaptive mutex in WTF. Luckily, this isn't a new
concept. This patch implements a mutex that is reminiscent of the kinds of low-overhead locks
that JVMs use. The actual implementation here is inspired by some of the ideas from [1]. The
idea is simple: the fast path is an inlined CAS to immediately acquire a lock that isn't held,
the slow path tries some number of spins to acquire the lock, and if that fails, the thread is
put on a queue and put to sleep. The queue is made up of statically allocated thread nodes and
the lock itself is a tagged pointer: either it is just bits telling us the complete lock state
(not held or held) or it is a pointer to the head of a queue of threads waiting to acquire the
lock. This approach gives WTF::Lock three different levels of adaptation: an inlined fast path
if the lock is not contended, a short burst of spinning for microcontention, and a full-blown
queue for critical sections that are held for a long time.

On a locking microbenchmark, this new Lock exhibits the following performance
characteristics:

  • Lock+unlock on an uncontended no-op critical section: 2x slower than SpinLock and 3x faster than a system mutex.
  • Lock+unlock on a contended no-op critical section: 2x slower than SpinLock and 100x faster than a system mutex.
  • CPU time spent in lock() on a lock held for a while: same as system mutex, 90x less than a SpinLock.
  • Memory usage: sizeof(void*), so on 64-bit it's 8x less than a system mutex but 2x worse than a SpinLock.

This patch replaces all uses of SpinLock with Lock, since our critical sections are not
no-ops so if you do basically anything in your critical section, the Lock overhead will be
invisible. Also, in all places where we used SpinLock, we could tolerate 8 bytes of overhead
instead of 4. Performance benchmarking using JSC macrobenchmarks shows no difference, which is
as it should be: the purpose of this change is to reduce CPU time wasted, not wallclock time.
This patch doesn't replace any uses of ByteSpinLock, since we expect that the space benefits
of having a lock that just uses a byte are still better than the CPU wastage benefits of
Lock. But, this work will enable some future work to create locks that will fit in just 1.6
bits: https://bugs.webkit.org/show_bug.cgi?id=147665.

[1] http://www.filpizlo.com/papers/pizlo-pppj2011-fable.pdf

  • WTF.vcxproj/WTF.vcxproj:
  • WTF.xcodeproj/project.pbxproj:
  • benchmarks: Added.
  • benchmarks/LockSpeedTest.cpp: Added.

(main):

  • wtf/CMakeLists.txt:
  • wtf/Lock.cpp: Added.

(WTF::LockBase::lockSlow):
(WTF::LockBase::unlockSlow):

  • wtf/Lock.h: Added.

(WTF::LockBase::lock):
(WTF::LockBase::unlock):
(WTF::LockBase::isHeld):
(WTF::Lock::Lock):

  • wtf/MetaAllocator.cpp:

(WTF::MetaAllocator::release):
(WTF::MetaAllocatorHandle::shrink):
(WTF::MetaAllocator::allocate):
(WTF::MetaAllocator::currentStatistics):
(WTF::MetaAllocator::addFreshFreeSpace):
(WTF::MetaAllocator::debugFreeSpaceSize):

  • wtf/MetaAllocator.h:
  • wtf/SpinLock.h:
  • wtf/ThreadingPthreads.cpp:
  • wtf/ThreadingWin.cpp:
  • wtf/text/AtomicString.cpp:
  • wtf/text/AtomicStringImpl.cpp:

(WTF::AtomicStringTableLocker::AtomicStringTableLocker):

Tools:

  • TestWebKitAPI/CMakeLists.txt:
  • TestWebKitAPI/TestWebKitAPI.vcxproj/TestWebKitAPI.vcxproj:
  • TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj:
  • TestWebKitAPI/Tests/WTF/Lock.cpp: Added.

(TestWebKitAPI::runLockTest):
(TestWebKitAPI::TEST):

Location:
trunk
Files:
5 added
40 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/JavaScriptCore/ChangeLog

    r188099 r188100  
     12015-08-05  Filip Pizlo  <fpizlo@apple.com>
     2
     3        Lightweight locks should be adaptive
     4        https://bugs.webkit.org/show_bug.cgi?id=147545
     5
     6        Reviewed by Geoffrey Garen.
     7
     8        * heap/CopiedBlock.h:
     9        (JSC::CopiedBlock::workListLock):
     10        * heap/CopiedBlockInlines.h:
     11        (JSC::CopiedBlock::shouldReportLiveBytes):
     12        (JSC::CopiedBlock::reportLiveBytes):
     13        * heap/CopiedSpace.h:
     14        (JSC::CopiedSpace::CopiedGeneration::CopiedGeneration):
     15        * heap/CopiedSpaceInlines.h:
     16        (JSC::CopiedSpace::recycleEvacuatedBlock):
     17        * heap/GCThreadSharedData.h:
     18        (JSC::GCThreadSharedData::getNextBlocksToCopy):
     19        * heap/ListableHandler.h:
     20        (JSC::ListableHandler::List::addThreadSafe):
     21        (JSC::ListableHandler::List::addNotThreadSafe):
     22        * heap/SlotVisitorInlines.h:
     23        (JSC::SlotVisitor::copyLater):
     24        * runtime/TypeProfilerLog.h:
     25
    1262015-08-06  Sukolsak Sakshuwong  <sukolsak@gmail.com>
    227
  • trunk/Source/JavaScriptCore/dfg/DFGCommon.cpp

    r183525 r188100  
    3535namespace JSC { namespace DFG {
    3636
    37 static StaticSpinLock crashLock;
     37static StaticLock crashLock;
    3838
    3939void startCrashing()
  • trunk/Source/JavaScriptCore/heap/CopiedBlock.h

    r186397 r188100  
    3232#include <wtf/Atomics.h>
    3333#include <wtf/DoublyLinkedList.h>
    34 #include <wtf/SpinLock.h>
     34#include <wtf/Lock.h>
    3535
    3636namespace JSC {
     
    5555
    5656    unsigned liveBytes();
    57     bool shouldReportLiveBytes(SpinLockHolder&, JSCell* owner);
    58     void reportLiveBytes(SpinLockHolder&, JSCell*, CopyToken, unsigned);
     57    bool shouldReportLiveBytes(LockHolder&, JSCell* owner);
     58    void reportLiveBytes(LockHolder&, JSCell*, CopyToken, unsigned);
    5959    void reportLiveBytesDuringCopying(unsigned);
    6060    void didSurviveGC();
     
    8686    bool hasWorkList();
    8787    CopyWorkList& workList();
    88     SpinLock& workListLock() { return m_workListLock; }
     88    Lock& workListLock() { return m_workListLock; }
    8989
    9090private:
     
    9999    size_t m_capacity;
    100100
    101     SpinLock m_workListLock;
     101    Lock m_workListLock;
    102102    std::unique_ptr<CopyWorkList> m_workList;
    103103
  • trunk/Source/JavaScriptCore/heap/CopiedBlockInlines.h

    r183851 r188100  
    3434namespace JSC {
    3535   
    36 inline bool CopiedBlock::shouldReportLiveBytes(SpinLockHolder&, JSCell* owner)
     36inline bool CopiedBlock::shouldReportLiveBytes(LockHolder&, JSCell* owner)
    3737{
    3838    // We want to add to live bytes if the owner isn't part of the remembered set or
     
    4444}
    4545
    46 inline void CopiedBlock::reportLiveBytes(SpinLockHolder&, JSCell* owner, CopyToken token, unsigned bytes)
     46inline void CopiedBlock::reportLiveBytes(LockHolder&, JSCell* owner, CopyToken token, unsigned bytes)
    4747{
    4848    checkConsistency();
  • trunk/Source/JavaScriptCore/heap/CopiedSpace.cpp

    r188002 r188100  
    192192    {
    193193        // Always put the block into the old gen because it's being promoted!
    194         SpinLockHolder locker(&m_toSpaceLock);
     194        LockHolder locker(&m_toSpaceLock);
    195195        m_oldGen.toSpace->push(block);
    196196        m_blockSet.add(block);
  • trunk/Source/JavaScriptCore/heap/CopiedSpace.h

    r188002 r188100  
    3434#include <wtf/DoublyLinkedList.h>
    3535#include <wtf/HashSet.h>
     36#include <wtf/Lock.h>
    3637#include <wtf/OSAllocator.h>
    3738#include <wtf/PageBlock.h>
    38 #include <wtf/SpinLock.h>
    3939#include <wtf/StdLibExtras.h>
    4040#include <wtf/ThreadingPrimitives.h>
     
    114114    HashSet<CopiedBlock*> m_blockSet;
    115115
    116     SpinLock m_toSpaceLock;
     116    Lock m_toSpaceLock;
    117117
    118118    struct CopiedGeneration {
  • trunk/Source/JavaScriptCore/heap/CopiedSpaceInlines.h

    r188002 r188100  
    9999    ASSERT(!block->m_isPinned);
    100100    {
    101         SpinLockHolder locker(&m_toSpaceLock);
     101        LockHolder locker(&m_toSpaceLock);
    102102        m_blockSet.remove(block);
    103103        if (collectionType == EdenCollection)
  • trunk/Source/JavaScriptCore/heap/GCThreadSharedData.cpp

    r183005 r188100  
    179179{
    180180    {
    181         SpinLockHolder locker(&m_copyLock);
     181        LockHolder locker(&m_copyLock);
    182182        if (m_vm->heap.operationInProgress() == EdenCollection) {
    183183            // Reset the vector to be empty, but don't throw away the backing store.
  • trunk/Source/JavaScriptCore/heap/GCThreadSharedData.h

    r181485 r188100  
    3434#include <condition_variable>
    3535#include <wtf/HashSet.h>
    36 #include <wtf/SpinLock.h>
     36#include <wtf/Lock.h>
    3737#include <wtf/Vector.h>
    3838
     
    9898    HashSet<void*> m_opaqueRoots;
    9999
    100     SpinLock m_copyLock;
     100    Lock m_copyLock;
    101101    Vector<CopiedBlock*> m_blocksToCopy;
    102102    size_t m_copyIndex;
     
    116116inline void GCThreadSharedData::getNextBlocksToCopy(size_t& start, size_t& end)
    117117{
    118     SpinLockHolder locker(&m_copyLock);
     118    LockHolder locker(&m_copyLock);
    119119    start = m_copyIndex;
    120120    end = std::min(m_blocksToCopy.size(), m_copyIndex + s_blockFragmentLength);
  • trunk/Source/JavaScriptCore/heap/ListableHandler.h

    r181485 r188100  
    2222
    2323#include <stdint.h>
     24#include <wtf/Lock.h>
    2425#include <wtf/Locker.h>
    2526#include <wtf/Noncopyable.h>
    26 #include <wtf/SpinLock.h>
    2727#include <wtf/ThreadingPrimitives.h>
    2828
     
    6666        void addThreadSafe(T* handler)
    6767        {
    68             SpinLockHolder locker(&m_lock);
     68            LockHolder locker(&m_lock);
    6969            addNotThreadSafe(handler);
    7070        }
     
    104104        }
    105105       
    106         SpinLock m_lock;
     106        Lock m_lock;
    107107        T* m_first;
    108108    };
  • trunk/Source/JavaScriptCore/heap/MachineStackMarker.cpp

    r188002 r188100  
    569569    // Prevent two VMs from suspending each other's threads at the same time,
    570570    // which can cause deadlock: <rdar://problem/20300842>.
    571     static StaticSpinLock mutex;
    572     std::lock_guard<StaticSpinLock> lock(mutex);
     571    static StaticLock mutex;
     572    std::lock_guard<StaticLock> lock(mutex);
    573573
    574574    *size = 0;
  • trunk/Source/JavaScriptCore/heap/SlotVisitorInlines.h

    r183974 r188100  
    251251    ASSERT(heap()->m_storageSpace.contains(block));
    252252
    253     SpinLockHolder locker(&block->workListLock());
     253    LockHolder locker(&block->workListLock());
    254254    if (heap()->operationInProgress() == FullCollection || block->shouldReportLiveBytes(locker, owner)) {
    255255        m_bytesCopied += bytes;
  • trunk/Source/JavaScriptCore/parser/SourceProvider.cpp

    r181485 r188100  
    2828
    2929#include "JSCInlines.h"
    30 #include <wtf/SpinLock.h>
     30#include <wtf/Lock.h>
    3131#include <wtf/StdLibExtras.h>
    3232
     
    4545}
    4646
    47 static StaticSpinLock providerIdLock;
     47static StaticLock providerIdLock;
    4848
    4949void SourceProvider::getID()
    5050{
    51     SpinLockHolder lock(&providerIdLock);
     51    LockHolder lock(&providerIdLock);
    5252    if (!m_id) {
    5353        static intptr_t nextProviderID = 0;
  • trunk/Source/JavaScriptCore/profiler/ProfilerDatabase.cpp

    r181485 r188100  
    3636static std::atomic<int> databaseCounter;
    3737
    38 static StaticSpinLock registrationLock;
     38static StaticLock registrationLock;
    3939static std::atomic<int> didRegisterAtExit;
    4040static Database* firstDatabase;
     
    139139        atexit(atExitCallback);
    140140   
    141     SpinLockHolder holder(registrationLock);
     141    LockHolder holder(registrationLock);
    142142    m_nextRegisteredDatabase = firstDatabase;
    143143    firstDatabase = this;
     
    146146void Database::removeDatabaseFromAtExit()
    147147{
    148     SpinLockHolder holder(registrationLock);
     148    LockHolder holder(registrationLock);
    149149    for (Database** current = &firstDatabase; *current; current = &(*current)->m_nextRegisteredDatabase) {
    150150        if (*current != this)
     
    164164Database* Database::removeFirstAtExitDatabase()
    165165{
    166     SpinLockHolder holder(registrationLock);
     166    LockHolder holder(registrationLock);
    167167    Database* result = firstDatabase;
    168168    if (result) {
  • trunk/Source/JavaScriptCore/runtime/TypeProfilerLog.h

    r187587 r188100  
    3333#include "Structure.h"
    3434#include "TypeProfiler.h"
    35 #include <wtf/ByteSpinLock.h>
    3635
    3736namespace JSC {
  • trunk/Source/WTF/ChangeLog

    r188002 r188100  
     12015-08-05  Filip Pizlo  <fpizlo@apple.com>
     2
     3        Lightweight locks should be adaptive
     4        https://bugs.webkit.org/show_bug.cgi?id=147545
     5
     6        Reviewed by Geoffrey Garen.
     7
     8        A common idiom in WebKit is to use spinlocks. We use them because the lock acquisition
     9        overhead is lower than system locks and because they take dramatically less space than system
     10        locks. The speed and space advantages of spinlocks can be astonishing: an uncontended spinlock
     11        acquire is up to 10x faster and under microcontention - short critical section with two or
     12        more threads taking turns - spinlocks are up to 100x faster. Spinlocks take only 1 byte or 4
     13        bytes depending on the flavor, while system locks take 64 bytes or more. Clearly, WebKit
     14        should continue to avoid system locks - they are just far too slow and far too big.
     15
     16        But there is a problem with this idiom. System lock implementations will sleep a thread when
     17        it attempts to acquire a lock that is held, while spinlocks will cause the thread to burn CPU.
     18        In WebKit spinlocks, the thread will repeatedly call sched_yield(). This is awesome for
     19        microcontention, but awful when the lock will not be released for a while. In fact, when
     20        critical sections take tens of microseconds or more, the CPU time cost of our spinlocks is
     21        almost 100x more than the CPU time cost of a system lock. This case doesn't arise too
     22        frequently in our current uses of spinlocks, but that's probably because right now there are
     23        places where we make a conscious decision to use system locks - even though they use more
     24        memory and are slower - because we don't want to waste CPU cycles when a thread has to wait a
     25        while to acquire the lock.
     26
     27        The solution is to just implement a modern adaptive mutex in WTF. Luckily, this isn't a new
     28        concept. This patch implements a mutex that is reminiscent of the kinds of low-overhead locks
     29        that JVMs use. The actual implementation here is inspired by some of the ideas from [1]. The
     30        idea is simple: the fast path is an inlined CAS to immediately acquire a lock that isn't held,
     31        the slow path tries some number of spins to acquire the lock, and if that fails, the thread is
     32        put on a queue and put to sleep. The queue is made up of statically allocated thread nodes and
     33        the lock itself is a tagged pointer: either it is just bits telling us the complete lock state
     34        (not held or held) or it is a pointer to the head of a queue of threads waiting to acquire the
     35        lock. This approach gives WTF::Lock three different levels of adaptation: an inlined fast path
     36        if the lock is not contended, a short burst of spinning for microcontention, and a full-blown
     37        queue for critical sections that are held for a long time.
     38
     39        On a locking microbenchmark, this new Lock exhibits the following performance
     40        characteristics:
     41
     42        - Lock+unlock on an uncontended no-op critical section: 2x slower than SpinLock and 3x faster
     43          than a system mutex.
     44
     45        - Lock+unlock on a contended no-op critical section: 2x slower than SpinLock and 100x faster
     46          than a system mutex.
     47
     48        - CPU time spent in lock() on a lock held for a while: same as system mutex, 90x less than a
     49          SpinLock.
     50
     51        - Memory usage: sizeof(void*), so on 64-bit it's 8x less than a system mutex but 2x worse than
     52          a SpinLock.
     53
     54        This patch replaces all uses of SpinLock with Lock, since our critical sections are not
     55        no-ops so if you do basically anything in your critical section, the Lock overhead will be
     56        invisible. Also, in all places where we used SpinLock, we could tolerate 8 bytes of overhead
     57        instead of 4. Performance benchmarking using JSC macrobenchmarks shows no difference, which is
     58        as it should be: the purpose of this change is to reduce CPU time wasted, not wallclock time.
     59        This patch doesn't replace any uses of ByteSpinLock, since we expect that the space benefits
     60        of having a lock that just uses a byte are still better than the CPU wastage benefits of
     61        Lock. But, this work will enable some future work to create locks that will fit in just 1.6
     62        bits: https://bugs.webkit.org/show_bug.cgi?id=147665.
     63
     64        [1] http://www.filpizlo.com/papers/pizlo-pppj2011-fable.pdf
     65
     66        * WTF.vcxproj/WTF.vcxproj:
     67        * WTF.xcodeproj/project.pbxproj:
     68        * benchmarks: Added.
     69        * benchmarks/LockSpeedTest.cpp: Added.
     70        (main):
     71        * wtf/CMakeLists.txt:
     72        * wtf/Lock.cpp: Added.
     73        (WTF::LockBase::lockSlow):
     74        (WTF::LockBase::unlockSlow):
     75        * wtf/Lock.h: Added.
     76        (WTF::LockBase::lock):
     77        (WTF::LockBase::unlock):
     78        (WTF::LockBase::isHeld):
     79        (WTF::Lock::Lock):
     80        * wtf/MetaAllocator.cpp:
     81        (WTF::MetaAllocator::release):
     82        (WTF::MetaAllocatorHandle::shrink):
     83        (WTF::MetaAllocator::allocate):
     84        (WTF::MetaAllocator::currentStatistics):
     85        (WTF::MetaAllocator::addFreshFreeSpace):
     86        (WTF::MetaAllocator::debugFreeSpaceSize):
     87        * wtf/MetaAllocator.h:
     88        * wtf/SpinLock.h:
     89        * wtf/ThreadingPthreads.cpp:
     90        * wtf/ThreadingWin.cpp:
     91        * wtf/text/AtomicString.cpp:
     92        * wtf/text/AtomicStringImpl.cpp:
     93        (WTF::AtomicStringTableLocker::AtomicStringTableLocker):
     94
    1952015-08-05  Filip Pizlo  <fpizlo@apple.com>
    296
  • trunk/Source/WTF/WTF.vcxproj/WTF.vcxproj

    r185847 r188100  
    1 <?xml version="1.0" encoding="utf-8"?>
     1<?xml version="1.0" encoding="utf-8"?>
    22<Project DefaultTargets="Build" ToolsVersion="12.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
    33  <ItemGroup Label="ProjectConfigurations">
     
    107107    <ClCompile Include="..\wtf\GregorianDateTime.cpp" />
    108108    <ClCompile Include="..\wtf\HashTable.cpp" />
     109    <ClCompile Include="..\wtf\Lock.cpp" />
    109110    <ClCompile Include="..\wtf\MainThread.cpp" />
    110111    <ClCompile Include="..\wtf\MD5.cpp" />
     
    224225    <ClInclude Include="..\wtf\IteratorRange.h" />
    225226    <ClInclude Include="..\wtf\ListHashSet.h" />
     227    <ClInclude Include="..\wtf\Lock.h" />
    226228    <ClInclude Include="..\wtf\Locker.h" />
    227229    <ClInclude Include="..\wtf\MainThread.h" />
  • trunk/Source/WTF/WTF.xcodeproj/project.pbxproj

    r186268 r188100  
    4141                0FDDBFA71666DFA300C55FEF /* StringPrintStream.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0FDDBFA51666DFA300C55FEF /* StringPrintStream.cpp */; };
    4242                0FDDBFA81666DFA300C55FEF /* StringPrintStream.h in Headers */ = {isa = PBXBuildFile; fileRef = 0FDDBFA61666DFA300C55FEF /* StringPrintStream.h */; };
     43                0FE1646A1B6FFC9600400E7C /* Lock.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0FE164681B6FFC9600400E7C /* Lock.cpp */; };
     44                0FE1646B1B6FFC9600400E7C /* Lock.h in Headers */ = {isa = PBXBuildFile; fileRef = 0FE164691B6FFC9600400E7C /* Lock.h */; };
    4345                0FED67B61B22D4D80066CE15 /* TinyPtrSet.h in Headers */ = {isa = PBXBuildFile; fileRef = 0FED67B51B22D4D80066CE15 /* TinyPtrSet.h */; };
    4446                14022F4118F5C3FC007FF0EB /* libbmalloc.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 14022F4018F5C3FC007FF0EB /* libbmalloc.a */; };
     
    322324                0FDDBFA51666DFA300C55FEF /* StringPrintStream.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StringPrintStream.cpp; sourceTree = "<group>"; };
    323325                0FDDBFA61666DFA300C55FEF /* StringPrintStream.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StringPrintStream.h; sourceTree = "<group>"; };
     326                0FE164681B6FFC9600400E7C /* Lock.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Lock.cpp; sourceTree = "<group>"; };
     327                0FE164691B6FFC9600400E7C /* Lock.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Lock.h; sourceTree = "<group>"; };
    324328                0FEC3EE4171B834700FDAC8D /* ByteSpinLock.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ByteSpinLock.h; sourceTree = "<group>"; };
    325329                0FED67B51B22D4D80066CE15 /* TinyPtrSet.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = TinyPtrSet.h; sourceTree = "<group>"; };
     
    771775                                A70DA0831799F04D00529A9B /* ListDump.h */,
    772776                                A8A472C1151A825A004123FF /* ListHashSet.h */,
     777                                0FE164681B6FFC9600400E7C /* Lock.cpp */,
     778                                0FE164691B6FFC9600400E7C /* Lock.h */,
    773779                                A8A472C3151A825A004123FF /* Locker.h */,
    774780                                1447AEC818FCE59400B3D7FF /* mbmalloc.cpp */,
     
    12071213                                A8A473B9151A825B004123FF /* utils.h in Headers */,
    12081214                                A8A4747D151A825B004123FF /* ValueCheck.h in Headers */,
     1215                                0FE1646B1B6FFC9600400E7C /* Lock.h in Headers */,
    12091216                                A8A4747E151A825B004123FF /* Vector.h in Headers */,
    12101217                                A8A4747F151A825B004123FF /* VectorTraits.h in Headers */,
     
    13381345                                A8A473A0151A825B004123FF /* DateMath.cpp in Sources */,
    13391346                                A8A473A2151A825B004123FF /* DecimalNumber.cpp in Sources */,
     1347                                0FE1646A1B6FFC9600400E7C /* Lock.cpp in Sources */,
    13401348                                A8A473AE151A825B004123FF /* diy-fp.cc in Sources */,
    13411349                                A8A473B0151A825B004123FF /* double-conversion.cc in Sources */,
  • trunk/Source/WTF/wtf/CMakeLists.txt

    r185358 r188100  
    4242    IteratorRange.h
    4343    ListHashSet.h
     44    Lock.h
    4445    Locker.h
    4546    MD5.h
     
    157158    GregorianDateTime.cpp
    158159    HashTable.cpp
     160    Lock.cpp
    159161    MD5.cpp
    160162    MainThread.cpp
  • trunk/Source/WTF/wtf/MetaAllocator.cpp

    r187488 r188100  
    6161ALWAYS_INLINE void MetaAllocator::release(MetaAllocatorHandle* handle)
    6262{
    63     SpinLockHolder locker(&m_lock);
     63    LockHolder locker(&m_lock);
    6464    if (handle->sizeInBytes()) {
    6565        decrementPageOccupancy(handle->start(), handle->sizeInBytes());
     
    9292    ASSERT(newSizeInBytes <= m_sizeInBytes);
    9393   
    94     SpinLockHolder locker(&m_allocator->m_lock);
     94    LockHolder locker(&m_allocator->m_lock);
    9595
    9696    newSizeInBytes = m_allocator->roundUp(newSizeInBytes);
     
    151151PassRefPtr<MetaAllocatorHandle> MetaAllocator::allocate(size_t sizeInBytes, void* ownerUID)
    152152{
    153     SpinLockHolder locker(&m_lock);
     153    LockHolder locker(&m_lock);
    154154
    155155    if (!sizeInBytes)
     
    197197MetaAllocator::Statistics MetaAllocator::currentStatistics()
    198198{
    199     SpinLockHolder locker(&m_lock);
     199    LockHolder locker(&m_lock);
    200200    Statistics result;
    201201    result.bytesAllocated = m_bytesAllocated;
     
    282282void MetaAllocator::addFreshFreeSpace(void* start, size_t sizeInBytes)
    283283{
    284     SpinLockHolder locker(&m_lock);
     284    LockHolder locker(&m_lock);
    285285    m_bytesReserved += sizeInBytes;
    286286    addFreeSpace(start, sizeInBytes);
     
    290290{
    291291#ifndef NDEBUG
    292     SpinLockHolder locker(&m_lock);
     292    LockHolder locker(&m_lock);
    293293    size_t result = 0;
    294294    for (FreeSpaceNode* node = m_freeSpaceSizeMap.first(); node; node = node->successor())
  • trunk/Source/WTF/wtf/MetaAllocator.h

    r181628 r188100  
    3232#include <wtf/Assertions.h>
    3333#include <wtf/HashMap.h>
     34#include <wtf/Lock.h>
    3435#include <wtf/MetaAllocatorHandle.h>
    3536#include <wtf/Noncopyable.h>
     
    3839#include <wtf/RefCounted.h>
    3940#include <wtf/RefPtr.h>
    40 #include <wtf/SpinLock.h>
    4141
    4242namespace WTF {
     
    184184    size_t m_bytesCommitted;
    185185   
    186     SpinLock m_lock;
     186    Lock m_lock;
    187187
    188188    MetaAllocatorTracker* m_tracker;
  • trunk/Source/WTF/wtf/SpinLock.h

    r181979 r188100  
    3232
    3333namespace WTF {
     34
     35// SpinLock is a very simple lock implementation that has extremely fast lock/unlock for very small
     36// uncontended critical sections. However, it will exhibit bad performance degradation when the lock
     37// becomes contended: the thread trying to acquire the lock will simply waste CPU cycles.
     38//
     39// For most (all?) locking use cases, it's better to use Lock (see wtf/Lock.h). That uses only a bit
     40// more memory (8 bytes instead of 4 on 64-bit), and is only a bit slower in the uncontended case
     41// (Lock needs CAS to unlock, while SpinLock doesn't), but will burn a lot less CPU time - for 10
     42// threads acquiring a 50 microsecond critical section, Lock will use up to 100x less kernel CPU time
     43// than SpinLock.
    3444
    3545// SpinLockBase is a struct without an explicitly defined constructors so that
  • trunk/Source/WTF/wtf/ThreadingPthreads.cpp

    r188002 r188100  
    11/*
    2  * Copyright (C) 2007, 2009 Apple Inc. All rights reserved.
     2 * Copyright (C) 2007, 2009, 2015 Apple Inc. All rights reserved.
    33 * Copyright (C) 2007 Justin Haygood (jhaygood@reaktix.com)
    44 * Copyright (C) 2011 Research In Motion Limited. All rights reserved.
  • trunk/Source/WTF/wtf/ThreadingWin.cpp

    r188002 r188100  
    11/*
    2  * Copyright (C) 2007, 2008 Apple Inc. All rights reserved.
     2 * Copyright (C) 2007, 2008, 2015 Apple Inc. All rights reserved.
    33 * Copyright (C) 2009 Google Inc. All rights reserved.
    44 * Copyright (C) 2009 Torch Mobile, Inc. All rights reserved.
  • trunk/Source/WTF/wtf/text/AtomicString.cpp

    r184612 r188100  
    2828
    2929#if USE(WEB_THREAD)
    30 #include "SpinLock.h"
     30#include "Lock.h"
    3131#endif
    3232
  • trunk/Source/WTF/wtf/text/AtomicStringImpl.cpp

    r185109 r188100  
    3434
    3535#if USE(WEB_THREAD)
    36 #include "SpinLock.h"
     36#include "Lock.h"
    3737#endif
    3838
     
    4343#if USE(WEB_THREAD)
    4444
    45 class AtomicStringTableLocker : public SpinLockHolder {
     45class AtomicStringTableLocker : public LockHolder {
    4646    WTF_MAKE_NONCOPYABLE(AtomicStringTableLocker);
    4747
    48     static StaticSpinLock s_stringTableLock;
     48    static StaticLock s_stringTableLock;
    4949public:
    5050    AtomicStringTableLocker()
    51         : SpinLockHolder(&s_stringTableLock)
    52     {
    53     }
    54 };
    55 
    56 StaticSpinLock AtomicStringTableLocker::s_stringTableLock;
     51        : LockHolder(&s_stringTableLock)
     52    {
     53    }
     54};
     55
     56StaticLock AtomicStringTableLocker::s_stringTableLock;
    5757
    5858#else
  • trunk/Source/WebCore/ChangeLog

    r188098 r188100  
     12015-08-05  Filip Pizlo  <fpizlo@apple.com>
     2
     3        Lightweight locks should be adaptive
     4        https://bugs.webkit.org/show_bug.cgi?id=147545
     5
     6        Reviewed by Geoffrey Garen.
     7
     8        No new tests because no new behavior.
     9
     10        * bindings/objc/WebScriptObject.mm:
     11        (WebCore::getJSWrapper):
     12        (WebCore::addJSWrapper):
     13        (WebCore::removeJSWrapper):
     14        (WebCore::removeJSWrapperIfRetainCountOne):
     15        * platform/ios/wak/WAKWindow.mm:
     16        (-[WAKWindow setExposedScrollViewRect:]):
     17        (-[WAKWindow exposedScrollViewRect]):
     18
    1192015-08-06  Alex Christensen  <achristensen@webkit.org>
    220
  • trunk/Source/WebCore/bindings/objc/WebScriptObject.mm

    r186268 r188100  
    4949#import <runtime/Completion.h>
    5050#import <runtime/Completion.h>
    51 #import <wtf/SpinLock.h>
     51#import <wtf/Lock.h>
    5252#import <wtf/Threading.h>
    5353#import <wtf/spi/cocoa/NSMapTableSPI.h>
     
    7373
    7474static NSMapTable* JSWrapperCache;
    75 static StaticSpinLock spinLock;
     75static StaticLock spinLock;
    7676
    7777NSObject* getJSWrapper(JSObject* impl)
    7878{
    7979    ASSERT(isMainThread());
    80     SpinLockHolder holder(&spinLock);
     80    LockHolder holder(&spinLock);
    8181
    8282    if (!JSWrapperCache)
     
    8989{
    9090    ASSERT(isMainThread());
    91     SpinLockHolder holder(&spinLock);
     91    LockHolder holder(&spinLock);
    9292
    9393    if (!JSWrapperCache)
     
    9898void removeJSWrapper(JSObject* impl)
    9999{
    100     SpinLockHolder holder(&spinLock);
     100    LockHolder holder(&spinLock);
    101101
    102102    if (!JSWrapperCache)
     
    107107static void removeJSWrapperIfRetainCountOne(NSObject* wrapper, JSObject* impl)
    108108{
    109     SpinLockHolder holder(&spinLock);
     109    LockHolder holder(&spinLock);
    110110
    111111    if (!JSWrapperCache)
  • trunk/Source/WebCore/platform/audio/mac/CARingBuffer.cpp

    r186279 r188100  
    201201void CARingBuffer::setCurrentFrameBounds(uint64_t startTime, uint64_t endTime)
    202202{
    203     ByteSpinLocker locker(m_currentFrameBoundsLock);
     203    LockHolder locker(m_currentFrameBoundsLock);
    204204    uint32_t nextPtr = m_timeBoundsQueuePtr + 1;
    205205    uint32_t index = nextPtr & kGeneralRingTimeBoundsQueueMask;
     
    213213void CARingBuffer::getCurrentFrameBounds(uint64_t &startTime, uint64_t &endTime)
    214214{
    215     ByteSpinLocker locker(m_currentFrameBoundsLock);
     215    LockHolder locker(m_currentFrameBoundsLock);
    216216    uint32_t curPtr = m_timeBoundsQueuePtr;
    217217    uint32_t index = curPtr & kGeneralRingTimeBoundsQueueMask;
  • trunk/Source/WebCore/platform/audio/mac/CARingBuffer.h

    r181368 r188100  
    3030
    3131#include <runtime/ArrayBuffer.h>
    32 #include <wtf/ByteSpinLock.h>
     32#include <wtf/Lock.h>
    3333#include <wtf/Vector.h>
    3434
     
    8585   
    8686    Vector<TimeBounds> m_timeBoundsQueue;
    87     ByteSpinLock m_currentFrameBoundsLock;
     87    Lock m_currentFrameBoundsLock;
    8888    int32_t m_timeBoundsQueuePtr;
    8989};
  • trunk/Source/WebCore/platform/ios/wak/WAKWindow.mm

    r185021 r188100  
    3737#import "WKViewPrivate.h"
    3838#import <QuartzCore/QuartzCore.h>
    39 #import <wtf/SpinLock.h>
     39#import <wtf/Lock.h>
    4040
    4141WEBCORE_EXPORT NSString * const WAKWindowScreenScaleDidChangeNotification = @"WAKWindowScreenScaleDidChangeNotification";
     
    5757
    5858@implementation WAKWindow {
    59     SpinLock _exposedScrollViewRectLock;
     59    Lock _exposedScrollViewRectLock;
    6060    CGRect _exposedScrollViewRect;
    6161}
     
    359359- (void)setExposedScrollViewRect:(CGRect)exposedScrollViewRect
    360360{
    361     SpinLockHolder locker(&_exposedScrollViewRectLock);
     361    LockHolder locker(&_exposedScrollViewRectLock);
    362362    _exposedScrollViewRect = exposedScrollViewRect;
    363363}
     
    366366{
    367367    {
    368         SpinLockHolder locker(&_exposedScrollViewRectLock);
     368        LockHolder locker(&_exposedScrollViewRectLock);
    369369        if (!CGRectIsNull(_exposedScrollViewRect))
    370370            return _exposedScrollViewRect;
  • trunk/Source/WebKit2/ChangeLog

    r188097 r188100  
     12015-08-05  Filip Pizlo  <fpizlo@apple.com>
     2
     3        Lightweight locks should be adaptive
     4        https://bugs.webkit.org/show_bug.cgi?id=147545
     5
     6        Reviewed by Geoffrey Garen.
     7
     8        * WebProcess/WebPage/EventDispatcher.cpp:
     9        (WebKit::EventDispatcher::clearQueuedTouchEventsForPage):
     10        (WebKit::EventDispatcher::getQueuedTouchEventsForPage):
     11        (WebKit::EventDispatcher::touchEvent):
     12        (WebKit::EventDispatcher::dispatchTouchEvents):
     13        * WebProcess/WebPage/EventDispatcher.h:
     14        * WebProcess/WebPage/ViewUpdateDispatcher.cpp:
     15        (WebKit::ViewUpdateDispatcher::visibleContentRectUpdate):
     16        (WebKit::ViewUpdateDispatcher::dispatchVisibleContentRectUpdate):
     17        * WebProcess/WebPage/ViewUpdateDispatcher.h:
     18
    1192015-08-06  Matt Rajca  <mrajca@apple.com>
    220
  • trunk/Source/WebKit2/WebProcess/WebPage/EventDispatcher.cpp

    r188002 r188100  
    173173void EventDispatcher::clearQueuedTouchEventsForPage(const WebPage& webPage)
    174174{
    175     SpinLockHolder locker(&m_touchEventsLock);
     175    LockHolder locker(&m_touchEventsLock);
    176176    m_touchEvents.remove(webPage.pageID());
    177177}
     
    179179void EventDispatcher::getQueuedTouchEventsForPage(const WebPage& webPage, TouchEventQueue& destinationQueue)
    180180{
    181     SpinLockHolder locker(&m_touchEventsLock);
     181    LockHolder locker(&m_touchEventsLock);
    182182    destinationQueue = m_touchEvents.take(webPage.pageID());
    183183}
     
    187187    bool updateListWasEmpty;
    188188    {
    189         SpinLockHolder locker(&m_touchEventsLock);
     189        LockHolder locker(&m_touchEventsLock);
    190190        updateListWasEmpty = m_touchEvents.isEmpty();
    191191        auto addResult = m_touchEvents.add(pageID, TouchEventQueue());
     
    218218    HashMap<uint64_t, TouchEventQueue> localCopy;
    219219    {
    220         SpinLockHolder locker(&m_touchEventsLock);
     220        LockHolder locker(&m_touchEventsLock);
    221221        localCopy.swap(m_touchEvents);
    222222    }
  • trunk/Source/WebKit2/WebProcess/WebPage/EventDispatcher.h

    r188002 r188100  
    3333#include <memory>
    3434#include <wtf/HashMap.h>
     35#include <wtf/Lock.h>
    3536#include <wtf/Noncopyable.h>
    3637#include <wtf/RefPtr.h>
    37 #include <wtf/SpinLock.h>
    3838#include <wtf/ThreadingPrimitives.h>
    3939
     
    9898    std::unique_ptr<WebCore::WheelEventDeltaTracker> m_recentWheelEventDeltaTracker;
    9999#if ENABLE(IOS_TOUCH_EVENTS)
    100     SpinLock m_touchEventsLock;
     100    Lock m_touchEventsLock;
    101101    HashMap<uint64_t, TouchEventQueue> m_touchEvents;
    102102#endif
  • trunk/Source/WebKit2/WebProcess/WebPage/ViewUpdateDispatcher.cpp

    r181485 r188100  
    5959    bool updateListWasEmpty;
    6060    {
    61         SpinLockHolder locker(&m_dataMutex);
     61        LockHolder locker(&m_dataMutex);
    6262        updateListWasEmpty = m_latestUpdate.isEmpty();
    6363        auto iterator = m_latestUpdate.find(pageID);
     
    7979    HashMap<uint64_t, UpdateData> update;
    8080    {
    81         SpinLockHolder locker(&m_dataMutex);
     81        LockHolder locker(&m_dataMutex);
    8282        update = WTF::move(m_latestUpdate);
    8383    }
  • trunk/Source/WebKit2/WebProcess/WebPage/ViewUpdateDispatcher.h

    r181485 r188100  
    3131#include "VisibleContentRectUpdateInfo.h"
    3232#include <wtf/HashMap.h>
     33#include <wtf/Lock.h>
    3334#include <wtf/Ref.h>
    34 #include <wtf/SpinLock.h>
    3535
    3636namespace WebKit {
     
    5858
    5959    Ref<WorkQueue> m_queue;
    60     SpinLock m_dataMutex;
     60    Lock m_dataMutex;
    6161    HashMap<uint64_t, UpdateData> m_latestUpdate;
    6262};
  • trunk/Tools/ChangeLog

    r188092 r188100  
     12015-08-06  Filip Pizlo  <fpizlo@apple.com>
     2
     3        Lightweight locks should be adaptive
     4        https://bugs.webkit.org/show_bug.cgi?id=147545
     5
     6        Reviewed by Geoffrey Garen.
     7
     8        * TestWebKitAPI/CMakeLists.txt:
     9        * TestWebKitAPI/TestWebKitAPI.vcxproj/TestWebKitAPI.vcxproj:
     10        * TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj:
     11        * TestWebKitAPI/Tests/WTF/Lock.cpp: Added.
     12        (TestWebKitAPI::runLockTest):
     13        (TestWebKitAPI::TEST):
     14
    1152015-08-06  Ryosuke Niwa  <rniwa@webkit.org>
    216
  • trunk/Tools/TestWebKitAPI/CMakeLists.txt

    r185608 r188100  
    7676    ${TESTWEBKITAPI_DIR}/Tests/WTF/IntegerToStringConversion.cpp
    7777    ${TESTWEBKITAPI_DIR}/Tests/WTF/ListHashSet.cpp
     78    ${TESTWEBKITAPI_DIR}/Tests/WTF/Lock.cpp
    7879    ${TESTWEBKITAPI_DIR}/Tests/WTF/MD5.cpp
    7980    ${TESTWEBKITAPI_DIR}/Tests/WTF/MathExtras.cpp
  • trunk/Tools/TestWebKitAPI/TestWebKitAPI.vcxproj/TestWebKitAPI.vcxproj

    r185608 r188100  
    1 <?xml version="1.0" encoding="utf-8"?>
     1<?xml version="1.0" encoding="utf-8"?>
    22<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
    33  <ItemGroup Label="ProjectConfigurations">
     
    320320    <ClCompile Include="..\Tests\WTF\IntegerToStringConversion.cpp" />
    321321    <ClCompile Include="..\Tests\WTF\ListHashSet.cpp" />
     322    <ClCompile Include="..\Tests\WTF\Lock.cpp" />
    322323    <ClCompile Include="..\Tests\WTF\MD5.cpp" />
    323324    <ClCompile Include="..\Tests\WTF\MathExtras.cpp" />
  • trunk/Tools/TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj

    r187962 r188100  
    1212                0F139E791A42457000F590F5 /* PlatformUtilitiesCocoa.mm in Sources */ = {isa = PBXBuildFile; fileRef = 0F139E721A423A2B00F590F5 /* PlatformUtilitiesCocoa.mm */; };
    1313                0F3B94A71A77267400DE3272 /* WKWebViewEvaluateJavaScript.mm in Sources */ = {isa = PBXBuildFile; fileRef = 0F3B94A51A77266C00DE3272 /* WKWebViewEvaluateJavaScript.mm */; };
     14                0FFC45A61B73EBEB0085BD62 /* Lock.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0FFC45A41B73EBE20085BD62 /* Lock.cpp */; };
    1415                1A02C870125D4CFD00E3F4BD /* find.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = 1A02C84B125D4A5E00E3F4BD /* find.html */; };
    1516                1A50AA201A2A51FC00F4C345 /* close-from-within-create-page.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = 1A50AA1F1A2A4EA500F4C345 /* close-from-within-create-page.html */; };
     
    429430                0FC6C4CB141027E0005B7F0C /* RedBlackTree.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = RedBlackTree.cpp; sourceTree = "<group>"; };
    430431                0FC6C4CE141034AD005B7F0C /* MetaAllocator.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = MetaAllocator.cpp; sourceTree = "<group>"; };
     432                0FFC45A41B73EBE20085BD62 /* Lock.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Lock.cpp; sourceTree = "<group>"; };
    431433                14464012167A8305000BD218 /* LayoutUnit.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = LayoutUnit.cpp; sourceTree = "<group>"; };
    432434                14F3B11215E45EAB00210069 /* SaturatedArithmeticOperations.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SaturatedArithmeticOperations.cpp; sourceTree = "<group>"; };
     
    10971099                                266FAFD215E5775200F61D5B /* IntegerToStringConversion.cpp */,
    10981100                                26300B1716755CD90066886D /* ListHashSet.cpp */,
     1101                                0FFC45A41B73EBE20085BD62 /* Lock.cpp */,
    10991102                                B4039F9C15E6D8B3007255D6 /* MathExtras.cpp */,
    11001103                                CD5393C71757BA9700C07123 /* MD5.cpp */,
     
    15681571                                7CCE7ECA1A411A7E00447C4C /* RenderedImageFromDOMRange.mm in Sources */,
    15691572                                51CD1C6C1B38CE4300142CA5 /* ModalAlerts.mm in Sources */,
     1573                                0FFC45A61B73EBEB0085BD62 /* Lock.cpp in Sources */,
    15701574                                7CCE7F0E1A411AE600447C4C /* ResizeReversePaginatedWebView.cpp in Sources */,
    15711575                                7CCE7F0F1A411AE600447C4C /* ResizeWindowAfterCrash.cpp in Sources */,
Note: See TracChangeset for help on using the changeset viewer.