OLD | NEW |
1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2006-2008 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 BASE_TASK_H_ | 5 #ifndef BASE_TASK_H_ |
6 #define BASE_TASK_H_ | 6 #define BASE_TASK_H_ |
7 | 7 |
8 #include "base/non_thread_safe.h" | 8 #include "base/non_thread_safe.h" |
9 #include "base/tracked.h" | 9 #include "base/tracked.h" |
10 #include "base/tuple.h" | 10 #include "base/tuple.h" |
(...skipping 187 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
198 // | 198 // |
199 // This traits-class is used by RunnableMethod to manage the lifetime of the | 199 // This traits-class is used by RunnableMethod to manage the lifetime of the |
200 // callee object. By default, it is assumed that the callee supports AddRef | 200 // callee object. By default, it is assumed that the callee supports AddRef |
201 // and Release methods. A particular class can specialize this template to | 201 // and Release methods. A particular class can specialize this template to |
202 // define other lifetime management. For example, if the callee is known to | 202 // define other lifetime management. For example, if the callee is known to |
203 // live longer than the RunnableMethod object, then a RunnableMethodTraits | 203 // live longer than the RunnableMethod object, then a RunnableMethodTraits |
204 // struct could be defined with empty RetainCallee and ReleaseCallee methods. | 204 // struct could be defined with empty RetainCallee and ReleaseCallee methods. |
205 | 205 |
206 template <class T> | 206 template <class T> |
207 struct RunnableMethodTraits { | 207 struct RunnableMethodTraits { |
208 static void RetainCallee(T* obj) { | 208 RunnableMethodTraits() { |
| 209 #ifndef NDEBUG |
| 210 origin_thread_id_ = PlatformThread::CurrentId(); |
| 211 #endif |
| 212 } |
| 213 |
| 214 ~RunnableMethodTraits() { |
| 215 #ifndef NDEBUG |
| 216 // If destroyed on a separate thread, then we had better have been using |
| 217 // thread-safe reference counting! |
| 218 if (origin_thread_id_ != PlatformThread::CurrentId()) |
| 219 DCHECK(T::ImplementsThreadSafeReferenceCounting()); |
| 220 #endif |
| 221 } |
| 222 |
| 223 void RetainCallee(T* obj) { |
209 obj->AddRef(); | 224 obj->AddRef(); |
210 } | 225 } |
211 static void ReleaseCallee(T* obj) { | 226 |
| 227 void ReleaseCallee(T* obj) { |
212 obj->Release(); | 228 obj->Release(); |
213 } | 229 } |
| 230 |
| 231 private: |
| 232 #ifndef NDEBUG |
| 233 PlatformThreadId origin_thread_id_; |
| 234 #endif |
214 }; | 235 }; |
215 | 236 |
216 // RunnableMethod and RunnableFunction ----------------------------------------- | 237 // RunnableMethod and RunnableFunction ----------------------------------------- |
217 // | 238 // |
218 // Runnable methods are a type of task that call a function on an object when | 239 // Runnable methods are a type of task that call a function on an object when |
219 // they are run. We implement both an object and a set of NewRunnableMethod and | 240 // they are run. We implement both an object and a set of NewRunnableMethod and |
220 // NewRunnableFunction functions for convenience. These functions are | 241 // NewRunnableFunction functions for convenience. These functions are |
221 // overloaded and will infer the template types, simplifying calling code. | 242 // overloaded and will infer the template types, simplifying calling code. |
222 // | 243 // |
223 // The template definitions all use the following names: | 244 // The template definitions all use the following names: |
224 // T - the class type of the object you're supplying | 245 // T - the class type of the object you're supplying |
225 // this is not needed for the Static version of the call | 246 // this is not needed for the Static version of the call |
226 // Method/Function - the signature of a pointer to the method or function you | 247 // Method/Function - the signature of a pointer to the method or function you |
227 // want to call | 248 // want to call |
228 // Param - the parameter(s) to the method, possibly packed as a Tuple | 249 // Param - the parameter(s) to the method, possibly packed as a Tuple |
229 // A - the first parameter (if any) to the method | 250 // A - the first parameter (if any) to the method |
230 // B - the second parameter (if any) to the mathod | 251 // B - the second parameter (if any) to the mathod |
231 // | 252 // |
232 // Put these all together and you get an object that can call a method whose | 253 // Put these all together and you get an object that can call a method whose |
233 // signature is: | 254 // signature is: |
234 // R T::MyFunction([A[, B]]) | 255 // R T::MyFunction([A[, B]]) |
235 // | 256 // |
236 // Usage: | 257 // Usage: |
237 // PostTask(FROM_HERE, NewRunnableMethod(object, &Object::method[, a[, b]]) | 258 // PostTask(FROM_HERE, NewRunnableMethod(object, &Object::method[, a[, b]]) |
238 // PostTask(FROM_HERE, NewRunnableFunction(&function[, a[, b]]) | 259 // PostTask(FROM_HERE, NewRunnableFunction(&function[, a[, b]]) |
239 | 260 |
240 // RunnableMethod and NewRunnableMethod implementation ------------------------- | 261 // RunnableMethod and NewRunnableMethod implementation ------------------------- |
241 | 262 |
242 template <class T, class Method, class Params> | 263 template <class T, class Method, class Params> |
243 class RunnableMethod : public CancelableTask, | 264 class RunnableMethod : public CancelableTask { |
244 public RunnableMethodTraits<T> { | |
245 public: | 265 public: |
246 RunnableMethod(T* obj, Method meth, const Params& params) | 266 RunnableMethod(T* obj, Method meth, const Params& params) |
247 : obj_(obj), meth_(meth), params_(params) { | 267 : obj_(obj), meth_(meth), params_(params) { |
248 RetainCallee(obj_); | 268 traits_.RetainCallee(obj_); |
249 } | 269 } |
| 270 |
250 ~RunnableMethod() { | 271 ~RunnableMethod() { |
251 ReleaseCallee(); | 272 ReleaseCallee(); |
252 } | 273 } |
253 | 274 |
254 virtual void Run() { | 275 virtual void Run() { |
255 if (obj_) | 276 if (obj_) |
256 DispatchToMethod(obj_, meth_, params_); | 277 DispatchToMethod(obj_, meth_, params_); |
257 } | 278 } |
258 | 279 |
259 virtual void Cancel() { | 280 virtual void Cancel() { |
260 ReleaseCallee(); | 281 ReleaseCallee(); |
261 } | 282 } |
262 | 283 |
263 private: | 284 private: |
264 void ReleaseCallee() { | 285 void ReleaseCallee() { |
265 if (obj_) { | 286 if (obj_) { |
266 RunnableMethodTraits<T>::ReleaseCallee(obj_); | 287 traits_.ReleaseCallee(obj_); |
267 obj_ = NULL; | 288 obj_ = NULL; |
268 } | 289 } |
269 } | 290 } |
270 | 291 |
271 T* obj_; | 292 T* obj_; |
272 Method meth_; | 293 Method meth_; |
273 Params params_; | 294 Params params_; |
| 295 RunnableMethodTraits<T> traits_; |
274 }; | 296 }; |
275 | 297 |
276 template <class T, class Method> | 298 template <class T, class Method> |
277 inline CancelableTask* NewRunnableMethod(T* object, Method method) { | 299 inline CancelableTask* NewRunnableMethod(T* object, Method method) { |
278 return new RunnableMethod<T, Method, Tuple0>(object, method, MakeTuple()); | 300 return new RunnableMethod<T, Method, Tuple0>(object, method, MakeTuple()); |
279 } | 301 } |
280 | 302 |
281 template <class T, class Method, class A> | 303 template <class T, class Method, class A> |
282 inline CancelableTask* NewRunnableMethod(T* object, Method method, const A& a) { | 304 inline CancelableTask* NewRunnableMethod(T* object, Method method, const A& a) { |
283 return new RunnableMethod<T, Method, Tuple1<A> >(object, | 305 return new RunnableMethod<T, Method, Tuple1<A> >(object, |
(...skipping 362 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
646 | 668 |
647 template <class T, typename ReturnValue> | 669 template <class T, typename ReturnValue> |
648 typename CallbackWithReturnValue<ReturnValue>::Type* | 670 typename CallbackWithReturnValue<ReturnValue>::Type* |
649 NewCallbackWithReturnValue(T* object, ReturnValue (T::*method)()) { | 671 NewCallbackWithReturnValue(T* object, ReturnValue (T::*method)()) { |
650 return new CallbackWithReturnValueImpl<T, ReturnValue (T::*)(), ReturnValue>( | 672 return new CallbackWithReturnValueImpl<T, ReturnValue (T::*)(), ReturnValue>( |
651 object, method); | 673 object, method); |
652 } | 674 } |
653 | 675 |
654 | 676 |
655 #endif // BASE_TASK_H_ | 677 #endif // BASE_TASK_H_ |
OLD | NEW |