From d3d8781f2ee6fc59cb0561a889d693ca95a3a56f Mon Sep 17 00:00:00 2001 From: Asad Sajjad Ahmed Date: Fri, 11 Oct 2024 13:06:16 +0200 Subject: [PATCH] varnishd: truncate thread name on Linux MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit On Linux, threads can not have name longer than 15 bytes plus a terminating '\0' byte: > PR_SET_NAME (since Linux 2.6.9) > Set the name of the calling thread, using the value in the loca‐ > tion pointed to by (char *) arg2. The name can be up to 16 > bytes long, including the terminating null byte. (If the length > of the string, including the terminating null byte, exceeds 16 > bytes, the string is silently truncated.) This is the same at‐ > tribute that can be set via pthread_setname_np(3) and retrieved > using pthread_getname_np(3). The attribute is likewise accessi‐ > ble via /proc/self/task/tid/comm (see proc(5)), where tid is the > thread ID of the calling thread, as returned by gettid(2). We have until now ignored the return value from pthread_setname_np(), this is not great as the call then becomes a NOP: > The pthread_setname_np() function can be used to set a > unique name for a thread, which can be useful for debugging multi‐ > threaded applications. The thread name is a meaningful C language > string, whose length is restricted to 16 characters, including the ter‐ > minating null byte ('\0'). > [...] > ERANGE The length of the string specified pointed to by name exceeds > the allowed limit. This patch truncates long names to 14 characters plus a tilde ('~') character. Signed-off-by: Asad Sajjad Ahmed --- bin/varnishd/cache/cache_main.c | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/bin/varnishd/cache/cache_main.c b/bin/varnishd/cache/cache_main.c index d10a70d3197..920980b5455 100644 --- a/bin/varnishd/cache/cache_main.c +++ b/bin/varnishd/cache/cache_main.c @@ -130,6 +130,22 @@ THR_GetWorker(void) static pthread_key_t name_key; +static void +thr_setname_generic(const char *name) +{ + char buf[16]; + + /* The Linux kernel enforces a strict limitation of 15 bytes name, + * truncate the name if we would overflow it. + */ + if (strlen(name) > 15) { + bprintf(buf, "%.14s~", name); + name = buf; + } + + PTOK(pthread_setname_np(pthread_self(), name)); +} + void THR_SetName(const char *name) { @@ -140,7 +156,7 @@ THR_SetName(const char *name) #elif defined(__NetBSD__) (void)pthread_setname_np(pthread_self(), "%s", (char *)(uintptr_t)name); #else - (void)pthread_setname_np(pthread_self(), name); + thr_setname_generic(name); #endif }