OLD | NEW |
1 // Copyright 2011 The Chromium Authors. All rights reserved. | 1 // Copyright 2011 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #ifndef CCScopedThreadProxy_h | 5 #ifndef CCScopedThreadProxy_h |
6 #define CCScopedThreadProxy_h | 6 #define CCScopedThreadProxy_h |
7 | 7 |
8 #include "CCThreadTask.h" | 8 #include "CCThreadTask.h" |
| 9 #include "base/threading/platform_thread.h" |
9 #include <wtf/ThreadSafeRefCounted.h> | 10 #include <wtf/ThreadSafeRefCounted.h> |
10 | 11 |
11 namespace WebCore { | 12 namespace WebCore { |
12 | 13 |
13 // This class is a proxy used to post tasks to an target thread from any other t
hread. The proxy may be shut down at | 14 // This class is a proxy used to post tasks to an target thread from any other t
hread. The proxy may be shut down at |
14 // any point from the target thread after which no more tasks posted to the prox
y will run. In other words, all | 15 // any point from the target thread after which no more tasks posted to the prox
y will run. In other words, all |
15 // tasks posted via a proxy are scoped to the lifecycle of the proxy. Use this w
hen posting tasks to an object that | 16 // tasks posted via a proxy are scoped to the lifecycle of the proxy. Use this w
hen posting tasks to an object that |
16 // might die with tasks in flight. | 17 // might die with tasks in flight. |
17 // | 18 // |
18 // The proxy must be created and shut down from the target thread, tasks may be
posted from any thread. | 19 // The proxy must be created and shut down from the target thread, tasks may be
posted from any thread. |
19 // | 20 // |
20 // Implementation note: Unlike ScopedRunnableMethodFactory in Chromium, pending
tasks are not cancelled by actually | 21 // Implementation note: Unlike ScopedRunnableMethodFactory in Chromium, pending
tasks are not cancelled by actually |
21 // destroying the proxy. Instead each pending task holds a reference to the prox
y to avoid maintaining an explicit | 22 // destroying the proxy. Instead each pending task holds a reference to the prox
y to avoid maintaining an explicit |
22 // list of outstanding tasks. | 23 // list of outstanding tasks. |
23 class CCScopedThreadProxy : public ThreadSafeRefCounted<CCScopedThreadProxy> { | 24 class CCScopedThreadProxy : public ThreadSafeRefCounted<CCScopedThreadProxy> { |
24 public: | 25 public: |
25 static PassRefPtr<CCScopedThreadProxy> create(CCThread* targetThread) | 26 static PassRefPtr<CCScopedThreadProxy> create(CCThread* targetThread) |
26 { | 27 { |
27 ASSERT(currentThread() == targetThread->threadID()); | 28 ASSERT(base::PlatformThread::CurrentId() == targetThread->threadID()); |
28 return adoptRef(new CCScopedThreadProxy(targetThread)); | 29 return adoptRef(new CCScopedThreadProxy(targetThread)); |
29 } | 30 } |
30 | 31 |
31 // Can be called from any thread. Posts a task to the target thread that run
s unless | 32 // Can be called from any thread. Posts a task to the target thread that run
s unless |
32 // shutdown() is called before it runs. | 33 // shutdown() is called before it runs. |
33 void postTask(PassOwnPtr<CCThread::Task> task) | 34 void postTask(PassOwnPtr<CCThread::Task> task) |
34 { | 35 { |
35 ref(); | 36 ref(); |
36 m_targetThread->postTask(createCCThreadTask(this, &CCScopedThreadProxy::
runTaskIfNotShutdown, task)); | 37 m_targetThread->postTask(createCCThreadTask(this, &CCScopedThreadProxy::
runTaskIfNotShutdown, task)); |
37 } | 38 } |
38 | 39 |
39 void shutdown() | 40 void shutdown() |
40 { | 41 { |
41 ASSERT(currentThread() == m_targetThread->threadID()); | 42 ASSERT(base::PlatformThread::CurrentId() == m_targetThread->threadID()); |
42 ASSERT(!m_shutdown); | 43 ASSERT(!m_shutdown); |
43 m_shutdown = true; | 44 m_shutdown = true; |
44 } | 45 } |
45 | 46 |
46 private: | 47 private: |
47 explicit CCScopedThreadProxy(CCThread* targetThread) | 48 explicit CCScopedThreadProxy(CCThread* targetThread) |
48 : m_targetThread(targetThread) | 49 : m_targetThread(targetThread) |
49 , m_shutdown(false) { } | 50 , m_shutdown(false) { } |
50 | 51 |
51 void runTaskIfNotShutdown(PassOwnPtr<CCThread::Task> popTask) | 52 void runTaskIfNotShutdown(PassOwnPtr<CCThread::Task> popTask) |
52 { | 53 { |
53 OwnPtr<CCThread::Task> task = popTask; | 54 OwnPtr<CCThread::Task> task = popTask; |
54 // If our shutdown flag is set, it's possible that m_targetThread has al
ready been destroyed so don't | 55 // If our shutdown flag is set, it's possible that m_targetThread has al
ready been destroyed so don't |
55 // touch it. | 56 // touch it. |
56 if (m_shutdown) { | 57 if (m_shutdown) { |
57 deref(); | 58 deref(); |
58 return; | 59 return; |
59 } | 60 } |
60 ASSERT(currentThread() == m_targetThread->threadID()); | 61 ASSERT(base::PlatformThread::CurrentId() == m_targetThread->threadID()); |
61 task->performTask(); | 62 task->performTask(); |
62 deref(); | 63 deref(); |
63 } | 64 } |
64 | 65 |
65 CCThread* m_targetThread; | 66 CCThread* m_targetThread; |
66 bool m_shutdown; // Only accessed on the target thread | 67 bool m_shutdown; // Only accessed on the target thread |
67 }; | 68 }; |
68 | 69 |
69 } | 70 } |
70 | 71 |
71 #endif | 72 #endif |
OLD | NEW |