• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022 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 "socperf.h"
17 #include "config_policy_utils.h"
18 #include "hitrace_meter.h"
19 
20 namespace OHOS {
21 namespace SOCPERF {
SocPerf()22 SocPerf::SocPerf()
23 {
24 }
25 
~SocPerf()26 SocPerf::~SocPerf()
27 {
28 }
29 
Init()30 bool SocPerf::Init()
31 {
32     debugLogEnabled = HiLogIsLoggable(LOG_TAG_DOMAIN_ID_SOC_PERF, LOG_TAG_SOC_PERF, LOG_DEBUG);
33 
34     if (!LoadConfigXmlFile(SOCPERF_RESOURCE_CONFIG_XML)) {
35         SOC_PERF_LOGE("%{public}s, Failed to load %{public}s", __func__, SOCPERF_RESOURCE_CONFIG_XML.c_str());
36         return false;
37     }
38 
39     if (!LoadConfigXmlFile(SOCPERF_BOOST_CONFIG_XML)) {
40         SOC_PERF_LOGE("%{public}s, Failed to load %{public}s", __func__, SOCPERF_BOOST_CONFIG_XML.c_str());
41         return false;
42     }
43 
44     PrintCachedInfo();
45 
46     if (!CreateHandlers()) {
47         SOC_PERF_LOGE("%{public}s, Failed to create handler threads", __func__);
48         return false;
49     }
50 
51     InitHandlerThreads();
52 
53     resNodeInfo.clear();
54     govResNodeInfo.clear();
55     resStrToIdInfo.clear();
56     limitRequest = std::vector<std::unordered_map<int32_t, int32_t>>(ACTION_TYPE_MAX);
57 
58     enabled = true;
59 
60     if (debugLogEnabled) {
61         SOC_PERF_LOGD("%{public}s, SocPerf Init SUCCESS!", __func__);
62     }
63 
64     return true;
65 }
66 
PerfRequest(int32_t cmdId,const std::string & msg)67 void SocPerf::PerfRequest(int32_t cmdId, const std::string& msg)
68 {
69     if (!enabled) {
70         SOC_PERF_LOGE("%{public}s, SocPerf disabled!", __func__);
71         return;
72     }
73     if (perfActionsInfo.find(cmdId) == perfActionsInfo.end()) {
74         SOC_PERF_LOGE("%{public}s, Invalid PerfRequest cmdId[%{public}d]", __func__, cmdId);
75         return;
76     }
77     if (debugLogEnabled) {
78         SOC_PERF_LOGD("%{public}s, cmdId[%{public}d]msg[%{public}s]", __func__, cmdId, msg.c_str());
79     }
80     std::string trace_str(__func__);
81     trace_str.append(",cmdId[").append(std::to_string(cmdId)).append("]");
82     trace_str.append(",msg[").append(msg).append("]");
83     StartTrace(HITRACE_TAG_OHOS, trace_str, -1);
84     DoFreqActions(perfActionsInfo[cmdId], EVENT_INVALID, ACTION_TYPE_PERF);
85     FinishTrace(HITRACE_TAG_OHOS);
86 }
87 
PerfRequestEx(int32_t cmdId,bool onOffTag,const std::string & msg)88 void SocPerf::PerfRequestEx(int32_t cmdId, bool onOffTag, const std::string& msg)
89 {
90     if (!enabled) {
91         SOC_PERF_LOGE("%{public}s, SocPerf disabled!", __func__);
92         return;
93     }
94     if (perfActionsInfo.find(cmdId) == perfActionsInfo.end()) {
95         SOC_PERF_LOGE("%{public}s, Invalid PerfRequestEx cmdId[%{public}d]", __func__, cmdId);
96         return;
97     }
98     if (debugLogEnabled) {
99         SOC_PERF_LOGD("%{public}s, cmdId[%{public}d]onOffTag[%{public}d]msg[%{public}s]",
100             __func__, cmdId, onOffTag, msg.c_str());
101     }
102     std::string trace_str(__func__);
103     trace_str.append(",cmdId[").append(std::to_string(cmdId)).append("]");
104     trace_str.append(",onOff[").append(std::to_string(onOffTag)).append("]");
105     trace_str.append(",msg[").append(msg).append("]");
106     StartTrace(HITRACE_TAG_OHOS, trace_str, -1);
107     DoFreqActions(perfActionsInfo[cmdId], onOffTag ? EVENT_ON : EVENT_OFF, ACTION_TYPE_PERF);
108     FinishTrace(HITRACE_TAG_OHOS);
109 }
110 
PowerLimitBoost(bool onOffTag,const std::string & msg)111 void SocPerf::PowerLimitBoost(bool onOffTag, const std::string& msg)
112 {
113     if (!enabled) {
114         SOC_PERF_LOGE("%{public}s, SocPerf disabled!", __func__);
115         return;
116     }
117     if (debugLogEnabled) {
118         SOC_PERF_LOGD("%{public}s, onOffTag[%{public}d]msg[%{public}s]", __func__, onOffTag, msg.c_str());
119     }
120     std::string trace_str(__func__);
121     trace_str.append(",onOff[").append(std::to_string(onOffTag)).append("]");
122     trace_str.append(",msg[").append(msg).append("]");
123     StartTrace(HITRACE_TAG_OHOS, trace_str, -1);
124     for (auto handler : handlers) {
125         auto event = AppExecFwk::InnerEvent::Get(INNER_EVENT_ID_POWER_LIMIT_BOOST_FREQ, onOffTag ? 1 : 0);
126         handler->SendEvent(event);
127     }
128     FinishTrace(HITRACE_TAG_OHOS);
129 }
130 
ThermalLimitBoost(bool onOffTag,const std::string & msg)131 void SocPerf::ThermalLimitBoost(bool onOffTag, const std::string& msg)
132 {
133     if (!enabled) {
134         SOC_PERF_LOGE("%{public}s, SocPerf disabled!", __func__);
135         return;
136     }
137     if (debugLogEnabled) {
138         SOC_PERF_LOGD("%{public}s, onOffTag[%{public}d]msg[%{public}s]", __func__, onOffTag, msg.c_str());
139     }
140     std::string trace_str(__func__);
141     trace_str.append(",onOff[").append(std::to_string(onOffTag)).append("]");
142     trace_str.append(",msg[").append(msg).append("]");
143     StartTrace(HITRACE_TAG_OHOS, trace_str, -1);
144     for (auto handler : handlers) {
145         auto event = AppExecFwk::InnerEvent::Get(INNER_EVENT_ID_THERMAL_LIMIT_BOOST_FREQ, onOffTag ? 1 : 0);
146         handler->SendEvent(event);
147     }
148     FinishTrace(HITRACE_TAG_OHOS);
149 }
150 
LimitRequest(int32_t clientId,const std::vector<int32_t> & tags,const std::vector<int64_t> & configs,const std::string & msg)151 void SocPerf::LimitRequest(int32_t clientId,
152     const std::vector<int32_t>& tags, const std::vector<int64_t>& configs, const std::string& msg)
153 {
154     if (!enabled) {
155         SOC_PERF_LOGE("%{public}s, SocPerf disabled!", __func__);
156         return;
157     }
158     if (tags.size() != configs.size()) {
159         SOC_PERF_LOGE("%{public}s, tags'size and configs' size must be the same!", __func__);
160         return;
161     }
162     if (clientId <= ACTION_TYPE_PERF || clientId >= ACTION_TYPE_MAX) {
163         SOC_PERF_LOGE("%{public}s, clientId must be between ACTION_TYPE_PERF and ACTION_TYPE_MAX!", __func__);
164         return;
165     }
166     if (debugLogEnabled) {
167         for (int32_t i = 0; i < (int32_t)tags.size(); i++) {
168             SOC_PERF_LOGD("%{public}s, clientId[%{public}d],tags[%{public}d],configs[%{public}lld],msg[%{public}s]",
169                 __func__, clientId, tags[i], (long long)configs[i], msg.c_str());
170         }
171     }
172     for (int32_t i = 0; i < (int32_t)tags.size(); i++) {
173         int32_t resId = tags[i];
174         auto handler = GetHandlerByResId(resId);
175         if (!handler) {
176             continue;
177         }
178         int64_t resValue = configs[i];
179         auto iter = limitRequest[clientId].find(resId);
180         if (iter != limitRequest[clientId].end()
181             && limitRequest[clientId][resId] != INVALID_VALUE) {
182             auto resAction = std::make_shared<ResAction>(
183                 limitRequest[clientId][resId], 0, clientId, EVENT_OFF);
184             auto event = AppExecFwk::InnerEvent::Get(INNER_EVENT_ID_DO_FREQ_ACTION, resAction, resId);
185             handler->SendEvent(event);
186             limitRequest[clientId].erase(iter);
187         }
188         if (resValue != INVALID_VALUE) {
189             auto resAction = std::make_shared<ResAction>(resValue, 0, clientId, EVENT_ON);
190             auto event = AppExecFwk::InnerEvent::Get(INNER_EVENT_ID_DO_FREQ_ACTION, resAction, resId);
191             handler->SendEvent(event);
192             limitRequest[clientId].insert(std::pair<int32_t, int32_t>(resId, resValue));
193         }
194     }
195 }
196 
DoFreqActions(std::shared_ptr<Actions> actions,int32_t onOff,int32_t actionType)197 void SocPerf::DoFreqActions(std::shared_ptr<Actions> actions, int32_t onOff, int32_t actionType)
198 {
199     for (auto iter = actions->actionList.begin(); iter != actions->actionList.end(); iter++) {
200         std::shared_ptr<Action> action = *iter;
201         for (int32_t i = 0; i < (int32_t)action->variable.size() - 1; i += RES_ID_AND_VALUE_PAIR) {
202             auto handler = GetHandlerByResId(action->variable[i]);
203             if (!handler) {
204                 continue;
205             }
206             auto resAction = std::make_shared<ResAction>(action->variable[i + 1], action->duration, actionType, onOff);
207             auto event = AppExecFwk::InnerEvent::Get(INNER_EVENT_ID_DO_FREQ_ACTION, resAction, action->variable[i]);
208             handler->SendEvent(event);
209         }
210     }
211 }
212 
GetRealConfigPath(const std::string configFile)213 std::string SocPerf::GetRealConfigPath(const std::string configFile)
214 {
215     char buf[PATH_MAX + 1];
216     char* configFilePath = GetOneCfgFile(configFile.c_str(), buf, PATH_MAX + 1);
217     char tmpPath[PATH_MAX + 1] = {0};
218     if (!configFilePath || strlen(configFilePath) == 0 || strlen(configFilePath) > PATH_MAX ||
219         !realpath(configFilePath, tmpPath)) {
220         SOC_PERF_LOGE("%{public}s, load %{public}s file fail", __func__, configFile.c_str());
221         return "";
222     }
223     return std::string(tmpPath);
224 }
225 
GetHandlerByResId(int32_t resId)226 std::shared_ptr<SocPerfHandler> SocPerf::GetHandlerByResId(int32_t resId)
227 {
228     if (!IsValidResId(resId)) {
229         return nullptr;
230     }
231     return handlers[resId / RES_ID_NUMS_PER_TYPE - 1];
232 }
233 
LoadConfigXmlFile(std::string configFile)234 bool SocPerf::LoadConfigXmlFile(std::string configFile)
235 {
236     std::string realConfigFile = GetRealConfigPath(configFile);
237     if (realConfigFile.size() <= 0) {
238         return false;
239     }
240     xmlKeepBlanksDefault(0);
241     xmlDoc* file = xmlReadFile(realConfigFile.c_str(), nullptr, XML_PARSE_NOERROR | XML_PARSE_NOWARNING);
242     if (!file) {
243         SOC_PERF_LOGE("%{public}s, Failed to open xml file", __func__);
244         return false;
245     }
246     xmlNode* rootNode = xmlDocGetRootElement(file);
247     if (!rootNode) {
248         SOC_PERF_LOGE("%{public}s, Failed to get xml file's RootNode", __func__);
249         xmlFreeDoc(file);
250         return false;
251     }
252     if (!xmlStrcmp(rootNode->name, reinterpret_cast<const xmlChar*>("Configs"))) {
253         if (realConfigFile.find(SOCPERF_RESOURCE_CONFIG_XML) != std::string::npos) {
254             xmlNode* child = rootNode->children;
255             for (; child; child = child->next) {
256                 if (!xmlStrcmp(child->name, reinterpret_cast<const xmlChar*>("Resource"))) {
257                     if (!LoadResource(child, realConfigFile)) {
258                         xmlFreeDoc(file);
259                         return false;
260                     }
261                 } else if (!xmlStrcmp(child->name, reinterpret_cast<const xmlChar*>("GovResource"))) {
262                     if (!LoadGovResource(child, realConfigFile)) {
263                         xmlFreeDoc(file);
264                         return false;
265                     }
266                 }
267             }
268         } else {
269             if (!LoadCmd(rootNode, realConfigFile)) {
270                 xmlFreeDoc(file);
271                 return false;
272             }
273         }
274     } else {
275         SOC_PERF_LOGE("%{public}s, Wrong format for xml file", __func__);
276         xmlFreeDoc(file);
277         return false;
278     }
279     xmlFreeDoc(file);
280     if (debugLogEnabled) {
281         SOC_PERF_LOGD("%{public}s, Success to Load %{public}s", __func__, configFile.c_str());
282     }
283     return true;
284 }
285 
CreateHandlers()286 bool SocPerf::CreateHandlers()
287 {
288     handlers = std::vector<std::shared_ptr<SocPerfHandler>>(MAX_HANDLER_THREADS);
289     std::string threadName = "socperf_handler";
290     for (int32_t i = 0; i < (int32_t)handlers.size(); i++) {
291         auto runner = AppExecFwk::EventRunner::Create(threadName);
292         if (!runner) {
293             SOC_PERF_LOGE("%{public}s, Failed to Create EventRunner", __func__);
294             return false;
295         }
296         handlers[i] = std::make_shared<SocPerfHandler>(runner);
297     }
298     if (debugLogEnabled) {
299         SOC_PERF_LOGD("%{public}s, Success to Create All Handler threads", __func__);
300     }
301     return true;
302 }
303 
InitHandlerThreads()304 void SocPerf::InitHandlerThreads()
305 {
306     for (auto iter = resNodeInfo.begin(); iter != resNodeInfo.end(); ++iter) {
307         std::shared_ptr<ResNode> resNode = iter->second;
308         auto handler = GetHandlerByResId(resNode->id);
309         if (!handler) {
310             continue;
311         }
312         auto event = AppExecFwk::InnerEvent::Get(INNER_EVENT_ID_INIT_RES_NODE_INFO, resNode);
313         handler->SendEvent(event);
314     }
315     for (auto iter = govResNodeInfo.begin(); iter != govResNodeInfo.end(); ++iter) {
316         std::shared_ptr<GovResNode> govResNode = iter->second;
317         auto handler = GetHandlerByResId(govResNode->id);
318         if (!handler) {
319             continue;
320         }
321         auto event = AppExecFwk::InnerEvent::Get(INNER_EVENT_ID_INIT_GOV_RES_NODE_INFO, govResNode);
322         handler->SendEvent(event);
323     }
324 }
325 
LoadResource(xmlNode * child,std::string configFile)326 bool SocPerf::LoadResource(xmlNode* child, std::string configFile)
327 {
328     xmlNode* grandson = child->children;
329     for (; grandson; grandson = grandson->next) {
330         if (!xmlStrcmp(grandson->name, reinterpret_cast<const xmlChar*>("res"))) {
331             char* id = reinterpret_cast<char*>(xmlGetProp(grandson, reinterpret_cast<const xmlChar*>("id")));
332             char* name = reinterpret_cast<char*>(xmlGetProp(grandson, reinterpret_cast<const xmlChar*>("name")));
333             char* pair = reinterpret_cast<char*>(xmlGetProp(grandson, reinterpret_cast<const xmlChar*>("pair")));
334             char* mode = reinterpret_cast<char*>(xmlGetProp(grandson, reinterpret_cast<const xmlChar*>("mode")));
335             if (!CheckResourceTag(id, name, pair, mode, configFile)) {
336                 return false;
337             }
338             xmlNode* greatGrandson = grandson->children;
339             std::shared_ptr<ResNode> resNode = std::make_shared<ResNode>(
340                 atoi(id), name, mode ? atoi(mode) : 0, pair ? atoi(pair) : INVALID_VALUE);
341             char *def = nullptr;
342             char *path  = nullptr;
343             char *node  = nullptr;
344             for (; greatGrandson; greatGrandson = greatGrandson->next) {
345                 if (!xmlStrcmp(greatGrandson->name, reinterpret_cast<const xmlChar*>("default"))) {
346                     def = reinterpret_cast<char*>(xmlNodeGetContent(greatGrandson));
347                 } else if (!xmlStrcmp(greatGrandson->name, reinterpret_cast<const xmlChar*>("path"))) {
348                     path = reinterpret_cast<char*>(xmlNodeGetContent(greatGrandson));
349                 } else if (!xmlStrcmp(greatGrandson->name, reinterpret_cast<const xmlChar*>("node"))) {
350                     node = reinterpret_cast<char*>(xmlNodeGetContent(greatGrandson));
351                 }
352             }
353             if (!CheckResourceTag(def, path, configFile)) {
354                 return false;
355             }
356             resNode->def = atoll(def);
357             resNode->path = path;
358             if (node && !LoadResourceAvailable(resNode, node)) {
359                 SOC_PERF_LOGE("%{public}s, Invalid resource node for %{public}s", __func__, configFile.c_str());
360                 return false;
361             }
362 
363             resStrToIdInfo.insert(std::pair<std::string, int32_t>(resNode->name, resNode->id));
364             resNodeInfo.insert(std::pair<int32_t, std::shared_ptr<ResNode>>(resNode->id, resNode));
365         }
366     }
367 
368     if (!CheckPairResIdValid() || !CheckResDefValid()) {
369         return false;
370     }
371 
372     return true;
373 }
374 
LoadGovResource(xmlNode * child,std::string configFile)375 bool SocPerf::LoadGovResource(xmlNode* child, std::string configFile)
376 {
377     xmlNode* grandson = child->children;
378     for (; grandson; grandson = grandson->next) {
379         if (xmlStrcmp(grandson->name, reinterpret_cast<const xmlChar*>("res"))) {
380             continue;
381         }
382         char* id = reinterpret_cast<char*>(xmlGetProp(grandson, reinterpret_cast<const xmlChar*>("id")));
383         char* name = reinterpret_cast<char*>(xmlGetProp(grandson, reinterpret_cast<const xmlChar*>("name")));
384         if (!CheckGovResourceTag(id, name, configFile)) {
385             return false;
386         }
387         xmlNode* greatGrandson = grandson->children;
388         std::shared_ptr<GovResNode> govResNode = std::make_shared<GovResNode>(atoi(id), name);
389         for (; greatGrandson; greatGrandson = greatGrandson->next) {
390             if (!xmlStrcmp(greatGrandson->name, reinterpret_cast<const xmlChar*>("default"))) {
391                 char* def = reinterpret_cast<char*>(xmlNodeGetContent(greatGrandson));
392                 if (!def || !IsNumber(def)) {
393                     SOC_PERF_LOGE("%{public}s, Invalid governor resource default for %{public}s",
394                         __func__, configFile.c_str());
395                     return false;
396                 }
397                 govResNode->def = atoll(def);
398             } else if (!xmlStrcmp(greatGrandson->name, reinterpret_cast<const xmlChar*>("path"))) {
399                 char* path = reinterpret_cast<char*>(xmlNodeGetContent(greatGrandson));
400                 if (!path) {
401                     SOC_PERF_LOGE("%{public}s, Invalid governor resource path for %{public}s",
402                         __func__, configFile.c_str());
403                     return false;
404                 }
405                 govResNode->paths.push_back(path);
406             } else if (!xmlStrcmp(greatGrandson->name, reinterpret_cast<const xmlChar*>("node"))) {
407                 char* level = reinterpret_cast<char*>(
408                     xmlGetProp(greatGrandson, reinterpret_cast<const xmlChar*>("level")));
409                 char* node = reinterpret_cast<char*>(xmlNodeGetContent(greatGrandson));
410                 if (!level || !IsNumber(level) || !node
411                     || !LoadGovResourceAvailable(govResNode, level, node)) {
412                     SOC_PERF_LOGE("%{public}s, Invalid governor resource node for %{public}s",
413                         __func__, configFile.c_str());
414                     return false;
415                 }
416             }
417         }
418 
419         resStrToIdInfo.insert(std::pair<std::string, int32_t>(govResNode->name, govResNode->id));
420         govResNodeInfo.insert(std::pair<int32_t, std::shared_ptr<GovResNode>>(govResNode->id, govResNode));
421     }
422 
423     if (!CheckGovResDefValid()) {
424         return false;
425     }
426 
427     return true;
428 }
429 
LoadCmd(xmlNode * rootNode,std::string configFile)430 bool SocPerf::LoadCmd(xmlNode* rootNode, std::string configFile)
431 {
432     xmlNode* child = rootNode->children;
433     for (; child; child = child->next) { // Iterate all cmdID
434         if (xmlStrcmp(child->name, reinterpret_cast<const xmlChar*>("cmd"))) {
435             continue;
436         }
437         char* id = reinterpret_cast<char*>(xmlGetProp(child, reinterpret_cast<const xmlChar*>("id")));
438         char* name = reinterpret_cast<char*>(xmlGetProp(child, reinterpret_cast<const xmlChar*>("name")));
439         if (!CheckCmdTag(id, name, configFile)) {
440             return false;
441         }
442         xmlNode* grandson = child->children;
443         std::shared_ptr<Actions> actions = std::make_shared<Actions>(atoi(id), name);
444         for (; grandson; grandson = grandson->next) { // Iterate all Action
445             std::shared_ptr<Action> action = std::make_shared<Action>();
446             xmlNode* greatGrandson = grandson->children;
447             for (; greatGrandson; greatGrandson = greatGrandson->next) { // Iterate duration and all res
448                 if (!xmlStrcmp(greatGrandson->name, reinterpret_cast<const xmlChar*>("duration"))) {
449                     char* duration = reinterpret_cast<char*>(xmlNodeGetContent(greatGrandson));
450                     if (!duration || !IsNumber(duration)) {
451                         SOC_PERF_LOGE("%{public}s, Invalid cmd duration for %{public}s",
452                             __func__, configFile.c_str());
453                         return false;
454                     }
455                     action->duration = atoi(duration);
456                 } else {
457                     char* resStr = reinterpret_cast<char*>(const_cast<xmlChar*>(greatGrandson->name));
458                     char* resValue = reinterpret_cast<char*>(xmlNodeGetContent(greatGrandson));
459                     if (!resStr || resStrToIdInfo.find(resStr) == resStrToIdInfo.end()
460                         || !resValue || !IsNumber(resValue)) {
461                         SOC_PERF_LOGE("%{public}s, Invalid cmd resource(%{public}s) for %{public}s",
462                             __func__, resStr, configFile.c_str());
463                         return false;
464                     }
465                     action->variable.push_back(resStrToIdInfo[resStr]);
466                     action->variable.push_back(atoll(resValue));
467                 }
468             }
469             actions->actionList.push_back(action);
470         }
471 
472         if (configFile.find(SOCPERF_BOOST_CONFIG_XML) != std::string::npos) {
473             perfActionsInfo.insert(std::pair<int32_t, std::shared_ptr<Actions>>(actions->id, actions));
474         }
475     }
476 
477     if (!CheckActionResIdAndValueValid(configFile)) {
478         return false;
479     }
480 
481     return true;
482 }
483 
CheckResourceTag(char * id,char * name,char * pair,char * mode,std::string configFile)484 bool SocPerf::CheckResourceTag(char* id, char* name, char* pair, char* mode, std::string configFile)
485 {
486     if (!id || !IsNumber(id) || !IsValidResId(atoi(id))) {
487         SOC_PERF_LOGE("%{public}s, Invalid resource id for %{public}s", __func__, configFile.c_str());
488         return false;
489     }
490     if (!name) {
491         SOC_PERF_LOGE("%{public}s, Invalid resource name for %{public}s", __func__, configFile.c_str());
492         return false;
493     }
494     if (pair && (!IsNumber(pair) || !IsValidResId(atoi(pair)))) {
495         SOC_PERF_LOGE("%{public}s, Invalid resource pair for %{public}s", __func__, configFile.c_str());
496         return false;
497     }
498     if (mode && !IsNumber(mode)) {
499         SOC_PERF_LOGE("%{public}s, Invalid resource mode for %{public}s", __func__, configFile.c_str());
500         return false;
501     }
502     return true;
503 }
504 
CheckResourceTag(char * def,char * path,std::string configFile)505 bool SocPerf::CheckResourceTag(char* def, char* path, std::string configFile)
506 {
507     if (!def || !IsNumber(def)) {
508         SOC_PERF_LOGE("%{public}s, Invalid resource default for %{public}s", __func__, configFile.c_str());
509         return false;
510     }
511     if (!path) {
512         SOC_PERF_LOGE("%{public}s, Invalid resource path for %{public}s", __func__, configFile.c_str());
513         return false;
514     }
515     return true;
516 }
517 
LoadResourceAvailable(std::shared_ptr<ResNode> resNode,char * node)518 bool SocPerf::LoadResourceAvailable(std::shared_ptr<ResNode> resNode, char* node)
519 {
520     std::string nodeStr = node;
521     std::vector<std::string> result = Split(nodeStr, " ");
522     for (auto str : result) {
523         if (IsNumber(str)) {
524             resNode->available.insert(stoll(str));
525         } else {
526             return false;
527         }
528     }
529     return true;
530 }
531 
CheckPairResIdValid()532 bool SocPerf::CheckPairResIdValid()
533 {
534     for (auto iter = resNodeInfo.begin(); iter != resNodeInfo.end(); ++iter) {
535         int32_t resId = iter->first;
536         std::shared_ptr<ResNode> resNode = iter->second;
537         int32_t pairResId = resNode->pair;
538         if (resNodeInfo.find(pairResId) == resNodeInfo.end()) {
539             SOC_PERF_LOGE("%{public}s, resId[%{public}d]'s pairResId[%{public}d] is not valid",
540                 __func__, resId, pairResId);
541             return false;
542         }
543     }
544     return true;
545 }
546 
CheckResDefValid()547 bool SocPerf::CheckResDefValid()
548 {
549     for (auto iter = resNodeInfo.begin(); iter != resNodeInfo.end(); ++iter) {
550         int32_t resId = iter->first;
551         std::shared_ptr<ResNode> resNode = iter->second;
552         int64_t def = resNode->def;
553         if (!resNode->available.empty() && resNode->available.find(def) == resNode->available.end()) {
554             SOC_PERF_LOGE("%{public}s, resId[%{public}d]'s def[%{public}lld] is not valid", __func__,
555                 resId, (long long)def);
556             return false;
557         }
558     }
559     return true;
560 }
561 
CheckGovResourceTag(char * id,char * name,std::string configFile)562 bool SocPerf::CheckGovResourceTag(char* id, char* name, std::string configFile)
563 {
564     if (!id || !IsNumber(id) || !IsValidResId(atoi(id))) {
565         SOC_PERF_LOGE("%{public}s, Invalid governor resource id for %{public}s", __func__, configFile.c_str());
566         return false;
567     }
568     if (!name) {
569         SOC_PERF_LOGE("%{public}s, Invalid governor resource name for %{public}s", __func__, configFile.c_str());
570         return false;
571     }
572     return true;
573 }
574 
LoadGovResourceAvailable(std::shared_ptr<GovResNode> govResNode,char * level,char * node)575 bool SocPerf::LoadGovResourceAvailable(std::shared_ptr<GovResNode> govResNode, char* level, char* node)
576 {
577     govResNode->available.insert(atoll(level));
578     std::string nodeStr = node;
579     std::vector<std::string> result = Split(nodeStr, "|");
580     if (result.size() != govResNode->paths.size()) {
581         SOC_PERF_LOGE("%{public}s, Invalid governor resource node matches paths", __func__);
582         return false;
583     }
584     govResNode->levelToStr.insert(std::pair<int32_t, std::vector<std::string>>(atoll(level), result));
585     return true;
586 }
587 
CheckGovResDefValid()588 bool SocPerf::CheckGovResDefValid()
589 {
590     for (auto iter = govResNodeInfo.begin(); iter != govResNodeInfo.end(); ++iter) {
591         int32_t govResId = iter->first;
592         std::shared_ptr<GovResNode> govResNode = iter->second;
593         int32_t def = govResNode->def;
594         if (govResNode->available.find(def) == govResNode->available.end()) {
595             SOC_PERF_LOGE("%{public}s, govResId[%{public}d]'s def[%{public}d] is not valid", __func__, govResId, def);
596             return false;
597         }
598     }
599     return true;
600 }
601 
CheckCmdTag(char * id,char * name,std::string configFile)602 bool SocPerf::CheckCmdTag(char* id, char* name, std::string configFile)
603 {
604     if (!id || !IsNumber(id)) {
605         SOC_PERF_LOGE("%{public}s, Invalid cmd id for %{public}s", __func__, configFile.c_str());
606         return false;
607     }
608     if (!name) {
609         SOC_PERF_LOGE("%{public}s, Invalid cmd name for %{public}s", __func__, configFile.c_str());
610         return false;
611     }
612     return true;
613 }
614 
CheckActionResIdAndValueValid(std::string configFile)615 bool SocPerf::CheckActionResIdAndValueValid(std::string configFile)
616 {
617     std::unordered_map<int32_t, std::shared_ptr<Actions>> actionsInfo;
618     if (configFile.find(SOCPERF_BOOST_CONFIG_XML) != std::string::npos) {
619         actionsInfo = perfActionsInfo;
620     }
621     for (auto actionsIter = actionsInfo.begin(); actionsIter != actionsInfo.end(); ++actionsIter) {
622         int32_t actionId = actionsIter->first;
623         std::shared_ptr<Actions> actions = actionsIter->second;
624         for (auto actionIter = actions->actionList.begin(); actionIter != actions->actionList.end(); ++actionIter) {
625             std::shared_ptr<Action> action = *actionIter;
626             for (int32_t i = 0; i < (int32_t)action->variable.size() - 1; i += RES_ID_AND_VALUE_PAIR) {
627                 int32_t resId = action->variable[i];
628                 int64_t resValue = action->variable[i + 1];
629                 if (resNodeInfo.find(resId) != resNodeInfo.end()) {
630                     if (resNodeInfo[resId]->available.find(resValue) == resNodeInfo[resId]->available.end()) {
631                         SOC_PERF_LOGE("%{public}s, action[%{public}d]'s resValue[%{public}lld] is not valid",
632                             __func__, actionId, (long long)resValue);
633                         return false;
634                     }
635                 } else if (govResNodeInfo.find(resId) != govResNodeInfo.end()) {
636                     if (govResNodeInfo[resId]->available.find(resValue) == govResNodeInfo[resId]->available.end()) {
637                         SOC_PERF_LOGE("%{public}s, action[%{public}d]'s resValue[%{public}lld] is not valid",
638                             __func__, actionId, (long long)resValue);
639                         return false;
640                     }
641                 } else {
642                     SOC_PERF_LOGE("%{public}s, action[%{public}d]'s resId[%{public}d] is not valid",
643                         __func__, actionId, resId);
644                     return false;
645                 }
646             }
647         }
648     }
649     return true;
650 }
651 
PrintCachedInfo()652 void SocPerf::PrintCachedInfo()
653 {
654     if (debugLogEnabled) {
655         SOC_PERF_LOGD("------------------------------------");
656         SOC_PERF_LOGD("resNodeInfo(%{public}d)", (int32_t)resNodeInfo.size());
657         for (auto iter = resNodeInfo.begin(); iter != resNodeInfo.end(); ++iter) {
658             std::shared_ptr<ResNode> resNode = iter->second;
659             resNode->PrintString();
660         }
661         SOC_PERF_LOGD("------------------------------------");
662         SOC_PERF_LOGD("govResNodeInfo(%{public}d)", (int32_t)govResNodeInfo.size());
663         for (auto iter = govResNodeInfo.begin(); iter != govResNodeInfo.end(); ++iter) {
664             std::shared_ptr<GovResNode> govResNode = iter->second;
665             govResNode->PrintString();
666         }
667         SOC_PERF_LOGD("------------------------------------");
668         SOC_PERF_LOGD("perfActionsInfo(%{public}d)", (int32_t)perfActionsInfo.size());
669         for (auto iter = perfActionsInfo.begin(); iter != perfActionsInfo.end(); ++iter) {
670             std::shared_ptr<Actions> actions = iter->second;
671             actions->PrintString();
672         }
673         SOC_PERF_LOGD("------------------------------------");
674     }
675 }
676 } // namespace SOCPERF
677 } // namespace OHOS
678