• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2023 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 #include <benchmark/benchmark.h>
17 
18 #include <cstdlib>
19 #include <ctime>
20 #include <map>
21 #include <unordered_map>
22 #include <vector>
23 
24 #include "utils.h"
25 
26 namespace android {
27 namespace os {
28 namespace statsd {
29 
30 namespace {
31 
32 template <typename ContainerType>
benchmarkFunctionForVector(std::vector<ContainerType> & vec,int capacity)33 void benchmarkFunctionForVector(std::vector<ContainerType>& vec, int capacity) {
34     ContainerType result = false;
35     for (int i = 0; i < capacity; i++) {
36         vec[i] = !result;
37         result = !result;
38     }
39 
40     int resultInt = 0;
41     for (int i = 0; i < capacity; i++) {
42         resultInt += vec[i];
43     }
44 
45     // Make sure the variable is not optimized away by compiler
46     benchmark::DoNotOptimize(vec);
47     benchmark::DoNotOptimize(resultInt);
48 }
49 
50 template <typename ContainerType>
benchmarkStdFillForVector(std::vector<ContainerType> & vec,int capacity)51 void benchmarkStdFillForVector(std::vector<ContainerType>& vec, int capacity) {
52     std::fill(vec.begin(), vec.end(), true);
53     int resultInt = 0;
54     for (int i = 0; i < capacity; i++) {
55         resultInt += vec[i];
56     }
57 
58     // Make sure the variable is not optimized away by compiler
59     benchmark::DoNotOptimize(vec);
60     benchmark::DoNotOptimize(resultInt);
61 }
62 
63 template <typename ContainerType>
benchmarkUpdateKeyValueContainer(benchmark::State & state)64 void benchmarkUpdateKeyValueContainer(benchmark::State& state) {
65     const int kHashesCount = state.range(0);
66 
67     ContainerType matcherStats;
68 
69     auto hashIds = generateRandomHashIds(kHashesCount);
70     for (auto& v : hashIds) {
71         matcherStats[v] = 1;
72     }
73 
74     int64_t result = 0;
75     while (state.KeepRunning()) {
76         for (auto& v : hashIds) {
77             matcherStats[v]++;
78         }
79         for (auto& v : hashIds) {
80             result += matcherStats[v];
81         }
82         benchmark::DoNotOptimize(result);
83         benchmark::ClobberMemory();
84     }
85 }
86 
87 }  //  namespace
88 
BM_BasicVectorBoolUsage(benchmark::State & state)89 static void BM_BasicVectorBoolUsage(benchmark::State& state) {
90     const int capacity = state.range(0);
91     std::vector<bool> vec(capacity);
92 
93     while (state.KeepRunning()) {
94         benchmarkFunctionForVector<bool>(vec, capacity);
95     }
96 }
97 BENCHMARK(BM_BasicVectorBoolUsage)->Args({5})->Args({10})->Args({20})->Args({50})->Args({100});
98 
BM_VectorBoolStdFill(benchmark::State & state)99 static void BM_VectorBoolStdFill(benchmark::State& state) {
100     const int capacity = state.range(0);
101     std::vector<bool> vec(capacity);
102 
103     while (state.KeepRunning()) {
104         benchmarkStdFillForVector<bool>(vec, capacity);
105     }
106 }
107 BENCHMARK(BM_VectorBoolStdFill)->Args({5})->Args({10})->Args({20})->Args({50})->Args({100});
108 
BM_BasicVectorInt8Usage(benchmark::State & state)109 static void BM_BasicVectorInt8Usage(benchmark::State& state) {
110     const int capacity = state.range(0);
111     std::vector<int8_t> vec(capacity);
112 
113     while (state.KeepRunning()) {
114         benchmarkFunctionForVector<int8_t>(vec, capacity);
115     }
116 }
117 BENCHMARK(BM_BasicVectorInt8Usage)->Args({5})->Args({10})->Args({20})->Args({50})->Args({100});
118 
BM_VectorInt8StdFill(benchmark::State & state)119 static void BM_VectorInt8StdFill(benchmark::State& state) {
120     const int capacity = state.range(0);
121     std::vector<int8_t> vec(capacity);
122 
123     while (state.KeepRunning()) {
124         benchmarkStdFillForVector<int8_t>(vec, capacity);
125     }
126 }
127 BENCHMARK(BM_VectorInt8StdFill)->Args({5})->Args({10})->Args({20})->Args({50})->Args({100});
128 
BM_DictUpdateWithMap(benchmark::State & state)129 static void BM_DictUpdateWithMap(benchmark::State& state) {
130     benchmarkUpdateKeyValueContainer<std::map<int64_t, int>>(state);
131 }
132 BENCHMARK(BM_DictUpdateWithMap)->Args({500})->Args({1000})->Args({2000});
133 
BM_DictUpdateWithUnorderedMap(benchmark::State & state)134 static void BM_DictUpdateWithUnorderedMap(benchmark::State& state) {
135     benchmarkUpdateKeyValueContainer<std::unordered_map<int64_t, int>>(state);
136 }
137 BENCHMARK(BM_DictUpdateWithUnorderedMap)->Args({500})->Args({1000})->Args({2000});
138 
139 }  //  namespace statsd
140 }  //  namespace os
141 }  //  namespace android
142