| Index: third_party/WebKit/Source/modules/compositorworker/CompositorWorkerThread.cpp | 
| diff --git a/third_party/WebKit/Source/modules/compositorworker/CompositorWorkerThread.cpp b/third_party/WebKit/Source/modules/compositorworker/CompositorWorkerThread.cpp | 
| index fa420027933081e3485cf6dce85ce7dc3144510f..d0f51a47ade67425444287a3a157c1cf1f054685 100644 | 
| --- a/third_party/WebKit/Source/modules/compositorworker/CompositorWorkerThread.cpp | 
| +++ b/third_party/WebKit/Source/modules/compositorworker/CompositorWorkerThread.cpp | 
| @@ -5,17 +5,133 @@ | 
| #include "config.h" | 
| #include "modules/compositorworker/CompositorWorkerThread.h" | 
|  | 
| +#include "bindings/core/v8/V8GCController.h" | 
| #include "bindings/core/v8/V8Initializer.h" | 
| #include "core/workers/WorkerObjectProxy.h" | 
| #include "core/workers/WorkerThreadStartupData.h" | 
| #include "modules/compositorworker/CompositorWorkerGlobalScope.h" | 
| -#include "modules/compositorworker/CompositorWorkerManager.h" | 
| +#include "platform/ThreadSafeFunctional.h" | 
| +#include "platform/TraceEvent.h" | 
| #include "public/platform/Platform.h" | 
|  | 
| namespace blink { | 
|  | 
| +namespace { | 
| + | 
| +class CompositorWorkerSharedState { | 
| +public: | 
| +    static CompositorWorkerSharedState& instance() | 
| +    { | 
| +        AtomicallyInitializedStaticReference(CompositorWorkerSharedState, compositorWorkerSharedState, (new CompositorWorkerSharedState())); | 
| +        return compositorWorkerSharedState; | 
| +    } | 
| + | 
| +    WebThreadSupportingGC* compositorWorkerThread() | 
| +    { | 
| +        MutexLocker lock(m_mutex); | 
| +        if (!m_thread && isMainThread()) { | 
| +            ASSERT(!m_workerCount); | 
| +            WebThread* platformThread = Platform::current()->compositorThread(); | 
| +            m_thread = WebThreadSupportingGC::createForThread(platformThread); | 
| +        } | 
| +        return m_thread.get(); | 
| +    } | 
| + | 
| +    void initializeBackingThread() | 
| +    { | 
| +        MutexLocker lock(m_mutex); | 
| +        ASSERT(m_thread->isCurrentThread()); | 
| +        ++m_workerCount; | 
| +        if (m_workerCount > 1) | 
| +            return; | 
| + | 
| +        m_thread->initialize(); | 
| + | 
| +        // Initialize the isolate at the same time. | 
| +        ASSERT(!m_isolate); | 
| +        m_isolate = V8PerIsolateData::initialize(); | 
| +        V8Initializer::initializeWorker(m_isolate); | 
| + | 
| +        OwnPtr<V8IsolateInterruptor> interruptor = adoptPtr(new V8IsolateInterruptor(m_isolate)); | 
| +        ThreadState::current()->addInterruptor(interruptor.release()); | 
| +        ThreadState::current()->registerTraceDOMWrappers(m_isolate, V8GCController::traceDOMWrappers); | 
| +    } | 
| + | 
| +    void shutdownBackingThread() | 
| +    { | 
| +        MutexLocker lock(m_mutex); | 
| +        ASSERT(m_thread->isCurrentThread()); | 
| +        ASSERT(m_workerCount > 0); | 
| +        --m_workerCount; | 
| +        if (m_workerCount == 0) { | 
| +            m_thread->shutdown(); | 
| +            m_thread = nullptr; | 
| +        } | 
| +    } | 
| + | 
| +    v8::Isolate* initializeIsolate() | 
| +    { | 
| +        MutexLocker lock(m_mutex); | 
| +        ASSERT(m_thread->isCurrentThread()); | 
| +        ASSERT(m_isolate); | 
| +        // It is safe to use the existing isolate even if TerminateExecution() has been | 
| +        // called on it, without calling CancelTerminateExecution(). | 
| +        return m_isolate; | 
| +    } | 
| + | 
| +    void willDestroyIsolate() | 
| +    { | 
| +        MutexLocker lock(m_mutex); | 
| +        ASSERT(m_thread->isCurrentThread()); | 
| +        if (m_workerCount == 1) | 
| +            V8PerIsolateData::willBeDestroyed(m_isolate); | 
| +    } | 
| + | 
| +    void destroyIsolate() | 
| +    { | 
| +        MutexLocker lock(m_mutex); | 
| +        if (!m_thread) { | 
| +            ASSERT(m_workerCount == 0); | 
| +            V8PerIsolateData::destroy(m_isolate); | 
| +            m_isolate = nullptr; | 
| +        } | 
| +    } | 
| + | 
| +    void terminateV8Execution() | 
| +    { | 
| +        MutexLocker lock(m_mutex); | 
| +        ASSERT(isMainThread()); | 
| +        if (m_workerCount > 1) | 
| +            return; | 
| + | 
| +        v8::V8::TerminateExecution(m_isolate); | 
| +    } | 
| + | 
| +    bool hasThreadForTest() | 
| +    { | 
| +        return m_thread; | 
| +    } | 
| + | 
| +    bool hasIsolateForTest() | 
| +    { | 
| +        return m_isolate; | 
| +    } | 
| + | 
| +private: | 
| +    CompositorWorkerSharedState() {} | 
| +    ~CompositorWorkerSharedState() {} | 
| + | 
| +    Mutex m_mutex; | 
| +    OwnPtr<WebThreadSupportingGC> m_thread; | 
| +    int m_workerCount = 0; | 
| +    v8::Isolate* m_isolate = nullptr; | 
| +}; | 
| + | 
| +} // namespace | 
| + | 
| PassRefPtr<CompositorWorkerThread> CompositorWorkerThread::create(PassRefPtr<WorkerLoaderProxy> workerLoaderProxy, WorkerObjectProxy& workerObjectProxy, double timeOrigin) | 
| { | 
| +    TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("compositor-worker"), "CompositorWorkerThread::create"); | 
| ASSERT(isMainThread()); | 
| return adoptRef(new CompositorWorkerThread(workerLoaderProxy, workerObjectProxy, timeOrigin)); | 
| } | 
| @@ -31,44 +147,65 @@ CompositorWorkerThread::~CompositorWorkerThread() | 
| { | 
| } | 
|  | 
| +WebThreadSupportingGC* CompositorWorkerThread::sharedBackingThread() | 
| +{ | 
| +    return CompositorWorkerSharedState::instance().compositorWorkerThread(); | 
| +} | 
| + | 
| PassRefPtrWillBeRawPtr<WorkerGlobalScope> CompositorWorkerThread::createWorkerGlobalScope(PassOwnPtr<WorkerThreadStartupData> startupData) | 
| { | 
| +    TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("compositor-worker"), "CompositorWorkerThread::createWorkerGlobalScope"); | 
| return CompositorWorkerGlobalScope::create(this, startupData, m_timeOrigin); | 
| } | 
|  | 
| WebThreadSupportingGC& CompositorWorkerThread::backingThread() | 
| { | 
| -    return CompositorWorkerManager::instance()->compositorWorkerThread(); | 
| +    return *CompositorWorkerSharedState::instance().compositorWorkerThread(); | 
| } | 
|  | 
| void CompositorWorkerThread::initializeBackingThread() | 
| { | 
| -    CompositorWorkerManager::instance()->initializeBackingThread(); | 
| +    TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("compositor-worker"), "CompositorWorkerThread::initializeBackingThread"); | 
| +    CompositorWorkerSharedState::instance().initializeBackingThread(); | 
| } | 
|  | 
| void CompositorWorkerThread::shutdownBackingThread() | 
| { | 
| -    CompositorWorkerManager::instance()->shutdownBackingThread(); | 
| +    TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("compositor-worker"), "CompositorWorkerThread::shutdownBackingThread"); | 
| +    CompositorWorkerSharedState::instance().shutdownBackingThread(); | 
| } | 
|  | 
| v8::Isolate* CompositorWorkerThread::initializeIsolate() | 
| { | 
| -    return CompositorWorkerManager::instance()->initializeIsolate(); | 
| +    return CompositorWorkerSharedState::instance().initializeIsolate(); | 
| } | 
|  | 
| void CompositorWorkerThread::willDestroyIsolate() | 
| { | 
| -    CompositorWorkerManager::instance()->willDestroyIsolate(); | 
| +    TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("compositor-worker"), "CompositorWorkerThread::willDestroyIsolate"); | 
| +    CompositorWorkerSharedState::instance().willDestroyIsolate(); | 
| } | 
|  | 
| void CompositorWorkerThread::destroyIsolate() | 
| { | 
| -    CompositorWorkerManager::instance()->destroyIsolate(); | 
| +    TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("compositor-worker"), "CompositorWorkerThread::destroyIsolate"); | 
| +    CompositorWorkerSharedState::instance().destroyIsolate(); | 
| } | 
|  | 
| void CompositorWorkerThread::terminateV8Execution() | 
| { | 
| -    CompositorWorkerManager::instance()->terminateV8Execution(); | 
| +    TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("compositor-worker"), "CompositorWorkerThread::terminateV8Execution"); | 
| +    CompositorWorkerSharedState::instance().terminateV8Execution(); | 
| +} | 
| + | 
| +bool CompositorWorkerThread::hasThreadForTest() | 
| +{ | 
| +    return CompositorWorkerSharedState::instance().hasThreadForTest(); | 
| +} | 
| + | 
| +bool CompositorWorkerThread::hasIsolateForTest() | 
| +{ | 
| +    return CompositorWorkerSharedState::instance().hasIsolateForTest(); | 
| } | 
|  | 
| } // namespace blink | 
|  |