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
16 #include "hw_cast_provider.h"
17 #include <thread>
18 #include "cast_session_manager.h"
19 #include "hw_cast_stream_player.h"
20 #include "avsession_log.h"
21 #include "avsession_errors.h"
22
23 using namespace OHOS::CastEngine::CastEngineClient;
24 using namespace OHOS::CastEngine;
25
26 namespace OHOS::AVSession {
27 const uint32_t UNTRUSTED_DEVICE = 0;
28 const uint32_t TRUSTED_DEVICE = 1;
29
~HwCastProvider()30 HwCastProvider::~HwCastProvider()
31 {
32 SLOGI("destruct the HwCastProvider");
33 Release();
34 }
35
Init()36 void HwCastProvider::Init()
37 {
38 SLOGI("Init the HwCastProvider");
39 CastSessionManager::GetInstance().RegisterListener(shared_from_this());
40 }
41
StartDiscovery(int castCapability)42 bool HwCastProvider::StartDiscovery(int castCapability)
43 {
44 SLOGI("start discovery and the castCapability is %{public}d", castCapability);
45 return CastSessionManager::GetInstance().StartDiscovery(castCapability);
46 }
47
StopDiscovery()48 void HwCastProvider::StopDiscovery()
49 {
50 SLOGI("stop discovery");
51 CastSessionManager::GetInstance().StopDiscovery();
52 }
53
SetDiscoverable(const bool enable)54 int32_t HwCastProvider::SetDiscoverable(const bool enable)
55 {
56 SLOGI("SetDiscoverable in %{public}d", static_cast<int32_t>(enable));
57 return CastSessionManager::GetInstance().SetDiscoverable(enable);
58 }
59
Release()60 void HwCastProvider::Release()
61 {
62 SLOGI("Release the HwCastProvider");
63 {
64 std::lock_guard lockGuard(mutexLock_);
65 hwCastProviderSessionMap_.clear();
66 avCastControllerMap_.clear();
67 castStateListenerList_.clear();
68 castFlag_.clear();
69 }
70 if (!isRelease_) {
71 SLOGI("release in with check pass");
72 isRelease_ = true;
73 } else {
74 SLOGW("already in release, check return");
75 return;
76 }
77 CastSessionManager::GetInstance().UnregisterListener();
78 CastSessionManager::GetInstance().Release();
79 SLOGD("Release done");
80 }
81
StartCastSession()82 int HwCastProvider::StartCastSession()
83 {
84 SLOGI("StartCastSession begin");
85 CastSessionProperty property = {CastEngine::ProtocolType::CAST_PLUS_STREAM, CastEngine::EndType::CAST_SOURCE};
86 std::shared_ptr<ICastSession> castSession = nullptr;
87 CastSessionManager::GetInstance().CreateCastSession(property, castSession);
88 int castId;
89 {
90 SLOGI("StartCastSession pre check lock");
91 std::lock_guard lockGuard(mutexLock_);
92 SLOGI("StartCastSession check lock");
93 std::vector<bool>::iterator iter = find(castFlag_.begin(), castFlag_.end(), false);
94 if (iter == castFlag_.end()) {
95 SLOGE("StartCastSession faileded");
96 return AVSESSION_ERROR;
97 }
98 *iter = true;
99 castId = iter - castFlag_.begin();
100 auto hwCastProviderSession = std::make_shared<HwCastProviderSession>(castSession);
101 if (hwCastProviderSession) {
102 hwCastProviderSession->Init();
103 }
104 hwCastProviderSessionMap_[castId] = hwCastProviderSession;
105 }
106 SLOGI("StartCastSession successed and return the castId is %{public}d", castId);
107
108 return castId;
109 }
StopCastSession(int castId)110 void HwCastProvider::StopCastSession(int castId)
111 {
112 SLOGI("StopCastSession begin with %{public}d", castId);
113 std::lock_guard lockGuard(mutexLock_);
114 SLOGI("StopCastSession check lock");
115
116 auto hwCastStreamPlayer = avCastControllerMap_[castId];
117 if (hwCastStreamPlayer) {
118 hwCastStreamPlayer->Release();
119 }
120
121 if (hwCastProviderSessionMap_.find(castId) == hwCastProviderSessionMap_.end()) {
122 SLOGE("no need to release castSession for castId %{public}d is not exit in hwCastProviderSessionMap_", castId);
123 return;
124 }
125 auto hwCastProviderSession = hwCastProviderSessionMap_[castId];
126 if (hwCastProviderSession) {
127 hwCastProviderSession->Release();
128 }
129 hwCastProviderSessionMap_.erase(castId);
130 castFlag_[castId] = false;
131 avCastControllerMap_.erase(castId);
132 }
133
AddCastDevice(int castId,DeviceInfo deviceInfo)134 bool HwCastProvider::AddCastDevice(int castId, DeviceInfo deviceInfo)
135 {
136 SLOGI("AddCastDevice with config castSession and corresonding castId is %{public}d", castId);
137 std::lock_guard lockGuard(mutexLock_);
138 SLOGI("add device check lock done");
139
140 if (hwCastProviderSessionMap_.find(castId) == hwCastProviderSessionMap_.end()) {
141 SLOGE("the castId corresonding to castSession is not exist");
142 return false;
143 }
144 auto hwCastProviderSession = hwCastProviderSessionMap_[castId];
145 if (!hwCastProviderSession) {
146 SLOGE("the castId corresonding to castSession is nullptr");
147 return false;
148 }
149
150 lastCastId_ = castId;
151 return hwCastProviderSession->AddDevice(deviceInfo.deviceId_);
152 }
153
RemoveCastDevice(int castId,DeviceInfo deviceInfo)154 bool HwCastProvider::RemoveCastDevice(int castId, DeviceInfo deviceInfo)
155 {
156 SLOGI("RemoveCastDevice with config castSession and corresonding castId is %{public}d", castId);
157 std::lock_guard lockGuard(mutexLock_);
158 SLOGI("remove device check lock");
159 if (hwCastProviderSessionMap_.find(castId) == hwCastProviderSessionMap_.end()) {
160 SLOGE("the castId corresonding to castSession is not exist");
161 return false;
162 }
163 auto hwCastProviderSession = hwCastProviderSessionMap_[castId];
164 if (!hwCastProviderSession) {
165 SLOGE("the castId corresonding to castSession is nullptr");
166 return false;
167 }
168
169 return hwCastProviderSession->RemoveDevice(deviceInfo.deviceId_);
170 }
171
RegisterCastStateListener(std::shared_ptr<IAVCastStateListener> listener)172 bool HwCastProvider::RegisterCastStateListener(std::shared_ptr<IAVCastStateListener> listener)
173 {
174 SLOGI("RegisterCastStateListener in");
175 std::lock_guard lockGuard(mutexLock_);
176 SLOGI("RegisterCastStateListener in pass lock");
177 if (listener == nullptr) {
178 SLOGE("RegisterCastStateListener the listener is nullptr");
179 return false;
180 }
181 if (find(castStateListenerList_.begin(), castStateListenerList_.end(), listener) != castStateListenerList_.end()) {
182 SLOGE("RegisterCastStateListener the listener is already be registered");
183 return false;
184 }
185 SLOGI("RegisterCastStateListener successed, and save it in the castStateListenerList_");
186 castStateListenerList_.emplace_back(listener);
187
188 return true;
189 }
190
UnRegisterCastStateListener(std::shared_ptr<IAVCastStateListener> listener)191 bool HwCastProvider::UnRegisterCastStateListener(std::shared_ptr<IAVCastStateListener> listener)
192 {
193 SLOGI("UnRegisterCastStateListener in");
194 std::lock_guard lockGuard(mutexLock_);
195 SLOGI("UnRegisterCastStateListener in pass lock");
196 if (listener == nullptr) {
197 SLOGE("UnRegisterCastStateListener the listener is nullptr");
198 return false;
199 }
200 for (auto iter = castStateListenerList_.begin(); iter != castStateListenerList_.end();) {
201 if (*iter == listener) {
202 castStateListenerList_.erase(iter);
203 SLOGI("UnRegisterCastStateListener successed, and erase it from castStateListenerList_");
204 return true;
205 } else {
206 ++iter;
207 }
208 }
209 SLOGE("listener is not found in castStateListenerList_, so UnRegisterCastStateListener failed");
210
211 return false;
212 }
213
GetRemoteController(int castId)214 std::shared_ptr<IAVCastControllerProxy> HwCastProvider::GetRemoteController(int castId)
215 {
216 SLOGI("get remote controller with castId %{public}d", static_cast<int32_t>(castId));
217 std::lock_guard lockGuard(mutexLock_);
218 SLOGI("get remote controller check lock with castId %{public}d", static_cast<int32_t>(castId));
219 if (avCastControllerMap_.find(castId) != avCastControllerMap_.end()) {
220 SLOGI("the castId corresonding to streamPlayer is already exist");
221 return avCastControllerMap_[castId];
222 }
223 if (hwCastProviderSessionMap_.find(castId) == hwCastProviderSessionMap_.end()) {
224 SLOGE("No castSession corresonding to castId exists");
225 return nullptr;
226 }
227 auto hwCastProviderSession = hwCastProviderSessionMap_[castId];
228 if (hwCastProviderSession == nullptr) {
229 SLOGE("castSession corresonding to castId is nullptr");
230 return nullptr;
231 }
232 std::shared_ptr<IStreamPlayer> streamPlayer = hwCastProviderSession->CreateStreamPlayer();
233 std::shared_ptr<HwCastStreamPlayer> hwCastStreamPlayer = std::make_shared<HwCastStreamPlayer>(streamPlayer);
234 if (!hwCastStreamPlayer) {
235 SLOGE("the created hwCastStreamPlayer is nullptr");
236 return nullptr;
237 }
238 hwCastStreamPlayer->Init();
239 avCastControllerMap_[castId] = hwCastStreamPlayer;
240 SLOGI("Create streamPlayer finished");
241 return hwCastStreamPlayer;
242 }
243
RegisterCastSessionStateListener(int castId,std::shared_ptr<IAVCastSessionStateListener> listener)244 bool HwCastProvider::RegisterCastSessionStateListener(int castId,
245 std::shared_ptr<IAVCastSessionStateListener> listener)
246 {
247 SLOGD("RegisterCastSessionStateListener for castId %{public}d", castId);
248 if (listener == nullptr) {
249 SLOGE("RegisterCastSessionStateListener failed for the listener is nullptr");
250 return false;
251 }
252 std::lock_guard lockGuard(mutexLock_);
253 SLOGI("register castsession state listener check lock with castId %{public}d", static_cast<int32_t>(castId));
254 if (hwCastProviderSessionMap_.find(castId) == hwCastProviderSessionMap_.end()) {
255 SLOGE("RegisterCastSessionStateListener failed for the castSession corresponding to castId is not exit");
256 return false;
257 }
258 auto hwCastProviderSession = hwCastProviderSessionMap_[castId];
259 if (hwCastProviderSession == nullptr) {
260 SLOGE("RegisterCastSessionStateListener failed for the hwCastProviderSession is nullptr");
261 return false;
262 }
263
264 return hwCastProviderSession->RegisterCastSessionStateListener(listener);
265 }
266
UnRegisterCastSessionStateListener(int castId,std::shared_ptr<IAVCastSessionStateListener> listener)267 bool HwCastProvider::UnRegisterCastSessionStateListener(int castId,
268 std::shared_ptr<IAVCastSessionStateListener> listener)
269 {
270 if (listener == nullptr) {
271 SLOGE("UnRegisterCastSessionStateListener failed for the listener is nullptr");
272 return false;
273 }
274 std::lock_guard lockGuard(mutexLock_);
275 SLOGI("unregister castsession state listener check lock with castId %{public}d", static_cast<int32_t>(castId));
276 if (hwCastProviderSessionMap_.find(castId) == hwCastProviderSessionMap_.end()) {
277 SLOGE("UnRegisterCastSessionStateListener failed for the castSession corresponding to castId is not exit");
278 return false;
279 }
280 auto hwCastProviderSession = hwCastProviderSessionMap_[castId];
281 if (hwCastProviderSession == nullptr) {
282 SLOGE("UnRegisterCastSessionStateListener failed for the hwCastProviderSession is nullptr");
283 return false;
284 }
285
286 return hwCastProviderSession->UnRegisterCastSessionStateListener(listener);
287 }
288
289
OnDeviceFound(const std::vector<CastRemoteDevice> & deviceList)290 void HwCastProvider::OnDeviceFound(const std::vector<CastRemoteDevice> &deviceList)
291 {
292 std::vector<DeviceInfo> deviceInfoList;
293 if (deviceList.empty()) {
294 SLOGW("recv empty deviceList, return");
295 return;
296 }
297 SLOGI("get deviceList size %{public}zu", deviceList.size());
298 for (CastRemoteDevice castRemoteDevice : deviceList) {
299 SLOGI("get devices with deviceName %{public}s", castRemoteDevice.deviceName.c_str());
300 DeviceInfo deviceInfo;
301 deviceInfo.castCategory_ = AVCastCategory::CATEGORY_REMOTE;
302 deviceInfo.deviceId_ = castRemoteDevice.deviceId;
303 deviceInfo.deviceName_ = castRemoteDevice.deviceName;
304 deviceInfo.deviceType_ = static_cast<int>(castRemoteDevice.deviceType);
305 deviceInfo.ipAddress_ = castRemoteDevice.ipAddress;
306 deviceInfo.supportedProtocols_ = ProtocolType::TYPE_CAST_PLUS_STREAM;
307 deviceInfo.authenticationStatus_ = static_cast<int>(castRemoteDevice.subDeviceType) == 0 ?
308 TRUSTED_DEVICE : UNTRUSTED_DEVICE;
309 deviceInfoList.emplace_back(deviceInfo);
310 }
311 for (auto listener : castStateListenerList_) {
312 if (listener != nullptr) {
313 SLOGI("trigger the OnDeviceAvailable for registered listeners");
314 listener->OnDeviceAvailable(deviceInfoList);
315 }
316 }
317 }
318
OnDeviceOffline(const std::string & deviceId)319 void HwCastProvider::OnDeviceOffline(const std::string& deviceId)
320 {
321 SLOGI("Received on device offline event");
322 for (auto listener : castStateListenerList_) {
323 if (listener != nullptr) {
324 SLOGI("trigger the OnDeviceOffline for registered listeners");
325 listener->OnDeviceOffline(deviceId);
326 }
327 }
328 }
329
WaitSessionRelease()330 void HwCastProvider::WaitSessionRelease()
331 {
332 SLOGI("waitSessionRelease get in");
333 std::lock_guard lockGuard(mutexLock_);
334 if (hwCastProviderSessionMap_.find(lastCastId_) == hwCastProviderSessionMap_.end()) {
335 SLOGI("waitSessionRelease for the castId is not exit, check cache session");
336 return;
337 }
338 auto hwCastProviderSession = lastCastSession;
339 if (hwCastProviderSession == nullptr) {
340 SLOGI("waitSessionRelease failed for the hwCastProviderSession is nullptr");
341 return;
342 }
343 hwCastProviderSession->CheckProcessDone();
344 SLOGI("waitSessionRelease get done");
345 }
346
OnSessionCreated(const std::shared_ptr<CastEngine::ICastSession> & castSession)347 void HwCastProvider::OnSessionCreated(const std::shared_ptr<CastEngine::ICastSession> &castSession)
348 {
349 SLOGI("Cast provider received session create event");
350 std::thread([this, castSession]() {
351 SLOGI("Cast pvd received session create event and create task thread");
352 WaitSessionRelease();
353 SLOGI("Cast pvd received session create event and wait session release done");
354 for (auto listener : castStateListenerList_) {
355 listener->OnSessionNeedDestroy();
356 SLOGI("Cast pvd received session create event and session destroy check done");
357 }
358 int32_t castId;
359 {
360 std::lock_guard lockGuard(mutexLock_);
361 std::vector<bool>::iterator iter = find(castFlag_.begin(), castFlag_.end(), false);
362 if (iter == castFlag_.end()) {
363 SLOGE("Do not trigger callback due to the castFlag_ used up.");
364 return;
365 }
366 *iter = true;
367 castId = iter - castFlag_.begin();
368 SLOGI("Cast task thread to find flag");
369 }
370 auto hwCastProviderSession = std::make_shared<HwCastProviderSession>(castSession);
371 hwCastProviderSession->Init();
372 {
373 std::lock_guard lockGuard(mutexLock_);
374 hwCastProviderSessionMap_[castId] = hwCastProviderSession;
375 lastCastSession = hwCastProviderSession;
376 lastCastId_ = castId;
377 SLOGI("Cast task thread to create player");
378 std::shared_ptr<IStreamPlayer> streamPlayer = hwCastProviderSession->CreateStreamPlayer();
379 std::shared_ptr<HwCastStreamPlayer> hwCastStreamPlayer = std::make_shared<HwCastStreamPlayer>(streamPlayer);
380 hwCastStreamPlayer->Init();
381 avCastControllerMap_[castId] = hwCastStreamPlayer;
382 }
383 SLOGI("Create streamPlayer finished %{public}d", castId);
384 for (auto listener : castStateListenerList_) {
385 listener->OnSessionCreated(castId);
386 }
387 SLOGI("do session create notify finished %{public}d", castId);
388 }).detach();
389 }
390
OnServiceDied()391 void HwCastProvider::OnServiceDied()
392 {
393 for (auto listener : castStateListenerList_) {
394 if (listener != nullptr) {
395 SLOGI("trigger the OnServiceDied for registered listeners");
396 listener->OnCastServerDied();
397 }
398 }
399 }
400 } // namespace OHOS::AVSession
401