[scudo] [GWP-ASan] Add GWP-ASan variant of scudo benchmarks.
authorMitch Phillips <31459023+hctim@users.noreply.github.com>
Mon, 10 May 2021 18:59:45 +0000 (11:59 -0700)
committerMitch Phillips <31459023+hctim@users.noreply.github.com>
Mon, 10 May 2021 19:14:48 +0000 (12:14 -0700)
GWP-ASan is the "production" variant as compiled by compiler-rt, and it's useful to be able to benchmark changes in GWP-ASan or Scudo's GWP-ASan hooks across versions. GWP-ASan is sampled, and sampled allocations are much slower, but given the amount of allocations that happen under test here - we actually get a reasonable representation of GWP-ASan's negligent performance impact between runs.

Reviewed By: cryptoad

Differential Revision: https://reviews.llvm.org/D101865

compiler-rt/lib/scudo/standalone/benchmarks/CMakeLists.txt
compiler-rt/lib/scudo/standalone/benchmarks/malloc_benchmark.cpp
compiler-rt/lib/scudo/standalone/combined.h

index 6eb0bd6..26d023c 100644 (file)
@@ -18,4 +18,16 @@ foreach(arch ${SCUDO_STANDALONE_SUPPORTED_ARCH})
                 $<TARGET_OBJECTS:RTScudoStandalone.${arch}>)
   set_property(TARGET ScudoBenchmarks.${arch} APPEND_STRING PROPERTY
                COMPILE_FLAGS "${SCUDO_BENCHMARK_CFLAGS}")
+
+  if (COMPILER_RT_HAS_GWP_ASAN)
+    add_benchmark(
+      ScudoBenchmarksWithGwpAsan.${arch} malloc_benchmark.cpp
+      $<TARGET_OBJECTS:RTScudoStandalone.${arch}>
+      $<TARGET_OBJECTS:RTGwpAsan.${arch}>
+      $<TARGET_OBJECTS:RTGwpAsanBacktraceLibc.${arch}>
+      $<TARGET_OBJECTS:RTGwpAsanSegvHandler.${arch}>)
+    set_property(
+      TARGET ScudoBenchmarksWithGwpAsan.${arch} APPEND_STRING PROPERTY
+      COMPILE_FLAGS "${SCUDO_BENCHMARK_CFLAGS} -DGWP_ASAN_HOOKS")
+  endif()
 endforeach()
index ce48dc0..661fff4 100644 (file)
 #include "benchmark/benchmark.h"
 
 #include <memory>
+#include <vector>
+
+void *CurrentAllocator;
+template <typename Config> void PostInitCallback() {
+  reinterpret_cast<scudo::Allocator<Config> *>(CurrentAllocator)->initGwpAsan();
+}
 
 template <typename Config> static void BM_malloc_free(benchmark::State &State) {
-  using AllocatorT = scudo::Allocator<Config>;
+  using AllocatorT = scudo::Allocator<Config, PostInitCallback<Config>>;
   auto Deleter = [](AllocatorT *A) {
     A->unmapTestOnly();
     delete A;
   };
   std::unique_ptr<AllocatorT, decltype(Deleter)> Allocator(new AllocatorT,
                                                            Deleter);
+  CurrentAllocator = Allocator.get();
   Allocator->reset();
 
   const size_t NBytes = State.range(0);
@@ -55,18 +62,19 @@ BENCHMARK_TEMPLATE(BM_malloc_free, scudo::FuchsiaConfig)
 
 template <typename Config>
 static void BM_malloc_free_loop(benchmark::State &State) {
-  using AllocatorT = scudo::Allocator<Config>;
+  using AllocatorT = scudo::Allocator<Config, PostInitCallback<Config>>;
   auto Deleter = [](AllocatorT *A) {
     A->unmapTestOnly();
     delete A;
   };
   std::unique_ptr<AllocatorT, decltype(Deleter)> Allocator(new AllocatorT,
                                                            Deleter);
+  CurrentAllocator = Allocator.get();
   Allocator->reset();
 
   const size_t NumIters = State.range(0);
   size_t PageSize = scudo::getPageSizeCached();
-  void *Ptrs[NumIters];
+  std::vector<void *> Ptrs(NumIters);
 
   for (auto _ : State) {
     size_t SizeLog2 = 0;
index 146408a..03a85ec 100644 (file)
@@ -51,8 +51,7 @@ public:
   typedef typename Params::template TSDRegistryT<ThisT> TSDRegistryT;
 
   void callPostInitCallback() {
-    static pthread_once_t OnceControl = PTHREAD_ONCE_INIT;
-    pthread_once(&OnceControl, PostInitCallback);
+    pthread_once(&PostInitNonce, PostInitCallback);
   }
 
   struct QuarantineCallback {
@@ -952,6 +951,7 @@ private:
   SecondaryT Secondary;
   QuarantineT Quarantine;
   TSDRegistryT TSDRegistry;
+  pthread_once_t PostInitNonce = PTHREAD_ONCE_INIT;
 
 #ifdef GWP_ASAN_HOOKS
   gwp_asan::GuardedPoolAllocator GuardedAlloc;