1 /*
2 * Copyright (c) 2021-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 "sys_event_service_ohos.h"
17
18 #include <codecvt>
19 #include <regex>
20 #include <set>
21
22 #include "accesstoken_kit.h"
23 #include "compliant_event_checker.h"
24 #include "data_publisher.h"
25 #include "event_json_parser.h"
26 #include "event_query_wrapper_builder.h"
27 #include "if_system_ability_manager.h"
28 #include "ipc_skeleton.h"
29 #include "iservice_registry.h"
30 #include "hiview_logger.h"
31 #include "ret_code.h"
32 #include "running_status_log_util.h"
33 #include "string_ex.h"
34 #include "string_util.h"
35 #include "system_ability_definition.h"
36 #include "sys_event_sequence_mgr.h"
37 #include "time_util.h"
38 #include "tokenid_kit.h"
39
40 using namespace std;
41 using namespace OHOS::HiviewDFX::EventStore;
42
43 namespace OHOS {
44 namespace HiviewDFX {
45 DEFINE_LOG_TAG("HiView-SysEventService");
46 namespace {
47 constexpr pid_t HID_ROOT = 0;
48 constexpr pid_t HID_SHELL = 2000;
49 constexpr pid_t HID_OHOS = 1000;
50 const std::vector<int> EVENT_TYPES = {1, 2, 3, 4}; // FAULT = 1, STATISTIC = 2 SECURITY = 3, BEHAVIOR = 4
51 const string READ_DFX_SYSEVENT_PERMISSION = "ohos.permission.READ_DFX_SYSEVENT";
52 const string DFX_DUMP_PERMISSION = "ohos.permission.DUMP";
53 constexpr size_t REGEX_LEN_LIMIT = 32; // max(domainLen, nameLen, tagLen)
54
IsMatchedWithRegex(const string & rule,const string & match)55 bool IsMatchedWithRegex(const string& rule, const string& match)
56 {
57 if (rule.empty()) {
58 return true;
59 }
60 if ((rule.length() > REGEX_LEN_LIMIT) || !StringUtil::IsValidRegex(rule)) {
61 return false;
62 }
63 smatch result;
64 const regex pattern(rule);
65 return regex_search(match, result, pattern);
66 }
67
MatchContent(int type,const string & rule,const string & match)68 bool MatchContent(int type, const string& rule, const string& match)
69 {
70 if (match.empty()) {
71 return false;
72 }
73 switch (type) {
74 case RuleType::WHOLE_WORD:
75 return rule.empty() || match.compare(rule) == 0;
76 case RuleType::PREFIX:
77 return rule.empty() || match.find(rule) == 0;
78 case RuleType::REGULAR:
79 return IsMatchedWithRegex(rule, match);
80 default:
81 HIVIEW_LOGE("invalid rule type %{public}d.", type);
82 return false;
83 }
84 }
85
MatchEventType(int rule,int match)86 bool MatchEventType(int rule, int match)
87 {
88 return rule == INVALID_EVENT_TYPE || rule == match;
89 }
90
IsMatchedRule(const OHOS::HiviewDFX::SysEventRule & rule,const string & domain,const string & eventName,const string & tag,uint32_t eventType)91 bool IsMatchedRule(const OHOS::HiviewDFX::SysEventRule& rule, const string& domain,
92 const string& eventName, const string& tag, uint32_t eventType)
93 {
94 if (rule.tag.empty()) {
95 return MatchContent(rule.ruleType, rule.domain, domain)
96 && MatchContent(rule.ruleType, rule.eventName, eventName)
97 && MatchEventType(rule.eventType, eventType);
98 }
99 return MatchContent(rule.ruleType, rule.tag, tag)
100 && MatchEventType(rule.eventType, eventType);
101 }
102
MatchRules(const std::vector<SysEventRule> & rules,const string & domain,const string & eventName,const string & tag,uint32_t eventType)103 bool MatchRules(const std::vector<SysEventRule>& rules, const string& domain, const string& eventName,
104 const string& tag, uint32_t eventType)
105 {
106 return any_of(rules.begin(), rules.end(), [domain, eventName, tag, eventType] (auto& rule) {
107 if (IsMatchedRule(rule, domain, eventName, tag, eventType)) {
108 HIVIEW_LOGD("rule type is %{public}d, domain is %{public}s, eventName is %{public}s, "
109 "tag is %{public}s, eventType is %{public}u for matched",
110 rule.ruleType, rule.domain.empty() ? "empty" : rule.domain.c_str(),
111 rule.eventName.empty() ? "empty" : rule.eventName.c_str(),
112 rule.tag.empty() ? "empty" : rule.tag.c_str(), eventType);
113 return true;
114 }
115 return false;
116 });
117 }
118
CheckEventSubscriberAddingValidity(const std::vector<std::string> & events)119 int32_t CheckEventSubscriberAddingValidity(const std::vector<std::string>& events)
120 {
121 size_t maxEventNum = 30; // count of total events is limited to 30.
122 if (events.size() > maxEventNum) {
123 OHOS::HiviewDFX::RunningStatusLogUtil::LogTooManyEvents(maxEventNum);
124 return ERR_TOO_MANY_EVENTS;
125 }
126 return IPC_CALL_SUCCEED;
127 }
128
CheckEventQueryingValidity(const std::vector<SysEventQueryRule> & rules,size_t limit)129 int32_t CheckEventQueryingValidity(const std::vector<SysEventQueryRule>& rules, size_t limit)
130 {
131 if (rules.size() > limit) {
132 RunningStatusLogUtil::LogTooManyQueryRules(rules);
133 return ERR_TOO_MANY_QUERY_RULES;
134 }
135 return IPC_CALL_SUCCEED;
136 }
137
IsSystemAppCaller()138 bool IsSystemAppCaller()
139 {
140 uint64_t tokenId = IPCSkeleton::GetCallingFullTokenID();
141 return Security::AccessToken::TokenIdKit::IsSystemAppByFullTokenID(tokenId);
142 }
143
IsNativeCaller()144 bool IsNativeCaller()
145 {
146 auto callerToken = IPCSkeleton::GetCallingTokenID();
147 auto tokenType = Security::AccessToken::AccessTokenKit::GetTokenTypeFlag(callerToken);
148 return (tokenType == Security::AccessToken::ATokenTypeEnum::TOKEN_NATIVE)
149 || (tokenType == Security::AccessToken::ATokenTypeEnum::TOKEN_SHELL);
150 }
151 }
152
153 sptr<SysEventServiceOhos> SysEventServiceOhos::instance_(new SysEventServiceOhos);
154
GetInstance()155 sptr<SysEventServiceOhos> SysEventServiceOhos::GetInstance()
156 {
157 return instance_;
158 }
159
~SysEventServiceOhos()160 SysEventServiceOhos::~SysEventServiceOhos()
161 {
162 instance_ = nullptr;
163 }
164
StartService(SysEventServiceBase * service)165 void SysEventServiceOhos::StartService(SysEventServiceBase *service)
166 {
167 GetSysEventService(service);
168 sptr<ISystemAbilityManager> samgr = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
169 if (samgr == nullptr) {
170 HIVIEW_LOGE("failed to find SystemAbilityManager.");
171 return;
172 }
173 if (instance_ == nullptr) {
174 HIVIEW_LOGE("SysEventServiceOhos service is null.");
175 return;
176 }
177 int ret = samgr->AddSystemAbility(DFX_SYS_EVENT_SERVICE_ABILITY_ID, instance_);
178 if (ret != 0) {
179 HIVIEW_LOGE("failed to add sys event service ability.");
180 }
181 }
182
OnSysEvent(std::shared_ptr<SysEvent> & event)183 void SysEventServiceOhos::OnSysEvent(std::shared_ptr<SysEvent>& event)
184 {
185 {
186 lock_guard<mutex> lock(publisherMutex_);
187 dataPublisher_->OnSysEvent(event);
188 }
189 lock_guard<mutex> lock(listenersMutex_);
190 CompliantEventChecker compliantEventChecker;
191 for (auto listener = registeredListeners_.begin(); listener != registeredListeners_.end(); ++listener) {
192 OHOS::sptr<ISysEventCallback> callback = iface_cast<ISysEventCallback>(listener->first);
193 if (callback == nullptr) {
194 HIVIEW_LOGE("interface is null, no need to match rules.");
195 continue;
196 }
197 if ((listener->second.uid == HID_SHELL) &&
198 !compliantEventChecker.IsCompliantEvent(event->domain_, event->eventName_)) {
199 HIVIEW_LOGD("event [%{public}s|%{public}s] isn't compliant for the process with uid %{public}d",
200 event->domain_.c_str(), event->eventName_.c_str(), listener->second.uid);
201 continue;
202 }
203 bool isMatched = MatchRules(listener->second.rules, event->domain_, event->eventName_,
204 event->GetTag(), event->eventType_);
205 HIVIEW_LOGD("pid %{public}d rules match %{public}s.", listener->second.pid, isMatched ? "success" : "fail");
206 if (isMatched) {
207 callback->Handle(event->domain_, event->eventName_,
208 static_cast<uint32_t>(event->eventType_), event->AsJsonStr());
209 }
210 }
211 }
212
OnRemoteDied(const wptr<IRemoteObject> & remote)213 void SysEventServiceOhos::OnRemoteDied(const wptr<IRemoteObject>& remote)
214 {
215 if (remote == nullptr) {
216 HIVIEW_LOGE("remote is null");
217 return;
218 }
219 auto remoteObject = remote.promote();
220 if (remoteObject == nullptr) {
221 HIVIEW_LOGE("object in remote is null.");
222 return;
223 }
224 lock_guard<mutex> lock(listenersMutex_);
225 auto listener = registeredListeners_.find(remoteObject);
226 if (listener != registeredListeners_.end()) {
227 listener->first->RemoveDeathRecipient(deathRecipient_);
228 HIVIEW_LOGE("pid %{public}d has died and remove listener.", listener->second.pid);
229 registeredListeners_.erase(listener);
230 }
231 }
232
GetSysEventService(SysEventServiceBase * service)233 SysEventServiceBase* SysEventServiceOhos::GetSysEventService(SysEventServiceBase* service)
234 {
235 static SysEventServiceBase* ref = nullptr;
236 if (service != nullptr) {
237 ref = service;
238 }
239 return ref;
240 }
241
AddListener(const std::vector<SysEventRule> & rules,const sptr<ISysEventCallback> & callback)242 ErrCode SysEventServiceOhos::AddListener(const std::vector<SysEventRule>& rules,
243 const sptr<ISysEventCallback>& callback)
244 {
245 if (!HasAccessPermission() || !(IsSystemAppCaller() || IsNativeCaller())) {
246 return ERR_NO_PERMISSION;
247 }
248 size_t watchRuleCntLimit = 20; // count of listener rule for each watcher is limited to 20.
249 if (rules.size() > watchRuleCntLimit) {
250 OHOS::HiviewDFX::RunningStatusLogUtil::LogTooManyWatchRules(rules);
251 return ERR_TOO_MANY_WATCH_RULES;
252 }
253 lock_guard<mutex> lock(listenersMutex_);
254 size_t watcherTotalCntLimit = 30; // count of total watches is limited to 30.
255 if (registeredListeners_.size() >= watcherTotalCntLimit) {
256 OHOS::HiviewDFX::RunningStatusLogUtil::LogTooManyWatchers(watcherTotalCntLimit);
257 return ERR_TOO_MANY_WATCHERS;
258 }
259 auto service = GetSysEventService();
260 if (service == nullptr) {
261 HIVIEW_LOGE("subscribe fail, sys event service is null.");
262 return ERR_REMOTE_SERVICE_IS_NULL;
263 }
264 if (callback == nullptr) {
265 HIVIEW_LOGE("subscribe fail, callback is null.");
266 return ERR_LISTENER_NOT_EXIST;
267 }
268 OHOS::sptr<OHOS::IRemoteObject> callbackObject = callback->AsObject();
269 if (callbackObject == nullptr) {
270 HIVIEW_LOGE("subscribe fail, object in callback is null.");
271 return ERR_LISTENER_STATUS_INVALID;
272 }
273 ListenerInfo listenerInfo {IPCSkeleton::GetCallingPid(), IPCSkeleton::GetCallingUid(), rules};
274 if (registeredListeners_.find(callbackObject) != registeredListeners_.end()) {
275 registeredListeners_[callbackObject] = listenerInfo;
276 HIVIEW_LOGD("uid %{public}d pid %{public}d listener has been added and update rules.",
277 listenerInfo.uid, listenerInfo.pid);
278 return IPC_CALL_SUCCEED;
279 }
280 if (callbackObject->IsProxyObject() && !callbackObject->AddDeathRecipient(deathRecipient_)) {
281 HIVIEW_LOGE("subscribe fail, can not add death recipient.");
282 return ERR_ADD_DEATH_RECIPIENT;
283 }
284 registeredListeners_.insert(make_pair(callbackObject, listenerInfo));
285 HIVIEW_LOGD("uid %{public}d pid %{public}d listener is added successfully, total is %{public}zu.",
286 listenerInfo.uid, listenerInfo.pid, registeredListeners_.size());
287 return IPC_CALL_SUCCEED;
288 }
289
RemoveListener(const OHOS::sptr<ISysEventCallback> & callback)290 ErrCode SysEventServiceOhos::RemoveListener(const OHOS::sptr<ISysEventCallback>& callback)
291 {
292 if (!HasAccessPermission() || !(IsSystemAppCaller() || IsNativeCaller())) {
293 return ERR_NO_PERMISSION;
294 }
295 auto service = GetSysEventService();
296 if (service == nullptr) {
297 HIVIEW_LOGE("sys event service is null.");
298 return ERR_REMOTE_SERVICE_IS_NULL;
299 }
300 if (callback == nullptr) {
301 HIVIEW_LOGE("callback is null.");
302 return ERR_LISTENER_NOT_EXIST;
303 }
304 OHOS::sptr<OHOS::IRemoteObject> callbackObject = callback->AsObject();
305 if (callbackObject == nullptr) {
306 HIVIEW_LOGE("object in callback is null.");
307 return ERR_LISTENER_STATUS_INVALID;
308 }
309 int32_t uid = IPCSkeleton::GetCallingUid();
310 int32_t pid = IPCSkeleton::GetCallingPid();
311 lock_guard<mutex> lock(listenersMutex_);
312 if (registeredListeners_.empty()) {
313 HIVIEW_LOGD("has no any listeners.");
314 return ERR_LISTENERS_EMPTY;
315 }
316 auto registeredListener = registeredListeners_.find(callbackObject);
317 if (registeredListener != registeredListeners_.end()) {
318 if (callbackObject->IsProxyObject() && !callbackObject->RemoveDeathRecipient(deathRecipient_)) {
319 HIVIEW_LOGE("uid %{public}d pid %{public}d listener can not remove death recipient.", uid, pid);
320 return ERR_ADD_DEATH_RECIPIENT;
321 }
322 registeredListeners_.erase(registeredListener);
323 HIVIEW_LOGD("uid %{public}d pid %{public}d has found listener and removes it.", uid, pid);
324 return IPC_CALL_SUCCEED;
325 } else {
326 HIVIEW_LOGD("uid %{public}d pid %{public}d has not found listener.", uid, pid);
327 return ERR_LISTENER_NOT_EXIST;
328 }
329 }
330
BuildEventQuery(std::shared_ptr<EventQueryWrapperBuilder> builder,const std::vector<SysEventQueryRule> & rules)331 bool SysEventServiceOhos::BuildEventQuery(std::shared_ptr<EventQueryWrapperBuilder> builder,
332 const std::vector<SysEventQueryRule>& rules)
333 {
334 if (builder == nullptr) {
335 return false;
336 }
337 auto callingUid = IPCSkeleton::GetCallingUid();
338 if (rules.empty() && (callingUid == HID_SHELL || callingUid == HID_ROOT ||
339 callingUid == HID_OHOS)) {
340 builder->Append("", "", 0, "");
341 return true;
342 }
343 return !any_of(rules.cbegin(), rules.cend(), [this, callingUid, &builder] (auto& rule) {
344 if (rule.domain.empty() && callingUid != HID_SHELL && callingUid != HID_ROOT &&
345 callingUid != HID_OHOS) {
346 return true;
347 }
348 return any_of(rule.eventList.cbegin(), rule.eventList.cend(),
349 [this, callingUid, &builder, &rule] (auto& eventName) {
350 if (eventName.empty() && callingUid != HID_SHELL && callingUid != HID_ROOT &&
351 callingUid != HID_OHOS) {
352 return true;
353 }
354 auto eventType = EventJsonParser::GetInstance()->GetTypeByDomainAndName(rule.domain, eventName);
355 HIVIEW_LOGD("event type configured with domain[%{public}s] and name[%{public}s] "
356 " is %{public}u, and event type in query rule is %{public}u.",
357 rule.domain.c_str(), eventName.c_str(), eventType, rule.eventType);
358 if ((!rule.domain.empty() && !eventName.empty() && eventType == INVALID_EVENT_TYPE) ||
359 (eventType != INVALID_EVENT_TYPE && rule.eventType != INVALID_EVENT_TYPE &&
360 eventType != rule.eventType)) {
361 return false;
362 }
363 eventType = eventType == INVALID_EVENT_TYPE ? rule.eventType : eventType;
364 builder->Append(rule.domain, eventName, eventType, rule.condition);
365 return false;
366 });
367 });
368 }
369
Query(const QueryArgument & queryArgument,const std::vector<SysEventQueryRule> & rules,const OHOS::sptr<IQuerySysEventCallback> & callback)370 ErrCode SysEventServiceOhos::Query(const QueryArgument& queryArgument, const std::vector<SysEventQueryRule>& rules,
371 const OHOS::sptr<IQuerySysEventCallback>& callback)
372 {
373 if (callback == nullptr) {
374 return ERR_LISTENER_NOT_EXIST;
375 }
376 if (!HasAccessPermission() || !(IsSystemAppCaller() || IsNativeCaller())) {
377 callback->OnComplete(ERR_NO_PERMISSION, 0, EventStore::SysEventSequenceManager::GetInstance().GetSequence());
378 return ERR_NO_PERMISSION;
379 }
380 auto checkRet = CheckEventQueryingValidity(rules, 100); // count of query rule limits to 100 in query.
381 if (checkRet != IPC_CALL_SUCCEED) {
382 callback->OnComplete(checkRet, 0, EventStore::SysEventSequenceManager::GetInstance().GetSequence());
383 return checkRet;
384 }
385 auto queryWrapperBuilder = std::make_shared<EventQueryWrapperBuilder>(queryArgument);
386 auto buildRet = BuildEventQuery(queryWrapperBuilder, rules);
387 if (!buildRet || queryWrapperBuilder == nullptr || !queryWrapperBuilder->IsValid()) {
388 HIVIEW_LOGW("invalid query rule, exit sys event querying.");
389 callback->OnComplete(ERR_QUERY_RULE_INVALID, 0,
390 EventStore::SysEventSequenceManager::GetInstance().GetSequence());
391 return ERR_QUERY_RULE_INVALID;
392 }
393 if (queryArgument.maxEvents == 0) {
394 HIVIEW_LOGW("query count is 0, query complete directly.");
395 callback->OnComplete(IPC_CALL_SUCCEED, 0, EventStore::SysEventSequenceManager::GetInstance().GetSequence());
396 return IPC_CALL_SUCCEED;
397 }
398 auto queryWrapper = queryWrapperBuilder->Build();
399 if (queryWrapper == nullptr) {
400 HIVIEW_LOGW("query wrapper build failed.");
401 callback->OnComplete(ERR_QUERY_RULE_INVALID, 0,
402 EventStore::SysEventSequenceManager::GetInstance().GetSequence());
403 return ERR_QUERY_RULE_INVALID;
404 }
405 queryWrapper->SetMaxSequence(EventStore::SysEventSequenceManager::GetInstance().GetSequence());
406 auto queryRetCode = IPC_CALL_SUCCEED;
407 queryWrapper->Query(callback, queryRetCode);
408 return queryRetCode;
409 }
410
HasAccessPermission() const411 bool SysEventServiceOhos::HasAccessPermission() const
412 {
413 using namespace Security::AccessToken;
414 auto tokenId = IPCSkeleton::GetCallingTokenID();
415 if ((AccessTokenKit::VerifyAccessToken(tokenId, READ_DFX_SYSEVENT_PERMISSION) == RET_SUCCESS) ||
416 (AccessTokenKit::VerifyAccessToken(tokenId, DFX_DUMP_PERMISSION) == RET_SUCCESS)) {
417 return true;
418 }
419 return false;
420 }
421
Dump(int32_t fd,const std::vector<std::u16string> & args)422 int SysEventServiceOhos::Dump(int32_t fd, const std::vector<std::u16string> &args)
423 {
424 if (fd < 0) {
425 HIVIEW_LOGE("invalid fd.");
426 return -1;
427 }
428 dprintf(fd, "%s\n", "Hiview SysEventService");
429 return 0;
430 }
431
OnRemoteDied(const wptr<IRemoteObject> & remote)432 void CallbackDeathRecipient::OnRemoteDied(const wptr<IRemoteObject>& remote)
433 {
434 auto service = SysEventServiceOhos::GetInstance();
435 if (service == nullptr) {
436 HIVIEW_LOGE("SysEventServiceOhos service is null.");
437 return;
438 }
439 service->OnRemoteDied(remote);
440 }
441
AddSubscriber(const std::vector<SysEventQueryRule> & rules,int64_t & funcResult)442 ErrCode SysEventServiceOhos::AddSubscriber(const std::vector<SysEventQueryRule>& rules, int64_t& funcResult)
443 {
444 if (!HasAccessPermission() || !IsSystemAppCaller()) {
445 return ERR_NO_PERMISSION;
446 }
447 std::vector<std::string> events;
448 MergeEventList(rules, events);
449 auto checkRet = CheckEventSubscriberAddingValidity(events);
450 if (checkRet != IPC_CALL_SUCCEED) {
451 return checkRet;
452 }
453 int32_t uid = IPCSkeleton::GetCallingUid();
454 lock_guard<mutex> lock(publisherMutex_);
455 if (auto ret = dataPublisher_->AddSubscriber(uid, events); ret != IPC_CALL_SUCCEED) {
456 return ret;
457 }
458 funcResult = static_cast<int64_t>(TimeUtil::GetMilliseconds());
459 return IPC_CALL_SUCCEED;
460 }
461
MergeEventList(const std::vector<SysEventQueryRule> & rules,std::vector<std::string> & events) const462 void SysEventServiceOhos::MergeEventList(const std::vector<SysEventQueryRule>& rules,
463 std::vector<std::string>& events) const
464 {
465 for_each(rules.cbegin(), rules.cend(), [&](const SysEventQueryRule &rule) {
466 auto eventList = rule.eventList;
467 for_each(eventList.cbegin(), eventList.cend(), [&](const std::string &event) {
468 events.push_back(event);
469 });
470 });
471 }
472
RemoveSubscriber()473 ErrCode SysEventServiceOhos::RemoveSubscriber()
474 {
475 if (!HasAccessPermission() || !IsSystemAppCaller()) {
476 return ERR_NO_PERMISSION;
477 }
478 int32_t uid = IPCSkeleton::GetCallingUid();
479 lock_guard<mutex> lock(publisherMutex_);
480 auto ret = dataPublisher_->RemoveSubscriber(uid);
481 if (ret != IPC_CALL_SUCCEED) {
482 return ret;
483 }
484 return IPC_CALL_SUCCEED;
485 }
486
Export(const QueryArgument & queryArgument,const std::vector<SysEventQueryRule> & rules,int64_t & funcResult)487 ErrCode SysEventServiceOhos::Export(const QueryArgument &queryArgument,
488 const std::vector<SysEventQueryRule>& rules, int64_t& funcResult)
489 {
490 if (!HasAccessPermission() || !IsSystemAppCaller()) {
491 return ERR_NO_PERMISSION;
492 }
493 auto checkRet = CheckEventQueryingValidity(rules, 10); // count of query rule limits to 10 in export.
494 if (checkRet != IPC_CALL_SUCCEED) {
495 return checkRet;
496 }
497 int32_t uid = IPCSkeleton::GetCallingUid();
498 lock_guard<mutex> lock(publisherMutex_);
499 auto lastTimeStamp = dataPublisher_->GetTimeStampByUid(uid);
500 int64_t currentTime = static_cast<int64_t>(TimeUtil::GetMilliseconds());
501 if (std::abs(currentTime - lastTimeStamp) < TimeUtil::SECONDS_PER_HOUR * TimeUtil::SEC_TO_MILLISEC) {
502 HIVIEW_LOGD("forbid export, time frequency limit < 1 h.");
503 return ERR_EXPORT_FREQUENCY_OVER_LIMIT;
504 }
505
506 auto queryWrapperBuilder = std::make_shared<EventQueryWrapperBuilder>(queryArgument);
507 auto buildRet = BuildEventQuery(queryWrapperBuilder, rules);
508 if (!buildRet || queryWrapperBuilder == nullptr || !queryWrapperBuilder->IsValid()) {
509 HIVIEW_LOGW("invalid query rule, exit sys event exporting.");
510 return ERR_QUERY_RULE_INVALID;
511 }
512 if (queryArgument.maxEvents == 0) {
513 HIVIEW_LOGW("export count is 0, export complete directly.");
514 funcResult = currentTime;
515 return IPC_CALL_SUCCEED;
516 }
517 auto queryWrapper = queryWrapperBuilder->Build();
518 if (queryWrapper == nullptr) {
519 HIVIEW_LOGW("export wrapper build failed.");
520 return ERR_QUERY_RULE_INVALID;
521 }
522 queryWrapper->SetMaxSequence(EventStore::SysEventSequenceManager::GetInstance().GetSequence());
523 dataPublisher_->AddExportTask(queryWrapper, currentTime, uid);
524 funcResult = currentTime;
525 return IPC_CALL_SUCCEED;
526 }
527
SetWorkLoop(std::shared_ptr<EventLoop> looper)528 void SysEventServiceOhos::SetWorkLoop(std::shared_ptr<EventLoop> looper)
529 {
530 if (looper == nullptr) {
531 HIVIEW_LOGW("SetWorkLoop failed, looper is null.");
532 return;
533 }
534 dataPublisher_->SetWorkLoop(looper);
535 }
536 } // namespace HiviewDFX
537 } // namespace OHOS
538