Fedora Account System
Red Hat Associate
Red Hat Customer
A simple systemtap script can generate C code. When one of these is when fed to gcc, it produces what looks like erroneous stringop-overflow warnings. Since systemtap uses -Werror in its processing, these turn into errors. /tmp/stap6KnM9x/stap_3930209_src.c:800:11: error: ‘strlcpy’ writing 512 bytes into a region of size 8 overflows the destination [-Werror=stringop-overflow=] 800 | strlcpy (l->__tmp16, global(s___global_spaces), MAXSTRINGLEN); | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ /tmp/stap6KnM9x/stap_3930209_src.c:46:19: note: destination object ‘__tmp10’ of size 8 46 | int64_t __tmp10; | ^~~~~~~ Attaching the .i file. gcc --std=gnu99 -c foo.i -fvisibility=hidden -O2 -Wall -Werror -Wno-unused -Wno-strict-aliasing -Wno-pointer-to-int-cast -Wno-int-to-pointer-cast -Wno-pragmas -Wno-pointer-sign -Wno-format Almost the same errors are detected on gcc15.2.1 (f43) and gcc16.0.1 (rawhide). The data structure holding those __tmp values is tricky, and has nested anonymous structures and unions (because they are temporaries for evaluating the compiled systemtap script code). But the C code looks OK, and such constructs aren't new. Reproducible: Always
Created attachment 2123539 [details] preprocessed input
With gcc trunk I also see: In file included from /usr/share/systemtap/runtime/dyninst/print.c:19, from /usr/share/systemtap/runtime/print.c:21, from /usr/share/systemtap/runtime/runtime_context.h:22, from /tmp/stap6KnM9x/stap_3930209_src.c:281: /usr/share/systemtap/runtime/vsprintf.c: In function ‘_stp_vsprint_memory.constprop’: /usr/share/systemtap/runtime/vsprintf.c:341:23: error: ‘strnlen’ specified bound 8192 exceeds source size 7 [-Werror=stringop-overread] 341 | len = strnlen(ptr, clamp_t(size_t, precision, 0, STP_BUFFER_SIZE)); | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
(Yeah, I think that's a separate false positive.)
Based on the preprocessed source, simply updating the precision when ptr is reset to "<NULL>" should get rid of the warning: --- /tmp/foo2.i 2026-01-23 17:06:09.174220695 -0500 +++ /tmp/foo3.i 2026-01-23 17:06:01.664693280 -0500 @@ -16654,8 +16654,10 @@ struct context * __restrict__ c; if (format == 's') { - if ((unsigned long)ptr < (1UL << 12)) + if ((unsigned long)ptr < (1UL << 12)) { ptr = "<NULL>"; + precision = sizeof (ptr) - 1; + } len = strnlen(ptr, ({ size_t __val = (precision); size_t __min = (0); size_t __max = (8192); __val = __val < __min ? __min: __val; __val > __max ? __max: __val; })); } else if (precision > 0) Back to the original issue, here's a reduced reproducer: #define SIZE 8 struct probe_144795_locals *probe_144795_l; void strlcpy (char *, const char *, long) __attribute__ ((__access__ (__write_only__, 1, 3))); struct probe_144795_locals { union { struct { char __tmp7[SIZE]; int __tmp10; int __tmp11; }; struct { char __tmp15[SIZE]; char __tmp16[SIZE]; }; }; }; void probe_144795(const char *in) { probe_144795_l->__tmp10 = probe_144795_l->__tmp11 = 0; strlcpy (probe_144795_l->__tmp16, in, SIZE); } $ gcc -c ~/waccess-bug.c -O2 -Werror=stringop-overflow Looks like the vectorizer somehow confuses waccess into thinking that the access is to __tmp10 instead of actually __tmp16. I've traced it back to r12-4240, so this has been around for a while. I'll file this upstream if there isn't already a report on this.
nice work, thanks!
This bug appears to have been reported against 'rawhide' during the Fedora Linux 45 development cycle. Changing version to 45.