]> git.ipfire.org Git - thirdparty/haproxy.git/commitdiff
MINOR: task: turn the WQ lock to an RW_LOCK
authorWilly Tarreau <w@1wt.eu>
Tue, 28 May 2019 16:48:07 +0000 (18:48 +0200)
committerWilly Tarreau <w@1wt.eu>
Tue, 28 May 2019 17:15:44 +0000 (19:15 +0200)
For now it's exclusively used as a write lock though, thus it remains
100% equivalent to the spinlock it replaces.

include/proto/task.h
src/task.c

index 0aea72630526e4892fe612df8cfc24e2816f5774..585d8900abfb7b9ee3734e3e61a7ed57533fbf24 100644 (file)
@@ -102,7 +102,7 @@ extern int global_rqueue_size; /* Number of element sin the global runqueue */
 extern struct task_per_thread task_per_thread[MAX_THREADS];
 
 __decl_hathreads(extern HA_SPINLOCK_T rq_lock);  /* spin lock related to run queue */
-__decl_hathreads(extern HA_SPINLOCK_T wq_lock);  /* spin lock related to wait queue */
+__decl_hathreads(extern HA_RWLOCK_T wq_lock);    /* RW lock related to the wait queue */
 
 
 static inline void task_insert_into_tasklet_list(struct task *t);
@@ -180,10 +180,10 @@ static inline struct task *task_unlink_wq(struct task *t)
        if (likely(task_in_wq(t))) {
                locked = atleast2(t->thread_mask);
                if (locked)
-                       HA_SPIN_LOCK(TASK_WQ_LOCK, &wq_lock);
+                       HA_RWLOCK_WRLOCK(TASK_WQ_LOCK, &wq_lock);
                __task_unlink_wq(t);
                if (locked)
-                       HA_SPIN_UNLOCK(TASK_WQ_LOCK, &wq_lock);
+                       HA_RWLOCK_WRUNLOCK(TASK_WQ_LOCK, &wq_lock);
        }
        return t;
 }
@@ -400,10 +400,10 @@ static inline void task_queue(struct task *task)
 
 #ifdef USE_THREAD
        if (atleast2(task->thread_mask)) {
-               HA_SPIN_LOCK(TASK_WQ_LOCK, &wq_lock);
+               HA_RWLOCK_WRLOCK(TASK_WQ_LOCK, &wq_lock);
                if (!task_in_wq(task) || tick_is_lt(task->expire, task->wq.key))
                        __task_queue(task, &timers);
-               HA_SPIN_UNLOCK(TASK_WQ_LOCK, &wq_lock);
+               HA_RWLOCK_WRUNLOCK(TASK_WQ_LOCK, &wq_lock);
        } else
 #endif
        {
@@ -424,14 +424,15 @@ static inline void task_schedule(struct task *task, int when)
 
 #ifdef USE_THREAD
        if (atleast2(task->thread_mask)) {
-               HA_SPIN_LOCK(TASK_WQ_LOCK, &wq_lock);
+               /* FIXME: is it really needed to lock the WQ during the check ? */
+               HA_RWLOCK_WRLOCK(TASK_WQ_LOCK, &wq_lock);
                if (task_in_wq(task))
                        when = tick_first(when, task->expire);
 
                task->expire = when;
                if (!task_in_wq(task) || tick_is_lt(task->expire, task->wq.key))
                        __task_queue(task, &timers);
-               HA_SPIN_UNLOCK(TASK_WQ_LOCK, &wq_lock);
+               HA_RWLOCK_WRUNLOCK(TASK_WQ_LOCK, &wq_lock);
        } else
 #endif
        {
index 5cf7d74e2e57e53ba4b7278273f68eb32ddd82e8..5845ffe044a0b4ef9f8ca2a487ec8970d4fbaf63 100644 (file)
@@ -45,7 +45,7 @@ unsigned int niced_tasks = 0;      /* number of niced tasks in the run queue */
 THREAD_LOCAL struct task *curr_task = NULL; /* task currently running or NULL */
 
 __decl_aligned_spinlock(rq_lock); /* spin lock related to run queue */
-__decl_aligned_spinlock(wq_lock); /* spin lock related to wait queue */
+__decl_aligned_rwlock(wq_lock);   /* RW lock related to the wait queue */
 
 #ifdef USE_THREAD
 struct eb_root timers;      /* sorted timers tree, global */
@@ -211,7 +211,7 @@ int wake_expired_tasks()
 
 #ifdef USE_THREAD
        while (1) {
-               HA_SPIN_LOCK(TASK_WQ_LOCK, &wq_lock);
+               HA_RWLOCK_WRLOCK(TASK_WQ_LOCK, &wq_lock);
   lookup_next:
                eb = eb32_lookup_ge(&timers, now_ms - TIMER_LOOK_BACK);
                if (!eb) {
@@ -253,10 +253,10 @@ int wake_expired_tasks()
                        goto lookup_next;
                }
                task_wakeup(task, TASK_WOKEN_TIMER);
-               HA_SPIN_UNLOCK(TASK_WQ_LOCK, &wq_lock);
+               HA_RWLOCK_WRUNLOCK(TASK_WQ_LOCK, &wq_lock);
        }
 
-       HA_SPIN_UNLOCK(TASK_WQ_LOCK, &wq_lock);
+       HA_RWLOCK_WRUNLOCK(TASK_WQ_LOCK, &wq_lock);
 #endif
        return ret;
 }