1
#ifndef __tascel_SplitQueueOpt_h__
2
#define __tascel_SplitQueueOpt_h__
4
#include "TerminationDetector.h"
9
* A set of task queues shared among processes.
11
* Each process has a local queue with a maximum number of possible tasks.
12
* A process can steal tasks from any other process's queue and have
13
* tasks stolen from its own queue.
15
* This implementation splits the queue into a local and shared portion.
16
* This allows the local process to modify its queue without locking.
18
* Compared to the original SplitQueue, this SplitQueueOpt is further
19
* optimized by allowing a stealing process to steal without locking all of
20
* the queue state, as described in "Scalable Work Stealing", SC'09.
25
* The local queue state which other procs can modify.
27
* Queue state is further split into two pieces. The vtail2 is separated
28
* so that it can be updated independent of the rest of the queue state.
32
* The local queue state which other procs can modify.
35
int dirty; /**< whether a steal has occurred */
36
int split; /**< the split between head and tail */
37
int tail; /**< the tail of the queue */
38
int size_shared;/**< the number of shared tasks in the queue */
40
int vtail2; /**< incremented after a steal completes */
43
const int max_ntsks; /**< max number of tasks allowed in queue */
44
const int tsk_size; /**< size of a single task */
45
char **q; /**< addresses of queue data on all procs */
46
sq_state_t **sq_state; /**< addresses of queue state on all procs */
47
int *head; /**< pointer to this procs head_val */
48
int *size_local; /**< pointer to this procs size_local_val */
49
int *vtail1; /**< pointer to this procs vtail1_val */
50
int *tail; /**< pointer to this procs tail state */
51
int *vtail2; /**< pointer to this procs vtail2 state */
52
int *size_shared; /**< pointer to this procs size_shared state */
53
int *split; /**< pointer to this procs split state */
54
int *dirty; /**< pointer to this procs dirty state */
55
int size_local_val; /**< size of local portion of local queue */
56
int head_val; /**< index of the local queue's head */
57
int vtail1_val; /**< the true end index of the queue */
58
TerminationDetector td; /**< the termination detector */
59
int **locks; /**< Locks for mutual exclusion */
62
* Moves tasks from the shared portion to the local portion.
64
* @param[in] _nacquire number of tasks to move
66
int acquireFromShared(int _nacquire);
69
* Moves tasks from the local portion to the shared portion.
71
* @param[in] ndonate number of tasks to move
73
void releaseToShared(int ndonate);
76
* If all steal operations have completed, update vtail1.
81
* Returns true if the local queue is empty.
86
* Returns true if the local queue is full.
91
* Returns true if this proc can add tasks to its local private portion.
93
bool spaceAvailable() const;
96
* Obtain the lock (locks[proc])
97
* @param[in] proc Process whose lock needs to be obainted
98
* @param[in] num_tries If non-blocking lock, number of
99
* attempts. Negative number results in a blocking call.
100
* @return true if locking succeeded
102
bool lock(int proc, int num_tries=-1);
105
* Release the lock (locks[proc])
106
* @param[in] proc Process whose lock needs to be released
108
void unlock(int proc);
113
* Constructs the SplitQueueOpt instance.
115
* @param[in] tsk_size size of a single task
116
* @param[in] max_ntsks max number of tasks allowed in a queue
118
* @pre tsk_size must be the same value on all procs
119
* @pre max_ntsks must be the same value on all procs
121
SplitQueueOpt(int tsk_size, int max_ntsks);
124
* Destroys the SplitQueue instance.
129
* Retrieves a task from the private portion of the local queue.
131
* @param[out] dscr the retrieved task
132
* @param[in] dlen size of the retrieved task
134
* @pre dscr is not NULL
135
* @pre dlen == tsk_size
137
bool getTask(void *dscr, int dlen);
140
* Adds a task to the private portion of the local queue.
142
* @param[in] dscr the task to add
143
* @param[in] dlen size of the added task
145
* @pre dscr is not NULL
146
* @pre dlen == tsk_size
148
void addTask(void *dscr, int dlen);
151
* Steals one or more tasks from the given proc's shared portion.
153
* @param[in] proc to steal from
155
bool steal(int proc);
158
* Returns true if all of the tasks have been processed.
160
bool hasTerminated();
163
* Returns the number of tasks in the entire local queue.
165
int numTasks() const {
166
return *size_local + *size_shared;
170
* Runs the termination detector.
174
}; /* SplitQueueOpt */
177
#endif /*__tascel_SplitQueueOpt_h__*/