<html><head><meta http-equiv="Content-Type" content="text/html charset=windows-1252"></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;"><br><div><div>On May 7, 2014, at 12:25 AM, Kostya Serebryany <<a href="mailto:kcc@google.com">kcc@google.com</a>> wrote:</div><blockquote type="cite"><div class="gmail_extra"><div class="gmail_quote">On Wed, May 7, 2014 at 1:05 AM, Marshall Clow <span dir="ltr"><<a href="mailto:mclow.lists@gmail.com" target="_blank">mclow.lists@gmail.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin: 0px 0px 0px 0.8ex; border-left-width: 1px; border-left-color: rgb(204, 204, 204); border-left-style: solid; padding-left: 1ex; position: static; z-index: auto;">Address sanitizer does not currently check for accesses beyond the end of a vector, but within the memory block managed by the vector.<br><br>For example:<br>        vector<int> v;<br>        v.reserve(10); // make space for 10 elements, but vector is still empty<br>        cout << v[1]; // access outside the “valid elements” of the vector.<br><br>This patch adds the ability to detect these kinds of errors to libc++ when using Address Sanitizer.<br>Thanks to Kostya for most of the code here.<br></blockquote></div></div></blockquote><blockquote type="cite"><br></blockquote><blockquote type="cite"><div dir="ltr"><div>Looks great, ship it! </div></div></blockquote><div><blockquote type="cite"><br></blockquote></div><blockquote type="cite"><div dir="ltr"><div>Few minor comments below. </div><div><br></div><div>+++ include/__config    (working copy)</div><div>+#ifndef _LIBCPP_HAS_NO_ASAN<br></div><div><br></div><div>
Do you prefer double-negative statements? </div><div>#ifdef _LIBCPP_HAS_ASAN</div><div>might be easier to read, but that's not critical. </div></div></blockquote><div><br></div>The reason is that this way you can turn on address sanitizer in your project, but still disable ASAN in libc++ if you want</div><div>by adding "-D _LIBCPP_HAS_NO_ASAN=1 “ to the command line.</div><div><br></div><div><blockquote type="cite"><div dir="ltr"><div>+++ test/containers/sequences/vector/asan.pass.cpp      (working copy)</div><div><div>+#ifndef _LIBCPP_HAS_NO_ASAN</div><div>+extern "C" void __asan_set_error_exit_code(int);</div></div><div><br></div><div>+++ test/support/asan_testing.h (working copy)</div><div><div>+#ifndef _LIBCPP_HAS_NO_ASAN</div>
<div>+extern "C" int __sanitizer_verify_contiguous_container</div><div>+     ( const void *beg, const void *mid, const void *end );</div></div><div><br></div><div>I understand the desire to not incluide <sanitizer/asan_interface.h> in include/__config,</div>
<div>but why not include it in the test files? </div></div></blockquote><div><br></div>Because I didn’t want to add an external dependency to the libc++ test suite.</div><div>Interestingly enough, people are using the libc++ test suite on other compilers than clang,</div><div>and on other standard library implementations, too.</div><div><br></div><div>Is that the right path when using GCC as well?</div><div><div><br></div></div><div><br></div><div><blockquote type="cite"><div dir="ltr"><div>+++ test/containers/sequences/vector/asan.pass.cpp      (working copy)</div><div><div>+#if __cplusplus >= 201103L</div>
<div>+    {</div><div>+        typedef int T;</div><div>+        typedef std::vector<T, min_allocator<T>> C;</div><div>+        const T t[] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};</div><div>+        C c(std::begin(t), std::end(t));</div>
<div>+        c.reserve(2*c.size());</div><div>+        T foo = c[c.size()];    // bad, but not caught by ASAN</div><div>+    }</div><div>+#endif</div></div><div><br></div><div>Maybe add a comment explaining why ASAN does not catch it</div>
<div>(because asan can't handle arbitrary allocator)?</div></div></blockquote><div><br></div><div>Can do.</div></div><div><br></div><div>— Marshall</div><div><br></div></body></html>