@@ -62,10 +62,10 @@ static void worker(void* arg) {
6262  uv_sem_post ((uv_sem_t * ) arg );
6363  arg  =  NULL ;
6464
65+   uv_mutex_lock (& mutex );
6566  for  (;;) {
66-     uv_mutex_lock ( & mutex ); 
67+     /* ` mutex` should always be locked at this point. */ 
6768
68-   wait_for_work :
6969    /* Keep waiting while either no work is present or only slow I/O 
7070       and we're at the threshold for that. */ 
7171    while  (QUEUE_EMPTY (& wq ) || 
@@ -93,13 +93,13 @@ static void worker(void* arg) {
9393         other work in the queue is done. */ 
9494      if  (slow_io_work_running  >= slow_work_thread_threshold ()) {
9595        QUEUE_INSERT_TAIL (& wq , q );
96-         goto  wait_for_work ;
96+         continue ;
9797      }
9898
9999      /* If we encountered a request to run slow I/O work but there is none 
100100         to run, that means it's cancelled => Start over. */ 
101101      if  (QUEUE_EMPTY (& slow_io_pending_wq ))
102-         goto  wait_for_work ;
102+         continue ;
103103
104104      is_slow_work  =  1 ;
105105      slow_io_work_running ++ ;
@@ -122,13 +122,19 @@ static void worker(void* arg) {
122122    w -> work (w );
123123
124124    uv_mutex_lock (& w -> loop -> wq_mutex );
125-     if  (is_slow_work )
126-       slow_io_work_running -- ;
127125    w -> work  =  NULL ;  /* Signal uv_cancel() that the work req is done 
128126                        executing. */ 
129127    QUEUE_INSERT_TAIL (& w -> loop -> wq , & w -> wq );
130128    uv_async_send (& w -> loop -> wq_async );
131129    uv_mutex_unlock (& w -> loop -> wq_mutex );
130+ 
131+     /* Lock `mutex` since that is expected at the start of the next 
132+      * iteration. */ 
133+     uv_mutex_lock (& mutex );
134+     if  (is_slow_work ) {
135+       /* `slow_io_work_running` is protected by `mutex`. */ 
136+       slow_io_work_running -- ;
137+     }
132138  }
133139}
134140
0 commit comments