• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2025 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 <fstream>
17 #include <sstream>
18 #include <set>
19 #include "perf_test.h"
20 #include "ipc_skeleton.h"
21 
22 namespace OHOS::perftest {
23     using namespace std;
24 
GetPidByBundleName(string bundleName)25     int32_t PerfTest::GetPidByBundleName(string bundleName)
26     {
27         string getPidCmd = "pidof " + bundleName;
28         int32_t pid = -1;
29         FILE *fp = popen(getPidCmd.c_str(), "r");
30         if (fp == nullptr) {
31             LOG_E("Excute popen to get process pid failed");
32             return pid;
33         }
34         string pidStr;
35         char bufferInfo[1024] = { '\0' };
36         while (fgets(bufferInfo, sizeof(bufferInfo), fp) != nullptr) {
37             pidStr += bufferInfo;
38         }
39         pclose(fp);
40         LOG_I("Pid of process %{public}s is %{public}s", bundleName.c_str(), pidStr.c_str());
41         stringstream pidStream(pidStr);
42         pidStream >> pid;
43         return pid;
44     }
45 
RunTest(ApiCallErr & error)46     void PerfTest::RunTest(ApiCallErr &error)
47     {
48         LOG_I("%{public}s called", __func__);
49         auto bundleName = perfTestStrategy_->GetBundleName();
50         auto dataCollections = perfTestStrategy_->GetDataCollections();
51         for (auto dataCollection : dataCollections) {
52             dataCollection.second->SetBundleName(bundleName);
53         }
54         isMeasureRunning_ = true;
55         measureResult_.clear();
56         for (int32_t iteration = 0; iteration < perfTestStrategy_->GetIterations(); iteration++) {
57             for (auto& dataCollection : dataCollections) {
58                 dataCollection.second->StartCollection(error);
59                 if (error.code_ != NO_ERROR) {
60                     isMeasureRunning_ = false;
61                     return;
62                 }
63             }
64             perfTestCallback_->OnCall(perfTestStrategy_->GetActionCodeRef(), perfTestStrategy_->GetTimeout(), error);
65             if (error.code_ != NO_ERROR) {
66                 LOG_E("ActionCode call error");
67                 isMeasureRunning_ = false;
68                 return;
69             }
70             for (auto& dataCollection : dataCollections) {
71                 double res = dataCollection.second->StopCollectionAndGetResult(error);
72                 if (error.code_ != NO_ERROR) {
73                     isMeasureRunning_ = false;
74                     return;
75                 }
76                 measureResult_[dataCollection.first].push_back(res);
77             }
78             perfTestCallback_->OnCall(perfTestStrategy_->GetResetCodeRef(), perfTestStrategy_->GetTimeout(), error);
79             if (error.code_ != NO_ERROR) {
80                 LOG_E("ResetCode call error");
81                 isMeasureRunning_ = false;
82                 return;
83             }
84         }
85         isMeasureRunning_ = false;
86         isMeasureComplete_ = true;
87     }
88 
GetMeasureResult(PerfMetric perfMetric,ApiCallErr & error)89     nlohmann::json PerfTest::GetMeasureResult(PerfMetric perfMetric, ApiCallErr &error)
90     {
91         LOG_I("%{public}s called", __func__);
92         nlohmann::json resData;
93         if (perfTestStrategy_->GetPerfMetrics().count(perfMetric) == ZERO) {
94             error = ApiCallErr(ERR_INVALID_INPUT, "PerfMetric: " + to_string(perfMetric) + " is not set to measure");
95             return resData;
96         }
97         if (!isMeasureComplete_ || measureResult_.count(perfMetric) == ZERO ||
98             measureResult_[perfMetric].size() != perfTestStrategy_->GetIterations()) {
99             error = ApiCallErr(ERR_GET_RESULT_FAILED,
100                                "PerfMetric: " + to_string(perfMetric) + " has not been measured yet");
101             return resData;
102         }
103         list<double> resList = measureResult_[perfMetric];
104         list<double> validResList;
105         for (auto res : resList) {
106             if (res > INVALID_VALUE) {
107                 validResList.push_back(res);
108             }
109         }
110         resData["metric"] = perfMetric;
111         resData["roundValues"] = resList;
112         if (validResList.empty()) {
113             resData["maximum"] = INITIAL_VALUE;
114             resData["minimum"] = INITIAL_VALUE;
115             resData["average"] = INITIAL_VALUE;
116         } else {
117             resData["maximum"] = *max_element(validResList.begin(), validResList.end());
118             resData["minimum"] = *min_element(validResList.begin(), validResList.end());
119             resData["average"] = accumulate(validResList.begin(), validResList.end(), 0.0) / validResList.size();
120         }
121         return resData;
122     }
123 
IsMeasureRunning()124     bool PerfTest::IsMeasureRunning()
125     {
126         return isMeasureRunning_;
127     }
128 
Destroy(ApiCallErr & error)129     void PerfTest::Destroy(ApiCallErr &error)
130     {
131         list<string> codeRefs;
132         codeRefs.push_back(perfTestStrategy_->GetActionCodeRef());
133         if (!perfTestStrategy_->GetResetCodeRef().empty()) {
134             codeRefs.push_back(perfTestStrategy_->GetResetCodeRef());
135         }
136         perfTestCallback_->OnDestroy(codeRefs, error);
137     }
138 } // namespace OHOS::perftest
139