1 /*
2 * Copyright (c) 2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include <benchmark/benchmark.h>
17 #include "safe_map.h"
18 #include <array>
19 #include <future>
20 #include <iostream>
21 #include <thread>
22 #include <chrono>
23 #include "benchmark_log.h"
24 #include "benchmark_assert.h"
25 using namespace std;
26 using std::chrono::system_clock;
27
28 namespace OHOS {
29 namespace {
30
31 class BenchmarkSafeMap : public benchmark::Fixture {
32 public:
SetUp(const::benchmark::State & state)33 void SetUp(const ::benchmark::State& state) override
34 {
35 }
36
TearDown(const::benchmark::State & state)37 void TearDown(const ::benchmark::State& state) override
38 {
39 }
40
BenchmarkSafeMap()41 BenchmarkSafeMap()
42 {
43 Iterations(iterations);
44 Repetitions(repetitions);
45 ReportAggregatesOnly();
46 }
47
48 ~BenchmarkSafeMap() override = default;
49
50 protected:
51 const int32_t repetitions = 3;
52 const int32_t iterations = 50;
53 };
54
55 const int INSERT_ONE = 1;
56 const int INSERT_TWO = 2;
57 const int INSERT_THREE = 3;
58 const int INSERT_FOUR = 4;
59 const int INSERT_FIVE = 5;
60 const int INSERT_SIX = 6;
61
62 /*
63 * @tc.name: testUtilsCopyAndAssign001
64 * @tc.desc: single thread test the normal feature insert and erase and EnsureInsert
65 */
BENCHMARK_F(BenchmarkSafeMap,testUtilsCopyAndAssign001)66 BENCHMARK_F(BenchmarkSafeMap, testUtilsCopyAndAssign001)(benchmark::State& state)
67 {
68 BENCHMARK_LOGD("SafeMap testUtilsCopyAndAssign001 start.");
69 while (state.KeepRunning()) {
70 SafeMap<string, int> demoData;
71 // insert new
72 demoData.Insert("A", INSERT_ONE);
73 AssertFalse(demoData.IsEmpty(), "demoData.IsEmpty() did not equal false as expected.", state);
74 AssertEqual(demoData.Size(), INSERT_ONE, "demoData.Size() did not equal INSERT_ONE as expected.", state);
75
76 SafeMap<string, int> newdemo = demoData;
77 int tar = -1;
78 AssertTrue(newdemo.Find("A", tar), "newdemo.Find(\"A\", tar) did not equal true as expected.", state);
79 AssertEqual(INSERT_ONE, tar, "INSERT_ONE did not equal tar as expected.", state);
80
81 tar = -1;
82 SafeMap<string, int> newdemo2;
83 newdemo2 = demoData;
84 AssertTrue(newdemo2.Find("A", tar), "newdemo2.Find(\"A\", tar) did not equal true as expected.", state);
85 AssertEqual(INSERT_ONE, tar, "INSERT_ONE did not equal tar as expected.", state);
86 }
87 BENCHMARK_LOGD("SafeMap testUtilsCopyAndAssign001 end.");
88 }
89
90 /*
91 * @tc.name: testUtilsoperator001
92 * @tc.desc: SafeMap
93 */
BENCHMARK_F(BenchmarkSafeMap,testUtilsoperator001)94 BENCHMARK_F(BenchmarkSafeMap, testUtilsoperator001)(benchmark::State& state)
95 {
96 BENCHMARK_LOGD("SafeMap testUtilsoperator001 start.");
97 while (state.KeepRunning()) {
98 SafeMap<string, int> demoData;
99 // insert new
100 demoData.Insert("A", INSERT_ONE);
101 AssertFalse(demoData.IsEmpty(), "demoData.IsEmpty() did not equal false as expected.", state);
102 AssertEqual(demoData.Size(), INSERT_ONE, "demoData.Size() did not equal INSERT_ONE as expected.", state);
103
104 int valueA;
105 bool foundA = demoData.Find("A", valueA);
106 AssertTrue(foundA, "demoData.Find(\"A\", valueA) did not return true as expected.", state);
107 AssertEqual(valueA, INSERT_ONE, "Value retrieved did not equal INSERT_ONE as expected.", state);
108
109 SafeMap<string, int> newdemo = demoData;
110 int valueNewDemoA;
111 bool foundNewDemoA = newdemo.Find("A", valueNewDemoA);
112 AssertTrue(foundNewDemoA, "newdemo.Find(\"A\", valueNewDemoA) did not return true as expected.", state);
113 AssertEqual(valueNewDemoA, INSERT_ONE, "Value retrieved did not equal INSERT_ONE as expected.", state);
114
115 int tar = -1;
116 newdemo.Insert("B", INSERT_SIX);
117 bool foundB = newdemo.Find("B", tar);
118 AssertTrue(foundB, "newdemo.Find(\"B\", tar) did not return true as expected.", state);
119 AssertEqual(INSERT_SIX, tar, "INSERT_SIX did not equal tar as expected.", state);
120
121 SafeMap<string, int> newdemo2;
122 newdemo2 = newdemo;
123 int valueNewDemo2A;
124 bool foundNewDemo2A = newdemo2.Find("A", valueNewDemo2A);
125 AssertTrue(foundNewDemo2A, "newdemo2.Find(\"A\", valueNewDemo2A) did not return true as expected.", state);
126 AssertEqual(valueNewDemo2A, INSERT_ONE, "Value retrieved did not equal INSERT_ONE as expected.", state);
127 }
128 BENCHMARK_LOGD("SafeMap testUtilsoperator001 end.");
129 }
130
131 /*
132 * @tc.name: testUtilsNormalFeatureInsert001
133 * @tc.desc: SafeMap
134 */
BENCHMARK_F(BenchmarkSafeMap,testUtilsNormalFeatureInsert001)135 BENCHMARK_F(BenchmarkSafeMap, testUtilsNormalFeatureInsert001)(benchmark::State& state)
136 {
137 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureInsert001 start.");
138 while (state.KeepRunning()) {
139 SafeMap<string, int> demoData;
140 AssertTrue(demoData.IsEmpty(), "demoData.IsEmpty() did not equal true as expected.", state);
141
142 // insert new
143 demoData.Insert("A", INSERT_ONE);
144 AssertFalse(demoData.IsEmpty(), "demoData.IsEmpty() did not equal false as expected.", state);
145 AssertEqual(demoData.Size(), INSERT_ONE, "demoData.Size() did not equal INSERT_ONE as expected.", state);
146
147 // insert copy one should fail
148 AssertFalse(demoData.Insert("A", INSERT_TWO),
149 "demoData.Insert(\"A\", INSERT_TWO) did not equal false as expected.", state);
150 AssertEqual(demoData.Size(), INSERT_ONE, "demoData.Size() did not equal INSERT_ONE as expected.", state);
151 }
152 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureInsert001 end.");
153 }
154
155 /*
156 * @tc.name: testUtilsNormalFeatureEnsureInsert001
157 * @tc.desc: SafeMap
158 */
BENCHMARK_F(BenchmarkSafeMap,testUtilsNormalFeatureEnsureInsert001)159 BENCHMARK_F(BenchmarkSafeMap, testUtilsNormalFeatureEnsureInsert001)(benchmark::State& state)
160 {
161 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureEnsureInsert001 start.");
162 while (state.KeepRunning()) {
163 SafeMap<string, int> demoData;
164 AssertTrue(demoData.IsEmpty(), "demoData.IsEmpty() did not equal true as expected.", state);
165
166 demoData.Insert("A", INSERT_ONE);
167 demoData.EnsureInsert("B", INSERT_TWO);
168
169 AssertFalse(demoData.IsEmpty(), "demoData.IsEmpty() did not equal false as expected.", state);
170 AssertEqual(demoData.Size(), INSERT_TWO, "demoData.Size() did not equal INSERT_TWO as expected.", state);
171
172 // insert copy one and new one
173 demoData.EnsureInsert("B", INSERT_FIVE);
174 demoData.EnsureInsert("C", INSERT_SIX);
175 AssertEqual(demoData.Size(), INSERT_THREE, "demoData.Size() did not equal INSERT_THREE as expected.", state);
176 }
177 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureEnsureInsert001 end.");
178 }
179
180 /*
181 * @tc.name: testUtilsNormalFeatureFind001
182 * @tc.desc: SafeMap
183 */
BENCHMARK_F(BenchmarkSafeMap,testUtilsNormalFeatureFind001)184 BENCHMARK_F(BenchmarkSafeMap, testUtilsNormalFeatureFind001)(benchmark::State& state)
185 {
186 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureFind001 start.");
187 while (state.KeepRunning()) {
188 SafeMap<string, int> demoData;
189 AssertTrue(demoData.IsEmpty(), "demoData.IsEmpty() did not equal true as expected.", state);
190
191 demoData.Insert("A", INSERT_ONE);
192 demoData.Insert("B", 10000);
193 demoData.EnsureInsert("B", INSERT_TWO);
194 demoData.EnsureInsert("C", INSERT_SIX);
195
196 AssertFalse(demoData.IsEmpty(), "demoData.IsEmpty() did not equal false as expected.", state);
197 AssertEqual(demoData.Size(), INSERT_THREE, "demoData.Size() did not equal INSERT_THREE as expected.", state);
198
199 int i = 0;
200 AssertTrue(demoData.Find("A", i), "demoData.Find(\"A\", i) did not equal true as expected.", state);
201 AssertEqual(i, INSERT_ONE, "i did not equal INSERT_ONE as expected.", state);
202 AssertTrue(demoData.Find("B", i), "demoData.Find(\"B\", i) did not equal true as expected.", state);
203 AssertEqual(i, INSERT_TWO, "i did not equal INSERT_TWO as expected.", state);
204
205 AssertTrue(demoData.Find("C", i), "demoData.Find(\"C\", i) did not equal true as expected.", state);
206 AssertEqual(i, INSERT_SIX, "i did not equal INSERT_SIX as expected.", state);
207 }
208 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureFind001 end.");
209 }
210
211 /*
212 * @tc.name: testUtilsNormalFeatureFindAndSet001
213 * @tc.desc: SafeMap
214 */
BENCHMARK_F(BenchmarkSafeMap,testUtilsNormalFeatureFindAndSet001)215 BENCHMARK_F(BenchmarkSafeMap, testUtilsNormalFeatureFindAndSet001)(benchmark::State& state)
216 {
217 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureFindAndSet001 start.");
218 while (state.KeepRunning()) {
219 SafeMap<string, int> demoData;
220 AssertTrue(demoData.IsEmpty(), "demoData.IsEmpty() did not equal true as expected.", state);
221
222 demoData.Insert("A", INSERT_ONE);
223 demoData.EnsureInsert("B", INSERT_TWO);
224
225 int oldvalue = 0;
226 int newvalue = 3;
227 AssertTrue(demoData.FindOldAndSetNew("A", oldvalue, newvalue),
228 "demoData.FindOldAndSetNew(\"A\", oldvalue, newvalue) did not equal true as expected.", state);
229
230 // old value
231 AssertEqual(oldvalue, INSERT_ONE, "oldvalue did not equal INSERT_ONE as expected.", state);
232
233 newvalue = 4;
234 AssertTrue(demoData.FindOldAndSetNew("B", oldvalue, newvalue),
235 "demoData.FindOldAndSetNew(\"B\", oldvalue, newvalue) did not equal true as expected.", state);
236
237 // old value
238 AssertEqual(oldvalue, INSERT_TWO, "oldvalue did not equal INSERT_TWO as expected.", state);
239
240 int i = -1;
241 AssertTrue(demoData.Find("A", i), "demoData.Find(\"A\", i) did not equal true as expected.", state);
242
243 // new value
244 AssertEqual(i, INSERT_THREE, "i did not equal INSERT_THREE as expected.", state);
245 AssertTrue(demoData.Find("B", i), "demoData.Find(\"B\", i) did not equal true as expected.", state);
246
247 // new value
248 AssertEqual(i, INSERT_FOUR, "i did not equal INSERT_FOUR as expected.", state);
249 }
250 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureFindAndSet001 end.");
251 }
252
253 /*
254 * @tc.name: testUtilsNormalFeatureEraseAndClear001
255 * @tc.desc: SafeMap
256 */
BENCHMARK_F(BenchmarkSafeMap,testUtilsNormalFeatureEraseAndClear001)257 BENCHMARK_F(BenchmarkSafeMap, testUtilsNormalFeatureEraseAndClear001)(benchmark::State& state)
258 {
259 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureEraseAndClear001 start.");
260 while (state.KeepRunning()) {
261 SafeMap<string, int> demoData;
262 AssertTrue(demoData.IsEmpty(), "demoData.IsEmpty() did not equal true as expected.", state);
263
264 demoData.Insert("A", INSERT_ONE);
265 demoData.EnsureInsert("B", INSERT_TWO);
266
267 AssertEqual(demoData.Size(), INSERT_TWO, "demoData.Size() did not equal INSERT_TWO as expected.", state);
268 demoData.Erase("A");
269 AssertEqual(demoData.Size(), INSERT_ONE, "demoData.Size() did not equal INSERT_ONE as expected.", state);
270
271 demoData.Clear();
272 AssertEqual(demoData.Size(), 0, "demoData.Size() did not equal 0 as expected.", state);
273 }
274 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureEraseAndClear001 end.");
275 }
276
277 /*
278 * @tc.name: testUtilsNormalFeatureIterate001
279 * @tc.desc: Using Iterate to change the second parameter of SafeMap
280 */
Callback(const std::string str,int & value)281 void Callback(const std::string str, int& value)
282 {
283 value++;
284 }
285
BENCHMARK_F(BenchmarkSafeMap,testUtilsNormalFeatureIterate001)286 BENCHMARK_F(BenchmarkSafeMap, testUtilsNormalFeatureIterate001)(benchmark::State& state)
287 {
288 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureIterate001 start.");
289 while (state.KeepRunning()) {
290 SafeMap<string, int> demoData;
291 AssertTrue(demoData.IsEmpty(), "demoData.IsEmpty() did not equal true as expected.", state);
292
293 demoData.Insert("A", INSERT_ONE);
294 demoData.Insert("B", INSERT_TWO);
295 demoData.Insert("C", INSERT_THREE);
296 demoData.Insert("D", INSERT_FOUR);
297 demoData.Iterate(Callback);
298
299 AssertEqual(demoData.Size(), INSERT_FOUR, "demoData.Size() did not equal INSERT_FOUR as expected.", state);
300
301 int valueA;
302 bool foundA = demoData.Find("A", valueA);
303 AssertTrue(foundA, "Key \"A\" was not found as expected.", state);
304 AssertEqual(valueA, INSERT_TWO, "Value for key \"A\" did not equal INSERT_TWO as expected.", state);
305
306 int valueB;
307 bool foundB = demoData.Find("B", valueB);
308 AssertTrue(foundB, "Key \"B\" was not found as expected.", state);
309 AssertEqual(valueB, INSERT_THREE, "Value for key \"B\" did not equal INSERT_THREE as expected.", state);
310
311 int valueC;
312 bool foundC = demoData.Find("C", valueC);
313 AssertTrue(foundC, "Key \"C\" was not found as expected.", state);
314 AssertEqual(valueC, INSERT_FOUR, "Value for key \"C\" did not equal INSERT_FOUR as expected.", state);
315
316 int valueD;
317 bool foundD = demoData.Find("D", valueD);
318 AssertTrue(foundD, "Key \"D\" was not found as expected.", state);
319 AssertEqual(valueD, INSERT_FIVE, "Value for key \"D\" did not equal INSERT_FIVE as expected.", state);
320 }
321 BENCHMARK_LOGD("SafeMap testUtilsNormalFeatureIterate001 end.");
322 }
323
324 /*
325 * @tc.name: testSafeMapConstructor001
326 * @tc.desc: SafeMapConstructor
327 */
BENCHMARK_F(BenchmarkSafeMap,testSafeMapConstructor001)328 BENCHMARK_F(BenchmarkSafeMap, testSafeMapConstructor001)(benchmark::State& state)
329 {
330 BENCHMARK_LOGD("SafeMap testSafeMapConstructor001 start.");
331 while (state.KeepRunning()) {
332 SafeMap<string, int> demoData;
333
334 bool result = demoData.Insert("ONE", INSERT_ONE);
335 AssertEqual(result, true, "result did not equal true as expected.", state);
336 result = demoData.Insert("TWO", INSERT_TWO);
337 AssertEqual(result, true, "result did not equal true as expected.", state);
338
339 SafeMap<string, int> demoData1(demoData);
340 int valueOne;
341 int valueTwo;
342 bool foundOne = demoData1.Find("ONE", valueOne);
343 bool foundTwo = demoData1.Find("TWO", valueTwo);
344 AssertTrue(foundOne && foundTwo, "Not all keys were found as expected.", state);
345 AssertEqual(valueOne, INSERT_ONE, "Value for key \"ONE\" did not match as expected.", state);
346 AssertEqual(valueTwo, INSERT_TWO, "Value for key \"TWO\" did not match as expected.", state);
347 }
348 BENCHMARK_LOGD("SafeMap testSafeMapConstructor001 end.");
349 }
350
351 /*
352 * @tc.name: testSafeMapOperator001
353 * @tc.desc: SafeMapConstructor
354 */
BENCHMARK_F(BenchmarkSafeMap,testSafeMapOperator001)355 BENCHMARK_F(BenchmarkSafeMap, testSafeMapOperator001)(benchmark::State& state)
356 {
357 BENCHMARK_LOGD("SafeMap testSafeMapOperator001 start.");
358 while (state.KeepRunning()) {
359 SafeMap<string, int> demoData;
360
361 bool result = demoData.Insert("ONE", INSERT_ONE);
362 AssertEqual(result, true, "result did not equal true as expected.", state);
363 result = demoData.Insert("TWO", INSERT_TWO);
364 AssertEqual(result, true, "result did not equal true as expected.", state);
365
366 int valueOne;
367 int valueTwo;
368 bool foundOne = demoData.Find("ONE", valueOne);
369 bool foundTwo = demoData.Find("TWO", valueTwo);
370 AssertTrue(foundOne, "Key \"ONE\" was not found as expected.", state);
371 AssertTrue(foundTwo, "Key \"TWO\" was not found as expected.", state);
372 AssertEqual(valueOne, INSERT_ONE, "Value for key \"ONE\" did not equal INSERT_ONE as expected.", state);
373 AssertEqual(valueTwo, INSERT_TWO, "Value for key \"TWO\" did not equal INSERT_TWO as expected.", state);
374 }
375 BENCHMARK_LOGD("SafeMap testSafeMapOperator001 end.");
376 }
377
378 /*
379 * @tc.name: testSafeMapOperator002
380 * @tc.desc: SafeMapConstructor
381 */
BENCHMARK_F(BenchmarkSafeMap,testSafeMapOperator002)382 BENCHMARK_F(BenchmarkSafeMap, testSafeMapOperator002)(benchmark::State& state)
383 {
384 BENCHMARK_LOGD("SafeMap testSafeMapOperator002 start.");
385 while (state.KeepRunning()) {
386 SafeMap<string, int> demoData;
387
388 bool result = demoData.Insert("ONE", INSERT_ONE);
389 AssertEqual(result, true, "result did not equal true as expected.", state);
390
391 SafeMap<string, int> demoData1;
392 result = demoData1.Insert("TWO", INSERT_ONE);
393 AssertEqual(result, true, "result did not equal true as expected.", state);
394
395 int valueDemoData;
396 int valueDemoData1;
397 bool foundDemoData = demoData.Find("ONE", valueDemoData);
398 bool foundDemoData1 = demoData1.Find("TWO", valueDemoData1);
399 BENCHMARK_LOGD("SafeMap data1:%{public}d data2:%{public}d", foundDemoData, foundDemoData1);
400 AssertEqual(valueDemoData, valueDemoData1,
401 "Values for keys \"ONE\" in demoData and demoData1 did not match as expected.", state);
402 }
403 BENCHMARK_LOGD("SafeMap testSafeMapOperator002 end.");
404 }
405
406 /*
407 * @tc.name: testUtilsConcurrentIterate001
408 * @tc.desc: 10 threads test in iterate operation to rewrite a SafeMap.
409 */
410 const int SLEEP_FOR_FIFTY_MILLISECOND = 50;
411 const int THREAD_NUM = 10;
412 const int DATA_NUM = 5;
BENCHMARK_F(BenchmarkSafeMap,testUtilsConcurrentIterate001)413 BENCHMARK_F(BenchmarkSafeMap, testUtilsConcurrentIterate001)(benchmark::State& state)
414 {
415 BENCHMARK_LOGD("SafeMap testUtilsConcurrentIterate001 start.");
416 while (state.KeepRunning()) {
417 SafeMap<string, int> demoData;
418 for (int i = 0; i < DATA_NUM; i++) {
419 demoData.Insert("A" + std::to_string(i), 0);
420 }
421 std::thread threads[THREAD_NUM];
422
423 auto lamfuncIterate = [](SafeMap<string, int>& data, const int& cnt,
424 std::chrono::time_point<std::chrono::high_resolution_clock> absTime) {
425 auto callback_it = [cnt](const string data, int& value) {
426 value = cnt;
427 };
428 std::this_thread::sleep_until(absTime);
429 data.Iterate(callback_it);
430 };
431
432 auto timeT = std::chrono::high_resolution_clock::now();
433 timeT += std::chrono::milliseconds(SLEEP_FOR_FIFTY_MILLISECOND);
434
435 for (int i = 0; i < THREAD_NUM; ++i) {
436 threads[i] = std::thread(lamfuncIterate, std::ref(demoData), i, timeT);
437 }
438
439 for (auto& t : threads) {
440 t.join();
441 }
442
443 for (int i = 0; i < DATA_NUM - 1; i++) {
444 int valueCurrent;
445 int valueNext;
446 bool foundCurrent = demoData.Find("A" + std::to_string(i), valueCurrent);
447 bool foundNext = demoData.Find("A" + std::to_string(i + 1), valueNext);
448
449 AssertTrue(foundCurrent && foundNext, "Not all keys were found as expected.", state);
450 AssertEqual(valueCurrent, valueNext,
451 ("Values for keys \"A" + std::to_string(i) + "\" and \"A" + std::to_string(i + 1) +
452 "\" did not match as expected.").c_str(), state);
453 }
454 }
455 BENCHMARK_LOGD("SafeMap testUtilsConcurrentIterate001 end.");
456 }
457
458 /*
459 * @tc.name: testUtilsConcurrentWriteAndRead001
460 * @tc.desc: 100 threads test in writein to the same key of the map, while read at same time and no throw
461 */
BENCHMARK_F(BenchmarkSafeMap,testUtilsConcurrentWriteAndRead001)462 BENCHMARK_F(BenchmarkSafeMap, testUtilsConcurrentWriteAndRead001)(benchmark::State& state)
463 {
464 BENCHMARK_LOGD("SafeMap testUtilsConcurrentWriteAndRead001 start.");
465 SafeMap<string, int> demoData;
466 std::thread threads[THREAD_NUM];
467 std::thread checkThread[THREAD_NUM];
468 while (state.KeepRunning()) {
469 auto lamfuncInsert = [](SafeMap<string, int>& data, const string& key,
470 const int& value, std::chrono::time_point<std::chrono::high_resolution_clock> absTime) {
471 std::this_thread::sleep_until(absTime);
472 data.EnsureInsert(key, value);
473 };
474
475 auto lamfuncCheck = [](SafeMap<string, int>& data, const string& key,
476 std::chrono::time_point<std::chrono::high_resolution_clock> absTime) {
477 std::this_thread::sleep_until(absTime);
478 thread_local int i = -1;
479 data.Find(key, i);
480 };
481
482 auto timeT = std::chrono::high_resolution_clock::now();
483 timeT += std::chrono::milliseconds(SLEEP_FOR_FIFTY_MILLISECOND);
484 string key("A");
485
486 for (int i = 0; i < THREAD_NUM; ++i) {
487 threads[i] = std::thread(lamfuncInsert, std::ref(demoData), key, i, timeT);
488 checkThread[i] = std::thread(lamfuncCheck, std::ref(demoData), key, timeT);
489 }
490
491 for (auto& t : threads) {
492 t.join();
493 }
494
495 for (auto& t : checkThread) {
496 t.join();
497 }
498 }
499 BENCHMARK_LOGD("SafeMap testUtilsConcurrentWriteAndRead001 end.");
500 }
501
ClearAllContainer(SafeMap<string,int> & demoData,std::vector<std::future<int>> & vcfi,vector<int> & result)502 void ClearAllContainer(SafeMap<string, int>& demoData, std::vector<std::future<int>>& vcfi, vector<int>& result)
503 {
504 demoData.Clear();
505 result.clear();
506 vcfi.clear();
507 }
508
509 /*
510 * @tc.name: testUtilsConcurrentWriteAndFind001
511 * @tc.desc: 100 threads test in writein to the corresponding key of the map,
512 * while read at same time and check the results
513 */
BENCHMARK_F(BenchmarkSafeMap,testUtilsConcurrentWriteAndFind001)514 BENCHMARK_F(BenchmarkSafeMap, testUtilsConcurrentWriteAndFind001)(benchmark::State& state)
515 {
516 BENCHMARK_LOGD("SafeMap testUtilsConcurrentWriteAndFind001 start.");
517 SafeMap<string, int> demoData;
518 std::thread threads[THREAD_NUM];
519 std::vector<std::future<int>> vcfi;
520 while (state.KeepRunning()) {
521 auto lamfuncInsert = [](SafeMap<string, int>& data, const string& key, const int& value,
522 std::chrono::time_point<std::chrono::high_resolution_clock> absTime) {
523 std::this_thread::sleep_until(absTime);
524 data.EnsureInsert(key, value);
525 };
526 auto lamfuncCheckLoop = [](SafeMap<string, int>& data, const string& key,
527 std::chrono::time_point<std::chrono::high_resolution_clock> absTime) {
528 std::this_thread::sleep_until(absTime);
529 thread_local int i = -1;
530 while (!data.Find(key, i)) {
531 std::this_thread::sleep_for(std::chrono::microseconds(10));
532 }
533 return i;
534 };
535 auto timeT = std::chrono::high_resolution_clock::now();
536 timeT += std::chrono::milliseconds(SLEEP_FOR_FIFTY_MILLISECOND);
537 string key("A");
538 for (int i = 0; i < THREAD_NUM; ++i) {
539 threads[i] = std::thread(lamfuncInsert, std::ref(demoData), key + std::to_string(i), i, timeT);
540 vcfi.push_back(std::async(std::launch::async, lamfuncCheckLoop,
541 std::ref(demoData), key + std::to_string(i), timeT));
542 }
543 for (auto& t : threads) {
544 t.join();
545 }
546 vector<int> result;
547 for (auto& t : vcfi) {
548 result.push_back(t.get());
549 }
550 std::sort(result.begin(), result.end());
551 for (int i = 0; i < THREAD_NUM; ++i) {
552 AssertEqual(i, result[i], "tmp did not equal result[i+10] as expected.", state);
553 }
554 ClearAllContainer(demoData, vcfi, result);
555 }
556 BENCHMARK_LOGD("SafeMap testUtilsConcurrentWriteAndFind001 end.");
557 }
558
559 /*
560 * @tc.name: testUtilsConcurrentWriteAndFindAndSet001
561 * @tc.desc: 100 threads test in writein to the corresponding key of the map,
562 * while findandfix at same time and check the results
563 */
BENCHMARK_F(BenchmarkSafeMap,testUtilsConcurrentWriteAndFindAndSet001)564 BENCHMARK_F(BenchmarkSafeMap, testUtilsConcurrentWriteAndFindAndSet001)(benchmark::State& state)
565 {
566 SafeMap<string, int> demoData;
567 std::thread threads[THREAD_NUM];
568 std::vector<std::future<int>> vcfi;
569 while (state.KeepRunning()) {
570 auto lamfuncInsert = [](SafeMap<string, int>& data, const string& key,
571 const int& value, std::chrono::time_point<std::chrono::high_resolution_clock> absTime) {
572 std::this_thread::sleep_until(absTime);
573 data.EnsureInsert(key, value);
574 };
575 auto lamfuncCheckLoop = [](SafeMap<string, int>& data, const string& key,
576 const int& newvalue, std::chrono::time_point<std::chrono::high_resolution_clock> absTime) {
577 std::this_thread::sleep_until(absTime);
578 thread_local int i = -1;
579 while (!data.FindOldAndSetNew(key, i, newvalue)) {
580 std::this_thread::sleep_for(std::chrono::microseconds(10));
581 }
582 return i;
583 };
584 auto timeT = std::chrono::high_resolution_clock::now();
585 timeT += std::chrono::milliseconds(SLEEP_FOR_FIFTY_MILLISECOND);
586 string key("A");
587 for (int i = 0; i < THREAD_NUM; ++i) {
588 threads[i] = std::thread(lamfuncInsert, std::ref(demoData),
589 key + std::to_string(i), i, timeT);
590 vcfi.push_back(std::async(std::launch::async, lamfuncCheckLoop,
591 std::ref(demoData), key + std::to_string(i), i + 1, timeT));
592 }
593 for (auto& t : threads)
594 t.join();
595 vector<int> result;
596 for (auto& t : vcfi)
597 result.push_back(t.get());
598 std::sort(result.begin(), result.end());
599 for (int i = 0; i < THREAD_NUM; ++i) {
600 AssertEqual(i, result[i], "i did not equal result[i] as expected.", state);
601 }
602 result.clear();
603 for (int i = 0; i < THREAD_NUM; ++i) {
604 int t = -1;
605 AssertTrue((demoData.Find("A" + std::to_string(i), t)), "demoData.Find did not equal true.", state);
606 result.push_back(t);
607 }
608 std::sort(result.begin(), result.end());
609 for (int i = 0; i < THREAD_NUM; ++i) {
610 AssertEqual(i + 1, result[i], "i + 1 did not equal result[i] as expected.", state);
611 }
612 ClearAllContainer(demoData, vcfi, result);
613 }
614 }
615 } // namespace
616 } // namespace OHOS
617 // Run the benchmark
618 BENCHMARK_MAIN();
619