• 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 "intellisense_server.h"
17 #include <list>
18 #include <map>
19 #include <new>
20 #include <set>
21 #include <string>
22 #include <vector>
23 #include <hitrace_meter.h>
24 #include "qos_common.h"
25 #include "para_config.h"
26 #include "rtg_interface.h"
27 #include "rme_log_domain.h"
28 
29 namespace OHOS {
30 namespace RME {
31 namespace {
32     static std::string configFilePath = "/system/etc/frame_aware_sched/hwrme.xml"; // need To check the exact file path.
33     constexpr int WEB_BASE_UID = 1000001;
34     constexpr int WEB_END_UID = 1099999;
35 }
36 using namespace std;
37 using namespace QosCommon;
38 
39 DEFINE_RMELOG_INTELLISENSE("ueaServer-IntelliSenseServer");
40 IMPLEMENT_SINGLE_INSTANCE(IntelliSenseServer);
41 
Init()42 void IntelliSenseServer::Init()
43 {
44     if (!ReadXml()) {
45         RME_LOGI("[Init]: readXml failed!");
46         return;
47     }
48     m_switch = std::stoi(m_generalPara["enable"]);
49     if (!m_switch) {
50         RME_LOGI("[Init]:xml switch close!");
51         return;
52     }
53     int ret = EnableRtg(true);
54     if (ret < 0) {
55         RME_LOGE("[Init]: enable rtg failed!");
56         return;
57     }
58     m_unsupportApp = {
59         "com.ohos.launcher",
60         "com.ohos.systemui",
61         "com.ohos.screenlock",
62         "com.ohos.wallpaper"
63     };
64     RME_LOGI("[Init]:Init rtg and readXml finish!");
65 }
66 
ReadXml()67 bool IntelliSenseServer::ReadXml()
68 {
69     if (!m_needReadXml) {
70         return false;
71     }
72     m_needReadXml = false;
73     if (ParaConfig::IsXmlPrepared(configFilePath)) {
74         m_generalPara = ParaConfig::GetGeneralConfig();
75         m_subEventPara = ParaConfig::GetSubEventConfig();
76         m_fpsList = ParaConfig::GetFpsList();
77         m_renderTypeList = ParaConfig::GetRenderTypeList();
78         if (!m_generalPara.empty() && !m_subEventPara.empty() && !m_fpsList.empty() && !m_renderTypeList.empty()) {
79             m_readXmlSuc = true;
80             RME_LOGI("[ReadXml]: read slide scene xml success!");
81             return true;
82         }
83     }
84     RME_LOGE("[ReadXml]: read slide scene xml not success!");
85     return false;
86 }
87 
NewForeground(int pid,int uid)88 void IntelliSenseServer::NewForeground(int pid, int uid)
89 {
90     HITRACE_METER(HITRACE_TAG_ACE);
91     int newCreatedRtg = 0;
92     for (auto iter = m_historyApp.begin(); iter != m_historyApp.end(); iter++) {
93         if (iter->GetAppUid() == uid) {
94             RME_LOGI("[ReportMessage]pid %{public}d change to foreground.", pid);
95             if (iter->GetAppState() != AppState::APP_FOREGROUND) {
96                 iter->SetUiTid(pid);
97                 newCreatedRtg = TryCreateRtgForApp(&*iter);
98             }
99             if (newCreatedRtg) {
100                 iter->SetAppState(AppState::APP_FOREGROUND);
101             } else {
102                 iter->SetAppState(AppState::APP_FOREGROUND_WITHOUT_RTG);
103             }
104             break;
105         }
106     }
107 }
108 
TryCreateRtgForApp(AppInfo * app)109 int IntelliSenseServer::TryCreateRtgForApp(AppInfo *app)
110 {
111     if (!app) {
112         RME_LOGE("[TryCreateRtg]: null app!");
113         return 0;
114     }
115     int grpId = CreateNewRtgGrp(RT_PRIO, RT_NUM);
116     if (grpId <= 0) {
117         RME_LOGE("[TryCreateRtg]: createNewRtgGroup failed! grpId:%{public}d", grpId);
118         app->SetRtgrp(0);
119         return grpId;
120     }
121     app->SetRtgrp(grpId);
122     int uiTid = app->GetUiTid();
123     int renderTid = app->GetRenderTid();
124     if (uiTid > 0) {
125         AddThreadToRtg(uiTid, grpId, 0); // add ui thread
126     }
127     if (renderTid > 0) {
128         AddThreadToRtg(renderTid, grpId, 0); // add render thread
129     }
130     return grpId;
131 }
132 
NewBackground(int pid)133 void IntelliSenseServer::NewBackground(int pid)
134 {
135     HITRACE_METER(HITRACE_TAG_ACE);
136     RME_LOGI("[ReportMessage]pid %{public}d change to background.", pid);
137     for (auto iter = m_historyApp.begin(); iter != m_historyApp.end(); iter++) {
138         if (iter->GetAppPid() != pid) {
139             continue;
140         }
141         iter->SetAppState(AppState::APP_BACKGROUND);
142         int grpId = iter->GetRtgrp();
143         if (grpId > 0) {
144             EndScene(grpId);
145             DestroyRtgGrp(grpId);
146         }
147     }
148 }
149 
NewAppRecord(int pid,int uid)150 void IntelliSenseServer::NewAppRecord(int pid, int uid)
151 {
152     for (auto iter = m_historyApp.begin(); iter != m_historyApp.end(); iter++) {
153         if (iter->GetAppUid() == uid) {
154             RME_LOGI("[NewAppRecord]pid %{public}d already exist.", pid);
155             return;
156         }
157     }
158     AppInfo tempRecord(pid, uid);
159     tempRecord.SetAppState(AppState::APP_FOREGROUND_WITHOUT_RTG);
160     m_historyApp.push_back(tempRecord);
161 }
162 
NewDiedProcess(int pid)163 void IntelliSenseServer::NewDiedProcess(int pid)
164 {
165     HITRACE_METER(HITRACE_TAG_ACE);
166     RME_LOGI("[ReportMessage]pid %{public}d died.", pid);
167     for (auto iter = m_historyApp.begin(); iter != m_historyApp.end();) {
168         if (iter->GetAppPid() == pid) {
169             int grpId = iter->GetRtgrp();
170             if (grpId > 0) {
171                 EndScene(grpId);
172                 DestroyRtgGrp(grpId);
173             }
174             iter = m_historyApp.erase(iter);
175         } else {
176             iter++;
177         }
178     }
179 }
180 
GetRecordOfPid(int pid)181 std::list<AppInfo>::iterator IntelliSenseServer::GetRecordOfPid(int pid)
182 {
183     for (auto iter = m_historyApp.begin(); iter != m_historyApp.end(); iter++) {
184         if (iter->GetAppPid() == pid) {
185             return iter;
186         }
187     }
188     return m_historyApp.end();
189 }
190 
ReportRenderThread(const int pid,const int uid,int renderTid)191 void IntelliSenseServer::ReportRenderThread(const int pid, const int uid, int renderTid)
192 {
193     if (uid >= WEB_BASE_UID && uid <= WEB_END_UID) {
194         return;
195     }
196     if (!m_switch) {
197         return;
198     }
199     HITRACE_METER(HITRACE_TAG_ACE);
200     auto record = GetRecordOfPid(pid);
201     if (record == m_historyApp.end()) {
202         RME_LOGE("Didn't find render in history app %{public}d with render %{public}d", pid, renderTid);
203         return;
204     }
205     record->SetRenderTid(renderTid);
206     int grpId = record->GetRtgrp();
207     if (grpId >= 0 && record->GetAppState() == AppState::APP_FOREGROUND) {
208         int ret = AddThreadToRtg(renderTid, grpId, 0); // add render thread
209         RME_LOGE("web test ReportRenderThread uid is %{public}d", uid);
210         if (ret != 0) {
211             RME_LOGE("[OnFore]:add render thread fail! pid:%{public}d,rtg:%{public}d!ret:%{publid}d",
212                 renderTid, grpId, ret);
213         }
214     }
215 }
216 
ReportWindowFocus(const int pid,const int uid,int isFocus)217 void IntelliSenseServer::ReportWindowFocus(const int pid, const int uid, int isFocus)
218 {
219     if (!m_switch) {
220         return;
221     }
222     HITRACE_METER(HITRACE_TAG_ACE);
223     switch (isFocus) {
224         case static_cast<int>(WindowState::FOCUS_YES): // isFocus: 0
225             RME_LOGI("[ReportWindowFocus]:%{public}d get focus", pid);
226             break;
227         case static_cast<int>(WindowState::FOCUS_NO): // isFocus: 1
228             RME_LOGI("[ReportWindowFocus]:%{public}d lost focus", pid);
229             break;
230         default:
231             RME_LOGI("[ReportWindowFocus]:unknown msg!");
232             break;
233     }
234 }
235 
CheckCgroupState(CgroupPolicy cgroup)236 inline CgroupPolicy IntelliSenseServer::CheckCgroupState(CgroupPolicy cgroup)
237 {
238     return ((cgroup == CgroupPolicy::SP_FOREGROUND) || (cgroup == CgroupPolicy::SP_TOP_APP)) ?
239         CgroupPolicy::SP_FOREGROUND : CgroupPolicy::SP_BACKGROUND;
240 }
241 
ReportCgroupChange(const int pid,const int uid,const int oldGroup,const int newGroup)242 void IntelliSenseServer::ReportCgroupChange(const int pid, const int uid, const int oldGroup, const int newGroup)
243 {
244     if (uid >= WEB_BASE_UID && uid <= WEB_END_UID) {
245         return;
246     }
247     if (!m_switch) {
248         return;
249     }
250     HITRACE_METER(HITRACE_TAG_ACE);
251     CgroupPolicy oldState = CheckCgroupState(static_cast<CgroupPolicy>(oldGroup));
252     CgroupPolicy newState = CheckCgroupState(static_cast<CgroupPolicy>(newGroup));
253     if (oldState == newState) {
254         return;
255     }
256     if (newState == CgroupPolicy::SP_BACKGROUND) {
257         RME_LOGI("CgroupChange NewBackground");
258         NewBackground(pid);
259         AuthBackground(uid);
260     } else if (newState == CgroupPolicy::SP_FOREGROUND) {
261         RME_LOGI("web test CgroupChange NewForeground uid is %{public}d", uid);
262         NewForeground(pid, uid);
263         AuthForeground(uid);
264     }
265 }
266 
ReportAppInfo(const int pid,const int uid,const std::string bundleName,ThreadState state)267 void IntelliSenseServer::ReportAppInfo(const int pid, const int uid, const std::string bundleName, ThreadState state)
268 {
269     if (!m_switch) {
270         return;
271     }
272     if (state == ThreadState::CREATE) {
273         AuthForeground(uid);
274     }
275     RME_LOGI("Get app info:%{public}d %{public}d %{public}s %{public}d",
276         pid, uid, bundleName.c_str(), static_cast<int>(state));
277 }
278 
ReportProcessInfo(const int pid,const int uid,const std::string bundleName,ThreadState state)279 void IntelliSenseServer::ReportProcessInfo(const int pid,
280     const int uid, const std::string bundleName, ThreadState state)
281 {
282     if (uid >= WEB_BASE_UID && uid <= WEB_END_UID) {
283         return;
284     }
285     if (!m_switch) {
286         return;
287     }
288     HITRACE_METER(HITRACE_TAG_ACE);
289     if (m_unsupportApp.find(bundleName) != m_unsupportApp.end()) {
290         return;
291     }
292     switch (state) {
293         case ThreadState::DIED:
294             RME_LOGI("ProcessInfo NewDiedProcess");
295             AuthAppKilled(uid);
296             NewDiedProcess(pid);
297             break;
298         case ThreadState::CREATE:
299             RME_LOGI("ProcessInfo NewAppRecord");
300             NewAppRecord(pid, uid);
301             break;
302         default:
303             RME_LOGI("unknown state : %{public}d", static_cast<int>(state));
304             break;
305     }
306     return;
307 }
308 
SetPara(const int32_t currentFps,const int32_t currentRenderType)309 void IntelliSenseServer::SetPara(const int32_t currentFps, const int32_t currentRenderType)
310 {
311     if (!m_switch) {
312         return;
313     }
314     RME_LOGI("[SetPara]:ioctl SetPara!\n");
315     std::string key = std::to_string(currentRenderType) + " " + std::to_string(currentFps);
316     map<std::string, int> tempMap = m_subEventPara[key];
317     RME_LOGI("[SetPara]:subEventPara map size: %{public}zu", tempMap.size());
318 }
319 
AuthAppKilled(int uid)320 void IntelliSenseServer::AuthAppKilled(int uid)
321 {
322     int ret = AuthDelete(uid);
323     if (ret == 0) {
324         RME_LOGI("auth_delete %{public}d success", uid);
325     } else {
326         RME_LOGE("auth_delete %{public}d failed", uid);
327     }
328 }
329 
AuthForeground(int uid)330 void IntelliSenseServer::AuthForeground(int uid)
331 {
332     unsigned int flag = AF_RTG_ALL;
333     int status = AUTH_STATUS_FOREGROUND;
334     int ret = AuthEnable(uid, flag, status);
335     if (ret == 0) {
336         RME_LOGI("auth_enable %{public}d success", uid);
337     } else {
338         RME_LOGE("auth_enable %{public}d failed", uid);
339     }
340 }
341 
AuthBackground(int uid)342 void IntelliSenseServer::AuthBackground(int uid)
343 {
344     int ret = AuthPause(uid);
345     if (ret == 0) {
346         RME_LOGI("auth_pause %{public}d success", uid);
347     } else {
348         RME_LOGE("auth_pause %{public}d failed", uid);
349     }
350 }
351 
352 } // namespace RME
353 } // namesapce OHOS
354