[cfe-dev] questions about libc++'s _LIBCPP_DEBUG

Kostya Serebryany kcc at google.com
Thu Jan 24 05:31:22 PST 2013


Hi,

I have a few questions about libc++'s _LIBCPP_DEBUG.

Is this the right mailing list?

Is the _LIBCPP_DEBUG mode being maintained/developed?
I see at least two compile-time problems:

1. __LIBCPP_DEBUG is used a few places in include/string instead of
_LIBCPP_DEBUG (two '_' instead of one)

2.  =================
% cat erase.cc
#include <string>

void foo(std::string &s) {
  s.erase(10, std::string::npos);
}
% clang++ ./erase.cc -I/home/kcc/llvm/projects/libcxx/include
-D_LIBCPP_DEBUG -c
In file included from ./erase.cc:1:
In file included from /home/kcc/llvm/projects/libcxx/include/string:434:
In file included from /home/kcc/llvm/projects/libcxx/include/algorithm:594:
In file included from /home/kcc/llvm/projects/libcxx/include/memory:596:
/home/kcc/llvm/projects/libcxx/include/iterator:1486:30: error: elaborated
type refers to a typedef
    friend class _Container::__self;
                             ^
./erase.cc:4:11: note: in instantiation of template class
'std::__1::__debug_iter<std::__1::basic_string<char>, const char *>'
requested here
  s.erase(10, std::string::npos);
          ^
/home/kcc/llvm/projects/libcxx/include/string:1043:58: note: declared here
    typedef basic_string                                 __self;
                                                         ^
1 error generated.
=================


Last, and the most interesting question.
The STL buffer overflow checks are incomplete because there is
string::data() which returns the object guts as a raw pointer.
Compare these two tests: when using s[3] the checks work, but when using
s.data()[3] checks don't work

==> string_data_test.cc <==
#include <string>
int main() {
  std::string s("012");
  return s.data()[3];
}

==> string_operator_test.cc <==
#include <string>
int main() {
  std::string s("012");
  return s[3];
}

Same applies to vector.
I have a proof-of-concept patch that adds AddressSanitizer annotations to
include/string
and allows to find buffer overflows even in s.data()[3].
Would someone be interested in helping me polish this patch and commit it?


% libc++clang -g  string_data_test.cc -fsanitize=address -O1; ./a.out
=================================================================
==6693== ERROR: AddressSanitizer: use-after-poison on address
0x7fff81527524 at pc 0x41812d bp 0x7fff815274f0 sp 0x7fff815274e8
READ of size 1 at 0x7fff81527524 thread T0
    #0 0x41812c in main /home/kcc/stl_checks/string_data_test.cc:4
    #1 0x7f0b92c9a76c (/lib/x86_64-linux-gnu/libc.so.6+0x2176c)
    #2 0x417c64 (/home/kcc/stl_checks/a.out+0x417c64)
Address 0x7fff81527524 is located at offset 36 in frame <main> of T0's
stack:
  This frame has 1 object(s):
    [32, 72) 's'


Thanks,

--kcc
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-dev/attachments/20130124/51f6dfc2/attachment.html>


More information about the cfe-dev mailing list