Hi Thierry,

Okay found a simple reproduction with tcploop with a 6 second delay in there and a short sleep before calling kqueue.

./tcploop 81 L W N20 A R S:"response1\r\n" R P6000 S:"response2\r\n" R [ F K ]

     gettimeofday(&before_poll, NULL);
+    usleep(100);
     status = kevent(kqueue_fd[tid], // int kq

Together with the attached config the issue is reproduced every time the /myapplet url is requested.

Output as below:
00000000:stats.clihdr[0007:ffffffff]: Accept-Language: nl-NL,nl;q=0.9,en-US;q=0.8,en;q=0.7
[info] 130/195936 (76770) : Wait for it..
[info] 130/195937 (76770) : Wait response 2..
  xref_get_peer_and_lock xref->peer == 1

Hope this helps to come up with a solution..

Thanks in advance,
PiBa-NL (Pieter)

Op 9-5-2018 om 19:47 schreef PiBa-NL:
Hi Thierry,

Op 9-5-2018 om 18:30 schreef Thierry Fournier:
It seems a dead lock, but you observe a loop.
Effectively it is a deadlock, it keeps looping over these few lines of code below from xref.h <http://git.haproxy.org/?p=haproxy.git;a=blob_plain;f=include/common/xref.h;hb=29d698040d6bb56b29c036aeba05f0d52d8ce94b>.. The XCHG just swaps the 2 values (both are '1') and continues on, then the local==BUSY check is true it loops and swaps 1 and 1 again, and the circle continues..

Thanks for looking into it :) Ill try and get 'simpler' reproduction with some well placed sleep() as you suggest.
Regards,
PiBa-NL

http://git.haproxy.org/?p=haproxy.git;a=blob;f=include/common/xref.h;h=6dfa7b62758dfaebe12d25f66aaa858dc873a060;hb=29d698040d6bb56b29c036aeba05f0d52d8ce94b

function myapplet(applet)

  core.Info("Wait for it..")
  core.sleep(1)

  local result = ""
    con = core.tcp()
    con:settimeout(1)
    con:connect("127.0.0.1",81)
    con:send("Test1\r\n")
    r = con:receive("*l")
    result = result .. tostring(r)
    con:send("Test\r\n")
  core.Info("Wait response 2..")
    r2 = con:receive("*l")
    result = result .. tostring(r2)
  core.Info("close..")
    con:close()
  core.Info("DONE")

        response = "Finished"
        applet:add_header("Server", "haproxy/webstats")
        applet:add_header("Content-Type", "text/html")
        applet:start_response()
        applet:send(response)

end

core.register_service("myapplet", "http", myapplet)
global
  lua-load /root/haproxytest/hang_timeout_close.lua

defaults
        mode http
        timeout connect 5s
        timeout client 30s
        timeout server 60s
  
frontend stats
        bind *:80
        stats enable
        stats admin if TRUE
        stats refresh 1s

  acl myapplet path -m beg /myapplet
  http-request use-service lua.myapplet if myapplet

 include/common/xref.h | 4 ++++
 src/ev_kqueue.c       | 1 +
 2 files changed, 5 insertions(+)

diff --git a/include/common/xref.h b/include/common/xref.h
index 6dfa7b6..e6905a1 100644
--- a/include/common/xref.h
+++ b/include/common/xref.h
@@ -25,6 +25,10 @@ static inline void xref_create(struct xref *xref_a, struct 
xref *xref_b)
 
 static inline struct xref *xref_get_peer_and_lock(struct xref *xref)
 {
+       if (xref->peer == 1) {
+               printf("  xref_get_peer_and_lock xref->peer == 1 \n");
+       }
+
        struct xref *local;
        struct xref *remote;
 
diff --git a/src/ev_kqueue.c b/src/ev_kqueue.c
index bf7f666..732f20d 100644
--- a/src/ev_kqueue.c
+++ b/src/ev_kqueue.c
@@ -145,6 +145,7 @@ REGPRM2 static void _do_poll(struct poller *p, int exp)
 
        fd = global.tune.maxpollevents;
        gettimeofday(&before_poll, NULL);
+       usleep(100);
        status = kevent(kqueue_fd[tid], // int kq
                        NULL,      // const struct kevent *changelist
                        0,         // int nchanges

Reply via email to