]> git.ipfire.org Git - thirdparty/haproxy.git/commitdiff
BUG/MINOR: hlua_fcn/queue: fix broken pop_wait()
authorAurelien DARRAGON <adarragon@haproxy.com>
Wed, 10 May 2023 17:30:26 +0000 (19:30 +0200)
committerChristopher Faulet <cfaulet@haproxy.com>
Thu, 11 May 2023 07:23:14 +0000 (09:23 +0200)
queue:pop_wait() was broken during late refactor prior to merge.
(Due to small modifications to ensure that pop() returns nil on empty
queue instead of nothing)

Because of this, pop_wait() currently behaves exactly as pop(), resulting
in 100% active CPU when used in a while loop.

Indeed, _hlua_queue_pop() should explicitly return 0 when the queue is
empty since pop_wait logic relies on this and the pushnil should be
handled directly in queue:pop() function instead.

Adding some comments as well to document this.

src/hlua_fcn.c

index 761cfae880b3f08c471b7f9dcb2fa566dfabb8c8..27396144eec27aecab9222201900c94cd209f182 100644 (file)
@@ -583,18 +583,18 @@ static int hlua_queue_push(lua_State *L)
        return 1;
 }
 
-/* queue:pop(): returns the first item at the top of que queue or nil if
- * the queue is empty.
+/* internal queue pop helper, returns 1 if it successfuly popped an item
+ * from the queue and pushed it on lua stack.
+ *
+ * Else it returns 0 (nothing is pushed on the stack)
  */
 static int _hlua_queue_pop(lua_State *L, struct hlua_queue *queue)
 {
        struct hlua_queue_item *item;
 
        item = MT_LIST_POP(&queue->list, typeof(item), list);
-       if (!item) {
-               lua_pushnil(L);
-               return 1; /* nothing in queue, return nil */
-       }
+       if (!item)
+               return 0; /* nothing in queue */
 
        HA_ATOMIC_DEC(&queue->size);
        /* push lua obj on the stack */
@@ -605,12 +605,20 @@ static int _hlua_queue_pop(lua_State *L, struct hlua_queue *queue)
 
        return 1;
 }
+
+/* queue:pop(): returns the first item at the top of que queue or nil if
+ * the queue is empty.
+ */
 static int hlua_queue_pop(lua_State *L)
 {
        struct hlua_queue *queue = hlua_check_queue(L, 1);
 
        BUG_ON(!queue);
-       return _hlua_queue_pop(L, queue);
+       if (!_hlua_queue_pop(L, queue)) {
+               /* nothing in queue, push nil */
+               lua_pushnil(L);
+       }
+       return 1; /* either item or nil is at the top of the stack */
 }
 
 /* queue:pop_wait(): same as queue:pop() but doesn't return on empty queue.