• 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_common_log.h"
20 #include "app_manager_access_client.h"
21 #include "ipc_skeleton.h"
22 #include "privacy_error.h"
23 #include "securec.h"
24 
25 namespace OHOS {
26 namespace Security {
27 namespace AccessToken {
28 namespace {
29 static const std::string SCENE_BOARD_PKG_NAME = "com.ohos.sceneboard";
30 std::recursive_mutex g_instanceMutex;
31 }
OnProcessDied(const ProcessData & processData)32 void PrivacyAppUsingSecCompStateObserver::OnProcessDied(const ProcessData &processData)
33 {
34     LOGI(PRI_DOMAIN, PRI_TAG, "OnProcessDied pid %{public}d", processData.pid);
35     PrivacySecCompEnhanceAgent::GetInstance().RemoveSecCompEnhance(processData.pid);
36 }
37 
NotifyAppManagerDeath()38 void PrivacySecCompAppManagerDeathCallback::NotifyAppManagerDeath()
39 {
40     LOGI(PRI_DOMAIN, PRI_TAG, "AppManagerDeath called");
41 
42     PrivacySecCompEnhanceAgent::GetInstance().OnAppMgrRemoteDiedHandle();
43 }
44 
GetInstance()45 PrivacySecCompEnhanceAgent& PrivacySecCompEnhanceAgent::GetInstance()
46 {
47     static PrivacySecCompEnhanceAgent* instance = nullptr;
48     if (instance == nullptr) {
49         std::lock_guard<std::recursive_mutex> lock(g_instanceMutex);
50         if (instance == nullptr) {
51             PrivacySecCompEnhanceAgent* tmp = new PrivacySecCompEnhanceAgent();
52             instance = std::move(tmp);
53         }
54     }
55     return *instance;
56 }
57 
InitAppObserver()58 void PrivacySecCompEnhanceAgent::InitAppObserver()
59 {
60     if (observer_ != nullptr) {
61         return;
62     }
63     observer_ = new (std::nothrow) PrivacyAppUsingSecCompStateObserver();
64     if (observer_ == nullptr) {
65         LOGE(PRI_DOMAIN, PRI_TAG, "New observer failed.");
66         return;
67     }
68     if (AppManagerAccessClient::GetInstance().RegisterApplicationStateObserver(observer_) != 0) {
69         LOGE(PRI_DOMAIN, PRI_TAG, "Register observer failed.");
70         observer_ = nullptr;
71         return;
72     }
73     if (appManagerDeathCallback_ == nullptr) {
74         appManagerDeathCallback_ = std::make_shared<PrivacySecCompAppManagerDeathCallback>();
75         AppManagerAccessClient::GetInstance().RegisterDeathCallback(appManagerDeathCallback_);
76     }
77 }
78 
PrivacySecCompEnhanceAgent()79 PrivacySecCompEnhanceAgent::PrivacySecCompEnhanceAgent()
80 {
81     InitAppObserver();
82 }
83 
~PrivacySecCompEnhanceAgent()84 PrivacySecCompEnhanceAgent::~PrivacySecCompEnhanceAgent()
85 {
86     if (observer_ != nullptr) {
87         AppManagerAccessClient::GetInstance().UnregisterApplicationStateObserver(observer_);
88         observer_ = nullptr;
89     }
90 }
91 
OnAppMgrRemoteDiedHandle()92 void PrivacySecCompEnhanceAgent::OnAppMgrRemoteDiedHandle()
93 {
94     LOGI(PRI_DOMAIN, PRI_TAG, "OnAppMgrRemoteDiedHandle.");
95     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
96     secCompEnhanceData_.clear();
97     observer_ = nullptr;
98 }
99 
RemoveSecCompEnhance(int pid)100 void PrivacySecCompEnhanceAgent::RemoveSecCompEnhance(int pid)
101 {
102     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
103     for (auto iter = secCompEnhanceData_.begin(); iter != secCompEnhanceData_.end(); ++iter) {
104         if (iter->pid == pid) {
105             secCompEnhanceData_.erase(iter);
106             LOGI(PRI_DOMAIN, PRI_TAG, "Remove pid %{public}d data.", pid);
107             return;
108         }
109     }
110     LOGE(PRI_DOMAIN, PRI_TAG, "Not found pid %{public}d data.", pid);
111     return;
112 }
113 
RegisterSecCompEnhance(const SecCompEnhanceData & enhanceData)114 int32_t PrivacySecCompEnhanceAgent::RegisterSecCompEnhance(const SecCompEnhanceData& enhanceData)
115 {
116     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
117     InitAppObserver();
118     int pid = IPCSkeleton::GetCallingPid();
119     if (std::any_of(secCompEnhanceData_.begin(), secCompEnhanceData_.end(),
120         [pid](const auto& e) { return e.pid == pid; })) {
121             LOGE(PRI_DOMAIN, PRI_TAG, "Register sec comp enhance exist, pid %{public}d.", pid);
122             return PrivacyError::ERR_CALLBACK_ALREADY_EXIST;
123     }
124     SecCompEnhanceData enhance;
125     enhance.callback = enhanceData.callback;
126     enhance.pid = pid;
127     enhance.token = IPCSkeleton::GetCallingTokenID();
128     enhance.challenge = enhanceData.challenge;
129     enhance.sessionId = enhanceData.sessionId;
130     enhance.seqNum = enhanceData.seqNum;
131     enhance.isSceneBoard = false;
132     if (memcpy_s(enhance.key, AES_KEY_STORAGE_LEN, enhanceData.key, AES_KEY_STORAGE_LEN) != EOK) {
133         return PrivacyError::ERR_CALLBACK_ALREADY_EXIST;
134     }
135     HapTokenInfo info;
136     if (AccessTokenKit::GetHapTokenInfo(enhance.token, info) == AccessTokenKitRet::RET_SUCCESS) {
137         if (info.bundleName == SCENE_BOARD_PKG_NAME) {
138             enhance.isSceneBoard = true;
139         }
140     }
141     secCompEnhanceData_.emplace_back(enhance);
142     LOGI(PRI_DOMAIN, PRI_TAG, "Register sec comp enhance success, pid %{public}d, total %{public}u.",
143         pid, static_cast<uint32_t>(secCompEnhanceData_.size()));
144     return RET_SUCCESS;
145 }
146 
UpdateSecCompEnhance(int32_t pid,uint32_t seqNum)147 int32_t PrivacySecCompEnhanceAgent::UpdateSecCompEnhance(int32_t pid, uint32_t seqNum)
148 {
149     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
150     InitAppObserver();
151     for (auto iter = secCompEnhanceData_.begin(); iter != secCompEnhanceData_.end(); ++iter) {
152         if (iter->pid == pid) {
153             iter->seqNum = seqNum;
154             LOGI(PRI_DOMAIN, PRI_TAG, "Update pid=%{public}d data successful.", pid);
155             return RET_SUCCESS;
156         }
157     }
158     return ERR_PARAM_INVALID;
159 }
160 
GetSecCompEnhance(int32_t pid,SecCompEnhanceData & enhanceData)161 int32_t PrivacySecCompEnhanceAgent::GetSecCompEnhance(int32_t pid, SecCompEnhanceData& enhanceData)
162 {
163     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
164     InitAppObserver();
165     for (auto iter = secCompEnhanceData_.begin(); iter != secCompEnhanceData_.end(); ++iter) {
166         if (iter->pid == pid) {
167             enhanceData = *iter;
168             LOGI(PRI_DOMAIN, PRI_TAG, "Get pid %{public}d data.", pid);
169             return RET_SUCCESS;
170         }
171     }
172     return ERR_PARAM_INVALID;
173 }
174 
GetSpecialSecCompEnhance(const std::string & bundleName,std::vector<SecCompEnhanceData> & enhanceList)175 int32_t PrivacySecCompEnhanceAgent::GetSpecialSecCompEnhance(const std::string& bundleName,
176     std::vector<SecCompEnhanceData>& enhanceList)
177 {
178     std::lock_guard<std::mutex> lock(secCompEnhanceMutex_);
179     for (auto iter = secCompEnhanceData_.begin(); iter != secCompEnhanceData_.end(); iter++) {
180         if ((*iter).isSceneBoard) {
181             enhanceList.emplace_back(*iter);
182         }
183     }
184     return RET_SUCCESS;
185 }
186 } // namespace AccessToken
187 } // namespace Security
188 } // namespace OHOS
189