diff options
author | Prakash Surya <[email protected]> | 2011-12-16 09:44:31 -0800 |
---|---|---|
committer | Brian Behlendorf <[email protected]> | 2011-12-16 13:26:54 -0800 |
commit | e7e5f78e7bf6dc86337483f4d9f01becc017d185 (patch) | |
tree | 36355eabeffff2829fe1aff8c3ac879c33168861 /include/sys | |
parent | c2dceb5cd5221f7e1bde915218f5d2cf69920959 (diff) |
Swap taskq_ent_t with taskqid_t in taskq_thread_t
The taskq_t's active thread list is sorted based on its
tqt_ent->tqent_id field. The list is kept sorted solely by inserting
new taskq_thread_t's in their correct sorted location; no other
means is used. This means that once inserted, if a taskq_thread_t's
tqt_ent->tqent_id field changes, the list runs the risk of no
longer being sorted.
Prior to the introduction of the taskq_dispatch_prealloc() interface,
this was not a problem as a taskq_ent_t actively being serviced under
the old interface should always have a static tqent_id field. Thus,
once the taskq_thread_t is added to the taskq_t's active thread list,
the taskq_thread_t's tqt_ent->tqent_id field would remain constant.
Now, this is no longer the case. Currently, if using the
taskq_dispatch_prealloc() interface, any given taskq_ent_t actively
being serviced _may_ have its tqent_id value incremented. This happens
when the preallocated taskq_ent_t structure is recursively dispatched.
Thus, a taskq_thread_t could potentially have its tqt_ent->tqent_id
field silently modified from under its feet. If this were to happen
to a taskq_thread_t on a taskq_t's active thread list, this would
compromise the integrity of the order of the list (as the list
_may_ no longer be sorted).
To get around this, the taskq_thread_t's taskq_ent_t pointer was
replaced with its own static copy of the tqent_id. So, as a taskq_ent_t
is pulled off of the taskq_t's pending list, a static copy of its
tqent_id is made and this copy is used to sort the active thread
list. Using a static copy is key in ensuring the integrity of the
order of the active thread list. Even if the underlying taskq_ent_t
is recursively dispatched (as has its tqent_id modified), this
static copy stored inside the taskq_thread_t will remain constant.
Signed-off-by: Prakash Surya <[email protected]>
Signed-off-by: Brian Behlendorf <[email protected]>
Issue #71
Diffstat (limited to 'include/sys')
-rw-r--r-- | include/sys/taskq.h | 2 |
1 files changed, 1 insertions, 1 deletions
diff --git a/include/sys/taskq.h b/include/sys/taskq.h index 54d869afe..0a7143375 100644 --- a/include/sys/taskq.h +++ b/include/sys/taskq.h @@ -96,7 +96,7 @@ typedef struct taskq_thread { struct list_head tqt_active_list; struct task_struct *tqt_thread; taskq_t *tqt_tq; - taskq_ent_t *tqt_ent; + taskqid_t tqt_id; } taskq_thread_t; /* Global system-wide dynamic task queue available for all consumers */ |