I suffer strange segfault in program using std::sort on std::vector<float>. The segfault occures in destructor of sorted std::vector after several sort/clear cycles. The values to reproduce the crash is actually decoded audio. I'm so sorry, I can't evaluate the proper sequence of bad values so I've uploaded the whole chunk here: http://downmusic.ru/test1 (110 mb sorry but i found no better way...) I know it's not the ideal way but maybe it helps. As far as I found out it is because of NaNs in float vector. Also, std::stable_sort never leads to crash as I've tested.
Created attachment 18638 [details] The preprocessed file of the program
Console output of g++ -v -save-temps -o gcc_sort -Wall -lQtCore -DQT_SHARED -I/usr/include/QtCore gcc_sort.cpp: Using built-in specs. Target: x86_64-unknown-linux-gnu Configured with: ../gcc-4.3.2/configure --prefix=/usr --libexecdir=/usr/lib --enable-shared --enable-threads=posix --enable-__cxa_atexit --enable-clocale=gnu --enable-languages=c,c++,fortran,objc,treelang --disable-multilib --enable-c99 --enable-long-long Thread model: posix gcc version 4.3.2 (GCC) COLLECT_GCC_OPTIONS='-v' '-save-temps' '-o' 'gcc_sort' '-Wall' '-DQT_SHARED' '-I/usr/include/QtCore' '-shared-libgcc' '-mtune=generic' /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/cc1plus -E -quiet -v -I/usr/include/QtCore -D_GNU_SOURCE -DQT_SHARED gcc_sort.cpp -mtune=generic -Wall -fpch-preprocess -o gcc_sort.ii ignoring nonexistent directory "/usr/local/include" ignoring nonexistent directory "/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../../../x86_64-unknown-linux-gnu/include" #include "..." search starts here: #include <...> search starts here: /usr/include/QtCore /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../../../include/c++/4.3.2 /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../../../include/c++/4.3.2/x86_64-unknown-linux-gnu /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../../../include/c++/4.3.2/backward /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/include /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/include-fixed /usr/include End of search list. COLLECT_GCC_OPTIONS='-v' '-save-temps' '-o' 'gcc_sort' '-Wall' '-DQT_SHARED' '-I/usr/include/QtCore' '-shared-libgcc' '-mtune=generic' /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/cc1plus -fpreprocessed gcc_sort.ii -quiet -dumpbase gcc_sort.cpp -mtune=generic -auxbase gcc_sort -Wall -version -o gcc_sort.s GNU C++ (GCC) version 4.3.2 (x86_64-unknown-linux-gnu) compiled by GNU C version 4.3.2, GMP version 4.2.4, MPFR version 2.3.2. GGC heuristics: --param ggc-min-expand=100 --param ggc-min-heapsize=131072 Compiler executable checksum: 181aa37d41253b88eaf3c45c4486e83b COLLECT_GCC_OPTIONS='-v' '-save-temps' '-o' 'gcc_sort' '-Wall' '-DQT_SHARED' '-I/usr/include/QtCore' '-shared-libgcc' '-mtune=generic' as -V -Qy -o gcc_sort.o gcc_sort.s GNU assembler version 2.18 (x86_64-unknown-linux-gnu) using BFD version (GNU Binutils) 2.18 COMPILER_PATH=/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/:/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/:/usr/lib/gcc/x86_64-unknown-linux-gnu/:/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/:/usr/lib/gcc/x86_64-unknown-linux-gnu/:/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/:/usr/lib/gcc/x86_64-unknown-linux-gnu/ LIBRARY_PATH=/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/:/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/:/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../../../lib/:/lib/../lib/:/usr/lib/../lib/:/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../../:/lib/:/usr/lib/ COLLECT_GCC_OPTIONS='-v' '-save-temps' '-o' 'gcc_sort' '-Wall' '-DQT_SHARED' '-I/usr/include/QtCore' '-shared-libgcc' '-mtune=generic' /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/collect2 --eh-frame-hdr -m elf_x86_64 -dynamic-linker /lib/ld-linux-x86-64.so.2 -o gcc_sort /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../../../lib/crt1.o /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../../../lib/crti.o /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/crtbegin.o -L/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2 -L/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2 -L/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../../../lib -L/lib/../lib -L/usr/lib/../lib -L/usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../.. -lQtCore gcc_sort.o -lstdc++ -lm -lgcc_s -lgcc -lc -lgcc_s -lgcc /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/crtend.o /usr/lib/gcc/x86_64-unknown-linux-gnu/4.3.2/../../../../lib/crtn.o
Created attachment 18639 [details] Source code that triggers the bug
I don't think this is a bug as the comparison function causes an unstable sort as NaNs are special and are unordered :).
Oh, I've tried to find info how the implementation manages NaNs but didn't find any clear info. So is it the expected behavior? And is it safe to use std::stable_sort for vectors with NaNs or I was just lucky? Actually, NaNs in the flow is an error in my program which I fixed, but I decided to save the faulty state to file the report.
so in floating point world, NaNs are considered unordered that is X == NaN is always false for all values of X including NaNs itself, likewise for >, <, <=, and >=. X != NaN is always true for all values of X including NaNs itself. So NaNs will cause weird stuff to happen because it is always unordered. Complex numbers are also considered unordered too :)
Is there anything in C++ Standard concerning this case? Maybe it's more preferrable to throw exception or something like this.. Now it seems to make memory leak in the operated vector. The output is like this: *** glibc detected *** /usr/local/share/workspace/playground/gcc_sort: munmap_chunk(): invalid pointer: 0x0000000001d2c550 *** *** glibc detected *** /usr/local/share/workspace/playground/gcc_sort: malloc(): memory corruption: 0x0000000001d2bca0 ***
Just to clarify, it is not a memory leak which is occurring, it is memory corruption. Basically when std::sort is given a type which is not totally ordered as required, it tends to corrupt the memory immediately before and after the given array. There are a few ways in which this could be detected, but if it was detected it's not obvious what the behaviour should then be, and obviously it would (slightly) slow down std::sort when given 'correct' types.
In C++03 this is not a bug. However, I seem to vaguely remember a recent discussion in the committee (basing on either a paper or a DR) about comparisons of floats, if somebody can find a reference I would appreciate it...
Yeah, I see.. But anyway, thank you for discussing it.