]> git.ipfire.org Git - thirdparty/haproxy.git/commitdiff
BUG/MINOR: activity: fix Delta_calls and Delta_bytes count
authorValentine Krasnobaeva <vkrasnobaeva@haproxy.com>
Tue, 28 May 2024 15:06:24 +0000 (17:06 +0200)
committerWilly Tarreau <w@1wt.eu>
Tue, 28 May 2024 17:25:08 +0000 (19:25 +0200)
Thanks to the commit 5714aff4a6bf
"DEBUG: pool: store the memprof bin on alloc() and update it on free()", the
amount of memory allocations and memory "frees" is shown now on the same line,
corresponded to the caller name. This is very convenient to debug memory leaks
(haproxy should run with -dMcaller option).

The implicit drawback of this solution is that we count twice same free_calls
and same free_tot (bytes) values in cli_io_handler_show_profiling(), when
we've calculed tot_free_calls and tot_free_bytes, by adding them to the these
totalizators for p_alloc, malloc and calloc allocator types. See the details
about why this happens in a such way in __pool_free() implementation and
also in the commit message for 5714aff4a6bf.

This double addition of free counters falses 'Delta_calls' and 'Delta_bytes',
sometimes we even noticed that they show negative values.

Same problem was with the calculation of average allocated buffer size for
lines, where we show simultaneously the number of allocated and freed bytes.

src/activity.c

index d9f03e56501d27bb64b3a97a9789d30275647a3d..5417deb6224063b4e2546729c3b730e2ea8d6c6c 100644 (file)
@@ -803,8 +803,14 @@ static int cli_io_handler_show_profiling(struct appctx *appctx)
                else
                        chunk_appendf(&trash, "[other]");
 
-               chunk_appendf(&trash," %s(%lld)", memprof_methods[entry->method],
-                             (long long)(entry->alloc_tot - entry->free_tot) / (long long)(entry->alloc_calls + entry->free_calls));
+               if ((tmp_memstats[i].method != MEMPROF_METH_P_ALLOC) &&
+                   (tmp_memstats[i].method != MEMPROF_METH_MALLOC) &&
+                   (tmp_memstats[i].method != MEMPROF_METH_CALLOC)) {
+                       chunk_appendf(&trash," %s(%lld)", memprof_methods[entry->method],
+                               (long long)(entry->alloc_tot - entry->free_tot) / (long long)(entry->alloc_calls + entry->free_calls));
+               } else
+                       chunk_appendf(&trash," %s(%lld)", memprof_methods[entry->method],
+                               (long long)(entry->alloc_tot) / (long long)(entry->alloc_calls));
 
                if (entry->alloc_tot && entry->free_tot) {
                        /* that's a realloc, show the total diff to help spot leaks */
@@ -829,9 +835,13 @@ static int cli_io_handler_show_profiling(struct appctx *appctx)
        tot_alloc_calls = tot_free_calls = tot_alloc_bytes = tot_free_bytes = 0;
        for (i = 0; i < max_lines; i++) {
                tot_alloc_calls += tmp_memstats[i].alloc_calls;
-               tot_free_calls  += tmp_memstats[i].free_calls;
                tot_alloc_bytes += tmp_memstats[i].alloc_tot;
-               tot_free_bytes  += tmp_memstats[i].free_tot;
+               if ((tmp_memstats[i].method != MEMPROF_METH_P_ALLOC) &&
+                   (tmp_memstats[i].method != MEMPROF_METH_MALLOC) &&
+                   (tmp_memstats[i].method != MEMPROF_METH_CALLOC)) {
+                       tot_free_calls  += tmp_memstats[i].free_calls;
+                       tot_free_bytes  += tmp_memstats[i].free_tot;
+               }
        }
 
        chunk_appendf(&trash,