OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2013 Google Inc. All rights reserved. | 2 * Copyright (C) 2013 Google Inc. All rights reserved. |
3 * | 3 * |
4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
6 * met: | 6 * met: |
7 * | 7 * |
8 * * Redistributions of source code must retain the above copyright | 8 * * Redistributions of source code must retain the above copyright |
9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
10 * * Neither the name of Google Inc. nor the names of its | 10 * * Neither the name of Google Inc. nor the names of its |
(...skipping 10 matching lines...) Expand all Loading... |
21 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY | 21 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
22 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | 22 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
23 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE | 23 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
24 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | 24 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
25 */ | 25 */ |
26 | 26 |
27 #ifndef ExecutionContextTask_h | 27 #ifndef ExecutionContextTask_h |
28 #define ExecutionContextTask_h | 28 #define ExecutionContextTask_h |
29 | 29 |
30 #include "core/CoreExport.h" | 30 #include "core/CoreExport.h" |
| 31 #include "platform/CrossThreadFunctional.h" |
31 #include "wtf/Allocator.h" | 32 #include "wtf/Allocator.h" |
32 #include "wtf/Functional.h" | 33 #include "wtf/Functional.h" |
33 #include "wtf/Noncopyable.h" | 34 #include "wtf/Noncopyable.h" |
34 #include "wtf/PtrUtil.h" | 35 #include "wtf/PtrUtil.h" |
35 #include "wtf/text/WTFString.h" | 36 #include "wtf/text/WTFString.h" |
| 37 #include <type_traits> |
36 | 38 |
37 namespace blink { | 39 namespace blink { |
38 | 40 |
39 class ExecutionContext; | 41 class ExecutionContext; |
40 | 42 |
41 class CORE_EXPORT ExecutionContextTask { | 43 class CORE_EXPORT ExecutionContextTask { |
42 WTF_MAKE_NONCOPYABLE(ExecutionContextTask); | 44 WTF_MAKE_NONCOPYABLE(ExecutionContextTask); |
43 USING_FAST_MALLOC(ExecutionContextTask); | 45 USING_FAST_MALLOC(ExecutionContextTask); |
44 public: | 46 public: |
45 ExecutionContextTask() { } | 47 ExecutionContextTask() { } |
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
99 // of using |bind| directly to state explicitly that there is no need to care | 101 // of using |bind| directly to state explicitly that there is no need to care |
100 // about thread safety when posting the task. | 102 // about thread safety when posting the task. |
101 // When posting tasks across threads, use |createCrossThreadTask|. | 103 // When posting tasks across threads, use |createCrossThreadTask|. |
102 template<typename FunctionType, typename... P> | 104 template<typename FunctionType, typename... P> |
103 std::unique_ptr<ExecutionContextTask> createSameThreadTask( | 105 std::unique_ptr<ExecutionContextTask> createSameThreadTask( |
104 FunctionType function, P&&... parameters) | 106 FunctionType function, P&&... parameters) |
105 { | 107 { |
106 return internal::createCallClosureTask(WTF::bind(function, std::forward<P>(p
arameters)...)); | 108 return internal::createCallClosureTask(WTF::bind(function, std::forward<P>(p
arameters)...)); |
107 } | 109 } |
108 | 110 |
| 111 // createCrossThreadTask(...) is ExecutionContextTask version of |
| 112 // crossThreadBind(). |
| 113 // Using WTF::bind() directly is not thread-safe due to temporary objects, see |
| 114 // https://crbug.com/390851 for details. |
| 115 // |
| 116 // Example: |
| 117 // void func1(int, const String&); |
| 118 // createCrossThreadTask(func1, 42, str); |
| 119 // func1(42, str2) will be called, where |str2| is a deep copy of |
| 120 // |str| (created by str.isolatedCopy()). |
| 121 // |
| 122 // Don't (if you pass the task across threads): |
| 123 // bind(func1, 42, str); |
| 124 // bind(func1, 42, str.isolatedCopy()); |
| 125 // |
| 126 // For functions: |
| 127 // void functionEC(MP1, ..., MPn, ExecutionContext*); |
| 128 // void function(MP1, ..., MPn); |
| 129 // class C { |
| 130 // void memberEC(MP1, ..., MPn, ExecutionContext*); |
| 131 // void member(MP1, ..., MPn); |
| 132 // }; |
| 133 // We create tasks represented by std::unique_ptr<ExecutionContextTask>: |
| 134 // createCrossThreadTask(functionEC, const P1& p1, ..., const Pn& pn); |
| 135 // createCrossThreadTask(memberEC, C* ptr, const P1& p1, ..., const Pn& pn); |
| 136 // createCrossThreadTask(function, const P1& p1, ..., const Pn& pn); |
| 137 // createCrossThreadTask(member, C* ptr, const P1& p1, ..., const Pn& pn); |
| 138 // (|ptr| can also be WeakPtr<C> or other pointer-like types) |
| 139 // and then the following are called on the target thread: |
| 140 // functionEC(p1, ..., pn, context); |
| 141 // ptr->memberEC(p1, ..., pn, context); |
| 142 // function(p1, ..., pn); |
| 143 // ptr->member(p1, ..., pn); |
| 144 // |
| 145 // ExecutionContext: |
| 146 // |context| is supplied by the target thread. |
| 147 // |
| 148 // Deep copies by crossThreadBind(): |
| 149 // |ptr|, |p1|, ..., |pn| are processed by crossThreadBind() and thus |
| 150 // CrossThreadCopier. |
| 151 // You don't have to call manually e.g. isolatedCopy(). |
| 152 // To pass things that cannot be copied by CrossThreadCopier |
| 153 // (e.g. pointers), use crossThreadUnretained() explicitly. |
| 154 |
| 155 template<typename FunctionType, typename... P> |
| 156 std::unique_ptr<ExecutionContextTask> createCrossThreadTask(FunctionType functio
n, P&&... parameters) |
| 157 { |
| 158 return internal::createCallClosureTask(crossThreadBind(function, std::forwar
d<P>(parameters)...)); |
| 159 } |
| 160 |
109 } // namespace blink | 161 } // namespace blink |
110 | 162 |
111 #endif | 163 #endif |
OLD | NEW |