• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-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 #ifndef RELIABILITY_WATCHDOG_INNER_H
17 #define RELIABILITY_WATCHDOG_INNER_H
18 
19 #include <atomic>
20 #include <condition_variable>
21 #include <csignal>
22 #include <memory>
23 #include <mutex>
24 #include <queue>
25 #include <set>
26 #include <string>
27 #include <thread>
28 
29 #include "watchdog_task.h"
30 #include "c/ffrt_dump.h"
31 #include "singleton.h"
32 #include "client/trace_collector_client.h"
33 #include "xcollie_define.h"
34 #include "watchdog_inner_data.h"
35 
36 namespace OHOS {
37 namespace HiviewDFX {
38 
39 class WatchdogInner : public Singleton<WatchdogInner> {
40     DECLARE_SINGLETON(WatchdogInner);
41 public:
42     std::map<int64_t, int> taskIdCnt;
43     int AddThread(const std::string &name, std::shared_ptr<AppExecFwk::EventHandler> handler, uint64_t interval);
44     int AddThread(const std::string &name, std::shared_ptr<AppExecFwk::EventHandler> handler,
45         TimeOutCallback timeOutCallback, uint64_t interval);
46     void RunOneShotTask(const std::string& name, Task&& task, uint64_t delay);
47     void RunPeriodicalTask(const std::string& name, Task&& task, uint64_t interval, uint64_t delay);
48     int64_t RunXCollieTask(const std::string& name, uint64_t timeout, XCollieCallback func, void *arg,
49         unsigned int flag);
50     void RemoveXCollieTask(int64_t id);
51     bool AddIpcFull(uint64_t interval, unsigned int flag, IpcFullCallback func, void *arg);
52     int64_t SetTimerCountTask(const std::string &name, uint64_t timeLimit, int countLimit);
53     void TriggerTimerCountTask(const std::string &name, bool bTrigger, const std::string &message);
54     void StopWatchdog();
55     bool IsCallbackLimit(unsigned int flag);
56     bool IpcCheck(uint64_t interval = IPC_FULL_INTERVAL, unsigned int flag = XCOLLIE_FLAG_DEFAULT,
57         IpcFullCallback func = nullptr, void *arg = nullptr, bool defaultType = true);
58     void InitFfrtWatchdog();
59     static bool WriteStringToFile(int32_t pid, const char *str);
60     static void FfrtCallback(uint64_t taskId, const char *taskInfo, uint32_t delayedTaskCount);
61     static void SendFfrtEvent(const std::string &msg, const std::string &eventName, const char *taskInfo,
62         const std::string& faultTimeStr, const bool isDumpStack = true);
63     static void LeftTimeExitProcess(const std::string &description);
64     static void KillPeerBinderProcess(const std::string &description);
65     bool StartScrollProfile(const TimePoint& endTime, int64_t durationTime, int sampleInterval);
66     void StartProfileMainThread(const TimePoint& endTime, int64_t durationTime, int sampleInterval);
67     bool CollectStack(std::string& stack, std::string& heaviestStack, int treeFormat = ENABLE_TREE_FORMAT);
68     bool Deinit();
69     void SetBundleInfo(const std::string& bundleName, const std::string& bundleVersion);
70     void SetForeground(const bool& isForeground);
71     bool GetForeground();
72     void RemoveInnerTask(const std::string& name);
73     void InitMainLooperWatcher(WatchdogInnerBeginFunc* beginFunc, WatchdogInnerEndFunc* endFunc);
74     void SetAppDebug(bool isAppDebug);
75     bool GetAppDebug();
76     int SetEventConfig(std::map<std::string, std::string> paramsMap);
77     bool SampleStackDetect(const TimePoint& endTime, int& reportTimes, int updateTimes, int ignoreTime,
78         bool isScroll = false);
79     void CollectTraceDetect(const TimePoint& endTime, int64_t durationTime);
80     void SetSpecifiedProcessName(const std::string& name);
81     std::string GetSpecifiedProcessName();
82     void SetScrollState(bool isScroll);
83     void StartSample(int duration, int interval, std::string& outFile);
84     bool CheckSample(const TimePoint& endTime, int64_t durationTime);
85 
86 public:
87     std::string currentScene_;
88     TimePoint bussinessBeginTime_;
89     TimeContent timeContent_ {0};
90     StackContent stackContent_;
91     TraceContent traceContent_;
92     std::map<std::string, int> jankParamsMap = {
93         {KEY_SAMPLE_INTERVAL, SAMPLE_DEFULE_INTERVAL}, {KEY_IGNORE_STARTUP_TIME, DEFAULT_IGNORE_STARTUP_TIME},
94         {KEY_SAMPLE_COUNT, SAMPLE_DEFULE_COUNT}, {KEY_SAMPLE_REPORT_TIMES, SAMPLE_DEFULE_REPORT_TIMES},
95         {KEY_LOG_TYPE, 0}, {KEY_SET_TIMES_FLAG, SET_TIMES_FLAG}, {KEY_CHECKER_INTERVAL, 0}
96     };
97     bool isScroll_ {false};
98 
99 private:
100     bool Start();
101     bool Stop();
102     bool SendMsgToHungtask(const std::string& msg);
103     bool KickWatchdog();
104     bool IsTaskExistLocked(const std::string& name);
105     bool IsExceedMaxTaskLocked();
106     int64_t InsertWatchdogTaskLocked(const std::string& name, WatchdogTask&& task);
107     bool IsInSleep(const WatchdogTask& queuedTaskCheck);
108     void CheckKickWatchdog(uint64_t now, const WatchdogTask& queuedTask);
109     bool CheckCurrentTaskLocked(const WatchdogTask& queuedTaskCheck);
110     uint64_t FetchNextTask(uint64_t now, WatchdogTask& task);
111     void ReInsertTaskIfNeed(WatchdogTask& task);
112     void CreateWatchdogThreadIfNeed();
113     bool ReportMainThreadEvent(int64_t tid, std::string eventName, bool isScroll = false, bool appStart = false);
114     bool CheckEventTimer(int64_t currentTime, int64_t reportBegin, int64_t reportEnd, int interval);
115     void DumpTraceProfile(int32_t interval);
116     int32_t StartTraceProfile();
117     void UpdateTime(int64_t& reportBegin, int64_t& reportEnd, TimePoint& lastEndTime, const TimePoint& endTime);
118     bool CheckThreadSampler();
119     bool InitThreadSamplerFuncs();
120     void ResetThreadSamplerFuncs();
121     static void GetFfrtTaskTid(int32_t& tid, const std::string& msg);
122     void UpdateJankParam(int sampleInterval, int ignoreStartUpTime, int sampleCount, int logType, int reportTimes);
123     int ConvertStrToNum(std::map<std::string, std::string> paramsMap, const std::string& key);
124     bool CheckSampleParam(std::map<std::string, std::string> paramsMap);
125     void SaveFreezeStackToFile(const std::string& outFile, int32_t pid);
126     bool AppStartSample(bool isScroll, AppStartContent& startContent);
127     void ClearParam(bool& isFinished);
128     void UpdateAppStartContent(const std::map<std::string, int64_t>& paramsMap, AppStartContent& startContent);
129     void ParseAppStartParams(const std::string& line, const std::string& eventName);
130     void ReadAppStartConfig(const std::string& filePath);
131     bool EnableAppStartSample(AppStartContent& startContent, int64_t durationTime, bool isScroll);
132 
133     static void ThreadSamplerSigHandler(int sig, siginfo_t* si, void* context);
134     bool InstallThreadSamplerSignal();
135     void UninstallThreadSamplerSignal();
136 
137     static SigActionType threadSamplerSigHandler_;
138     std::priority_queue<WatchdogTask> checkerQueue_; // protected by lock_
139     std::unique_ptr<std::thread> threadLoop_;
140     std::mutex lock_;
141     static std::mutex lockFfrt_;
142     std::condition_variable condition_;
143     std::atomic_bool isNeedStop_ = false;
144     std::once_flag flag_;
145     std::set<std::string> taskNameSet_;
146     std::set<int64_t> buissnessThreadInfo_;
147     std::shared_ptr<AppExecFwk::EventRunner> mainRunner_;
148     int cntCallback_;
149     time_t timeCallback_;
150     bool isHmos = false;
151     void* threadSamplerFuncHandler_  {nullptr};
152     ThreadSamplerInitFunc threadSamplerInitFunc_ {nullptr};
153     ThreadSamplerSampleFunc threadSamplerSampleFunc_ {nullptr};
154     ThreadSamplerCollectFunc threadSamplerCollectFunc_ {nullptr};
155     ThreadSamplerDeinitFunc threadSamplerDeinitFunc_ {nullptr};
156     uint64_t watchdogStartTime_ {0};
157     static std::mutex threadSamplerSignalMutex_;
158 
159     bool isMainThreadStackEnabled_ {false};
160     bool isMainThreadTraceEnabled_ {false};
161     std::string bundleName_;
162     std::string bundleVersion_;
163     bool isForeground_ {false};
164     bool isAppDebug_ {false};
165     std::shared_ptr<UCollectClient::TraceCollector> traceCollector_;
166     UCollectClient::AppCaller appCaller_ {
167         .actionId = 0,
168         .foreground = 0,
169         .uid = 0,
170         .pid = 0,
171         .happenTime = 0,
172         .beginTime = 0,
173         .endTime = 0,
174         .isBusinessJank = false,
175     };
176     std::string specifiedProcessName_;
177     uint64_t nextWeakUpTime_ {UINT64_MAX};
178     AppStartContent startSlowContent_;
179     AppStartContent scrollSlowContent_;
180 };
181 } // end of namespace HiviewDFX
182 } // end of namespace OHOS
183 #endif
184