Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fuzzing test and detect the memmove error #688

Merged
merged 2 commits into from
Nov 19, 2024

Conversation

SchrodingerZhu
Copy link
Collaborator

@SchrodingerZhu SchrodingerZhu commented Nov 16, 2024

To test, set

"SNMALLOC_ENABLE_FUZZING": "ON"
"FUZZTEST_FUZZING_MODE": "ON"

to cmake configuration.

Then,

cmake --build <build> --target snmalloc-fuzzer

Then,

<build>/fuzzing/snmalloc-fuzzer --fuzz=snmalloc_fuzzing.forward_memmove

I get the following error for snmalloc_fuzzing.forward_memmove:

schrodinger@Homotopy:~/snmalloc/build$ ./fuzzing/snmalloc-fuzzer --fuzz=snmalloc_fuzzing.forward_memmove
[.] Sanitizer coverage enabled. Counter map size: 44409, Cmp map size: 262144
Note: Google Test filter = snmalloc_fuzzing.forward_memmove
[==========] Running 1 test from 1 test suite.
[----------] Global test environment set-up.
[----------] 1 test from snmalloc_fuzzing
[ RUN      ] snmalloc_fuzzing.forward_memmove
FUZZTEST_PRNG_SEED=IG8seTL7ExaaXyZd6M1JsrfH4jMy3y79IenkCA8nPdI
[*] Corpus size:     1 | Edges covered:     15 | Fuzzing time:       3.125526ms | Total runs:  1.00e+00 | Runs/secs:   319 | Max stack usage:      304
[*] Corpus size:     2 | Edges covered:     16 | Fuzzing time:       3.301892ms | Total runs:  4.00e+00 | Runs/secs:  1211 | Max stack usage:      304
[*] Corpus size:     3 | Edges covered:     17 | Fuzzing time:       3.410009ms | Total runs:  9.00e+00 | Runs/secs:  2639 | Max stack usage:      304
[*] Corpus size:     4 | Edges covered:     18 | Fuzzing time:       3.887326ms | Total runs:  3.50e+01 | Runs/secs:  9003 | Max stack usage:      304
[*] Corpus size:     5 | Edges covered:     18 | Fuzzing time:       4.098467ms | Total runs:  4.10e+01 | Runs/secs: 10003 | Max stack usage:      304
[*] Corpus size:     6 | Edges covered:     18 | Fuzzing time:       4.836651ms | Total runs:  6.10e+01 | Runs/secs: 12612 | Max stack usage:      304
[*] Corpus size:     7 | Edges covered:     20 | Fuzzing time:       5.398901ms | Total runs:  6.40e+01 | Runs/secs: 11854 | Max stack usage:      304
[*] Corpus size:     8 | Edges covered:     22 | Fuzzing time:       5.749467ms | Total runs:  8.40e+01 | Runs/secs: 14610 | Max stack usage:      304
[*] Corpus size:     9 | Edges covered:     22 | Fuzzing time:       6.391884ms | Total runs:  1.08e+02 | Runs/secs: 16896 | Max stack usage:      304
[*] Corpus size:    10 | Edges covered:     26 | Fuzzing time:       7.228434ms | Total runs:  1.42e+02 | Runs/secs: 19644 | Max stack usage:      304
=================================================================
==84600==ERROR: AddressSanitizer: heap-buffer-overflow on address 0xfb4cd80227ff at pc 0xab7a1f184e58 bp 0xffffe07953f0 sp 0xffffe07953e8
READ of size 1 at 0xfb4cd80227ff thread T0
    #0 0xab7a1f184e54 in void snmalloc::copy_one<1ul>(void*, void const*) /home/schrodinger/snmalloc/src/snmalloc/global/memcpy.h:14:5
    #1 0xab7a1f184e54 in void snmalloc::block_reverse_copy<1ul, 0ul>(void*, void const*, unsigned long) /home/schrodinger/snmalloc/src/snmalloc/global/memcpy.h:51:7
    #2 0xab7a1f184e54 in void* snmalloc::memmove<true, false, snmalloc::GenericArch>(void*, void const*, unsigned long) /home/schrodinger/snmalloc/src/snmalloc/global/memcpy.h:503:7
    #3 0xab7a1f184e54 in forward_memmove(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long) /home/schrodinger/snmalloc/fuzzing/snmalloc-fuzzer.cpp:54:3
    #4 0xab7a1f20c238 in auto fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...)::operator()<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&>(auto&&...) const /home/schrodinger/snmalloc/build/_deps/fuzztest-src/./fuzztest/internal/fixture_driver.h:294:11
    #5 0xab7a1f20c238 in void std::__invoke_impl<void, fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...), std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&>(std::__invoke_other, fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...)&&, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/invoke.h:61:14
    #6 0xab7a1f20c238 in std::__invoke_result<fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...), std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&>::type std::__invoke<fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...), std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&>(fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...)&&, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/invoke.h:96:14
    #7 0xab7a1f20c238 in decltype(auto) std::__apply_impl<fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...), std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>&, 0ul, 1ul>(fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...)&&, std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>&, std::integer_sequence<unsigned long, 0ul, 1ul>) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/tuple:2921:14
    #8 0xab7a1f20c238 in decltype(auto) std::apply<fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...), std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>&>(fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...)&&, std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>&) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/tuple:2936:14
    #9 0xab7a1f20c238 in fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const /home/schrodinger/snmalloc/build/_deps/fuzztest-src/./fuzztest/internal/fixture_driver.h:292:5
    #10 0xab7a1f22fd5c in fuzztest::internal::FuzzTestFuzzerImpl::RunOneInput(fuzztest::internal::FuzzTestFuzzerImpl::Input const&) /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:1038:22
    #11 0xab7a1f233840 in fuzztest::internal::FuzzTestFuzzerImpl::TrySample(fuzztest::internal::FuzzTestFuzzerImpl::Input const&, bool) /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:770:26
    #12 0xab7a1f234434 in fuzztest::internal::FuzzTestFuzzerImpl::TrySampleAndUpdateInMemoryCorpus(fuzztest::internal::FuzzTestFuzzerImpl::Input, bool) /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:796:35
    #13 0xab7a1f239780 in fuzztest::internal::FuzzTestFuzzerImpl::RunInFuzzingMode(int*, char***, fuzztest::internal::Configuration const&)::$_0::operator()() const::'lambda'(fuzztest::internal::FuzzTestFuzzerImpl::Input)::operator()(fuzztest::internal::FuzzTestFuzzerImpl::Input) const /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:1179:7
    #14 0xab7a1f239780 in fuzztest::internal::FuzzTestFuzzerImpl::RunInFuzzingMode(int*, char***, fuzztest::internal::Configuration const&)::$_0::operator()() const /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:1222:9
    #15 0xab7a1f239780 in fuzztest::internal::FuzzTestFuzzerImpl::RunInFuzzingMode(int*, char***, fuzztest::internal::Configuration const&) /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:1103:25
    #16 0xab7a1f221b54 in fuzztest::internal::GTest_TestAdaptor::TestBody() /home/schrodinger/snmalloc/build/_deps/fuzztest-src/./fuzztest/internal/googletest_adaptor.h:86:7
    #17 0xab7a1f2f342c in void testing::internal::HandleSehExceptionsInMethodIfSupported<testing::Test, void>(testing::Test*, void (testing::Test::*)(), char const*) /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2612:10
    #18 0xab7a1f2f342c in void testing::internal::HandleExceptionsInMethodIfSupported<testing::Test, void>(testing::Test*, void (testing::Test::*)(), char const*) /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2648:14
    #19 0xab7a1f2f300c in testing::Test::Run() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2687:5
    #20 0xab7a1f2f7544 in testing::TestInfo::Run() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2836:11
    #21 0xab7a1f2fac80 in testing::TestSuite::Run() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:3015:30
    #22 0xab7a1f3378cc in testing::internal::UnitTestImpl::RunAllTests() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:5920:44
    #23 0xab7a1f336830 in bool testing::internal::HandleSehExceptionsInMethodIfSupported<testing::internal::UnitTestImpl, bool>(testing::internal::UnitTestImpl*, bool (testing::internal::UnitTestImpl::*)(), char const*) /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2612:10
    #24 0xab7a1f336830 in bool testing::internal::HandleExceptionsInMethodIfSupported<testing::internal::UnitTestImpl, bool>(testing::internal::UnitTestImpl*, bool (testing::internal::UnitTestImpl::*)(), char const*) /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2648:14
    #25 0xab7a1f336174 in testing::UnitTest::Run() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:5484:10
    #26 0xab7a1f20fd98 in RUN_ALL_TESTS() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/include/gtest/gtest.h:2317:73
    #27 0xab7a1f20fd98 in main /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/fuzztest_gtest_main.cc:28:10
    #28 0xff1cd8db84c0 in __libc_start_call_main csu/../sysdeps/nptl/libc_start_call_main.h:58:16
    #29 0xff1cd8db8594 in __libc_start_main csu/../csu/libc-start.c:360:3
    #30 0xab7a1f0994ec in _start (/home/schrodinger/snmalloc/build/fuzzing/snmalloc-fuzzer+0x894ec) (BuildId: 79d6194ed95b845349d610b3ba655c548ffd9902)

0xfb4cd80227ff is located 1 bytes before 19-byte region [0xfb4cd8022800,0xfb4cd8022813)
allocated by thread T0 here:
    #0 0xab7a1f17e8ec in operator new(unsigned long) (/home/schrodinger/snmalloc/build/fuzzing/snmalloc-fuzzer+0x16e8ec) (BuildId: 79d6194ed95b845349d610b3ba655c548ffd9902)
    #1 0xab7a1f18406c in std::__new_allocator<char>::allocate(unsigned long, void const*) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/new_allocator.h:151:27
    #2 0xab7a1f18406c in std::allocator<char>::allocate(unsigned long) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/allocator.h:196:32
    #3 0xab7a1f18406c in std::allocator_traits<std::allocator<char>>::allocate(std::allocator<char>&, unsigned long) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/alloc_traits.h:478:20
    #4 0xab7a1f18406c in std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>::_S_allocate(std::allocator<char>&, unsigned long) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/basic_string.h:131:16
    #5 0xab7a1f18406c in std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>::_M_create(unsigned long&, unsigned long) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/basic_string.tcc:159:14
    #6 0xab7a1f18406c in void std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>::_M_construct<char*>(char*, char*, std::forward_iterator_tag) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/basic_string.tcc:229:14
    #7 0xab7a1f18406c in std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>::basic_string(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>> const&) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/basic_string.h:556:2
    #8 0xab7a1f18406c in forward_memmove(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long) /home/schrodinger/snmalloc/fuzzing/snmalloc-fuzzer.cpp:52:25
    #9 0xab7a1f20c238 in auto fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...)::operator()<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&>(auto&&...) const /home/schrodinger/snmalloc/build/_deps/fuzztest-src/./fuzztest/internal/fixture_driver.h:294:11
    #10 0xab7a1f20c238 in void std::__invoke_impl<void, fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...), std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&>(std::__invoke_other, fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...)&&, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/invoke.h:61:14
    #11 0xab7a1f20c238 in std::__invoke_result<fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...), std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&>::type std::__invoke<fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...), std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&>(fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...)&&, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&, unsigned long&) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/bits/invoke.h:96:14
    #12 0xab7a1f20c238 in decltype(auto) std::__apply_impl<fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...), std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>&, 0ul, 1ul>(fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...)&&, std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>&, std::integer_sequence<unsigned long, 0ul, 1ul>) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/tuple:2921:14
    #13 0xab7a1f20c238 in decltype(auto) std::apply<fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...), std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>&>(fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const::'lambda'(auto&&...)&&, std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>&) /usr/lib/gcc/aarch64-linux-gnu/14/../../../../include/c++/14/tuple:2936:14
    #14 0xab7a1f20c238 in fuzztest::internal::FixtureDriver<fuzztest::Domain<std::tuple<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long>>, fuzztest::internal::NoFixture, void (*)(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, unsigned long), void*>::Test(fuzztest::internal::MoveOnlyAny&&) const /home/schrodinger/snmalloc/build/_deps/fuzztest-src/./fuzztest/internal/fixture_driver.h:292:5
    #15 0xab7a1f22fd5c in fuzztest::internal::FuzzTestFuzzerImpl::RunOneInput(fuzztest::internal::FuzzTestFuzzerImpl::Input const&) /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:1038:22
    #16 0xab7a1f233840 in fuzztest::internal::FuzzTestFuzzerImpl::TrySample(fuzztest::internal::FuzzTestFuzzerImpl::Input const&, bool) /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:770:26
    #17 0xab7a1f234434 in fuzztest::internal::FuzzTestFuzzerImpl::TrySampleAndUpdateInMemoryCorpus(fuzztest::internal::FuzzTestFuzzerImpl::Input, bool) /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:796:35
    #18 0xab7a1f239780 in fuzztest::internal::FuzzTestFuzzerImpl::RunInFuzzingMode(int*, char***, fuzztest::internal::Configuration const&)::$_0::operator()() const::'lambda'(fuzztest::internal::FuzzTestFuzzerImpl::Input)::operator()(fuzztest::internal::FuzzTestFuzzerImpl::Input) const /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:1179:7
    #19 0xab7a1f239780 in fuzztest::internal::FuzzTestFuzzerImpl::RunInFuzzingMode(int*, char***, fuzztest::internal::Configuration const&)::$_0::operator()() const /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:1222:9
    #20 0xab7a1f239780 in fuzztest::internal::FuzzTestFuzzerImpl::RunInFuzzingMode(int*, char***, fuzztest::internal::Configuration const&) /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/internal/runtime.cc:1103:25
    #21 0xab7a1f221b54 in fuzztest::internal::GTest_TestAdaptor::TestBody() /home/schrodinger/snmalloc/build/_deps/fuzztest-src/./fuzztest/internal/googletest_adaptor.h:86:7
    #22 0xab7a1f2f342c in void testing::internal::HandleSehExceptionsInMethodIfSupported<testing::Test, void>(testing::Test*, void (testing::Test::*)(), char const*) /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2612:10
    #23 0xab7a1f2f342c in void testing::internal::HandleExceptionsInMethodIfSupported<testing::Test, void>(testing::Test*, void (testing::Test::*)(), char const*) /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2648:14
    #24 0xab7a1f2f300c in testing::Test::Run() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2687:5
    #25 0xab7a1f2f7544 in testing::TestInfo::Run() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2836:11
    #26 0xab7a1f2fac80 in testing::TestSuite::Run() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:3015:30
    #27 0xab7a1f3378cc in testing::internal::UnitTestImpl::RunAllTests() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:5920:44
    #28 0xab7a1f336830 in bool testing::internal::HandleSehExceptionsInMethodIfSupported<testing::internal::UnitTestImpl, bool>(testing::internal::UnitTestImpl*, bool (testing::internal::UnitTestImpl::*)(), char const*) /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2612:10
    #29 0xab7a1f336830 in bool testing::internal::HandleExceptionsInMethodIfSupported<testing::internal::UnitTestImpl, bool>(testing::internal::UnitTestImpl*, bool (testing::internal::UnitTestImpl::*)(), char const*) /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:2648:14
    #30 0xab7a1f336174 in testing::UnitTest::Run() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/src/gtest.cc:5484:10
    #31 0xab7a1f20fd98 in RUN_ALL_TESTS() /home/schrodinger/snmalloc/build/_deps/googletest-src/googletest/include/gtest/gtest.h:2317:73
    #32 0xab7a1f20fd98 in main /home/schrodinger/snmalloc/build/_deps/fuzztest-src/fuzztest/fuzztest_gtest_main.cc:28:10
    #33 0xff1cd8db84c0 in __libc_start_call_main csu/../sysdeps/nptl/libc_start_call_main.h:58:16
    #34 0xff1cd8db8594 in __libc_start_main csu/../csu/libc-start.c:360:3
    #35 0xab7a1f0994ec in _start (/home/schrodinger/snmalloc/build/fuzzing/snmalloc-fuzzer+0x894ec) (BuildId: 79d6194ed95b845349d610b3ba655c548ffd9902)

SUMMARY: AddressSanitizer: heap-buffer-overflow /home/schrodinger/snmalloc/src/snmalloc/global/memcpy.h:14:5 in void snmalloc::copy_one<1ul>(void*, void const*)
Shadow bytes around the buggy address:
  0xfb4cd8022500: fd fd fd fd fa fa fd fd fd fd fa fa fd fd fd fd
  0xfb4cd8022580: fa fa fd fd fd fd fa fa fd fd fd fd fa fa fd fd
  0xfb4cd8022600: fd fd fa fa fd fd fd fd fa fa fd fd fd fd fa fa
  0xfb4cd8022680: fd fd fd fd fa fa fd fd fd fd fa fa fd fd fd fd
  0xfb4cd8022700: fa fa fd fd fd fd fa fa fd fd fd fd fa fa fd fd
=>0xfb4cd8022780: fd fd fa fa 00 00 00 07 fa fa 00 00 03 fa fa[fa]
  0xfb4cd8022800: 00 00 03 fa fa fa fa fa fa fa fa fa fa fa fa fa
  0xfb4cd8022880: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0xfb4cd8022900: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0xfb4cd8022980: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0xfb4cd8022a00: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
Shadow byte legend (one shadow byte represents 8 application bytes):
  Addressable:           00
  Partially addressable: 01 02 03 04 05 06 07 
  Heap left redzone:       fa
  Freed heap region:       fd
  Stack left redzone:      f1
  Stack mid redzone:       f2
  Stack right redzone:     f3
  Stack after return:      f5
  Stack use after scope:   f8
  Global redzone:          f9
  Global init order:       f6
  Poisoned by user:        f7
  Container overflow:      fc
  Array cookie:            ac
  Intra object redzone:    bb
  ASan internal:           fe
  Left alloca redzone:     ca
  Right alloca redzone:    cb
==84600==ABORTING

=================================================================
=== Fuzzing stats

Elapsed time: 345.63472ms
Total runs: 170
Edges covered: 26
Total edges: 44409
Corpus size: 10
Max stack used: 304

=================================================================
=== BUG FOUND!

/home/schrodinger/snmalloc/fuzzing/snmalloc-fuzzer.cpp:78: Counterexample found for snmalloc_fuzzing.forward_memmove.
The test fails with input:
argument 0: "\347\347\347\347\347\347\347\347\347\347\000\346\346\347\347\347\347\016"
argument 1: 1

=================================================================
=== Regression test draft

TEST(snmalloc_fuzzing, forward_memmoveRegression) {
  forward_memmove(
    std::string("\347\347\347\347\347\347\347\347\347\347\000\346\346\347\347\347\347\016", 18),
    1
  );
}

Please note that the code generated above is best effort and is intended
to use be used as a draft regression test.
For reproducing findings please rely on file based reproduction.
[!] Failed to write reproducer file!

=================================================================

And the following for backward:

schrodinger@Homotopy:~/snmalloc/build$ ./fuzzing/snmalloc-fuzzer --fuzz=snmalloc_fuzzing.backward_memmove
[.] Sanitizer coverage enabled. Counter map size: 44409, Cmp map size: 262144
Note: Google Test filter = snmalloc_fuzzing.backward_memmove
[==========] Running 1 test from 1 test suite.
[----------] Global test environment set-up.
[----------] 1 test from snmalloc_fuzzing
[ RUN      ] snmalloc_fuzzing.backward_memmove
FUZZTEST_PRNG_SEED=7a7eutElc3JgAA5-RrPzt9GA6ahAKG1rqyQl4vwzuCk
[*] Corpus size:     1 | Edges covered:     15 | Fuzzing time:       3.753967ms | Total runs:  1.00e+00 | Runs/secs:   266 | Max stack usage:      304
[*] Corpus size:     2 | Edges covered:     16 | Fuzzing time:       3.867176ms | Total runs:  2.00e+00 | Runs/secs:   517 | Max stack usage:      304
[*] Corpus size:     3 | Edges covered:     17 | Fuzzing time:       3.984284ms | Total runs:  1.00e+01 | Runs/secs:  2509 | Max stack usage:      304
[*] Corpus size:     4 | Edges covered:     18 | Fuzzing time:       4.342434ms | Total runs:  3.40e+01 | Runs/secs:  7829 | Max stack usage:      304
[*] Corpus size:     5 | Edges covered:     18 | Fuzzing time:       5.047901ms | Total runs:  6.60e+01 | Runs/secs: 13074 | Max stack usage:      304
[*] Corpus size:     6 | Edges covered:     20 | Fuzzing time:       5.470942ms | Total runs:  7.90e+01 | Runs/secs: 14439 | Max stack usage:      304
[*] Corpus size:     7 | Edges covered:     20 | Fuzzing time:       5.796376ms | Total runs:  8.50e+01 | Runs/secs: 14664 | Max stack usage:      304
[*] Corpus size:     8 | Edges covered:     21 | Fuzzing time:       6.095159ms | Total runs:  8.60e+01 | Runs/secs: 14109 | Max stack usage:      304
[*] Corpus size:     9 | Edges covered:     25 | Fuzzing time:       6.507801ms | Total runs:  1.01e+02 | Runs/secs: 15519 | Max stack usage:      304
[*] Corpus size:    10 | Edges covered:     25 | Fuzzing time:       7.228001ms | Total runs:  1.04e+02 | Runs/secs: 14388 | Max stack usage:      304
[*] Corpus size:    11 | Edges covered:     25 | Fuzzing time:       8.143634ms | Total runs:  1.06e+02 | Runs/secs: 13016 | Max stack usage:      304
[*] Corpus size:    12 | Edges covered:     26 | Fuzzing time:       8.708809ms | Total runs:  1.08e+02 | Runs/secs: 12401 | Max stack usage:      304
[*] Corpus size:    13 | Edges covered:     26 | Fuzzing time:       9.011276ms | Total runs:  1.19e+02 | Runs/secs: 13205 | Max stack usage:      304
[*] Corpus size:    14 | Edges covered:     27 | Fuzzing time:       9.240834ms | Total runs:  1.22e+02 | Runs/secs: 13202 | Max stack usage:      304
[*] Corpus size:    15 | Edges covered:     27 | Fuzzing time:       9.498451ms | Total runs:  1.27e+02 | Runs/secs: 13370 | Max stack usage:      304
[*] Corpus size:    16 | Edges covered:     28 | Fuzzing time:       9.856926ms | Total runs:  1.30e+02 | Runs/secs: 13188 | Max stack usage:      304

=================================================================
=== Fuzzing stats

Elapsed time: 11.028985ms
Total runs: 190
Edges covered: 28
Total edges: 44409
Corpus size: 16
Max stack used: 304

=================================================================
=== BUG FOUND!

/home/schrodinger/snmalloc/fuzzing/snmalloc-fuzzer.cpp:79: Counterexample found for snmalloc_fuzzing.backward_memmove.
The test fails with input:
argument 0: "\260\361\260\364\364\364\364\364\364\364\223\260X"
argument 1: 3

=================================================================
=== Regression test draft

TEST(snmalloc_fuzzing, backward_memmoveRegression) {
  backward_memmove(
    "\260\361\260\364\364\364\364\364\364\364\223\260X",
    3
  );
}

Please note that the code generated above is best effort and is intended
to use be used as a draft regression test.
For reproducing findings please rely on file based reproduction.
[!] Failed to write reproducer file!

=================================================================
Aborted

@SchrodingerZhu
Copy link
Collaborator Author

cc @devnexen @mjp41

@SchrodingerZhu
Copy link
Collaborator Author

Currently, only memory operations and a single-threaded random walk of the scoped allocator is included in fuzzing. I think this is good enough for a startup patch. We can add in more tests if you find this beneficial, but I prefer to do that in a separate patch instead.

@devnexen
Copy link
Collaborator

devnexen commented Nov 17, 2024

Having played with several times, I would be in favor of merging it.

Copy link
Member

@mjp41 mjp41 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM. I've been thinking we should do some fuzzing. I even have a local branch with some ideas, but this is much better. Thanks

Copy link
Member

@mjp41 mjp41 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM - Thanks so much for doing this. I guess we should add this to CI pipeline, and expand the usage for other tests, where we can.

@mjp41 mjp41 merged commit 0b53b93 into microsoft:main Nov 19, 2024
52 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants