1 /* 2 * Copyright (c) Huawei Technologies Co., Ltd. 2021. All rights reserved. 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 <thread> 17 #include <unistd.h> 18 19 #include <gtest/gtest.h> 20 #include "logging.h" 21 #include "profiler_data_repeater.h" 22 23 using namespace testing::ext; 24 25 namespace { 26 class ProfilerDataRepeaterTest : public ::testing::Test { 27 protected: SetUpTestCase()28 static void SetUpTestCase() {} TearDownTestCase()29 static void TearDownTestCase() {} 30 SetUp()31 void SetUp() override {} TearDown()32 void TearDown() override {} 33 }; 34 35 /** 36 * @tc.name: server 37 * @tc.desc: put plugin data. 38 * @tc.type: FUNC 39 */ 40 HWTEST_F(ProfilerDataRepeaterTest, PutPluginData, TestSize.Level1) 41 { 42 const int bufferSize = 10; 43 auto dataRepeater = std::make_shared<ProfilerDataRepeater<ProfilerPluginData>>(bufferSize); 44 ASSERT_NE(dataRepeater, nullptr); 45 46 for (int i = 0; i < bufferSize; i++) { 47 auto data = std::make_shared<ProfilerPluginData>(); 48 dataRepeater->PutPluginData(data); 49 EXPECT_EQ(dataRepeater->Size(), i + 1); 50 } 51 } 52 53 /** 54 * @tc.name: server 55 * @tc.desc: take plugin data. 56 * @tc.type: FUNC 57 */ 58 HWTEST_F(ProfilerDataRepeaterTest, TakePluginData, TestSize.Level1) 59 { 60 const int bufferSize = 10; 61 const int itemCounts = 10000; 62 auto inDataRepeater = std::make_shared<ProfilerDataRepeater<ProfilerPluginData>>(bufferSize); 63 ASSERT_NE(inDataRepeater, nullptr); 64 65 auto outDataRepeater = std::make_shared<ProfilerDataRepeater<ProfilerPluginData>>(bufferSize); 66 ASSERT_NE(outDataRepeater, nullptr); 67 __anonb9987f610202(int x) 68 auto f = [](int x) { return 2 * x + 1; }; 69 __anonb9987f610302() 70 std::thread worker([&]() { 71 for (int i = 0; i < itemCounts; i++) { 72 auto itemX = inDataRepeater->TakePluginData(); 73 74 // compute in worker thread 75 int x = itemX ? std::stoi(itemX->data()) : 0; 76 int y = f(x); 77 78 auto itemY = std::make_shared<ProfilerPluginData>(); 79 itemY->set_data(std::to_string(y)); 80 outDataRepeater->PutPluginData(itemY); 81 } 82 }); 83 84 for (int i = 0; i < itemCounts; i++) { 85 int x0 = i; 86 auto itemX = std::make_shared<ProfilerPluginData>(); 87 itemX->set_data(std::to_string(x0)); 88 inDataRepeater->PutPluginData(itemX); 89 90 auto itemY = outDataRepeater->TakePluginData(); 91 int y = itemY ? std::stoi(itemY->data()) : 0; 92 93 // redo compute in main thread 94 int y0 = f(x0); 95 96 // check results 97 EXPECT_EQ(y, y0); 98 } 99 worker.join(); 100 } 101 102 /** 103 * @tc.name: server 104 * @tc.desc: take plugin profiler data. 105 * @tc.type: FUNC 106 */ 107 HWTEST_F(ProfilerDataRepeaterTest, TakePluginDataVec, TestSize.Level1) 108 { 109 const int itemCounts = 10000; 110 const int bufferSize = itemCounts; 111 auto inDataRepeater = std::make_shared<ProfilerDataRepeater<ProfilerPluginData>>(bufferSize); 112 ASSERT_NE(inDataRepeater, nullptr); 113 114 auto outDataRepeater = std::make_shared<ProfilerDataRepeater<ProfilerPluginData>>(bufferSize); 115 ASSERT_NE(outDataRepeater, nullptr); 116 __anonb9987f610402(int x) 117 auto f = [](int x) { return 2 * x + 1; }; __anonb9987f610502() 118 std::thread worker([&]() { 119 for (int i = 0; i < itemCounts; i++) { 120 auto xData = inDataRepeater->TakePluginData(); 121 122 // compute in worker thread 123 int x = xData ? std::stoi(xData->data()) : 0; 124 int y = f(x); 125 126 auto yData = std::make_shared<ProfilerPluginData>(); 127 yData->set_data(std::to_string(y)); 128 outDataRepeater->PutPluginData(yData); 129 } 130 }); 131 132 std::vector<int> yVec; 133 for (int i = 0; i < itemCounts; i++) { 134 int x0 = i; 135 auto xData = std::make_shared<ProfilerPluginData>(); 136 xData->set_data(std::to_string(x0)); 137 inDataRepeater->PutPluginData(xData); 138 139 int y0 = f(x0); 140 yVec.push_back(y0); 141 } 142 worker.join(); 143 144 std::vector<ProfilerPluginDataPtr> pluginDataVec; 145 auto count = outDataRepeater->TakePluginData(pluginDataVec); 146 EXPECT_EQ(count, yVec.size()); 147 148 for (size_t i = 0; i < pluginDataVec.size(); i++) { 149 auto yData = pluginDataVec[i]; 150 int y = yData ? std::stoi(yData->data()) : 0; 151 EXPECT_EQ(y, yVec[i]); 152 } 153 } 154 155 /** 156 * @tc.name: server 157 * @tc.desc: close plugin profiler data. 158 * @tc.type: FUNC 159 */ 160 HWTEST_F(ProfilerDataRepeaterTest, Close, TestSize.Level1) 161 { 162 const int bufferSize = 10; 163 auto dataRepeater = std::make_shared<ProfilerDataRepeater<ProfilerPluginData>>(bufferSize); 164 ASSERT_NE(dataRepeater, nullptr); 165 166 dataRepeater->Close(); 167 } 168 169 /** 170 * @tc.name: server 171 * @tc.desc: reset plugin profiler data. 172 * @tc.type: FUNC 173 */ 174 HWTEST_F(ProfilerDataRepeaterTest, Reset, TestSize.Level1) 175 { 176 const int bufferSize = 10; 177 auto dataRepeater = std::make_shared<ProfilerDataRepeater<ProfilerPluginData>>(bufferSize); 178 ASSERT_NE(dataRepeater, nullptr); 179 180 dataRepeater->Reset(); 181 } 182 183 /** 184 * @tc.name: server 185 * @tc.desc: close plugin profiler data. 186 * @tc.type: FUNC 187 */ 188 HWTEST_F(ProfilerDataRepeaterTest, CloseWithFastProducer, TestSize.Level1) 189 { 190 const int bufferSize = 10; 191 const int numProducts = 20; 192 auto dataRepeater = std::make_shared<ProfilerDataRepeater<ProfilerPluginData>>(bufferSize); 193 ASSERT_NE(dataRepeater, nullptr); 194 __anonb9987f610602() 195 std::thread producer([=]() { 196 for (int i = 0; i < numProducts; i++) { 197 auto data = std::make_shared<ProfilerPluginData>(); 198 if (!dataRepeater->PutPluginData(data)) { 199 PROFILER_LOG_DEBUG(LOG_CORE, "put data %d FAILED!", i); 200 break; 201 } 202 } 203 }); 204 205 const int consumeDelayUs = 50 * 1000; __anonb9987f610702() 206 std::thread consumer([=]() { 207 for (int i = 0; i < numProducts; i++) { 208 auto data = dataRepeater->TakePluginData(); 209 if (!data) { 210 PROFILER_LOG_DEBUG(LOG_CORE, "get data %d FAILED!", i); 211 break; 212 } 213 usleep(consumeDelayUs); 214 } 215 }); 216 217 usleep(consumeDelayUs * 3); 218 dataRepeater->Close(); 219 producer.join(); 220 consumer.join(); 221 } 222 } // namespace