MCPcopy Create free account
hub / github.com/F-Stack/f-stack / task_alloc

Function task_alloc

freebsd/contrib/openzfs/lib/libzpool/taskq.c:41–84  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

39#define TASKQ_ACTIVE 0x00010000
40
41static taskq_ent_t *
42task_alloc(taskq_t *tq, int tqflags)
43{
44 taskq_ent_t *t;
45 int rv;
46
47again: if ((t = tq->tq_freelist) != NULL && tq->tq_nalloc >= tq->tq_minalloc) {
48 ASSERT(!(t->tqent_flags & TQENT_FLAG_PREALLOC));
49 tq->tq_freelist = t->tqent_next;
50 } else {
51 if (tq->tq_nalloc >= tq->tq_maxalloc) {
52 if (!(tqflags & KM_SLEEP))
53 return (NULL);
54
55 /*
56 * We don't want to exceed tq_maxalloc, but we can't
57 * wait for other tasks to complete (and thus free up
58 * task structures) without risking deadlock with
59 * the caller. So, we just delay for one second
60 * to throttle the allocation rate. If we have tasks
61 * complete before one second timeout expires then
62 * taskq_ent_free will signal us and we will
63 * immediately retry the allocation.
64 */
65 tq->tq_maxalloc_wait++;
66 rv = cv_timedwait(&tq->tq_maxalloc_cv,
67 &tq->tq_lock, ddi_get_lbolt() + hz);
68 tq->tq_maxalloc_wait--;
69 if (rv > 0)
70 goto again; /* signaled */
71 }
72 mutex_exit(&tq->tq_lock);
73
74 t = kmem_alloc(sizeof (taskq_ent_t), tqflags);
75
76 mutex_enter(&tq->tq_lock);
77 if (t != NULL) {
78 /* Make sure we start without any flags */
79 t->tqent_flags = 0;
80 tq->tq_nalloc++;
81 }
82 }
83 return (t);
84}
85
86static void
87task_free(taskq_t *tq, taskq_ent_t *t)

Callers 3

taskq_dispatchFunction · 0.70
taskq_createFunction · 0.70
taskq_destroyFunction · 0.70

Calls 3

mutex_exitFunction · 0.85
mutex_enterFunction · 0.85
cv_timedwaitFunction · 0.70

Tested by

no test coverage detected