]> git.ipfire.org Git - thirdparty/haproxy.git/commitdiff
BUG/MINOR: haload: fix CPU topology detection by omitting forced "nbthread"
authorFrederic Lecaille <flecaille@haproxy.com>
Fri, 24 Jul 2026 10:06:23 +0000 (12:06 +0200)
committerFrederic Lecaille <flecaille@haproxy.com>
Fri, 24 Jul 2026 10:10:47 +0000 (12:10 +0200)
Always writing "nbthread" in the generated global configuration forced a
static thread count, preventing HAProxy from using its automatic CPU
topology detection and correct core binding. This caused severe performance
degradation on large multi-core machines. Fix this by omitting the "nbthread"
directive when -t is not explicitly specified, while ensuring <arg_thrd>
is properly initialized to global.nbthread for internal calculations such as
connection and request rates.

Also ensure <arg_thrd> <= <arg_usr> when -R is specified for internal
calculations.

src/haload.c
src/haload_init.c

index e13e3cf777253eb31d2b9d8053bccd9cf6746e92..91b036ca17cc00e80bca9dc6d775a03943051237 100644 (file)
@@ -100,7 +100,7 @@ int arg_rcon = -1;     // max requests per conn
 int arg_reqs = -1;     // max total requests
 int arg_serr;          // stop on first error
 int arg_slow;          // slow start: delay in milliseconds
-int arg_thrd = 1;      // number of threads
+int arg_thrd;          // number of threads
 int arg_usr = 1;       // number of users
 int arg_wait = 10000;  // I/O time out (ms)
 
@@ -1916,6 +1916,20 @@ static int hld_init(void)
        if (!hld_cfg_finalize())
                goto err;
 
+       /* This is the location to initialize the default value for <arg_thrd>.
+        * Indeed, global.nthread is initialized late(after the parsing step).
+        */
+       if (arg_thrd == 0)
+               arg_thrd = global.nbthread;
+
+       if (arg_rate && arg_thrd > arg_usr) {
+               ha_alert("Thread count (%d) must not exceed connection count (%d)\n",
+                        arg_thrd, arg_usr);
+               goto err;
+       }
+
+       BUG_ON(arg_thrd != global.nbthread);
+
        /* Consider the case where <arg_reqs> < <arg_usr> */
        if (arg_reqs != -1 && arg_reqs < arg_usr)
                arg_usr = arg_reqs;
index 8da0b8f95c2456af2c4eb72df65554c2623b1208..82770eae6da6893803b97e4fe99fc2da8115864f 100644 (file)
@@ -28,7 +28,7 @@ static void  hld_usage(char *name, int argc)
                "        -n <reqs>        maximum total requests (-1)\n"
                "        -r <reqs>        number of requests per connection (-1)\n"
                "        -s <time>        soft start: time in sec to reach 100%% load\n"
-               "        -t <threads>     number of threads (1)\n"
+               "        -t <threads>     force number of threads (nbthread)\n"
                "        -u <users>       number of users (1)\n"
                "        -w <time>        I/O timeout in milliseconds (10000)\n"
                "        -A               ignore 1st req for resp time measurements\n"
@@ -50,7 +50,8 @@ static void  hld_usage(char *name, int argc)
                "URL format:\n"
                "        (http|https|quic)://<addr>:<port>/<path>\n"
                "Note: Options marked with an asterisk (*) are positional and MUST be placed\n"
-               "      BEFORE the URLs they are intended to affect.\n",
+               "      BEFORE the URLs they are intended to affect.\n"
+               "Note: When <arg_rate> is set, <arg_thrd> must be lesser or equal to <arg_usr>\n",
                name);
        exit(1);
 }
@@ -655,14 +656,10 @@ void haproxy_init_args(int argc, char **argv)
                goto leave;
        }
 
-       if (arg_thrd > arg_usr) {
-               ha_alert("Thread count must not exceed connection count\n");
-               goto leave;
-       }
-
        /* "global" section */
        hbuf_appendf(&buf, "%.*s", (int)gbuf.data, gbuf.area);
-       hbuf_appendf(&buf, "\tnbthread %d\n", arg_thrd);
+       if (arg_thrd != 0)
+               hbuf_appendf(&buf, "\tnbthread %d\n", arg_thrd);
        if (arg_mreqs)
                hbuf_appendf(&buf,
                             "\ttune.h2.be.max-concurrent-streams %d\n", arg_mreqs);