1/*
2 * Copyright 2014 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8#ifndef SkTaskGroup_DEFINED
9#define SkTaskGroup_DEFINED
10
11#include "SkTypes.h"
12
13struct SkRunnable;
14
15class SkTaskGroup : SkNoncopyable {
16public:
17    // Create one of these in main() to enable SkTaskGroups globally.
18    struct Enabler : SkNoncopyable {
19        explicit Enabler(int threads = -1);  // Default is system-reported core count.
20        ~Enabler();
21    };
22
23    SkTaskGroup();
24    ~SkTaskGroup() { this->wait(); }
25
26    // Add a task to this SkTaskGroup.  It will likely run on another thread.
27    // Neither add() method takes owership of any of its parameters.
28    void add(SkRunnable*);
29
30    template <typename T>
31    void add(void (*fn)(T*), T* arg) { this->add((void_fn)fn, (void*)arg); }
32
33    // Add a batch of N tasks, all calling fn with different arguments.
34    // Equivalent to a loop over add(fn, arg), but with perhaps less synchronization overhead.
35    template <typename T>
36    void batch(void (*fn)(T*), T* args, int N) { this->batch((void_fn)fn, args, N, sizeof(T)); }
37
38    // Block until all Tasks previously add()ed to this SkTaskGroup have run.
39    // You may safely reuse this SkTaskGroup after wait() returns.
40    void wait();
41
42private:
43    typedef void(*void_fn)(void*);
44
45    void add  (void_fn, void* arg);
46    void batch(void_fn, void* args, int N, size_t stride);
47
48    /*atomic*/ int32_t fPending;
49};
50
51#endif//SkTaskGroup_DEFINED
52