• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2023 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 #include "privacy_sec_comp_enhance_agent.h"
16 
17 #include "access_token.h"
18 #include "accesstoken_kit.h"
19 #include "accesstoken_log.h"
20 #include "app_manager_access_client.h"
21 #include "ipc_skeleton.h"
22 #include "privacy_error.h"
23 
24 namespace OHOS {
25 namespace Security {
26 namespace AccessToken {
27 namespace {
28 static constexpr OHOS::HiviewDFX::HiLogLabel LABEL = {
29     LOG_CORE, SECURITY_DOMAIN_PRIVACY, "PrivacySecCompEnhanceAgent"
30 };
31 }
OnProcessDied(const ProcessData & processData)32 void PrivacyAppUsingSecCompStateObserver::OnProcessDied(const ProcessData &processData)
33 {
34     ACCESSTOKEN_LOG_INFO(LABEL, "OnProcessDied die pid %{public}d", processData.pid);
35 
36     int pid = processData.pid;
37     PrivacySecCompEnhanceAgent::GetInstance().RemoveSecCompEnhance(pid);
38 }
39 
NotifyAppManagerDeath()40 void PrivacySecCompAppManagerDeathCallback::NotifyAppManagerDeath()
41 {
42     ACCESSTOKEN_LOG_INFO(LABEL, "PrivacySecComp AppManagerDeath called");
43 
44     PrivacySecCompEnhanceAgent::GetInstance().OnAppMgrRemoteDiedHandle();
45 }
46 
GetInstance()47 PrivacySecCompEnhanceAgent& PrivacySecCompEnhanceAgent::GetInstance()
48 {
49     static PrivacySecCompEnhanceAgent instance;
50     return instance;
51 }
52 
InitAppObserver()53 void PrivacySecCompEnhanceAgent::InitAppObserver()
54 {
55     if (observer_ != nullptr) {
56         return;
57     }
58     observer_ = new (std::nothrow) PrivacyAppUsingSecCompStateObserver();
59     if (observer_ == nullptr) {
60         ACCESSTOKEN_LOG_ERROR(LABEL, "new observer failed.");
61         return;
62     }
63     if (AppManagerAccessClient::GetInstance().RegisterApplicationStateObserver(observer_) != 0) {
64         ACCESSTOKEN_LOG_ERROR(LABEL, "register observer failed.");
65         observer_ = nullptr;
66         return;
67     }
68     if (appManagerDeathCallback_ == nullptr) {
69         appManagerDeathCallback_ = std::make_shared<PrivacySecCompAppManagerDeathCallback>();
70         AppManagerAccessClient::GetInstance().RegisterDeathCallbak(appManagerDeathCallback_);
71     }
72 }
73 
PrivacySecCompEnhanceAgent()74 PrivacySecCompEnhanceAgent::PrivacySecCompEnhanceAgent()
75 {
76     InitAppObserver();
77 }
78 
~PrivacySecCompEnhanceAgent()79 PrivacySecCompEnhanceAgent::~PrivacySecCompEnhanceAgent()
80 {
81     if (observer_ != nullptr) {
82         AppManagerAccessClient::GetInstance().UnregisterApplicationStateObserver(observer_);
83         observer_ = nullptr;
84     }
85 }
86 
OnAppMgrRemoteDiedHandle()87 void PrivacySecCompEnhanceAgent::OnAppMgrRemoteDiedHandle()
88 {
89     ACCESSTOKEN_LOG_INFO(LABEL, "OnAppMgrRemoteDiedHandle.");
90     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
91     secCompEnhanceData_.clear();
92     observer_ = nullptr;
93 }
94 
RemoveSecCompEnhance(int pid)95 void PrivacySecCompEnhanceAgent::RemoveSecCompEnhance(int pid)
96 {
97     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
98     for (auto iter = secCompEnhanceData_.begin(); iter != secCompEnhanceData_.end(); ++iter) {
99         if (iter->pid == pid) {
100             secCompEnhanceData_.erase(iter);
101             ACCESSTOKEN_LOG_INFO(LABEL, "remove pid %{public}d data.", pid);
102             return;
103         }
104     }
105     ACCESSTOKEN_LOG_ERROR(LABEL, "not found pid %{public}d data.", pid);
106     return;
107 }
108 
RegisterSecCompEnhance(const SecCompEnhanceData & enhanceData)109 int32_t PrivacySecCompEnhanceAgent::RegisterSecCompEnhance(const SecCompEnhanceData& enhanceData)
110 {
111     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
112     InitAppObserver();
113     int pid = IPCSkeleton::GetCallingPid();
114     if (std::any_of(secCompEnhanceData_.begin(), secCompEnhanceData_.end(),
115         [pid](const auto& e) { return e.pid == pid; })) {
116             ACCESSTOKEN_LOG_ERROR(LABEL, "register sec comp enhance exist, pid %{public}d.", pid);
117             return PrivacyError::ERR_CALLBACK_ALREADY_EXIST;
118     }
119     SecCompEnhanceData enhance;
120     enhance.callback = enhanceData.callback;
121     enhance.pid = pid;
122     enhance.token = IPCSkeleton::GetCallingTokenID();
123     enhance.challenge = enhanceData.challenge;
124     secCompEnhanceData_.emplace_back(enhance);
125     ACCESSTOKEN_LOG_INFO(LABEL, "register sec comp enhance success, pid %{public}d, total %{public}u.",
126         pid, static_cast<uint32_t>(secCompEnhanceData_.size()));
127     return RET_SUCCESS;
128 }
129 
GetSecCompEnhance(int32_t pid,SecCompEnhanceData & enhanceData)130 int32_t PrivacySecCompEnhanceAgent::GetSecCompEnhance(int32_t pid, SecCompEnhanceData& enhanceData)
131 {
132     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
133     InitAppObserver();
134     for (auto iter = secCompEnhanceData_.begin(); iter != secCompEnhanceData_.end(); ++iter) {
135         if (iter->pid == pid) {
136             enhanceData = *iter;
137             ACCESSTOKEN_LOG_INFO(LABEL, "get pid %{public}d data.", pid);
138             return RET_SUCCESS;
139         }
140     }
141     return ERR_PARAM_INVALID;
142 }
143 
GetSpecialSecCompEnhance(const std::string & bundleName,std::vector<SecCompEnhanceData> & enhanceList)144 int32_t PrivacySecCompEnhanceAgent::GetSpecialSecCompEnhance(const std::string& bundleName,
145     std::vector<SecCompEnhanceData>& enhanceList)
146 {
147     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
148     for (auto iter = secCompEnhanceData_.begin(); iter != secCompEnhanceData_.end(); iter++) {
149         HapTokenInfo info;
150         if (AccessTokenKit::GetHapTokenInfo(iter->token, info) == AccessTokenKitRet::RET_SUCCESS) {
151             if (bundleName == info.bundleName) {
152                 enhanceList.emplace_back(*iter);
153             }
154         }
155     }
156     return RET_SUCCESS;
157 }
158 } // namespace AccessToken
159 } // namespace Security
160 } // namespace OHOS
161