1 /*
2 * Copyright (c) 2024 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 "avsession_users_manager.h"
17 #include "account_manager_adapter.h"
18 #include "avsession_utils.h"
19
20 namespace OHOS::AVSession {
GetInstance()21 AVSessionUsersManager& AVSessionUsersManager::GetInstance()
22 {
23 static AVSessionUsersManager usersManager;
24 return usersManager;
25 }
26
Init()27 void AVSessionUsersManager::Init()
28 {
29 std::lock_guard lockGuard(userLock_);
30 AccountManagerAdapter::GetInstance().Init();
31 AccountManagerAdapter::GetInstance().AddAccountEventsListener([this] (const std::string &type, const int &userId) {
32 SLOGI("get event for %{public}d with type %{public}s, curUser: %{public}d", userId, type.c_str(), curUserId_);
33 if (type == AccountManagerAdapter::accountEventSwitched) {
34 curUserId_ = userId;
35 auto it = std::find(aliveUsers_.begin(), aliveUsers_.end(), curUserId_);
36 if (it == aliveUsers_.end()) {
37 aliveUsers_.push_back(curUserId_);
38 }
39 } else if (type == AccountManagerAdapter::accountEventRemoved) {
40 HandleUserRemoved(userId);
41 }
42 });
43 curUserId_ = AccountManagerAdapter::GetInstance().GetCurrentAccountUserId();
44 aliveUsers_.push_back(curUserId_);
45 }
46
HandleUserRemoved(int32_t userId)47 void AVSessionUsersManager::HandleUserRemoved(int32_t userId)
48 {
49 std::lock_guard lockGuard(userLock_);
50 SLOGI("HandleUserRemoved for user %{public}d", userId);
51 auto iterForStack = sessionStackMapByUserId_.find(userId);
52 if (iterForStack != sessionStackMapByUserId_.end()) {
53 std::shared_ptr<SessionStack> stackPtr = iterForStack->second;
54 CHECK_AND_RETURN_LOG(stackPtr != nullptr, "HandleUserRemoved with nullptr stack error");
55 std::vector<sptr<AVSessionItem>> allSession = stackPtr->GetAllSessions();
56 for (auto& sessionItem : allSession) {
57 CHECK_AND_RETURN_LOG(sessionItem != nullptr, "HandleUserRemoved session null");
58 std::string sessionId = sessionItem->GetSessionId();
59 stackPtr->RemoveSession(sessionId);
60 GetContainerFromAll().RemoveSession(sessionId);
61 }
62 sessionStackMapByUserId_.erase(iterForStack);
63 }
64 auto iterForFrontList = frontSessionListMapByUserId_.find(userId);
65 if (iterForFrontList != frontSessionListMapByUserId_.end()) {
66 frontSessionListMapByUserId_.erase(iterForFrontList);
67 }
68 auto iterForListenerMap = sessionListenersMapByUserId_.find(userId);
69 if (iterForListenerMap != sessionListenersMapByUserId_.end()) {
70 sessionListenersMapByUserId_.erase(iterForListenerMap);
71 }
72 auto iterForTop = topSessionsMapByUserId_.find(userId);
73 if (iterForTop != topSessionsMapByUserId_.end()) {
74 topSessionsMapByUserId_.erase(iterForTop);
75 }
76 aliveUsers_.remove_if([userId](int32_t element) { return element == userId; });
77 }
78
79
GetContainer()80 SessionStack& AVSessionUsersManager::GetContainer()
81 {
82 return GetContainerFromUser(curUserId_);
83 }
84
GetContainerFromUser(int32_t userId)85 SessionStack& AVSessionUsersManager::GetContainerFromUser(int32_t userId)
86 {
87 std::lock_guard lockGuard(userLock_);
88 std::shared_ptr<SessionStack> stackPtr = nullptr;
89 auto iter = sessionStackMapByUserId_.find(userId);
90 if (iter != sessionStackMapByUserId_.end()) {
91 stackPtr = iter->second;
92 } else {
93 SLOGI("create new stack for user %{public}d", userId);
94 stackPtr = std::make_shared<SessionStack>();
95 sessionStackMapByUserId_[userId] = stackPtr;
96 }
97 if (stackPtr == nullptr) {
98 SLOGE("error finding sessionStack ptr null, return default!");
99 static SessionStack sessionStack;
100 return sessionStack;
101 }
102 return *stackPtr;
103 }
104
GetContainerFromAll()105 SessionStack& AVSessionUsersManager::GetContainerFromAll()
106 {
107 if (sessionStackForAll_ == nullptr) {
108 sessionStackForAll_ = std::make_shared<SessionStack>();
109 }
110 return *sessionStackForAll_;
111 }
112
GetCurSessionListForFront()113 std::shared_ptr<std::list<sptr<AVSessionItem>>> AVSessionUsersManager::GetCurSessionListForFront()
114 {
115 std::lock_guard lockGuard(userLock_);
116 std::shared_ptr<std::list<sptr<AVSessionItem>>> sessionListForFront = nullptr;
117 auto iterForFrontList = frontSessionListMapByUserId_.find(curUserId_);
118 if (iterForFrontList != frontSessionListMapByUserId_.end()) {
119 sessionListForFront = iterForFrontList->second;
120 } else {
121 SLOGI("GetCurSessionListForFront without curUser: %{public}d, create new", curUserId_);
122 sessionListForFront = std::make_shared<std::list<sptr<AVSessionItem>>>();
123 frontSessionListMapByUserId_[curUserId_] = sessionListForFront;
124 }
125 return sessionListForFront;
126 }
127
GetCurrentUserId()128 int32_t AVSessionUsersManager::GetCurrentUserId()
129 {
130 std::lock_guard lockGuard(userLock_);
131 return curUserId_;
132 }
133
GetDirForCurrentUser(int32_t userId)134 std::string AVSessionUsersManager::GetDirForCurrentUser(int32_t userId)
135 {
136 std::lock_guard lockGuard(userLock_);
137 if (curUserId_ < 0) {
138 return AVSESSION_FILE_PUBLIC_DIR;
139 } else if (userId <= 0) {
140 return AVSESSION_FILE_DIR_HEAD + std::to_string(curUserId_) + AVSESSION_FILE_DIR_TAIL;
141 } else {
142 SLOGI("GetDirForCurrentUser with specific userId:%{public}d", userId);
143 return AVSESSION_FILE_DIR_HEAD + std::to_string(userId) + AVSESSION_FILE_DIR_TAIL;
144 }
145 }
146
AddSessionForCurrentUser(pid_t pid,const std::string & abilityName,sptr<AVSessionItem> & item)147 int32_t AVSessionUsersManager::AddSessionForCurrentUser(pid_t pid,
148 const std::string& abilityName, sptr<AVSessionItem>& item)
149 {
150 std::lock_guard lockGuard(userLock_);
151 SLOGI("add session for user %{public}d", curUserId_);
152 int32_t ret = AVSESSION_ERROR;
153 ret = GetContainerFromAll().AddSession(pid, abilityName, item);
154 CHECK_AND_RETURN_RET_LOG(ret == AVSESSION_SUCCESS, ret, "error when add session for all");
155 ret = GetContainerFromUser(curUserId_).AddSession(pid, abilityName, item);
156 CHECK_AND_RETURN_RET_LOG(ret == AVSESSION_SUCCESS, ret, "error when add session for user");
157 return ret;
158 }
159
RemoveSessionForAllUser(pid_t pid,const std::string & abilityName)160 sptr<AVSessionItem> AVSessionUsersManager::RemoveSessionForAllUser(pid_t pid, const std::string& abilityName)
161 {
162 std::lock_guard lockGuard(userLock_);
163 sptr<AVSessionItem> result;
164 SLOGI("remove session for pid %{public}d,abilityName %{public}s", static_cast<int>(pid), abilityName.c_str());
165 result = GetContainerFromAll().RemoveSession(pid, abilityName);
166 CHECK_AND_RETURN_RET_LOG(result != nullptr, result, "remove session from all get nullptr");
167 std::string sessionId = result->GetSessionId();
168 int32_t userId = result->GetUserId();
169 GetContainerFromUser(userId).RemoveSession(pid, abilityName);
170 std::string fileName = AVSessionUtils::GetCachePathName(userId) + sessionId + AVSessionUtils::GetFileSuffix();
171 AVSessionUtils::DeleteFile(fileName);
172 return result;
173 }
174
RemoveSessionForAllUser(const std::string & sessionId)175 sptr<AVSessionItem> AVSessionUsersManager::RemoveSessionForAllUser(const std::string& sessionId)
176 {
177 std::lock_guard lockGuard(userLock_);
178 sptr<AVSessionItem> result;
179 SLOGI("remove session for sessionId %{public}s", AVSessionUtils::GetAnonySessionId(sessionId).c_str());
180 result = GetContainerFromAll().RemoveSession(sessionId);
181 CHECK_AND_RETURN_RET_LOG(result != nullptr, result, "remove session from all get nullptr");
182 int32_t userId = result->GetUserId();
183 GetContainerFromUser(userId).RemoveSession(sessionId);
184 std::string fileName = AVSessionUtils::GetCachePathName(userId) + sessionId + AVSessionUtils::GetFileSuffix();
185 AVSessionUtils::DeleteFile(fileName);
186 return result;
187 }
188
RemoveSessionForAllUser(pid_t pid)189 std::vector<sptr<AVSessionItem>> AVSessionUsersManager::RemoveSessionForAllUser(pid_t pid)
190 {
191 std::lock_guard lockGuard(userLock_);
192 SLOGI("remove session for only pid %{public}d", static_cast<int>(pid));
193 std::vector<sptr<AVSessionItem>> result;
194 result = GetContainerFromAll().GetSessionsByPid(pid);
195 for (auto& sessionItem : result) {
196 CHECK_AND_RETURN_RET_LOG(sessionItem != nullptr, result, "RemoveSessionForAllUser session null");
197 std::string sessionId = sessionItem->GetSessionId();
198 int32_t userId = sessionItem->GetUserId();
199 GetContainerFromUser(userId).RemoveSession(sessionId);
200 GetContainerFromAll().RemoveSession(sessionId);
201 }
202 return result;
203 }
204
AddSessionListener(pid_t pid,const sptr<ISessionListener> & listener)205 void AVSessionUsersManager::AddSessionListener(pid_t pid, const sptr<ISessionListener>& listener)
206 {
207 std::lock_guard lockGuard(userLock_);
208 SLOGI("add sessionListener for pid %{public}d, curUser %{public}d", static_cast<int>(pid), curUserId_);
209 auto iterForListenerMap = sessionListenersMapByUserId_.find(curUserId_);
210 if (iterForListenerMap != sessionListenersMapByUserId_.end()) {
211 (iterForListenerMap->second)[pid] = listener;
212 } else {
213 std::map<pid_t, sptr<ISessionListener>> listenerMap;
214 listenerMap[pid] = listener;
215 sessionListenersMapByUserId_[curUserId_] = listenerMap;
216 }
217 }
218
AddSessionListenerForAllUsers(pid_t pid,const sptr<ISessionListener> & listener)219 void AVSessionUsersManager::AddSessionListenerForAllUsers(pid_t pid, const sptr<ISessionListener>& listener)
220 {
221 std::lock_guard lockGuard(userLock_);
222 SLOGI("add sessionListener for pid %{public}d, for all users", static_cast<int>(pid));
223 sessionListenersMap_[pid] = listener;
224 }
225
RemoveSessionListener(pid_t pid)226 void AVSessionUsersManager::RemoveSessionListener(pid_t pid)
227 {
228 std::lock_guard lockGuard(userLock_);
229 SLOGI("remove sessionListener for pid %{public}d, curUser %{public}d", static_cast<int>(pid), curUserId_);
230 auto iterForListenerMap = sessionListenersMapByUserId_.find(curUserId_);
231 if (iterForListenerMap != sessionListenersMapByUserId_.end()) {
232 (iterForListenerMap->second).erase(pid);
233 }
234 sessionListenersMap_.erase(pid);
235 }
236
GetSessionListener()237 std::map<pid_t, sptr<ISessionListener>>& AVSessionUsersManager::GetSessionListener()
238 {
239 return GetSessionListenerForCurUser();
240 }
241
GetSessionListenerForCurUser()242 std::map<pid_t, sptr<ISessionListener>>& AVSessionUsersManager::GetSessionListenerForCurUser()
243 {
244 std::lock_guard lockGuard(userLock_);
245 auto iterForListenerMap = sessionListenersMapByUserId_.find(curUserId_);
246 if (iterForListenerMap != sessionListenersMapByUserId_.end()) {
247 return iterForListenerMap->second;
248 } else {
249 std::map<pid_t, sptr<ISessionListener>> listenerMap;
250 sessionListenersMapByUserId_[curUserId_] = listenerMap;
251 SLOGI("get session listener map with null, create new map and return for user %{public}d", curUserId_);
252 return sessionListenersMapByUserId_[curUserId_];
253 }
254 }
255
GetSessionListenerForAllUsers()256 std::map<pid_t, sptr<ISessionListener>>& AVSessionUsersManager::GetSessionListenerForAllUsers()
257 {
258 return sessionListenersMap_;
259 }
260
NotifyAccountsEvent(const std::string & type,const int & userId)261 void AVSessionUsersManager::NotifyAccountsEvent(const std::string &type, const int &userId)
262 {
263 std::lock_guard lockGuard(userLock_);
264 // lock for AccountEventsListener callback
265 AccountManagerAdapter::GetInstance().HandleAccountsEvent(type, userId);
266 }
267
SetTopSession(sptr<AVSessionItem> session)268 void AVSessionUsersManager::SetTopSession(sptr<AVSessionItem> session)
269 {
270 SetTopSession(session, curUserId_);
271 }
272
SetTopSession(sptr<AVSessionItem> session,int32_t userId)273 void AVSessionUsersManager::SetTopSession(sptr<AVSessionItem> session, int32_t userId)
274 {
275 std::lock_guard lockGuard(userLock_);
276 topSessionsMapByUserId_[userId] = session;
277 }
278
GetTopSession()279 sptr<AVSessionItem> AVSessionUsersManager::GetTopSession()
280 {
281 return GetTopSession(curUserId_);
282 }
283
GetTopSession(int32_t userId)284 sptr<AVSessionItem> AVSessionUsersManager::GetTopSession(int32_t userId)
285 {
286 std::lock_guard lockGuard(userLock_);
287 auto iterForTop = topSessionsMapByUserId_.find(userId);
288 if (iterForTop != topSessionsMapByUserId_.end()) {
289 return iterForTop->second;
290 }
291 return nullptr;
292 }
293
ClearCache()294 void AVSessionUsersManager::ClearCache()
295 {
296 std::lock_guard lockGuard(userLock_);
297 for (const auto& userId : aliveUsers_) {
298 std::string cachePath(AVSessionUtils::GetCachePathName(userId));
299 AVSessionUtils::DeleteCacheFiles(cachePath);
300 }
301 }
302 }
303