[libcxx-commits] [libcxx] [libc++] Add benchmarks for copy algorithms (PR #127328)

Nikolas Klauser via libcxx-commits libcxx-commits at lists.llvm.org
Tue Feb 18 14:51:37 PST 2025


================
@@ -0,0 +1,87 @@
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+// UNSUPPORTED: c++03, c++11, c++14, c++17
+
+#include <algorithm>
+#include <deque>
+#include <iterator>
+#include <list>
+#include <string>
+#include <vector>
+
+#include "benchmark/benchmark.h"
+#include "../../GenerateInput.h"
+#include "test_macros.h"
+
+template <class Container, class Operation>
+void bm_general(std::string operation_name, Operation copy) {
+  auto bench = [copy](auto& st) {
+    auto const size = st.range(0);
+    using ValueType = typename Container::value_type;
+    Container c;
+    std::generate_n(std::back_inserter(c), size, [] { return Generate<ValueType>::random(); });
+
+    std::vector<ValueType> out(size);
+
+    for ([[maybe_unused]] auto _ : st) {
+      auto result = copy(c.begin(), c.end(), out.begin());
+      benchmark::DoNotOptimize(result);
+      benchmark::DoNotOptimize(out);
+      benchmark::DoNotOptimize(c);
+      benchmark::ClobberMemory();
----------------
philnik777 wrote:

When you `DoNotOptimize(<pointer>)`, the pointed-to data is already escaped and the compiler is forced to commit any writes to that data. `ClobberMemory()` forces committing all writes to any memory that was ever escaped. If you `DoNotOptimize` in a loop you shouldn't have to `ClobberMemory()` directly after unless there is other stuff commit to memory. I think I would write it (without the comments of course) as
```c++
benchmark::DoNotOptimize(c); // escape the arguments to make sure no constant folding can ever be performed
benchmark::DoNotOptimize(out);
auto result = copy(c.begin(), c.end(), out.begin());
benchmark::DoNotOptimize(result); // escape the results to ensure that all function effects have to be committed to memory
```
I tend to escape the function arguments before calling, since it guarantees the same behaviour in all loop iterations. In reality it's probably more a stylistic choice than anything else.

https://github.com/llvm/llvm-project/pull/127328


More information about the libcxx-commits mailing list