move Arena, ThreadCachedArena, and Malloc to memory/
[folly.git] / folly / test / ThreadCachedArenaTest.cpp
diff --git a/folly/test/ThreadCachedArenaTest.cpp b/folly/test/ThreadCachedArenaTest.cpp
deleted file mode 100644 (file)
index 1d24c77..0000000
+++ /dev/null
@@ -1,265 +0,0 @@
-/*
- * Copyright 2017 Facebook, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <folly/ThreadCachedArena.h>
-
-#include <algorithm>
-#include <iterator>
-#include <map>
-#include <mutex>
-#include <random>
-#include <thread>
-#include <unordered_map>
-
-#include <glog/logging.h>
-
-#include <folly/Benchmark.h>
-#include <folly/Memory.h>
-#include <folly/Range.h>
-#include <folly/portability/GTest.h>
-
-using namespace folly;
-
-namespace {
-
-class ArenaTester {
- public:
-  explicit ArenaTester(ThreadCachedArena& arena) : arena_(&arena) { }
-
-  void allocate(size_t count, size_t maxSize);
-  void verify();
-  void merge(ArenaTester&& other);
-
- private:
-  std::mutex mergeMutex_;
-  std::vector<std::pair<uint8_t, Range<uint8_t*>>> areas_;
-  ThreadCachedArena* arena_;
-};
-
-void ArenaTester::allocate(size_t count, size_t maxSize) {
-  // Allocate chunks of memory of random sizes
-  std::mt19937 rnd;
-  std::uniform_int_distribution<uint32_t> sizeDist(1, maxSize - 1);
-  areas_.clear();
-  areas_.reserve(count);
-  for (size_t i = 0; i < count; i++) {
-    size_t size = sizeDist(rnd);
-    uint8_t* p = static_cast<uint8_t*>(arena_->allocate(size));
-    areas_.emplace_back(uint8_t(rnd() & 0xff), Range<uint8_t*>(p, size));
-  }
-
-  // Fill each area with a different value, to prove that they don't overlap
-  // Fill in random order.
-  std::random_shuffle(areas_.begin(), areas_.end(), [&rnd](ptrdiff_t n) {
-    return std::uniform_int_distribution<uint32_t>(0, n - 1)(rnd);
-  });
-
-  for (auto& p : areas_) {
-    std::fill(p.second.begin(), p.second.end(), p.first);
-  }
-}
-
-void ArenaTester::verify() {
-  for (auto& p : areas_) {
-    for (auto v : p.second) {
-      EXPECT_EQ(p.first, v);
-    }
-  }
-}
-
-void ArenaTester::merge(ArenaTester&& other) {
-  {
-    std::lock_guard<std::mutex> lock(mergeMutex_);
-    std::move(other.areas_.begin(), other.areas_.end(),
-              std::back_inserter(areas_));
-  }
-  other.areas_.clear();
-}
-
-} // namespace
-
-TEST(ThreadCachedArena, BlockSize) {
-  static const size_t alignment = folly::max_align_v;
-  static const size_t requestedBlockSize = 64;
-
-  ThreadCachedArena arena(requestedBlockSize);
-  size_t blockSize = alignment;
-  uint8_t* prev = static_cast<uint8_t*>(arena.allocate(1));
-
-  // Keep allocating until we're no longer one single alignment away from the
-  // previous allocation -- that's when we've gotten to the next block.
-  uint8_t* p;
-  while ((p = static_cast<uint8_t*>(arena.allocate(1))) ==
-         prev + alignment) {
-    prev = p;
-    blockSize += alignment;
-  }
-
-  VLOG(1) << "Requested block size: " << requestedBlockSize << ", actual: "
-          << blockSize;
-  EXPECT_LE(requestedBlockSize, blockSize);
-}
-
-TEST(ThreadCachedArena, SingleThreaded) {
-  static const size_t requestedBlockSize = 64;
-  ThreadCachedArena arena(requestedBlockSize);
-  EXPECT_EQ(arena.totalSize(), sizeof(ThreadCachedArena));
-
-  ArenaTester tester(arena);
-  tester.allocate(100, 100 << 10);
-  tester.verify();
-
-  EXPECT_GT(arena.totalSize(), sizeof(ThreadCachedArena));
-}
-
-TEST(ThreadCachedArena, MultiThreaded) {
-  static const size_t requestedBlockSize = 64;
-  ThreadCachedArena arena(requestedBlockSize);
-  ArenaTester mainTester(arena);
-
-  // Do this twice, to catch the possibility that memory from the first
-  // round gets freed
-  static const size_t numThreads = 20;
-  for (size_t i = 0; i < 2; i++) {
-    std::vector<std::thread> threads;
-    threads.reserve(numThreads);
-    for (size_t j = 0; j < numThreads; j++) {
-      threads.emplace_back(
-          [&arena, &mainTester] () {
-            ArenaTester tester(arena);
-            tester.allocate(500, 1 << 10);
-            tester.verify();
-            mainTester.merge(std::move(tester));
-          });
-    }
-    for (auto& t : threads) {
-      t.join();
-    }
-  }
-
-  mainTester.verify();
-}
-
-TEST(ThreadCachedArena, StlAllocator) {
-  typedef std::unordered_map<
-    int, int, std::hash<int>, std::equal_to<int>,
-    StlAllocator<ThreadCachedArena, std::pair<const int, int>>> Map;
-
-  static const size_t requestedBlockSize = 64;
-  ThreadCachedArena arena(requestedBlockSize);
-
-  Map map {0, std::hash<int>(), std::equal_to<int>(),
-           StlAllocator<ThreadCachedArena, std::pair<const int, int>>(&arena)};
-
-  for (int i = 0; i < 1000; i++) {
-    map[i] = i;
-  }
-
-  for (int i = 0; i < 1000; i++) {
-    EXPECT_EQ(i, map[i]);
-  }
-}
-
-namespace {
-
-static const int kNumValues = 10000;
-
-BENCHMARK(bmUMStandard, iters) {
-  typedef std::unordered_map<int, int> Map;
-
-  while (iters--) {
-    Map map {0};
-    for (int i = 0; i < kNumValues; i++) {
-      map[i] = i;
-    }
-  }
-}
-
-BENCHMARK(bmUMArena, iters) {
-  typedef std::unordered_map<
-    int, int, std::hash<int>, std::equal_to<int>,
-    StlAllocator<ThreadCachedArena, std::pair<const int, int>>> Map;
-
-  while (iters--) {
-    ThreadCachedArena arena;
-
-    Map map {0, std::hash<int>(), std::equal_to<int>(),
-             StlAllocator<ThreadCachedArena, std::pair<const int, int>>(
-                 &arena)};
-
-    for (int i = 0; i < kNumValues; i++) {
-      map[i] = i;
-    }
-  }
-}
-
-BENCHMARK_DRAW_LINE()
-
-BENCHMARK(bmMStandard, iters) {
-  typedef std::map<int, int> Map;
-
-  while (iters--) {
-    Map map;
-    for (int i = 0; i < kNumValues; i++) {
-      map[i] = i;
-    }
-  }
-}
-
-BENCHMARK_DRAW_LINE()
-
-BENCHMARK(bmMArena, iters) {
-  typedef std::map<
-    int, int, std::less<int>,
-    StlAllocator<ThreadCachedArena, std::pair<const int, int>>> Map;
-
-  while (iters--) {
-    ThreadCachedArena arena;
-
-    Map map {std::less<int>(),
-             StlAllocator<ThreadCachedArena, std::pair<const int, int>>(
-                 &arena)};
-
-    for (int i = 0; i < kNumValues; i++) {
-      map[i] = i;
-    }
-  }
-}
-
-BENCHMARK_DRAW_LINE()
-
-} // namespace
-
-// Benchmark                               Iters   Total t    t/iter iter/sec
-// ----------------------------------------------------------------------------
-// Comparing benchmarks: bmUMStandard,bmUMArena
-//  + 143% bmUMStandard                     1570  2.005 s   1.277 ms  782.9
-// *       bmUMArena                        3817  2.003 s   524.7 us  1.861 k
-// ----------------------------------------------------------------------------
-// Comparing benchmarks: bmMStandard,bmMArena
-//  +79.0% bmMStandard                      1197  2.009 s   1.678 ms  595.8
-// *       bmMArena                         2135  2.002 s   937.6 us  1.042 k
-// ----------------------------------------------------------------------------
-
-int main(int argc, char *argv[]) {
-  testing::InitGoogleTest(&argc, argv);
-  gflags::ParseCommandLineFlags(&argc, &argv, true);
-  auto ret = RUN_ALL_TESTS();
-  if (!ret && FLAGS_benchmark) {
-    folly::runBenchmarks();
-  }
-  return ret;
-}