public inbox for glibc-bugs@sourceware.org help / color / mirror / Atom feed
From: "nars at yottadb dot com" <sourceware-bugzilla@sourceware.org> To: glibc-bugs@sourceware.org Subject: [Bug libc/29863] New: Segmentation fault in memcmp-sse2.S if memory contents can concurrently change Date: Wed, 07 Dec 2022 10:49:33 +0000 [thread overview] Message-ID: <bug-29863-131@http.sourceware.org/bugzilla/> (raw) https://sourceware.org/bugzilla/show_bug.cgi?id=29863 Bug ID: 29863 Summary: Segmentation fault in memcmp-sse2.S if memory contents can concurrently change Product: glibc Version: 2.36 Status: UNCONFIRMED Severity: normal Priority: P2 Component: libc Assignee: unassigned at sourceware dot org Reporter: nars at yottadb dot com CC: drepper.fsp at gmail dot com Target Milestone: --- Created attachment 14486 --> https://sourceware.org/bugzilla/attachment.cgi?id=14486&action=edit Simple C program that demonstrates the SIG-11 in memcmp-sse2.S Hi, We saw a occasional test failure after upgrading to Ubuntu 22.10. And after some investigation suspect the cause to be a GLIBC 2.36 regression. On the system we run the test on, a call to memcmp() ended up invoking sysdeps/x86_64/multiarch/memcmp-sse2.S in glibc. I have attached the /proc/cpuinfo information below in case it helps determine why the sse2 version of memcmp got invoked. Attached is a simple C program test.c. It spawns 2 threads. Thread 1 does memcmp() in a loop, 100,000 times. The memcmp() will return 0 most of the time since it is coded to compare identical buffers. Thread 2 changes just 1 byte in one of the buffers. It changes this byte to a different value and back again to the original value. Keeps doing this repeatedly. This causes the memcmp() in Thread 1 to alternately return 0 or 1 which is fine. But eventually, Thread 1 crashes with a Segmentation fault. Below is an example output. In this example, Thread 1 crashed in the 58,234th iteration. $ gcc test.c $ ./a.out . . i = 58232 : result = 1 i = 58233 : result = 1 i = 58234 : result = 1 Segmentation fault (core dumped) Below is the C stack and relevant register output from the crash. (gdb) where #0 __memcmp_sse2 () at ../sysdeps/x86_64/multiarch/memcmp-sse2.S:312 #1 0x000055efe46032d3 in childThread () #2 0x00007f6f45e90402 in start_thread (arg=<optimized out>) at ./nptl/pthread_create.c:442 #3 0x00007f6f45f1f590 in clone3 () at ../sysdeps/unix/sysv/linux/x86_64/clone3.S:81 (gdb) info registers rax 0xfffffff1 4294967281 rdx 0xfffffffffffffff1 -15 rsi 0x55efe4606040 94488817066048 rcx 0xffff 65535 I have pasted the memcmp-sse2.S source code with line numbers below corresponding to the flow of the assembly instructions around the time of the crash. That is, the memcmp() function call enters at line 59, executes line 71, 72 and then jumps to line 249 etc. The crash occurs in line 312 below. sysdeps/x86_64/multiarch/memcmp-sse2.S -------------------------------------- 59 ENTRY(MEMCMP) 71 cmpq $CHAR_PER_VEC, %rdx 72 ja L(more_1x_vec) 249 L(more_1x_vec): 255 movl $0xffff, %ecx 257 movups (%rsi), %xmm0 258 movups (%rdi), %xmm1 259 PCMPEQ %xmm0, %xmm1 260 pmovmskb %xmm1, %eax 261 subl %ecx, %eax 262 jnz L(ret_nonzero_vec_start_0) 269 subq $(CHAR_PER_VEC * 2), %rdx 271 ja L(more_2x_vec) 273 movups (VEC_SIZE * -1 + SIZE_OFFSET)(%rsi, %rdx, CHAR_SIZE), %xmm0 274 movups (VEC_SIZE * -1 + SIZE_OFFSET)(%rdi, %rdx, CHAR_SIZE), %xmm1 275 PCMPEQ %xmm0, %xmm1 276 pmovmskb %xmm1, %eax 277 subl %ecx, %eax 281 jnz L(ret_nonzero_vec_end_0) 299 L(ret_nonzero_vec_end_0): 300 bsfl %eax, %eax 311 addl %edx, %eax 312 movzbl (VEC_SIZE * -1 + SIZE_OFFSET)(%rsi, %rax), %ecx For the above failure to happen, the length of the memcmp() needs to be between 16 and 32. If the contents of the buffer did not change between lines 59 to 312 above, then we are guaranteed %rax holds a positive value at line 312. But if the contents can change concurrently (as is the case in the test program), we could end up with a negative value of %rax. And that causes the pointer arithmetic in line 312 to result in a stray pointer instead of one within the memcmp() buffer bounds. In case it helps, below is the commit that made the above changes. $ git log --graph --oneline --pretty=format:'%h%d; %ci; %cn; %s' sysdeps/x86_64/multiarch/memcmp-sse2.S | head -1 * ae308947ff; 2022-07-05 16:42:42 -0700; Noah Goldstein; x86: Add support for building {w}memcmp{eq} with explicit ISA level I have also added some more information below in case it helps. $ grep PRETTY_NAME /etc/os-release PRETTY_NAME="Ubuntu 22.10" $ uname -a Linux spencer 5.19.0-26-generic #27-Ubuntu SMP PREEMPT_DYNAMIC Wed Nov 23 20:44:15 UTC 2022 x86_64 x86_64 x86_64 GNU/Linux $ ldd --version | head -1 ldd (Ubuntu GLIBC 2.36-0ubuntu4) 2.36 $ grep -E "model name|flags" /proc/cpuinfo | sort -u flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush mmx fxsr sse sse2 ht syscall nx mmxext fxsr_opt pdpe1gb rdtscp lm constant_tsc rep_good acc_power nopl nonstop_tsc cpuid extd_apicid aperfmperf pni pclmulqdq monitor ssse3 fma cx16 sse4_1 sse4_2 movbe popcnt aes xsave avx f16c lahf_lm cmp_legacy svm extapic cr8_legacy abm sse4a misalignsse 3dnowprefetch osvw ibs xop skinit wdt lwp fma4 tce nodeid_msr tbm topoext perfctr_core perfctr_nb bpext ptsc mwaitx cpb hw_pstate ssbd vmmcall fsgsbase bmi1 avx2 smep bmi2 xsaveopt arat npt lbrv svm_lock nrip_save tsc_scale vmcb_clean flushbyasid decodeassists pausefilter pfthreshold avic v_vmsave_vmload vgif overflow_recov model name : AMD A12-9800E RADEON R7, 12 COMPUTE CORES 4C+8G Let me know if you need any more information. Thanks, Narayanan. -- You are receiving this mail because: You are on the CC list for the bug.
next reply other threads:[~2022-12-07 10:49 UTC|newest] Thread overview: 25+ messages / expand[flat|nested] mbox.gz Atom feed top 2022-12-07 10:49 nars at yottadb dot com [this message] 2022-12-12 13:02 ` [Bug libc/29863] " nars at yottadb dot com 2022-12-13 18:26 ` pinskia at gcc dot gnu.org 2022-12-13 18:28 ` pinskia at gcc dot gnu.org 2022-12-13 18:33 ` nars at yottadb dot com 2022-12-13 18:39 ` pinskia at gcc dot gnu.org 2022-12-13 18:45 ` nars at yottadb dot com 2022-12-13 18:52 ` pinskia at gcc dot gnu.org 2022-12-13 19:13 ` goldstein.w.n at gmail dot com 2022-12-13 19:36 ` bhaskar at yottadb dot com 2022-12-13 20:09 ` goldstein.w.n at gmail dot com 2022-12-13 20:18 ` goldstein.w.n at gmail dot com 2022-12-13 20:46 ` nars at yottadb dot com 2022-12-13 21:09 ` hjl.tools at gmail dot com 2022-12-13 21:53 ` bhaskar at yottadb dot com 2022-12-13 23:01 ` goldstein.w.n at gmail dot com 2022-12-13 23:16 ` nars at yottadb dot com 2022-12-13 23:39 ` goldstein.w.n at gmail dot com 2022-12-14 0:14 ` goldstein.w.n at gmail dot com 2022-12-14 7:45 ` sam at gentoo dot org 2022-12-14 15:40 ` nars at yottadb dot com 2022-12-14 18:17 ` nars at yottadb dot com 2023-05-14 21:46 ` ppluzhnikov at google dot com 2023-05-14 21:48 ` ppluzhnikov at google dot com 2023-05-14 21:49 ` ppluzhnikov at google dot com
Reply instructions: You may reply publicly to this message via plain-text email using any one of the following methods: * Save the following mbox file, import it into your mail client, and reply-to-all from there: mbox Avoid top-posting and favor interleaved quoting: https://en.wikipedia.org/wiki/Posting_style#Interleaved_style * Reply using the --to, --cc, and --in-reply-to switches of git-send-email(1): git send-email \ --in-reply-to=bug-29863-131@http.sourceware.org/bugzilla/ \ --to=sourceware-bugzilla@sourceware.org \ --cc=glibc-bugs@sourceware.org \ /path/to/YOUR_REPLY https://kernel.org/pub/software/scm/git/docs/git-send-email.html * If your mail client supports setting the In-Reply-To header via mailto: links, try the mailto: linkBe sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).