Bug#1004069: g++-11: AddressSanitizer false positive in std::sort
Package: g++-11
Version: 11.2.0-13
Severity: normal
X-Debbugs-Cc: rodymac@riseup.net
Dear Maintainer,
% cat cc.cc
// For some combinations of
// - the type of inner::a
// - the array size of inner::a
// - the size of the std::array in main
// AddressSanitizer gives a pointer comparison error when calling
std::sort.
// Clearly, it is sensitive to sizeof(outer) but I couldn't reduce to
the exact byte count.
//
// It also runs without failure if the run-time flags are built into the
executeble with:
// const char *__asan_default_options() { return
"detect_invalid_pointer_pairs=2"; }
#include <array>
#include <algorithm>
struct inner {
int a[39];// OK for 38 or less if size of std::array is 13
// double a[10];// OK for 9 or less if size of std::array is 24
constexpr bool operator<(const inner &o) const { return a[0] < o.a[0];
}
};
struct outer {
char dummy;// If this member is not here, then no errors from ASAN
inner i;
constexpr bool operator <(const outer &o) const noexcept {return
o.i<i;}
};
int main(){
std::array<outer, 13> a;// 24 for a double inner::a
std::sort(a.begin(), a.end());
return 0;
}
% g++ -std=c++20 -fno-omit-frame-pointer -fsanitize=address
-fsanitize=pointer-subtract cc.cc
% ASAN_OPTIONS="detect_invalid_pointer_pairs=2" ./a.out
=================================================================
==1663139==ERROR: AddressSanitizer: invalid-pointer-pair: 0x7ffe40fb9dc0
0x7ffe40fb95a0
#0 0x55e1cde17591 in void std::__sort<outer*,
__gnu_cxx::__ops::_Iter_less_iter>(outer*, outer*,
__gnu_cxx::__ops::_Iter_less_iter) (/tmp/a.out+0x1591)
#1 0x55e1cde174d1 in void std::sort<outer*>(outer*, outer*)
(/tmp/a.out+0x14d1)
#2 0x55e1cde172d7 in main (/tmp/a.out+0x12d7)
#3 0x7f80ce3ea7ec in __libc_start_main ../csu/libc-start.c:332
#4 0x55e1cde17149 in _start (/tmp/a.out+0x1149)
Address 0x7ffe40fb9dc0 is located in stack of thread T0 at offset 2112
in frame
#0 0x55e1cde17218 in main (/tmp/a.out+0x1218)
This frame has 1 object(s):
[32, 2112) 'a' (line 23) <== Memory access at offset 2112 overflows
this variable
HINT: this may be a false positive if your program uses some custom
stack unwind mechanism, swapcontext or vfork
(longjmp and C++ exceptions *are* supported)
Address 0x7ffe40fb95a0 is located in stack of thread T0 at offset 32 in
frame
#0 0x55e1cde17218 in main (/tmp/a.out+0x1218)
This frame has 1 object(s):
[32, 2112) 'a' (line 23) <== Memory access at offset 32 is inside
this variable
HINT: this may be a false positive if your program uses some custom
stack unwind mechanism, swapcontext or vfork
(longjmp and C++ exceptions *are* supported)
SUMMARY: AddressSanitizer: invalid-pointer-pair (/tmp/a.out+0x1591) in
void std::__sort<outer*, __gnu_cxx::__ops::_Iter_less_iter>(outer*,
outer*, __gnu_cxx::__ops::_Iter_less_iter)
==1663139==ABORTING
Here comes my system info, althought I checked and the same error
happens in all of Debian Bookworm (g++ 11.2), Bullseye (g++ 10.2),
Ubuntu Impish (g++ 11.2), Hirsute (g++ 10.3), and Focal (g++ 9.3).
-- System Information:
Debian Release: bookworm/sid
APT prefers testing
APT policy: (990, 'testing')
Architecture: amd64 (x86_64)
Foreign Architectures: i386
Kernel: Linux 5.15.0-2-amd64 (SMP w/8 CPU threads)
Kernel taint flags: TAINT_WARN, TAINT_OOT_MODULE, TAINT_UNSIGNED_MODULE
Locale: LANG=en_US.UTF-8, LC_CTYPE=en_US.UTF-8 (charmap=UTF-8), LANGUAGE
not set
Shell: /bin/sh linked to /bin/dash
Init: systemd (via /run/systemd/system)
LSM: AppArmor: enabled
Versions of packages g++-11 depends on:
ii gcc-11 11.2.0-13
ii gcc-11-base 11.2.0-13
ii libc6 2.33-2
ii libgmp10 2:6.2.1+dfsg-3
ii libisl23 0.24-2
ii libmpc3 1.2.1-1
ii libmpfr6 4.1.0-3
ii libstdc++-11-dev 11.2.0-13
ii libzstd1 1.4.8+dfsg-3
ii zlib1g 1:1.2.11.dfsg-2
g++-11 recommends no packages.
Versions of packages g++-11 suggests:
pn g++-11-multilib <none>
ii gcc-11-doc 11.2.0-1
-- no debconf information
Reply to: