OLD | NEW |
(Empty) | |
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. |
| 4 |
| 5 #include "config.h" |
| 6 #include "modules/compositorworker/CompositorWorkerManager.h" |
| 7 |
| 8 #include "platform/ThreadSafeFunctional.h" |
| 9 #include "platform/WebThreadSupportingGC.h" |
| 10 #include "wtf/MainThread.h" |
| 11 #include "wtf/ThreadingPrimitives.h" |
| 12 |
| 13 namespace blink { |
| 14 |
| 15 namespace { |
| 16 |
| 17 class SharedV8Isolate final : public WorkerIsolateWrapper { |
| 18 WTF_MAKE_NONCOPYABLE(SharedV8Isolate); |
| 19 public: |
| 20 explicit SharedV8Isolate(v8::Isolate* isolate) |
| 21 : m_isolate(isolate) { } |
| 22 ~SharedV8Isolate() override |
| 23 { |
| 24 CompositorWorkerManager::instance()->destroyIsolate(); |
| 25 } |
| 26 |
| 27 private: |
| 28 // WorkerIsolateWrapper: |
| 29 v8::Isolate* isolate() const override { return m_isolate; } |
| 30 void willDestroy() override |
| 31 { |
| 32 CompositorWorkerManager::instance()->willDestroyIsolate(); |
| 33 } |
| 34 |
| 35 void terminateExecution() override |
| 36 { |
| 37 CompositorWorkerManager::instance()->terminateIsolate(); |
| 38 } |
| 39 |
| 40 v8::Isolate* m_isolate; |
| 41 }; |
| 42 |
| 43 static CompositorWorkerManager* s_instance = nullptr; |
| 44 |
| 45 static Mutex& singletonMutex() |
| 46 { |
| 47 AtomicallyInitializedStaticReference(Mutex, mutex, new Mutex); |
| 48 return mutex; |
| 49 } |
| 50 |
| 51 static void destroyThread(WebThreadSupportingGC* thread) |
| 52 { |
| 53 delete thread; |
| 54 } |
| 55 |
| 56 } // namespace |
| 57 |
| 58 void CompositorWorkerManager::initialize() |
| 59 { |
| 60 MutexLocker lock(singletonMutex()); |
| 61 ASSERT(!s_instance); |
| 62 s_instance = new CompositorWorkerManager(); |
| 63 } |
| 64 |
| 65 void CompositorWorkerManager::shutdown() |
| 66 { |
| 67 MutexLocker lock(singletonMutex()); |
| 68 ASSERT(s_instance); |
| 69 delete s_instance; |
| 70 s_instance = nullptr; |
| 71 } |
| 72 |
| 73 CompositorWorkerManager* CompositorWorkerManager::instance() |
| 74 { |
| 75 MutexLocker lock(singletonMutex()); |
| 76 ASSERT(s_instance); |
| 77 return s_instance; |
| 78 } |
| 79 |
| 80 CompositorWorkerManager::CompositorWorkerManager() |
| 81 { |
| 82 } |
| 83 |
| 84 CompositorWorkerManager::~CompositorWorkerManager() |
| 85 { |
| 86 } |
| 87 |
| 88 WebThreadSupportingGC& CompositorWorkerManager::compositorWorkerThread() |
| 89 { |
| 90 MutexLocker lock(m_mutex); |
| 91 if (!m_thread) { |
| 92 ASSERT(isMainThread()); |
| 93 ASSERT(!m_workerCount); |
| 94 m_thread = WebThreadSupportingGC::create("CompositorWorker Thread"); |
| 95 } |
| 96 return *m_thread.get(); |
| 97 } |
| 98 |
| 99 void CompositorWorkerManager::initializeBackingThread() |
| 100 { |
| 101 ASSERT(m_thread->isCurrentThread()); |
| 102 MutexLocker lock(m_mutex); |
| 103 ++m_workerCount; |
| 104 if (m_workerCount == 1) |
| 105 m_thread->initialize(); |
| 106 } |
| 107 |
| 108 void CompositorWorkerManager::shutdownBackingThread() |
| 109 { |
| 110 MutexLocker lock(m_mutex); |
| 111 ASSERT(m_thread->isCurrentThread()); |
| 112 ASSERT(m_workerCount > 0); |
| 113 --m_workerCount; |
| 114 if (m_workerCount == 0) { |
| 115 m_thread->shutdown(); |
| 116 Platform::current()->mainThread()->postTask(FROM_HERE, threadSafeBind(de
stroyThread, AllowCrossThreadAccess(m_thread.leakPtr()))); |
| 117 } |
| 118 } |
| 119 |
| 120 PassOwnPtr<WorkerIsolateWrapper> CompositorWorkerManager::createIsolate() |
| 121 { |
| 122 MutexLocker lock(m_mutex); |
| 123 ASSERT(m_thread->isCurrentThread()); |
| 124 if (!m_isolate) |
| 125 m_isolate = WorkerIsolateWrapper::createDefault(); |
| 126 // It is safe to use the existing isolate even if TerminateExecution() has b
een |
| 127 // called on it, without calling CancelTerminateExecution(). |
| 128 return adoptPtr(new SharedV8Isolate(m_isolate->isolate())); |
| 129 } |
| 130 |
| 131 void CompositorWorkerManager::willDestroyIsolate() |
| 132 { |
| 133 MutexLocker lock(m_mutex); |
| 134 ASSERT(m_thread->isCurrentThread()); |
| 135 if (m_workerCount == 1) |
| 136 m_isolate->willDestroy(); |
| 137 } |
| 138 |
| 139 void CompositorWorkerManager::destroyIsolate() |
| 140 { |
| 141 MutexLocker lock(m_mutex); |
| 142 if (!m_thread) { |
| 143 ASSERT(m_workerCount == 0); |
| 144 m_isolate.clear(); |
| 145 } |
| 146 } |
| 147 |
| 148 void CompositorWorkerManager::terminateIsolate() |
| 149 { |
| 150 MutexLocker lock(m_mutex); |
| 151 ASSERT(isMainThread()); |
| 152 if (m_workerCount > 1) |
| 153 return; |
| 154 |
| 155 m_isolate->terminateExecution(); |
| 156 } |
| 157 |
| 158 } // namespace blink |
OLD | NEW |