xref: /aosp_15_r20/external/webrtc/third_party/crc32c/src/src/crc32c_benchmark.cc (revision d9f758449e529ab9291ac668be2861e7a55c2422)
1 // Copyright 2017 The CRC32C Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. See the AUTHORS file for names of contributors.
4 
5 #include <cstddef>
6 #include <cstdint>
7 
8 #include "crc32c/crc32c_config.h"
9 
10 #include "benchmark/benchmark.h"
11 
12 #if CRC32C_TESTS_BUILT_WITH_GLOG
13 #include "glog/logging.h"
14 #endif  // CRC32C_TESTS_BUILT_WITH_GLOG
15 
16 #include "./crc32c_arm64.h"
17 #include "./crc32c_arm64_check.h"
18 #include "./crc32c_internal.h"
19 #include "./crc32c_sse42.h"
20 #include "./crc32c_sse42_check.h"
21 #include "crc32c/crc32c.h"
22 
23 class CRC32CBenchmark : public benchmark::Fixture {
24  public:
SetUp(const benchmark::State & state)25   void SetUp(const benchmark::State& state) override {
26     block_size_ = static_cast<size_t>(state.range(0));
27     block_data_ = std::string(block_size_, 'x');
28     block_buffer_ = reinterpret_cast<const uint8_t*>(block_data_.data());
29   }
30 
31  protected:
32   std::string block_data_;
33   const uint8_t* block_buffer_;
34   size_t block_size_;
35 };
36 
BENCHMARK_DEFINE_F(CRC32CBenchmark,Public)37 BENCHMARK_DEFINE_F(CRC32CBenchmark, Public)(benchmark::State& state) {
38   uint32_t crc = 0;
39   for (auto _ : state)
40     crc = crc32c::Extend(crc, block_buffer_, block_size_);
41   state.SetBytesProcessed(state.iterations() * block_size_);
42 }
43 BENCHMARK_REGISTER_F(CRC32CBenchmark, Public)
44     ->RangeMultiplier(16)
45     ->Range(256, 16777216);  // Block size.
46 
BENCHMARK_DEFINE_F(CRC32CBenchmark,Portable)47 BENCHMARK_DEFINE_F(CRC32CBenchmark, Portable)(benchmark::State& state) {
48   uint32_t crc = 0;
49   for (auto _ : state)
50     crc = crc32c::ExtendPortable(crc, block_buffer_, block_size_);
51   state.SetBytesProcessed(state.iterations() * block_size_);
52 }
53 BENCHMARK_REGISTER_F(CRC32CBenchmark, Portable)
54     ->RangeMultiplier(16)
55     ->Range(256, 16777216);  // Block size.
56 
57 #if HAVE_ARM64_CRC32C
58 
BENCHMARK_DEFINE_F(CRC32CBenchmark,ArmCRC32C)59 BENCHMARK_DEFINE_F(CRC32CBenchmark, ArmCRC32C)(benchmark::State& state) {
60   if (!crc32c::CanUseArm64Crc32()) {
61     state.SkipWithError("ARM CRC32C instructions not available or not enabled");
62     return;
63   }
64 
65   uint32_t crc = 0;
66   for (auto _ : state)
67     crc = crc32c::ExtendArm64(crc, block_buffer_, block_size_);
68   state.SetBytesProcessed(state.iterations() * block_size_);
69 }
70 BENCHMARK_REGISTER_F(CRC32CBenchmark, ArmCRC32C)
71     ->RangeMultiplier(16)
72     ->Range(256, 16777216);  // Block size.
73 
74 #endif  // HAVE_ARM64_CRC32C
75 
76 #if HAVE_SSE42 && (defined(_M_X64) || defined(__x86_64__))
77 
BENCHMARK_DEFINE_F(CRC32CBenchmark,Sse42)78 BENCHMARK_DEFINE_F(CRC32CBenchmark, Sse42)(benchmark::State& state) {
79   if (!crc32c::CanUseSse42()) {
80     state.SkipWithError("SSE4.2 instructions not available or not enabled");
81     return;
82   }
83 
84   uint32_t crc = 0;
85   for (auto _ : state)
86     crc = crc32c::ExtendSse42(crc, block_buffer_, block_size_);
87   state.SetBytesProcessed(state.iterations() * block_size_);
88 }
89 BENCHMARK_REGISTER_F(CRC32CBenchmark, Sse42)
90     ->RangeMultiplier(16)
91     ->Range(256, 16777216);  // Block size.
92 
93 #endif  // HAVE_SSE42 && (defined(_M_X64) || defined(__x86_64__))
94 
main(int argc,char ** argv)95 int main(int argc, char** argv) {
96 #if CRC32C_TESTS_BUILT_WITH_GLOG
97   google::InitGoogleLogging(argv[0]);
98   google::InstallFailureSignalHandler();
99 #endif  // CRC32C_TESTS_BUILT_WITH_GLOG
100 
101   benchmark::Initialize(&argc, argv);
102   benchmark::RunSpecifiedBenchmarks();
103   return 0;
104 }
105