From: Peter Griess Date: Thu, 26 Sep 2013 18:27:05 +0000 (-0500) Subject: Fix test for memory allocators that want to look backwards. X-Git-Tag: v0.22.0~832 X-Git-Url: http://demsky.eecs.uci.edu/git/?a=commitdiff_plain;h=e34bc9cae798da3c01eca891a60d452440e728df;p=folly.git Fix test for memory allocators that want to look backwards. Summary: - The NeedleFinderTest.NoSegFault test uses mprotect(2) to ensure that our needle implementations don't peek past the end of memory. However, some memory allocators (e.g. the defaulton OS X) seem to look at the last byte of a page. As a result, if we allocate 2 pages and mark the second as PROT_NONE, then ask the memory allocator for 2 more pages, it may end up peeking at the last byte of the second page, triggering a SIGBUS. To work around this, allocate 8 pages of memory and only mark the second as PROT_NONE. - Clear mprotect(2) bits before freeing memory. Test Plan: - fbconfig -r folly && fbmake runtests - ./configure && make check on Ubuntu/FC/Mac Reviewed By: delong.j@fb.com FB internal diff: D998592 --- diff --git a/folly/test/RangeTest.cpp b/folly/test/RangeTest.cpp index 445df424..a6fe97e9 100644 --- a/folly/test/RangeTest.cpp +++ b/folly/test/RangeTest.cpp @@ -441,8 +441,7 @@ const size_t kPageSize = 4096; void createProtectedBuf(StringPiece& contents, char** buf) { ASSERT_LE(contents.size(), kPageSize); const size_t kSuccess = 0; - char* tmp; - if (kSuccess != posix_memalign((void**)buf, kPageSize, 2 * kPageSize)) { + if (kSuccess != posix_memalign((void**)buf, kPageSize, 4 * kPageSize)) { ASSERT_FALSE(true); } mprotect(*buf + kPageSize, kPageSize, PROT_NONE); @@ -451,6 +450,11 @@ void createProtectedBuf(StringPiece& contents, char** buf) { contents.reset(*buf + newBegin, contents.size()); } +void freeProtectedBuf(char* buf) { + mprotect(buf + kPageSize, kPageSize, PROT_READ | PROT_WRITE); + free(buf); +} + TYPED_TEST(NeedleFinderTest, NoSegFault) { const string base = string(32, 'a') + string("b"); const string delims = string(32, 'c') + string("b"); @@ -482,8 +486,8 @@ TYPED_TEST(NeedleFinderTest, NoSegFault) { s1.begin(), s1.end()); auto e2 = (f2 == s2.end()) ? StringPiece::npos : f2 - s2.begin(); EXPECT_EQ(r2, e2); - free(buf1); - free(buf2); + freeProtectedBuf(buf1); + freeProtectedBuf(buf2); } } }