• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2023 Shenzhen Kaihong Digital Industry Development 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 "wfd_sink_scene.h"
17 #include <unistd.h>
18 #include "common/common_macro.h"
19 #include "common/reflect_registration.h"
20 #include "common/sharing_log.h"
21 #include "configuration/include/config.h"
22 #include "const_def.h"
23 #include "extend/magic_enum/magic_enum.hpp"
24 #include "iservice_registry.h"
25 #include "network/socket/socket_utils.h"
26 #include "kits/c/wifi_hid2d.h"
27 #include "system_ability_definition.h"
28 #include "utils/utils.h"
29 #include "wfd_session_def.h"
30 
31 using namespace OHOS::DistributedHardware;
32 namespace OHOS {
33 namespace Sharing {
34 constexpr int P2P_LISTEN_INTERVAL = 500;
35 constexpr int P2P_LISTEN_PERIOD = 500;
36 constexpr int DM_MAX_NAME_LENGTH = 32;
37 
OnAddSystemAbility(int32_t systemAbilityId,const std::string & deviceId)38 void WfdSinkScene::WfdSystemAbilityListener::OnAddSystemAbility(int32_t systemAbilityId, const std::string &deviceId)
39 {
40     if (systemAbilityId == WIFI_DEVICE_ABILITY_ID) {
41         SHARING_LOGI("%{public}s, id is %{public}d.", __FUNCTION__, systemAbilityId);
42         auto scene = scene_.lock();
43         if (scene == nullptr) {
44             SHARING_LOGE("WfdSinkScene is null");
45             return;
46         }
47         scene->OnWifiAbilityResume();
48     }
49 }
50 
OnRemoveSystemAbility(int32_t systemAbilityId,const std::string & deviceId)51 void WfdSinkScene::WfdSystemAbilityListener::OnRemoveSystemAbility(int32_t systemAbilityId,
52     const std::string& deviceId)
53 {
54     if (systemAbilityId == WIFI_DEVICE_ABILITY_ID) {
55         SHARING_LOGI("%{public}s, id is %{public}d.", __FUNCTION__, systemAbilityId);
56         auto scene = scene_.lock();
57         if (scene == nullptr) {
58             SHARING_LOGE("WfdSinkScene is null");
59             return;
60         }
61         scene->OnWifiAbilityDied();
62     }
63 }
64 
OnP2pStateChanged(int32_t state)65 void WfdSinkScene::WfdP2pCallback::OnP2pStateChanged(int32_t state)
66 {
67     SHARING_LOGI("state: %{public}d.", state);
68     auto parent = parent_.lock();
69     if (parent) {
70         switch (state) {
71             case (int32_t)Wifi::P2pState::P2P_STATE_NONE:
72                 break;
73             case (int32_t)Wifi::P2pState::P2P_STATE_IDLE:
74                 break;
75             case (int32_t)Wifi::P2pState::P2P_STATE_STARTING:
76                 break;
77             case (int32_t)Wifi::P2pState::P2P_STATE_STARTED:
78                 if (parent->isSinkRunning_) {
79                     parent->WfdP2pStart();
80                 }
81                 break;
82             case (int32_t)Wifi::P2pState::P2P_STATE_CLOSING:
83                 break;
84             case (int32_t)Wifi::P2pState::P2P_STATE_CLOSED:
85                 if (parent->isSinkRunning_) {
86                     parent->isSinkRunning_ = false;
87                     parent->WfdP2pStop();
88                     parent->OnInnerError("", SharingErrorCode::ERR_NETWORK_ERROR, "NETWORK ERROR, P2P MODULE STOPPED");
89                     WfdSinkHiSysEvent::GetInstance().P2PReportError(__func__,
90                                                                     SinkErrorCode::WIFI_DISPLAY_P2P_DISCONNECTED_STATE_CLOSED);
91                 }
92                 break;
93             default:
94                 SHARING_LOGI("none process case.");
95                 break;
96         }
97     }
98 }
99 
OnP2pPersistentGroupsChanged(void)100 void WfdSinkScene::WfdP2pCallback::OnP2pPersistentGroupsChanged(void)
101 {
102     SHARING_LOGD("trace.");
103 }
104 
OnP2pThisDeviceChanged(const Wifi::WifiP2pDevice & device)105 void WfdSinkScene::WfdP2pCallback::OnP2pThisDeviceChanged(const Wifi::WifiP2pDevice &device)
106 {
107     SHARING_LOGD("trace.");
108 }
109 
OnP2pPeersChanged(const std::vector<Wifi::WifiP2pDevice> & device)110 void WfdSinkScene::WfdP2pCallback::OnP2pPeersChanged(const std::vector<Wifi::WifiP2pDevice> &device)
111 {
112     SHARING_LOGD("trace.");
113     auto parent = parent_.lock();
114     if (parent) {
115         SHARING_LOGI("device size: %{public}zu.", device.size());
116         for (auto itDev : device) {
117             auto status = itDev.GetP2pDeviceStatus();
118             SHARING_LOGI("device mac: %{public}s, status: %{public}d.",
119                          GetAnonymousMAC(itDev.GetDeviceAddress()).c_str(), status);
120             switch (status) {
121                 case Wifi::P2pDeviceStatus::PDS_AVAILABLE: {
122                     ConnectionInfo connectionInfo;
123                     connectionInfo.mac = itDev.GetDeviceAddress();
124                     connectionInfo.deviceName = itDev.GetDeviceName();
125                     connectionInfo.primaryDeviceType = itDev.GetPrimaryDeviceType();
126                     connectionInfo.secondaryDeviceType = itDev.GetSecondaryDeviceType();
127                     connectionInfo.ctrlPort = itDev.GetWfdInfo().GetCtrlPort();
128                     connectionInfo.state = ConnectionState::DISCONNECTED;
129 
130                     parent->OnP2pPeerDisconnected(connectionInfo);
131                     break;
132                 }
133                 case Wifi::P2pDeviceStatus::PDS_CONNECTED: {
134                     std::unique_lock<std::mutex> lock(parent->currentConnectDevMutex_);
135                     parent->currentConnectDev_.mac = itDev.GetDeviceAddress();
136                     parent->currentConnectDev_.deviceName = itDev.GetDeviceName();
137                     parent->currentConnectDev_.primaryDeviceType = itDev.GetPrimaryDeviceType();
138                     parent->currentConnectDev_.secondaryDeviceType = itDev.GetSecondaryDeviceType();
139                     parent->currentConnectDev_.ctrlPort = itDev.GetWfdInfo().GetCtrlPort();
140                     parent->currentConnectDev_.ip = "";
141                     parent->currentConnectDev_.state = ConnectionState::CONNECTED;
142                     break;
143                 }
144                 default:
145                     SHARING_LOGI("none process case.");
146                     break;
147             }
148         }
149     }
150 }
151 
OnP2pPrivatePeersChanged(const std::string & priWfdInfo)152 void WfdSinkScene::WfdP2pCallback::OnP2pPrivatePeersChanged(const std::string &priWfdInfo)
153 {
154     SHARING_LOGD("trace.");
155 }
156 
OnP2pServicesChanged(const std::vector<Wifi::WifiP2pServiceInfo> & srvInfo)157 void WfdSinkScene::WfdP2pCallback::OnP2pServicesChanged(const std::vector<Wifi::WifiP2pServiceInfo> &srvInfo)
158 {
159     SHARING_LOGD("trace.");
160 }
161 
162 
OnP2pConnectionChanged(const Wifi::WifiP2pLinkedInfo & info)163 void WfdSinkScene::WfdP2pCallback::OnP2pConnectionChanged(const Wifi::WifiP2pLinkedInfo &info)
164 {
165     SHARING_LOGI("trace");
166     auto parent = parent_.lock();
167     RETURN_IF_NULL(parent);
168     if (!parent->isSinkRunning_) {
169         return;
170     }
171 
172     Wifi::P2pConnectedState state = info.GetConnectState();
173     if (state == Wifi::P2pConnectedState::P2P_DISCONNECTED) {
174         SHARING_LOGI("OnP2pConnectionChanged disconnected");
175         std::string mac;
176         {
177             std::unique_lock<std::mutex> lock(parent->currentConnectDevMutex_);
178             mac = parent->currentConnectDev_.mac;
179         }
180         if (mac != "") {
181             parent->OnP2pPeerDisconnected(mac);
182         }
183         {
184             std::unique_lock<std::mutex> lock(parent->localIpMutex_);
185             parent->localIp_ = "";
186         }
187         parent->WfdP2pStart();
188         return;
189     }
190 
191     parent->p2pInstance_->StopP2pListen();
192     Wifi::WifiP2pGroupInfo group;
193     if (Wifi::ErrCode::WIFI_OPT_SUCCESS != parent->p2pInstance_->GetCurrentGroup(group)) {
194         SHARING_LOGE("GetCurrentGroup failed");
195         return;
196     }
197     SHARING_LOGI("group frequency %{public}d", group.GetFrequency());
198     if (info.IsGroupOwner()) {
199         SHARING_LOGI("sink is go");
200         std::unique_lock<std::mutex> lock(parent->localIpMutex_);
201         parent->localIp_ = info.GetGroupOwnerAddress();
202         return;
203     } else {
204         SHARING_LOGI("sink is gc");
205         std::string remoteIp = info.GetGroupOwnerAddress();
206         if (remoteIp == "" || remoteIp == "0.0.0.0") {
207             SHARING_LOGE("get remoteIp ip failed");
208             return;
209         }
210         {
211             std::unique_lock<std::mutex> lock(parent->currentConnectDevMutex_);
212             parent->currentConnectDev_.ip = remoteIp;
213         }
214         std::string interface = group.GetInterface();
215         {
216             std::unique_lock<std::mutex> lock(parent->localIpMutex_);
217             parent->localIp_ = GetLocalP2pAddress(interface);
218             if (parent->localIp_.empty()) {
219                 SHARING_LOGW("get local ip failed");
220                 return;
221             }
222         }
223         wfdTrustListManager_.AddBoundDevice(group);
224     }
225     ConnectionInfo currentConnectDev;
226     {
227         std::unique_lock<std::mutex> lock(parent->currentConnectDevMutex_);
228         currentConnectDev = parent->currentConnectDev_;
229     }
230     parent->OnP2pPeerConnected(currentConnectDev);
231     std::unique_lock<std::mutex> lock(parent->currentConnectDevMutex_);
232     parent->currentConnectDev_ = currentConnectDev;
233 }
234 
OnP2pGcJoinGroup(const OHOS::Wifi::GcInfo & info)235 void WfdSinkScene::WfdP2pCallback::OnP2pGcJoinGroup(const OHOS::Wifi::GcInfo &info)
236 {
237     SHARING_LOGI("trace.");
238     auto parent = parent_.lock();
239     if (parent && parent->p2pInstance_) {
240         std::vector<Wifi::WifiP2pDevice> devices;
241         if (Wifi::ErrCode::WIFI_OPT_SUCCESS != parent->p2pInstance_->QueryP2pDevices(devices)) {
242             SHARING_LOGE("QueryP2pDevices failed");
243             return;
244         }
245         SHARING_LOGI("QueryP2pDevices ip:%{private}s addr: %{private}s host: %{private}s.",
246                      GetAnonymousIp(info.ip).c_str(), GetAnonymousMAC(info.mac).c_str(),
247                      GetAnonyString(info.host).c_str());
248         if (info.ip == "0.0.0.0" || info.ip == "") {
249             SHARING_LOGE("device: %{private}s leased ip is: 0.0.0.0.", GetAnonymousMAC(info.mac).c_str());
250             parent->OnInnerError(info.mac.c_str(), ERR_P2P_DHCP_INVALID_IP, "ip is: 0.0.0.0.");
251             return;
252         }
253 
254         for (auto itDev : devices) {
255             if (itDev.GetDeviceAddress() != info.mac) {
256                 continue;
257             }
258             ConnectionInfo connectionInfo;
259             connectionInfo.ip = info.ip;
260             connectionInfo.mac = itDev.GetDeviceAddress();
261             connectionInfo.primaryDeviceType = itDev.GetPrimaryDeviceType();
262             connectionInfo.secondaryDeviceType = itDev.GetSecondaryDeviceType();
263             connectionInfo.ctrlPort = itDev.GetWfdInfo().GetCtrlPort();
264             connectionInfo.deviceName = itDev.GetDeviceName();
265             connectionInfo.state = ConnectionState::CONNECTED;
266             {
267                 std::unique_lock<std::mutex> lock(parent->currentConnectDevMutex_);
268                 parent->currentConnectDev_ = connectionInfo;
269             }
270             SHARING_LOGD("device connected, mac: %{private}s, ip: %{private}s, port: %{private}d",
271                 GetAnonymousMAC(connectionInfo.mac).c_str(), GetAnonymousIp(connectionInfo.ip).c_str(),
272                 connectionInfo.ctrlPort);
273             parent->OnP2pPeerConnected(connectionInfo);
274             Wifi::WifiP2pGroupInfo group;
275             parent->p2pInstance_->GetCurrentGroup(group);
276             wfdTrustListManager_.AddBoundDevice(group);
277             return;
278         }
279     }
280 }
281 
OnP2pGcLeaveGroup(const OHOS::Wifi::GcInfo & info)282 void WfdSinkScene::WfdP2pCallback::OnP2pGcLeaveGroup(const OHOS::Wifi::GcInfo &info)
283 {
284     SHARING_LOGD("trace.");
285 }
286 
OnP2pDiscoveryChanged(bool isChange)287 void WfdSinkScene::WfdP2pCallback::OnP2pDiscoveryChanged(bool isChange)
288 {
289     SHARING_LOGD("isChange: %{public}d.", isChange);
290 }
291 
292 std::unordered_map<Wifi::ErrCode, SinkErrorCode> WfdSinkScene::WfdP2pCallback::wifiErrorMapping_ = {
293     { Wifi::WIFI_OPT_FAILED, SinkErrorCode::WIFI_DISPLAY_P2P_FAILED },
294     { Wifi::WIFI_OPT_NOT_SUPPORTED, SinkErrorCode::WIFI_DISPLAY_P2P_OPT_NOT_SUPPORTED },
295     { Wifi::WIFI_OPT_INVALID_PARAM, SinkErrorCode::WIFI_DISPLAY_P2P_OPT_INVALID_PARAM },
296     { Wifi::WIFI_OPT_FORBID_AIRPLANE, SinkErrorCode::WIFI_DISPLAY_P2P_OPT_FORBID_AIRPLANE },
297     { Wifi::WIFI_OPT_FORBID_POWSAVING, SinkErrorCode::WIFI_DISPLAY_P2P_OPT_FORBID_POWSAVING },
298     { Wifi::WIFI_OPT_PERMISSION_DENIED, SinkErrorCode::WIFI_DISPLAY_P2P_OPT_PERMISSION_DENIED },
299     { Wifi::WIFI_OPT_OPEN_FAIL_WHEN_CLOSING, SinkErrorCode::WIFI_DISPLAY_P2P_OPT_OPEN_FAIL_WHEN_CLOSING },
300     { Wifi::WIFI_OPT_P2P_NOT_OPENED, SinkErrorCode::WIFI_DISPLAY_P2P_OPT_P2P_NOT_OPENED },
301 };
302 
GetErrorCode(Wifi::ErrCode errorCode,SinkErrorCode & sharingError)303 bool WfdSinkScene::WfdP2pCallback::GetErrorCode(Wifi::ErrCode errorCode, SinkErrorCode &sharingError)
304 {
305     auto it = wifiErrorMapping_.find(errorCode);
306     if (it != wifiErrorMapping_.end()) {
307         sharingError = it->second;
308         SHARING_LOGI("wifi errorCode: %{public}d, sharingError:%{public}d", errorCode, sharingError);
309         return true;
310     } else {
311         SHARING_LOGI("unknow wifi errorCode: %{public}d", errorCode);
312         return false;
313     }
314 }
315 
OnP2pActionResult(Wifi::P2pActionCallback action,Wifi::ErrCode code)316 void WfdSinkScene::WfdP2pCallback::OnP2pActionResult(Wifi::P2pActionCallback action, Wifi::ErrCode code)
317 {
318     SHARING_LOGI("action %{public}hhu, code %{public}d", action, code);
319     auto parent = parent_.lock();
320     if (parent) {
321         SinkErrorCode sharingErrorCode;
322         if (code != Wifi::WIFI_OPT_SUCCESS) {
323             if (GetErrorCode(code, sharingErrorCode)) {
324                 SHARING_LOGI("wifi errorCode: %{public}d, sharingErrorCode:%{public}d", code, sharingErrorCode);
325                 WfdSinkHiSysEvent::GetInstance().P2PReportError(__func__, sharingErrorCode);
326             } else {
327                 SHARING_LOGI("default return action %{public}hhu, code %{public}d", action, code);
328                 WfdSinkHiSysEvent::GetInstance().P2PReportError(__func__, SinkErrorCode::WIFI_DISPLAY_P2P_FAILED);
329             }
330         }
331     }
332 }
333 
OnConfigChanged(Wifi::CfgType type,char * data,int32_t dataLen)334 void WfdSinkScene::WfdP2pCallback::OnConfigChanged(Wifi::CfgType type, char *data, int32_t dataLen)
335 {
336     SHARING_LOGD("trace.");
337 }
338 
OnP2pChrErrCodeReport(const int errCode)339 void WfdSinkScene::WfdP2pCallback::OnP2pChrErrCodeReport(const int errCode)
340 {
341     SHARING_LOGD("trace.");
342 }
343 
OnWifiStateChanged(int state)344 void WfdSinkScene::WifiCallback::OnWifiStateChanged(int state)
345 {
346     SHARING_LOGI("OnWifiStateChanged state %{public}d", state);
347     if (state == static_cast<int32_t>(Wifi::WifiState::ENABLED)) {
348         auto parent = parent_.lock();
349         if (parent && parent->isSinkRunning_) {
350             parent->WfdP2pStart();
351         }
352     }
353 }
354 
OnWifiConnectionChanged(int state,const OHOS::Wifi::WifiLinkedInfo & info)355 void WfdSinkScene::WifiCallback::OnWifiConnectionChanged(int state, const OHOS::Wifi::WifiLinkedInfo &info)
356 {
357     SHARING_LOGI("OnWifiConnectionChanged state %{public}d", state);
358     if (state == static_cast<int32_t>(Wifi::ConnState::CONNECTED) ||
359         state == static_cast<int32_t>(Wifi::ConnState::DISCONNECTED)) {
360         auto parent = parent_.lock();
361         if (!parent) {
362             return;
363         }
364         std::string mac;
365         {
366             std::unique_lock<std::mutex> lock(parent->currentConnectDevMutex_);
367             mac = parent->currentConnectDev_.mac;
368         }
369         if (parent->isSinkRunning_ && mac == "") {
370             parent->WfdP2pStart();
371         }
372     }
373 }
374 
OnWifiRssiChanged(int rssi)375 void WfdSinkScene::WifiCallback::OnWifiRssiChanged(int rssi)
376 {
377     SHARING_LOGD("trace.");
378 }
379 
OnWifiWpsStateChanged(int state,const std::string & pinCode)380 void WfdSinkScene::WifiCallback::OnWifiWpsStateChanged(int state, const std::string &pinCode)
381 {
382     SHARING_LOGD("trace.");
383 }
384 
OnStreamChanged(int direction)385 void WfdSinkScene::WifiCallback::OnStreamChanged(int direction)
386 {
387     SHARING_LOGD("trace.");
388 }
389 
OnDeviceConfigChanged(OHOS::Wifi::ConfigChange value)390 void WfdSinkScene::WifiCallback::OnDeviceConfigChanged(OHOS::Wifi::ConfigChange value)
391 {
392     SHARING_LOGD("trace.");
393 }
394 
OnChange()395 void WfdSinkScene::DeviceNameObserver::OnChange()
396 {
397     SHARING_LOGI("deviceName observer onChange");
398     auto scene = scene_.lock();
399     if (scene && scene->isSinkRunning_) {
400         scene->InitP2pName();
401     }
402 }
403 
WfdSinkScene()404 WfdSinkScene::WfdSinkScene()
405 {
406     SHARING_LOGI("id: %{public}u.", GetId());
407     currentConnectDev_.state = ConnectionState::DISCONNECTED;
408 }
409 
~WfdSinkScene()410 WfdSinkScene::~WfdSinkScene()
411 {
412     SHARING_LOGI("id: %{public}u.", GetId());
413     Release();
414 }
415 
Initialize()416 void WfdSinkScene::Initialize()
417 {
418     SHARING_LOGD("trace.");
419     SharingValue::Ptr values = nullptr;
420 
421     auto ret = Config::GetInstance().GetConfig("sharingWfd", "ctrlport", "defaultWfdCtrlport", values);
422     if (ret == CONFIGURE_ERROR_NONE) {
423         values->GetValue<int32_t>(ctrlPort_);
424     }
425 
426     ret = Config::GetInstance().GetConfig("sharingWfd", "abilityLimit", "accessDevMaximum", values);
427     if (ret == CONFIGURE_ERROR_NONE) {
428         values->GetValue<int32_t>(accessDevMaximum_);
429     }
430 
431     ret = Config::GetInstance().GetConfig("sharingWfd", "abilityLimit", "surfaceMaximum", values);
432     if (ret == CONFIGURE_ERROR_NONE) {
433         values->GetValue<int32_t>(surfaceMaximum_);
434     }
435 
436     ret = Config::GetInstance().GetConfig("sharingWfd", "abilityLimit", "foregroundMaximum", values);
437     if (ret == CONFIGURE_ERROR_NONE) {
438         values->GetValue<int32_t>(foregroundMaximum_);
439     }
440 
441     ret = Config::GetInstance().GetConfig("sharingWfd", "mediaFormat", "videoCodec", values);
442     if (ret == CONFIGURE_ERROR_NONE) {
443         int32_t videoCodec;
444         values->GetValue<int32_t>(videoCodec);
445         videoCodecId_ = static_cast<CodecId>(videoCodec);
446     }
447 
448     ret = Config::GetInstance().GetConfig("sharingWfd", "mediaFormat", "videoFormat", values);
449     if (ret == CONFIGURE_ERROR_NONE) {
450         int32_t videoFormat;
451         values->GetValue<int32_t>(videoFormat);
452         videoFormatId_ = static_cast<VideoFormat>(videoFormat);
453     }
454 
455     ret = Config::GetInstance().GetConfig("sharingWfd", "mediaFormat", "audioCodec", values);
456     if (ret == CONFIGURE_ERROR_NONE) {
457         int32_t audioCodec;
458         values->GetValue<int32_t>(audioCodec);
459         audioCodecId_ = static_cast<CodecId>(audioCodec);
460     }
461 
462     ret = Config::GetInstance().GetConfig("sharingWfd", "mediaFormat", "audioFormat", values);
463     if (ret == CONFIGURE_ERROR_NONE) {
464         int32_t audioFormat;
465         values->GetValue<int32_t>(audioFormat);
466         audioFormatId_ = static_cast<AudioFormat>(audioFormat);
467     }
468 
469     RegisterP2pListener();
470     RegisterWifiStatusChangeListener();
471     RegisterDevNameObserver();
472     InitP2pName();
473     isInitialized_ = true;
474     RegisterWfdAbilityListener();
475 }
476 
OnWifiAbilityResume()477 void WfdSinkScene::OnWifiAbilityResume()
478 {
479     SHARING_LOGI("%{public}s.", __FUNCTION__);
480     if (isInitialized_) {
481         return;
482     }
483     RegisterP2pListener();
484     RegisterWifiStatusChangeListener();
485     InitP2pName();
486     isInitialized_ = true;
487 }
488 
OnWifiAbilityDied()489 void WfdSinkScene::OnWifiAbilityDied()
490 {
491     SHARING_LOGI("%{public}s.", __FUNCTION__);
492     std::string mac;
493     {
494         std::unique_lock<std::mutex> lock(currentConnectDevMutex_);
495         mac = currentConnectDev_.mac;
496     }
497     if (mac != "") {
498         OnP2pPeerDisconnected(mac);
499     }
500     isInitialized_ = false;
501 }
502 
RegisterDevNameObserver()503 void WfdSinkScene::RegisterDevNameObserver()
504 {
505     SHARING_LOGI("RegisterDevNameObserver");
506     if (deviceNameObserver_ != nullptr) {
507         SHARING_LOGI("unregister old name observer");
508         UnRegisterDevNameObserver();
509     }
510 
511     deviceNameObserver_ = new (std::nothrow) DeviceNameObserver(shared_from_this());
512     if (deviceNameObserver_ == nullptr) {
513         SHARING_LOGE("new deviceNameObserver error");
514         return;
515     }
516     int32_t ret = DataShareHelper::GetInstance().RegisterObserver(deviceNameObserver_);
517     SHARING_LOGI("register name observer ret=%{public}d", ret);
518 }
519 
UnRegisterDevNameObserver()520 void WfdSinkScene::UnRegisterDevNameObserver()
521 {
522     int32_t ret = DataShareHelper::GetInstance().UnregisterObserver(deviceNameObserver_);
523     SHARING_LOGI("unregister name observer ret=%{public}d", ret);
524     deviceNameObserver_ = nullptr;
525 }
526 
InitP2pName()527 void WfdSinkScene::InitP2pName()
528 {
529     DmKit::InitDeviceManager();
530     std::string deviceName;
531     if (DeviceManager::GetInstance().GetLocalDisplayDeviceName(DM_PKG_NAME, DM_MAX_NAME_LENGTH, deviceName) != DM_OK) {
532         SHARING_LOGW("getLocalDeviceInfo from dm failed");
533     } else {
534         if (p2pInstance_) {
535             p2pInstance_->SetP2pDeviceName(deviceName);
536         }
537     }
538 }
539 
RegisterP2pListener()540 void WfdSinkScene::RegisterP2pListener()
541 {
542     p2pInstance_ = Wifi::WifiP2p::GetInstance(WIFI_P2P_ABILITY_ID);
543     RETURN_IF_NULL(p2pInstance_);
544     sptr<WfdP2pCallback> wfdP2pCallback(new WfdP2pCallback(shared_from_this()));
545     std::vector<std::string> event = {EVENT_P2P_PEER_DEVICE_CHANGE, EVENT_P2P_CONN_STATE_CHANGE,
546                                       EVENT_P2P_GC_JOIN_GROUP, EVENT_P2P_GC_LEAVE_GROUP, EVENT_P2P_ACTION_RESULT};
547     p2pInstance_->RegisterCallBack(wfdP2pCallback, event);
548 }
549 
RegisterWifiStatusChangeListener()550 void WfdSinkScene::RegisterWifiStatusChangeListener()
551 {
552     auto deviceInstance = Wifi::WifiDevice::GetInstance(WIFI_DEVICE_ABILITY_ID);
553     RETURN_IF_NULL(deviceInstance);
554     auto callback = sptr<Wifi::IWifiDeviceCallBack> (new WifiCallback(shared_from_this()));
555     std::vector<std::string> events = {EVENT_STA_POWER_STATE_CHANGE, EVENT_STA_CONN_STATE_CHANGE};
556     deviceInstance->RegisterCallBack(callback, events);
557 }
558 
Release()559 void WfdSinkScene::Release()
560 {
561     SHARING_LOGD("trace.");
562     UnRegisterWfdAbilityListener();
563     UnRegisterDevNameObserver();
564     std::unique_lock<std::mutex> lock(mutex_);
565     auto sharingAdapter = sharingAdapter_.lock();
566     if (sharingAdapter != nullptr) {
567         for (auto &item : devConnectionMap_) {
568             uint32_t contextId = INVALID_ID;
569             uint32_t agentId = INVALID_ID;
570             if (item.second == nullptr) {
571                 continue;
572             }
573 
574             contextId = item.second->contextId;
575             agentId = item.second->agentId;
576 
577             if ((contextId == INVALID_ID) || (agentId == INVALID_ID)) {
578                 continue;
579             }
580 
581             auto sessionMsg = std::make_shared<WfdSinkSessionEventMsg>();
582             sessionMsg->type = EVENT_SESSION_TEARDOWN;
583             sessionMsg->toMgr = MODULE_CONTEXT;
584             sessionMsg->dstId = contextId;
585             sessionMsg->agentId = agentId;
586 
587             SharingEvent event;
588             event.eventMsg = std::move(sessionMsg);
589             sharingAdapter->ForwardEvent(contextId, agentId, event, true);
590 
591             P2pRemoveClient(*(item.second));
592 
593             sharingAdapter->DestroyAgent(contextId, agentId);
594         }
595     }
596 
597     devConnectionMap_.clear();
598     devSurfaceItemMap_.clear();
599     p2pInstance_.reset();
600 }
601 
OnDomainMsg(std::shared_ptr<BaseDomainMsg> & msg)602 void WfdSinkScene::OnDomainMsg(std::shared_ptr<BaseDomainMsg> &msg)
603 {
604     SHARING_LOGD("trace.");
605 }
606 
OnRequest(std::shared_ptr<BaseMsg> msg,std::shared_ptr<BaseMsg> & reply)607 void WfdSinkScene::OnRequest(std::shared_ptr<BaseMsg> msg, std::shared_ptr<BaseMsg> &reply)
608 {
609     SHARING_LOGD("trace.");
610     RETURN_IF_NULL(msg);
611     SHARING_LOGI("recv msg, msg id: %{public}d.", msg->GetMsgId());
612     switch (msg->GetMsgId()) {
613         case WfdSinkStartReq::MSG_ID: {
614             auto data = std::static_pointer_cast<WfdSinkStartReq>(msg);
615             auto rsp = std::make_shared<WfdCommonRsp>();
616 
617             rsp->ret = HandleStart(data, rsp);
618             reply = std::static_pointer_cast<BaseMsg>(rsp);
619             break;
620         }
621         case WfdSinkStopReq::MSG_ID: {
622             auto data = std::static_pointer_cast<WfdSinkStopReq>(msg);
623             auto rsp = std::make_shared<WfdCommonRsp>();
624 
625             rsp->ret = HandleStop(data, rsp);
626             reply = std::static_pointer_cast<BaseMsg>(rsp);
627             break;
628         }
629         case WfdAppendSurfaceReq::MSG_ID: {
630             auto data = std::static_pointer_cast<WfdAppendSurfaceReq>(msg);
631             auto rsp = std::make_shared<WfdCommonRsp>();
632 
633             rsp->ret = HandleAppendSurface(data, rsp);
634             reply = std::static_pointer_cast<BaseMsg>(rsp);
635             break;
636         }
637         case WfdRemoveSurfaceReq::MSG_ID: {
638             auto data = std::static_pointer_cast<WfdRemoveSurfaceReq>(msg);
639             auto rsp = std::make_shared<WfdCommonRsp>();
640 
641             rsp->ret = HandleRemoveSurface(data, rsp);
642             reply = std::static_pointer_cast<BaseMsg>(rsp);
643             break;
644         }
645         case SetMediaFormatReq::MSG_ID: {
646             auto data = std::static_pointer_cast<SetMediaFormatReq>(msg);
647             auto rsp = std::make_shared<WfdCommonRsp>();
648 
649             rsp->ret = HandleSetMediaFormat(data, rsp);
650             reply = std::static_pointer_cast<BaseMsg>(rsp);
651             break;
652         }
653         case SetSceneTypeReq::MSG_ID: {
654             auto data = std::static_pointer_cast<SetSceneTypeReq>(msg);
655             auto rsp = std::make_shared<WfdCommonRsp>();
656 
657             rsp->ret = HandleSetSceneType(data, rsp);
658             reply = std::static_pointer_cast<BaseMsg>(rsp);
659             break;
660         }
661         case WfdPlayReq::MSG_ID: {
662             auto data = std::static_pointer_cast<WfdPlayReq>(msg);
663             auto rsp = std::make_shared<WfdCommonRsp>();
664 
665             rsp->ret = HandlePlay(data, rsp);
666             reply = std::static_pointer_cast<BaseMsg>(rsp);
667             break;
668         }
669         case WfdPauseReq::MSG_ID: {
670             auto data = std::static_pointer_cast<WfdPauseReq>(msg);
671             auto rsp = std::make_shared<WfdCommonRsp>();
672 
673             rsp->ret = HandlePause(data, rsp);
674             reply = std::static_pointer_cast<BaseMsg>(rsp);
675             break;
676         }
677         case MuteReq::MSG_ID: {
678             auto data = std::static_pointer_cast<MuteReq>(msg);
679             auto rsp = std::make_shared<WfdCommonRsp>();
680 
681             rsp->ret = HandleMute(data, rsp);
682             reply = std::static_pointer_cast<BaseMsg>(rsp);
683             break;
684         }
685         case UnMuteReq::MSG_ID: {
686             auto data = std::static_pointer_cast<UnMuteReq>(msg);
687             auto rsp = std::make_shared<WfdCommonRsp>();
688 
689             rsp->ret = HandleUnMute(data, rsp);
690             reply = std::static_pointer_cast<BaseMsg>(rsp);
691             break;
692         }
693         case WfdCloseReq::MSG_ID: {
694             auto data = std::static_pointer_cast<WfdCloseReq>(msg);
695             auto rsp = std::make_shared<WfdCommonRsp>();
696 
697             rsp->ret = HandleClose(data, rsp);
698             reply = std::static_pointer_cast<BaseMsg>(rsp);
699             break;
700         }
701         case GetSinkConfigReq::MSG_ID: {
702             auto data = std::static_pointer_cast<GetSinkConfigReq>(msg);
703             auto rsp = std::make_shared<GetSinkConfigRsp>();
704 
705             rsp->foregroundMaximum = INVALID_ID;
706             HandleGetConfig(data, rsp);
707             reply = std::static_pointer_cast<BaseMsg>(rsp);
708             break;
709         }
710         case WfdGetBoundDevicesReq::MSG_ID: {
711             auto data = std::static_pointer_cast<WfdGetBoundDevicesReq>(msg);
712             auto rsp = std::make_shared<WfdGetBoundDevicesRsp>();
713 
714             HandleGetBoundDevices(data, rsp);
715             reply = std::static_pointer_cast<BaseMsg>(rsp);
716             break;
717         }
718         case WfdDeleteBoundDeviceReq::MSG_ID: {
719             auto data = std::static_pointer_cast<WfdDeleteBoundDeviceReq>(msg);
720             auto rsp = std::make_shared<WfdCommonRsp>();
721 
722             HandleDeleteBoundDevice(data, rsp);
723             reply = std::static_pointer_cast<BaseMsg>(rsp);
724             break;
725         }
726         default:
727             SHARING_LOGW("unknown msg request.");
728             break;
729     }
730 }
731 
SetWifiScene(uint32_t scene)732 void WfdSinkScene::SetWifiScene(uint32_t scene)
733 {
734     SHARING_LOGI("SetWifiScene %{public}u start", scene);
735     std::string ifName = "p2p0";
736     Hid2dUpperScene upperScene;
737     upperScene.scene = scene;
738     upperScene.fps = -1;
739     upperScene.bw = 0;
740     if (Hid2dSetUpperScene(ifName.c_str(), &upperScene) != 0) {
741         SHARING_LOGE("SetWifiScene scene: %{public}u error", scene);
742     }
743     SHARING_LOGI("SetWifiScene %{public}u over", scene);
744 }
745 
HandleStart(std::shared_ptr<WfdSinkStartReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)746 int32_t WfdSinkScene::HandleStart(std::shared_ptr<WfdSinkStartReq> &msg, std::shared_ptr<WfdCommonRsp> &reply)
747 {
748     SHARING_LOGD("trace.");
749     (void)msg;
750     (void)reply;
751     if (isSinkRunning_) {
752         SHARING_LOGW("p2p sink is running.");
753         return 0;
754     }
755     RETURN_INVALID_IF_NULL(p2pInstance_);
756     int32_t ret = 0;
757     int32_t status = 0;
758     p2pInstance_->GetP2pEnableStatus(status);
759     switch (status) {
760         case (int32_t)Wifi::P2pState::P2P_STATE_NONE:
761         case (int32_t)Wifi::P2pState::P2P_STATE_IDLE:
762         case (int32_t)Wifi::P2pState::P2P_STATE_STARTING:
763         case (int32_t)Wifi::P2pState::P2P_STATE_CLOSING:
764             WfdSinkHiSysEvent::GetInstance().P2PReportError(__func__,
765                                                             SinkErrorCode::WIFI_DISPLAY_P2P_DISCONNECTED_STATE_CLOSED);
766             OnInnerError(0, 0, SharingErrorCode::ERR_STATE_EXCEPTION, "HandleStart current p2p state: CLOSING");
767             ret = -1;
768             break;
769         case (int32_t)Wifi::P2pState::P2P_STATE_STARTED:
770             isSinkRunning_ = true;
771             WfdP2pStart();
772             break;
773         case (int32_t)Wifi::P2pState::P2P_STATE_CLOSED:
774             if (Wifi::ErrCode::WIFI_OPT_SUCCESS != p2pInstance_->EnableP2p()) {
775                 SHARING_LOGE("EnableP2p failed");
776                 return -1;
777             }
778             isSinkRunning_ = true;
779             WfdP2pStart();
780             break;
781         default:
782             SHARING_LOGI("none process case.");
783             break;
784     }
785 
786     return ret;
787 }
788 
HandleStop(std::shared_ptr<WfdSinkStopReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)789 int32_t WfdSinkScene::HandleStop(std::shared_ptr<WfdSinkStopReq> &msg, std::shared_ptr<WfdCommonRsp> &reply)
790 {
791     SHARING_LOGD("handle stop, now connect device num: %{public}zu.", devConnectionMap_.size());
792     (void)msg;
793     (void)reply;
794     if (!isSinkRunning_) {
795         SHARING_LOGW("p2p sink is not running.");
796         return -1;
797     }
798 
799     isSinkRunning_ = false;
800     WfdP2pStop();
801 
802     return 0;
803 }
804 
HandleAppendSurface(std::shared_ptr<WfdAppendSurfaceReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)805 int32_t WfdSinkScene::HandleAppendSurface(std::shared_ptr<WfdAppendSurfaceReq> &msg,
806                                           std::shared_ptr<WfdCommonRsp> &reply)
807 {
808     SHARING_LOGD("trace.");
809     (void)reply;
810     RETURN_INVALID_IF_NULL(msg);
811     auto sharingAdapter = sharingAdapter_.lock();
812     RETURN_INVALID_IF_NULL(sharingAdapter);
813 
814     {
815         std::unique_lock<std::mutex> lock(mutex_);
816         auto itemDev = devConnectionMap_.find(msg->deviceId);
817         if (itemDev == devConnectionMap_.end() || itemDev->second == nullptr) {
818             lock.unlock();
819             SHARING_LOGE("can not find dev, mac: %{private}s.", GetAnonymousMAC(msg->deviceId).c_str());
820             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandleAppendSurface can't find the dev");
821             WfdSinkHiSysEvent::GetInstance().ReportError(__func__, "", SinkStage::SESSION_NEGOTIATION,
822                                                         SinkErrorCode::WIFI_DISPLAY_BAD_PARAMETER);
823             return -1;
824         }
825         int32_t surfaceNum = 0;
826         for (auto itemSurface = devSurfaceItemMap_.begin(); itemSurface != devSurfaceItemMap_.end();) {
827             if (!itemSurface->second->deleting) {
828                 surfaceNum++;
829             }
830             itemSurface++;
831         }
832 
833         if (surfaceNum >= surfaceMaximum_) {
834             lock.unlock();
835             SHARING_LOGE("surface is too much.");
836             OnInnerError(0, 0, SharingErrorCode::ERR_SERVICE_LIMIT, "HandleAppendSurface surface is too much");
837             WfdSinkHiSysEvent::GetInstance().ReportError(__func__, "", SinkStage::SESSION_NEGOTIATION,
838                                                         SinkErrorCode::WIFI_DISPLAY_ADD_SURFACE_ERROR);
839             return -1;
840         }
841 
842         sptr<IBufferProducer> producer = iface_cast<IBufferProducer>(msg->surface);
843         sptr<Surface> surfacePtr = Surface::CreateSurfaceAsProducer(producer);
844         if (surfacePtr == nullptr) {
845             SHARING_LOGE("invalid surface.");
846             return -1;
847         }
848 
849         uint64_t surfaceId = surfacePtr->GetUniqueId();
850         SHARING_LOGI("get surfaceId %{public}" PRIx64 ".", surfaceId);
851         if (devSurfaceItemMap_.count(surfaceId)) {
852             SHARING_LOGW("this surface is using, surfaceId: %{public}" PRIx64 ".", surfaceId);
853             lock.unlock();
854             OnInnerError(0, 0, SharingErrorCode::ERR_STATE_EXCEPTION, "HandleAppendSurface this surface is using");
855             WfdSinkHiSysEvent::GetInstance().ReportError(__func__, "", SinkStage::SESSION_NEGOTIATION,
856                                                         SinkErrorCode::WIFI_DISPLAY_ADD_SURFACE_ERROR);
857             return ERR_STATE_EXCEPTION;
858         }
859 
860         int32_t foregroundSurfaceNum = 0;
861         for (auto item : devSurfaceItemMap_) {
862             if ((item.second != nullptr) && (item.second->deviceId == msg->deviceId) && (!item.second->deleting)) {
863                 OnInnerError(0, 0, SharingErrorCode::ERR_STATE_EXCEPTION, "Only one surface can be set.");
864                 return ERR_STATE_EXCEPTION;
865             }
866 
867             if (item.second != nullptr && item.second->sceneType == SceneType::FOREGROUND) {
868                 foregroundSurfaceNum++;
869             }
870         }
871 
872         auto devSurfaceItem = std::make_shared<DevSurfaceItem>();
873         devSurfaceItem->contextId = itemDev->second->contextId;
874         devSurfaceItem->agentId = itemDev->second->agentId;
875         devSurfaceItem->deviceId = itemDev->second->mac;
876         devSurfaceItem->surfacePtr = surfacePtr;
877         devSurfaceItem->sceneType = (foregroundSurfaceNum >= foregroundMaximum_) ? BACKGROUND : FOREGROUND;
878         devSurfaceItemMap_.emplace(surfaceId, devSurfaceItem);
879 
880         if (itemDev->second->isRunning) {
881             uint32_t contextId = itemDev->second->contextId;
882             uint32_t agentId = itemDev->second->agentId;
883 
884             auto startSessionMsg = std::make_shared<WfdSinkSessionEventMsg>();
885             startSessionMsg->type = EVENT_WFD_REQUEST_IDR;
886             startSessionMsg->toMgr = MODULE_CONTEXT;
887             startSessionMsg->dstId = contextId;
888             startSessionMsg->agentId = agentId;
889 
890             SharingEvent event;
891             event.eventMsg = std::move(startSessionMsg);
892             if (sharingAdapter) {
893                 sharingAdapter->ForwardEvent(contextId, agentId, event, false);
894                 sharingAdapter->AppendSurface(itemDev->second->contextId, itemDev->second->agentId, surfacePtr,
895                                               devSurfaceItem->sceneType);
896             }
897             itemDev->second->state = ConnectionState::PLAYING;
898             OnConnectionChanged(*itemDev->second);
899         }
900     }
901     return 0;
902 }
903 
HandleRemoveSurface(std::shared_ptr<WfdRemoveSurfaceReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)904 int32_t WfdSinkScene::HandleRemoveSurface(std::shared_ptr<WfdRemoveSurfaceReq> &msg,
905                                           std::shared_ptr<WfdCommonRsp> &reply)
906 {
907     SHARING_LOGD("trace.");
908     (void)reply;
909     RETURN_INVALID_IF_NULL(msg);
910     auto sharingAdapter = sharingAdapter_.lock();
911     RETURN_INVALID_IF_NULL(sharingAdapter);
912     {
913         std::unique_lock<std::mutex> lock(mutex_);
914         auto itemDev = devConnectionMap_.find(msg->deviceId);
915         if (itemDev == devConnectionMap_.end() || itemDev->second == nullptr) {
916             lock.unlock();
917             SHARING_LOGE("can not find dev, mac: %{private}s.", GetAnonymousMAC(msg->deviceId).c_str());
918             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandleRemoveSurface can't find the dev");
919             WfdSinkHiSysEvent::GetInstance().ReportError(__func__, "", SinkStage::SESSION_NEGOTIATION,
920                                                         SinkErrorCode::WIFI_DISPLAY_BAD_PARAMETER);
921             return -1;
922         }
923 
924         auto item = devSurfaceItemMap_.find(msg->surfaceId);
925         if (item == devSurfaceItemMap_.end()) {
926             lock.unlock();
927             SHARING_LOGE("can not find surfaceid, surfaceid: %{public}" PRId64 ".", msg->surfaceId);
928             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandleAppendSurface can't find the dev");
929             return -1;
930         }
931 
932         SHARING_LOGW("del surface, surfaceid: %{public}" PRId64 ".", msg->surfaceId);
933         sharingAdapter->RemoveSurface(itemDev->second->contextId, itemDev->second->agentId, msg->surfaceId);
934     }
935 
936     return 0;
937 }
938 
HandleSetMediaFormat(std::shared_ptr<SetMediaFormatReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)939 int32_t WfdSinkScene::HandleSetMediaFormat(std::shared_ptr<SetMediaFormatReq> &msg,
940                                            std::shared_ptr<WfdCommonRsp> &reply)
941 {
942     SHARING_LOGD("trace.");
943     (void)reply;
944     RETURN_INVALID_IF_NULL(msg);
945     {
946         std::unique_lock<std::mutex> lock(mutex_);
947         auto itemDev = devConnectionMap_.find(msg->deviceId);
948         if (itemDev == devConnectionMap_.end() || itemDev->second == nullptr) {
949             lock.unlock();
950             SHARING_LOGE("can not find dev, mac: %{private}s.", GetAnonymousMAC(msg->deviceId).c_str());
951             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandleSetMediaFormat can not find dev");
952             WfdSinkHiSysEvent::GetInstance().ReportError(__func__, "", SinkStage::SESSION_NEGOTIATION,
953                                                         SinkErrorCode::WIFI_DISPLAY_BAD_PARAMETER);
954             return -1;
955         }
956         itemDev->second->videoCodecId = static_cast<CodecId>(msg->videoAttr.codecType);
957         itemDev->second->videoFormatId = static_cast<VideoFormat>(msg->videoAttr.formatId);
958         itemDev->second->audioCodecId = static_cast<CodecId>(msg->audioAttr.codecType);
959         itemDev->second->audioFormatId = static_cast<AudioFormat>(msg->audioAttr.formatId);
960     }
961 
962     return 0;
963 }
964 
HandleSetSceneType(std::shared_ptr<SetSceneTypeReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)965 int32_t WfdSinkScene::HandleSetSceneType(std::shared_ptr<SetSceneTypeReq> &msg, std::shared_ptr<WfdCommonRsp> &reply)
966 {
967     SHARING_LOGD("trace.");
968     (void)reply;
969     RETURN_INVALID_IF_NULL(msg);
970     auto sharingAdapter = sharingAdapter_.lock();
971     RETURN_INVALID_IF_NULL(sharingAdapter);
972 
973     uint32_t contextId = INVALID_ID;
974     uint32_t agentId = INVALID_ID;
975     {
976         std::unique_lock<std::mutex> lock(mutex_);
977         auto itemDev = devConnectionMap_.find(msg->deviceId);
978         if (itemDev == devConnectionMap_.end() || itemDev->second == nullptr) {
979             lock.unlock();
980             SHARING_LOGE("can not find dev, mac: %{private}s.", GetAnonymousMAC(msg->deviceId).c_str());
981             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandleSetSceneType can not find dev");
982             return -1;
983         }
984 
985         auto itemSurface = devSurfaceItemMap_.find(msg->surfaceId);
986         if (itemSurface == devSurfaceItemMap_.end() || itemSurface->second == nullptr
987             || itemSurface->second->deleting) {
988             lock.unlock();
989             SHARING_LOGE("can not find surfaceid, surfaceid: %{public}" PRId64 ".", msg->surfaceId);
990             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandleSetSceneType can't find the surfaceId");
991             return -1;
992         }
993 
994         contextId = itemDev->second->contextId;
995         agentId = itemDev->second->agentId;
996 
997         uint32_t foregroundSurfaceNum = 1;
998         if (msg->sceneType == SceneType::FOREGROUND) {
999             for (auto item : devSurfaceItemMap_) {
1000                 if ((item.first == msg->surfaceId) && (!item.second->deleting)) {
1001                     continue;
1002                 }
1003 
1004                 if (item.second->sceneType == SceneType::FOREGROUND) {
1005                     foregroundSurfaceNum++;
1006                 }
1007             }
1008 
1009             if (foregroundSurfaceNum > static_cast<uint32_t>(foregroundMaximum_)) {
1010                 lock.unlock();
1011                 SHARING_LOGE("foreground surfaces is too much.");
1012                 OnInnerError(0, 0, SharingErrorCode::ERR_SERVICE_LIMIT,
1013                              "HandleSetSceneType foreground surfaces is too much");
1014                 return -1;
1015             } else {
1016                 itemSurface->second->sceneType = SceneType::FOREGROUND;
1017             }
1018         } else {
1019             itemSurface->second->sceneType = SceneType::BACKGROUND;
1020         }
1021     }
1022 
1023     if ((contextId == INVALID_ID) || (agentId == INVALID_ID)) {
1024         SHARING_LOGW("invalid contextId: %{public}u, agentId: %{public}u.", contextId, agentId);
1025         return 0;
1026     }
1027 
1028     bool keyFrame = msg->sceneType == SceneType::BACKGROUND ? true : false;
1029     auto ret = sharingAdapter->SetKeyPlay(contextId, agentId, msg->surfaceId, keyFrame);
1030     if (!keyFrame) {
1031         sharingAdapter->SetKeyRedirect(contextId, agentId, msg->surfaceId, true);
1032     }
1033 
1034     return ret;
1035 }
1036 
HandlePlay(std::shared_ptr<WfdPlayReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)1037 int32_t WfdSinkScene::HandlePlay(std::shared_ptr<WfdPlayReq> &msg, std::shared_ptr<WfdCommonRsp> &reply)
1038 {
1039     SHARING_LOGD("trace.");
1040     (void)reply;
1041     RETURN_INVALID_IF_NULL(msg);
1042     auto sharingAdapter = sharingAdapter_.lock();
1043     RETURN_INVALID_IF_NULL(sharingAdapter);
1044 
1045     {
1046         std::unique_lock<std::mutex> lock(mutex_);
1047         auto itemDev = devConnectionMap_.find(msg->deviceId);
1048         if (itemDev == devConnectionMap_.end() || itemDev->second == nullptr) {
1049             lock.unlock();
1050             SHARING_LOGE("can not find dev, mac: %{private}s.", GetAnonymousMAC(msg->deviceId).c_str());
1051             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandlePlay can not find dev");
1052             return -1;
1053         }
1054 
1055         uint32_t contextId = itemDev->second->contextId;
1056         uint32_t agentId = itemDev->second->agentId;
1057         if (contextId == INVALID_ID || agentId == INVALID_ID) {
1058             lock.unlock();
1059             SHARING_LOGE("connected, create sink agent failed, devMac: %{private}s.",
1060                          GetAnonymousMAC(msg->deviceId).c_str());
1061             return -1;
1062         }
1063 
1064         if (itemDev->second->isRunning == true) {
1065             lock.unlock();
1066             return sharingAdapter->Resume(contextId, agentId, MEDIA_TYPE_AV);
1067         } else {
1068             itemDev->second->isRunning = true;
1069         }
1070 
1071         lock.unlock();
1072 
1073         auto startSessionMsg = std::make_shared<WfdSinkSessionEventMsg>();
1074         startSessionMsg->type = EVENT_SESSION_INIT;
1075         startSessionMsg->toMgr = MODULE_CONTEXT;
1076         startSessionMsg->dstId = contextId;
1077         startSessionMsg->agentId = agentId;
1078         startSessionMsg->remoteIp = itemDev->second->ip;
1079         {
1080             std::unique_lock<std::mutex> lock(localIpMutex_);
1081             startSessionMsg->localIp = localIp_;
1082         }
1083         startSessionMsg->mac = itemDev->second->mac;
1084         startSessionMsg->remotePort = itemDev->second->ctrlPort;
1085         startSessionMsg->videoFormat = itemDev->second->videoFormatId;
1086         startSessionMsg->audioFormat = itemDev->second->audioFormatId;
1087         startSessionMsg->localPort = SocketUtils::GetAvailableUdpPortPair();
1088         startSessionMsg->wfdParamsInfo = wfdParamsInfo_;
1089 
1090         SharingEvent event;
1091         event.eventMsg = std::move(startSessionMsg);
1092 
1093         sharingAdapter->ForwardEvent(contextId, agentId, event, true);
1094         sharingAdapter->Start(contextId, agentId);
1095 
1096         for (auto &item : devSurfaceItemMap_) {
1097             if ((item.second != nullptr) && (itemDev->first == item.second->deviceId) && (!item.second->deleting)) {
1098                 if (item.second->surfacePtr != nullptr) {
1099                     sharingAdapter->AppendSurface(contextId, agentId, item.second->surfacePtr, item.second->sceneType);
1100                 }
1101             }
1102         }
1103 
1104         sharingAdapter->Play(contextId, agentId);
1105     }
1106 
1107     return 0;
1108 }
1109 
HandlePause(std::shared_ptr<WfdPauseReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)1110 int32_t WfdSinkScene::HandlePause(std::shared_ptr<WfdPauseReq> &msg, std::shared_ptr<WfdCommonRsp> &reply)
1111 {
1112     SHARING_LOGD("trace.");
1113     (void)reply;
1114     RETURN_INVALID_IF_NULL(msg);
1115     auto sharingAdapter = sharingAdapter_.lock();
1116     RETURN_INVALID_IF_NULL(sharingAdapter);
1117 
1118     uint32_t contextId = INVALID_ID;
1119     uint32_t agentId = INVALID_ID;
1120     {
1121         std::unique_lock<std::mutex> lock(mutex_);
1122         auto itemDev = devConnectionMap_.find(msg->deviceId);
1123         if (itemDev == devConnectionMap_.end() || itemDev->second == nullptr) {
1124             lock.unlock();
1125             SHARING_LOGE("can not find dev, mac: %{private}s.", GetAnonymousMAC(msg->deviceId).c_str());
1126             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandlePause can not find dev");
1127             return -1;
1128         }
1129 
1130         contextId = itemDev->second->contextId;
1131         agentId = itemDev->second->agentId;
1132     }
1133 
1134     if ((contextId == INVALID_ID) || (agentId == INVALID_ID)) {
1135         return -1;
1136     }
1137 
1138     return sharingAdapter->Pause(contextId, agentId, MEDIA_TYPE_AV);
1139 }
1140 
HandleMute(std::shared_ptr<MuteReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)1141 int32_t WfdSinkScene::HandleMute(std::shared_ptr<MuteReq> &msg, std::shared_ptr<WfdCommonRsp> &reply)
1142 {
1143     SHARING_LOGD("trace.");
1144     (void)reply;
1145     RETURN_INVALID_IF_NULL(msg);
1146     auto sharingAdapter = sharingAdapter_.lock();
1147     RETURN_INVALID_IF_NULL(sharingAdapter);
1148 
1149     uint32_t contextId = INVALID_ID;
1150     uint32_t agentId = INVALID_ID;
1151     {
1152         std::unique_lock<std::mutex> lock(mutex_);
1153         auto itemDev = devConnectionMap_.find(msg->deviceId);
1154         if (itemDev == devConnectionMap_.end() || itemDev->second == nullptr) {
1155             lock.unlock();
1156             SHARING_LOGE("can not find dev, mac: %{private}s.", GetAnonymousMAC(msg->deviceId).c_str());
1157             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandleMute can not find dev");
1158             return -1;
1159         }
1160 
1161         contextId = itemDev->second->contextId;
1162         agentId = itemDev->second->agentId;
1163     }
1164 
1165     if ((contextId == INVALID_ID) || (agentId == INVALID_ID)) {
1166         return -1;
1167     }
1168 
1169     return sharingAdapter->Pause(contextId, agentId, MEDIA_TYPE_AUDIO);
1170 }
1171 
HandleUnMute(std::shared_ptr<UnMuteReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)1172 int32_t WfdSinkScene::HandleUnMute(std::shared_ptr<UnMuteReq> &msg, std::shared_ptr<WfdCommonRsp> &reply)
1173 {
1174     SHARING_LOGD("trace.");
1175     (void)reply;
1176     RETURN_INVALID_IF_NULL(msg);
1177     auto sharingAdapter = sharingAdapter_.lock();
1178     RETURN_INVALID_IF_NULL(sharingAdapter);
1179 
1180     uint32_t contextId = INVALID_ID;
1181     uint32_t agentId = INVALID_ID;
1182     {
1183         std::unique_lock<std::mutex> lock(mutex_);
1184         auto itemDev = devConnectionMap_.find(msg->deviceId);
1185         if (itemDev == devConnectionMap_.end() || itemDev->second == nullptr) {
1186             lock.unlock();
1187             SHARING_LOGE("can not find dev, mac: %{private}s.", GetAnonymousMAC(msg->deviceId).c_str());
1188             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandleUnMute can not find dev");
1189             return -1;
1190         }
1191 
1192         contextId = itemDev->second->contextId;
1193         agentId = itemDev->second->agentId;
1194     }
1195 
1196     if ((contextId == INVALID_ID) || (agentId == INVALID_ID)) {
1197         return -1;
1198     }
1199 
1200     return sharingAdapter->Resume(contextId, agentId, MEDIA_TYPE_AUDIO);
1201 }
1202 
HandleClose(std::shared_ptr<WfdCloseReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)1203 int32_t WfdSinkScene::HandleClose(std::shared_ptr<WfdCloseReq> &msg, std::shared_ptr<WfdCommonRsp> &reply)
1204 {
1205     SHARING_LOGD("trace.");
1206     (void)reply;
1207     RETURN_INVALID_IF_NULL(msg);
1208     auto sharingAdapter = sharingAdapter_.lock();
1209     RETURN_INVALID_IF_NULL(sharingAdapter);
1210 
1211     uint32_t contextId = INVALID_ID;
1212     uint32_t agentId = INVALID_ID;
1213 
1214     WfdSinkHiSysEvent::GetInstance().ChangeHisysEventScene(SinkBizScene::DISCONNECT_MIRRORING);
1215     WfdSinkHiSysEvent::GetInstance().StartReport(__func__, "", SinkStage::RECEIVE_DISCONNECT_EVENT,
1216                                                 SinkStageRes::SUCCESS);
1217 
1218     ConnectionInfo connectionInfo;
1219     {
1220         std::unique_lock<std::mutex> lock(mutex_);
1221         auto itemDev = devConnectionMap_.find(msg->deviceId);
1222         if (itemDev == devConnectionMap_.end() || itemDev->second == nullptr) {
1223             lock.unlock();
1224             SHARING_LOGE("can not find dev, mac: %{private}s.", GetAnonymousMAC(msg->deviceId).c_str());
1225             OnInnerError(0, 0, SharingErrorCode::ERR_BAD_PARAMETER, "HandleClose can not find dev");
1226             return -1;
1227         }
1228 
1229         connectionInfo.ip = itemDev->second->ip;
1230         connectionInfo.mac = itemDev->second->mac;
1231         connectionInfo.state = ConnectionState::DISCONNECTED;
1232         connectionInfo.surfaceId = itemDev->second->surfaceId;
1233         connectionInfo.deviceName = itemDev->second->deviceName;
1234         connectionInfo.primaryDeviceType = itemDev->second->primaryDeviceType;
1235         connectionInfo.secondaryDeviceType = itemDev->second->secondaryDeviceType;
1236 
1237         contextId = itemDev->second->contextId;
1238         agentId = itemDev->second->agentId;
1239 
1240         for (auto itemSurface = devSurfaceItemMap_.begin(); itemSurface != devSurfaceItemMap_.end();) {
1241             if ((itemSurface->second != nullptr) && (msg->deviceId == itemSurface->second->deviceId)) {
1242                 itemSurface->second->deleting = true;
1243             }
1244             itemSurface++;
1245         }
1246 
1247         P2pRemoveClient(connectionInfo);
1248 
1249         devConnectionMap_.erase(msg->deviceId);
1250     }
1251 
1252     if ((contextId == INVALID_ID) || (agentId == INVALID_ID)) {
1253         return -1;
1254     }
1255 
1256     OnConnectionChanged(connectionInfo);
1257     auto sessionMsg = std::make_shared<WfdSinkSessionEventMsg>();
1258     sessionMsg->type = EVENT_SESSION_TEARDOWN;
1259     sessionMsg->toMgr = MODULE_CONTEXT;
1260     sessionMsg->dstId = contextId;
1261     sessionMsg->agentId = agentId;
1262 
1263     SharingEvent event;
1264     event.eventMsg = std::move(sessionMsg);
1265     sharingAdapter->ForwardEvent(contextId, agentId, event, true);
1266 
1267     return sharingAdapter->DestroyAgent(contextId, agentId);
1268 }
1269 
HandleGetConfig(std::shared_ptr<GetSinkConfigReq> & msg,std::shared_ptr<GetSinkConfigRsp> & reply)1270 int32_t WfdSinkScene::HandleGetConfig(std::shared_ptr<GetSinkConfigReq> &msg, std::shared_ptr<GetSinkConfigRsp> &reply)
1271 {
1272     SHARING_LOGD("trace.");
1273     (void)msg;
1274     RETURN_INVALID_IF_NULL(reply);
1275     reply->accessDevMaximum = static_cast<uint32_t>(accessDevMaximum_);
1276     reply->foregroundMaximum = static_cast<uint32_t>(foregroundMaximum_);
1277     reply->surfaceMaximum = static_cast<uint32_t>(surfaceMaximum_);
1278 
1279     return 0;
1280 }
1281 
HandleGetBoundDevices(std::shared_ptr<WfdGetBoundDevicesReq> & msg,std::shared_ptr<WfdGetBoundDevicesRsp> & reply)1282 int32_t WfdSinkScene::HandleGetBoundDevices(std::shared_ptr<WfdGetBoundDevicesReq> &msg,
1283                                             std::shared_ptr<WfdGetBoundDevicesRsp> &reply)
1284 {
1285     SHARING_LOGI("%{public}s.", __FUNCTION__);
1286     (void)msg;
1287     (void)reply;
1288     reply->trustDevices = wfdTrustListManager_.GetAllBoundDevices();
1289     return 0;
1290 }
1291 
HandleDeleteBoundDevice(std::shared_ptr<WfdDeleteBoundDeviceReq> & msg,std::shared_ptr<WfdCommonRsp> & reply)1292 int32_t WfdSinkScene::HandleDeleteBoundDevice(std::shared_ptr<WfdDeleteBoundDeviceReq> &msg,
1293                                               std::shared_ptr<WfdCommonRsp> &reply)
1294 {
1295     SHARING_LOGI("%{public}s.", __FUNCTION__);
1296     (void)reply;
1297     RETURN_INVALID_IF_NULL(msg);
1298     reply->ret = wfdTrustListManager_.DeleteBoundDeviceGroup(msg->deviceAddress);
1299     return 0;
1300 }
1301 
RegisterWfdAbilityListener()1302 void WfdSinkScene::RegisterWfdAbilityListener()
1303 {
1304     SHARING_LOGI("%{public}s.", __FUNCTION__);
1305     std::unique_lock<std::mutex> lock(mutex_);
1306     auto samgrProxy = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
1307     if (samgrProxy == nullptr) {
1308         SHARING_LOGE("get system ability manager fail");
1309         return;
1310     }
1311     sysAbilityListener_ = new (std::nothrow) WfdSystemAbilityListener(shared_from_this());
1312     if (sysAbilityListener_ == nullptr) {
1313         SHARING_LOGE("sysAbilityListener create failed.");
1314         return;
1315     }
1316     int32_t ret = samgrProxy->SubscribeSystemAbility(WIFI_DEVICE_ABILITY_ID, sysAbilityListener_);
1317     SHARING_LOGI("result is %{public}d.", ret);
1318 }
1319 
UnRegisterWfdAbilityListener()1320 void WfdSinkScene::UnRegisterWfdAbilityListener()
1321 {
1322     SHARING_LOGI("%{public}s.", __FUNCTION__);
1323     std::unique_lock<std::mutex> lock(mutex_);
1324     if (sysAbilityListener_ == nullptr) {
1325         SHARING_LOGE("listener is null");
1326         return;
1327     }
1328     auto samgrProxy = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
1329     if (samgrProxy == nullptr) {
1330         SHARING_LOGE("get system ability manager fail");
1331         return;
1332     }
1333     int32_t ret = samgrProxy->UnSubscribeSystemAbility(WIFI_DEVICE_ABILITY_ID, sysAbilityListener_);
1334     SHARING_LOGI("result is %{public}d.", ret);
1335     sysAbilityListener_ = nullptr;
1336 }
1337 
WfdP2pStart()1338 void WfdSinkScene::WfdP2pStart()
1339 {
1340     SHARING_LOGI("trace.");
1341     if (p2pInstance_) {
1342         Wifi::WifiP2pWfdInfo wfdInfo;
1343         wfdInfo.SetWfdEnabled(true);
1344         wfdInfo.SetDeviceInfo(0x11);
1345         wfdInfo.SetCtrlPort(ctrlPort_);
1346         wfdInfo.SetMaxThroughput(0x00c8);
1347 
1348         p2pInstance_->SetP2pWfdInfo(wfdInfo);
1349         p2pInstance_->StartP2pListen(P2P_LISTEN_PERIOD, P2P_LISTEN_INTERVAL);
1350     }
1351 }
1352 
WfdP2pStop()1353 void WfdSinkScene::WfdP2pStop()
1354 {
1355     SHARING_LOGI("trace.");
1356     std::unique_lock<std::mutex> lock(mutex_);
1357     auto sharingAdapter = sharingAdapter_.lock();
1358     if (sharingAdapter != nullptr) {
1359         for (auto item : devConnectionMap_) {
1360             uint32_t contextId = item.second->contextId;
1361             uint32_t agentId = item.second->agentId;
1362 
1363             if ((contextId != INVALID_ID) && (agentId != INVALID_ID)) {
1364                 auto sessionMsg = std::make_shared<WfdSinkSessionEventMsg>();
1365                 sessionMsg->type = EVENT_SESSION_TEARDOWN;
1366                 sessionMsg->toMgr = MODULE_CONTEXT;
1367                 sessionMsg->dstId = contextId;
1368                 sessionMsg->agentId = agentId;
1369 
1370                 SharingEvent event;
1371                 event.eventMsg = std::move(sessionMsg);
1372                 sharingAdapter->ForwardEvent(contextId, agentId, event, true);
1373 
1374                 P2pRemoveClient(*(item.second));
1375 
1376                 sharingAdapter->DestroyAgent(contextId, agentId);
1377             }
1378         }
1379     }
1380 
1381     if (p2pInstance_) {
1382         p2pInstance_->StopP2pListen();
1383     }
1384 
1385     devSurfaceItemMap_.clear();
1386     devConnectionMap_.clear();
1387 }
1388 
FillAndReportDeviceInfo(const ConnectionInfo & connectionInfo)1389 void WfdSinkScene::FillAndReportDeviceInfo(const ConnectionInfo &connectionInfo)
1390 {
1391     Wifi::WifiP2pGroupInfo group;
1392     p2pInstance_->GetCurrentGroup(group);
1393     int32_t netWorkId = group.GetNetworkId();
1394     Wifi::WifiP2pDevice deviceInfo;
1395     p2pInstance_->QueryP2pLocalDevice(deviceInfo);
1396 
1397     WfdSinkHiSysEvent::SinkHisyseventDevInfo devInfo;
1398     {
1399         std::unique_lock<std::mutex> lock(localIpMutex_);
1400         devInfo.localIp = localIp_.c_str();
1401     }
1402     devInfo.localWifiMac = deviceInfo.GetDeviceAddress();
1403     devInfo.localDevName = deviceInfo.GetDeviceName();
1404     devInfo.localNetId = std::to_string(netWorkId);
1405     devInfo.peerDevName = connectionInfo.deviceName.c_str();
1406     devInfo.peerIp = connectionInfo.ip.c_str();
1407     devInfo.peerNetId = std::to_string(netWorkId);
1408     devInfo.peerWifiMac = connectionInfo.mac.c_str();
1409 
1410     WfdSinkHiSysEvent::GetInstance().SetHiSysEventDevInfo(devInfo);
1411 }
1412 
OnP2pPeerConnected(ConnectionInfo & connectionInfo)1413 void WfdSinkScene::OnP2pPeerConnected(ConnectionInfo &connectionInfo)
1414 {
1415     SHARING_LOGD("trace.");
1416     if (!isSinkRunning_) {
1417         SHARING_LOGW("sink service is not running.");
1418         return;
1419     }
1420 
1421     auto sharingAdapter = sharingAdapter_.lock();
1422     RETURN_IF_NULL(sharingAdapter);
1423 
1424     if (devConnectionMap_.size() >= (uint32_t)accessDevMaximum_) {
1425         SHARING_LOGE("too more device.");
1426         P2pRemoveClient(connectionInfo);
1427 
1428         auto ipcAdapter = ipcAdapter_.lock();
1429         RETURN_IF_NULL(ipcAdapter);
1430 
1431         auto msg = std::make_shared<WfdErrorMsg>();
1432         msg->message = "Maximum number of devices reached";
1433         msg->errorCode = ERR_RECEIVING_LIMIT;
1434 
1435         auto reply = std::static_pointer_cast<BaseMsg>(std::make_shared<WfdCommonRsp>());
1436         ipcAdapter->SendRequest(msg, reply);
1437 
1438         return;
1439     }
1440 
1441     {
1442         std::unique_lock<std::mutex> lock(mutex_);
1443         if (devConnectionMap_.count(connectionInfo.mac)) {
1444             SHARING_LOGW("devcie is alerady connected, mac: %{private}s.", GetAnonymousMAC(connectionInfo.mac).c_str());
1445             return;
1446         }
1447 
1448         uint32_t contextId = INVALID_ID;
1449         uint32_t agentId = INVALID_ID;
1450 
1451         sharingAdapter->CreateAgent(contextId, agentId, AgentType::SINK_AGENT, "WfdSinkSession");
1452         if (contextId == INVALID_ID || agentId == INVALID_ID) {
1453             lock.unlock();
1454             SHARING_LOGE("connected, create sink agent failed, devMac: %{private}s.",
1455                          GetAnonymousMAC(connectionInfo.mac).c_str());
1456             return;
1457         } else {
1458             SHARING_LOGI("connected, create sink agent, contextId: %{public}u, "
1459                 "agentId: %{public}u, devMac: %{private}s, devIp: %{private}s.", contextId, agentId,
1460                 GetAnonymousMAC(connectionInfo.mac).c_str(), GetAnonymousIp(connectionInfo.ip).c_str());
1461                 FillAndReportDeviceInfo(connectionInfo);
1462                 std::chrono::system_clock::time_point startTime = std::chrono::system_clock::now();
1463                 WfdSinkHiSysEvent::GetInstance().GetStartTime(startTime);
1464                 WfdSinkHiSysEvent::GetInstance().ChangeHisysEventScene(SinkBizScene::ESTABLISH_MIRRORING);
1465                 WfdSinkHiSysEvent::GetInstance().StartReport(__func__, "wpa_supplicant", SinkStage::P2P_CONNECT_SUCCESS,
1466                                                             SinkStageRes::SUCCESS);
1467         }
1468 
1469         connectionInfo.contextId = contextId;
1470         connectionInfo.agentId = agentId;
1471         connectionInfo.videoCodecId = videoCodecId_;
1472         connectionInfo.videoFormatId = videoFormatId_;
1473         connectionInfo.audioCodecId = audioCodecId_;
1474         connectionInfo.audioFormatId = audioFormatId_;
1475 
1476         std::shared_ptr<ConnectionInfo> connectionInfoPtr = std::make_shared<ConnectionInfo>(connectionInfo);
1477         RETURN_IF_NULL(connectionInfoPtr);
1478         devConnectionMap_.emplace(connectionInfo.mac, connectionInfoPtr);
1479         SHARING_LOGI("connected, devMac: %{private}s, devIp: %{private}s.", GetAnonymousMAC(connectionInfo.mac).c_str(),
1480             GetAnonymousIp(connectionInfo.ip).c_str());
1481     }
1482     SetWifiScene(1);
1483     OnConnectionChanged(connectionInfo);
1484 }
1485 
OnP2pPeerDisconnected(ConnectionInfo & connectionInfo)1486 void WfdSinkScene::OnP2pPeerDisconnected(ConnectionInfo &connectionInfo)
1487 {
1488     SHARING_LOGD("trace.");
1489     auto sharingAdapter = sharingAdapter_.lock();
1490     RETURN_IF_NULL(sharingAdapter);
1491 
1492     uint32_t contextId = INVALID_ID;
1493     uint32_t agentId = INVALID_ID;
1494     {
1495         std::unique_lock<std::mutex> lock(mutex_);
1496         auto itemDev = devConnectionMap_.find(connectionInfo.mac);
1497         if (itemDev == devConnectionMap_.end()) {
1498             lock.unlock();
1499             SHARING_LOGW("can not find dev, mac: %{private}s.", GetAnonymousMAC(connectionInfo.mac).c_str());
1500             return;
1501         }
1502         contextId = itemDev->second->contextId;
1503         agentId = itemDev->second->agentId;
1504         connectionInfo.surfaceId = itemDev->second->surfaceId;
1505 
1506         for (auto itemSurface = devSurfaceItemMap_.begin(); itemSurface != devSurfaceItemMap_.end();) {
1507             if (connectionInfo.mac == itemSurface->second->deviceId) {
1508                 itemSurface->second->deleting = true;
1509             }
1510             itemSurface++;
1511         }
1512 
1513         P2pRemoveClient(connectionInfo);
1514 
1515         devConnectionMap_.erase(connectionInfo.mac);
1516         SHARING_LOGI("disconnected, contextId: %{public}u, agentId: %{public}u, devMac: %{private}s.", contextId,
1517                      agentId, GetAnonymousMAC(connectionInfo.mac).c_str());
1518     }
1519 
1520     OnConnectionChanged(connectionInfo);
1521 
1522     if ((contextId == INVALID_ID) || (agentId == INVALID_ID)) {
1523         return;
1524     }
1525 
1526     auto sessionMsg = std::make_shared<WfdSinkSessionEventMsg>();
1527     sessionMsg->type = EVENT_SESSION_TEARDOWN;
1528     sessionMsg->toMgr = MODULE_CONTEXT;
1529     sessionMsg->dstId = contextId;
1530     sessionMsg->agentId = agentId;
1531 
1532     SharingEvent event;
1533     event.eventMsg = std::move(sessionMsg);
1534 
1535     sharingAdapter->ForwardEvent(contextId, agentId, event, true);
1536     sharingAdapter->DestroyAgent(contextId, agentId);
1537 }
1538 
OnP2pPeerDisconnected(const std::string & mac)1539 void WfdSinkScene::OnP2pPeerDisconnected(const std::string &mac)
1540 {
1541     SHARING_LOGD("trace.");
1542     uint32_t contextId = INVALID_ID;
1543     uint32_t agentId = INVALID_ID;
1544     std::shared_ptr<ConnectionInfo> connectionInfo = nullptr;
1545     {
1546         std::unique_lock<std::mutex> lock(mutex_);
1547         auto itemDev = devConnectionMap_.find(mac);
1548         if (itemDev == devConnectionMap_.end()) {
1549             lock.unlock();
1550             SHARING_LOGW("can not find dev, mac: %{private}s.", GetAnonymousMAC(mac).c_str());
1551             return;
1552         }
1553         contextId = itemDev->second->contextId;
1554         agentId = itemDev->second->agentId;
1555         connectionInfo = itemDev->second;
1556 
1557         for (auto itemSurface = devSurfaceItemMap_.begin(); itemSurface != devSurfaceItemMap_.end();) {
1558             if (mac == itemSurface->second->deviceId) {
1559                 itemSurface->second->deleting = true;
1560             }
1561             itemSurface++;
1562         }
1563 
1564         SHARING_LOGI("disconnected, contextId: %{public}u, agentId: %{public}u, devMac: %{private}s.", contextId,
1565                      agentId, GetAnonymousMAC(mac).c_str());
1566         P2pRemoveClient(*connectionInfo);
1567 
1568         devConnectionMap_.erase(mac);
1569     }
1570 
1571     if ((contextId == INVALID_ID) || (agentId == INVALID_ID)) {
1572         return;
1573     }
1574 
1575     auto sharingAdapter = sharingAdapter_.lock();
1576     if (sharingAdapter != nullptr) {
1577         sharingAdapter->DestroyAgent(contextId, agentId);
1578     }
1579 
1580     if (connectionInfo != nullptr) {
1581         connectionInfo->state = ConnectionState::DISCONNECTED;
1582         OnConnectionChanged(*connectionInfo);
1583     }
1584 }
1585 
ErrorCodeFiltering(int32_t & code)1586 void WfdSinkScene::ErrorCodeFiltering(int32_t &code)
1587 {
1588     SHARING_LOGD("the error code is %{public}d.", code);
1589     switch (ABSTRACT_ERR_BASE(code)) {
1590         case SharingErrorCode::ERR_CONTEXT_AGENT_BASE: // fall-through
1591         case SharingErrorCode::ERR_SESSION_BASE:
1592             code = SharingErrorCode::ERR_GENERAL_ERROR;
1593             SHARING_LOGD("the error change to %{public}d.", code);
1594             break;
1595         case SharingErrorCode::ERR_PROSUMER_BASE: {
1596             switch (code) {
1597                 case ERR_PROSUMER_START:
1598                     code = SharingErrorCode::ERR_CONNECTION_FAILURE;
1599                     break;
1600                 case ERR_PROSUMER_TIMEOUT:
1601                     code = SharingErrorCode::ERR_CONNECTION_TIMEOUT;
1602                     break;
1603                 case ERR_PROSUMER_DESTROY:
1604                     code = SharingErrorCode::ERR_STATE_EXCEPTION;
1605                     break;
1606                 default:
1607                     code = SharingErrorCode::ERR_GENERAL_ERROR;
1608                     break;
1609             }
1610             break;
1611         }
1612         default:
1613             SHARING_LOGI("none process case.");
1614             break;
1615     }
1616 }
1617 
OnInnerError(uint32_t contextId,uint32_t agentId,SharingErrorCode errorCode,std::string message)1618 void WfdSinkScene::OnInnerError(uint32_t contextId, uint32_t agentId, SharingErrorCode errorCode, std::string message)
1619 {
1620     SHARING_LOGD("trace.");
1621     auto ipcAdapter = ipcAdapter_.lock();
1622     RETURN_IF_NULL(ipcAdapter);
1623 
1624     auto msg = std::make_shared<WfdErrorMsg>();
1625     msg->contextId = contextId;
1626     msg->agentId = agentId;
1627     msg->errorCode = errorCode;
1628 
1629     for (auto &item : devConnectionMap_) {
1630         if ((contextId == item.second->contextId) && (agentId == item.second->agentId)) {
1631             msg->mac = item.second->mac;
1632             break;
1633         }
1634     }
1635 
1636     if (errorCode == SharingErrorCode::ERR_PROSUMER_TIMEOUT) {
1637         msg->message =
1638             "contextId: " + std::to_string(contextId) + ", agentId: " + std::to_string(agentId) + ", producer timeout";
1639     } else {
1640         msg->message = std::move(message);
1641     }
1642 
1643     ErrorCodeFiltering(msg->errorCode);
1644     auto reply = std::static_pointer_cast<BaseMsg>(std::make_shared<WfdCommonRsp>());
1645 
1646     SHARING_LOGW("receive errorCode: %{public}d.", errorCode);
1647     ipcAdapter->SendRequest(msg, reply);
1648 }
1649 
OnInnerError(std::string deviceId,SharingErrorCode errorCode,std::string message)1650 void WfdSinkScene::OnInnerError(std::string deviceId, SharingErrorCode errorCode, std::string message)
1651 {
1652     SHARING_LOGD("trace.");
1653     auto ipcAdapter = ipcAdapter_.lock();
1654     RETURN_IF_NULL(ipcAdapter);
1655 
1656     auto msg = std::make_shared<WfdErrorMsg>();
1657     msg->message = message;
1658     msg->mac = deviceId;
1659     msg->errorCode = errorCode;
1660 
1661     auto reply = std::static_pointer_cast<BaseMsg>(std::make_shared<WfdCommonRsp>());
1662 
1663     SHARING_LOGW("receive errorCode: %{public}d.", errorCode);
1664     ipcAdapter->SendRequest(msg, reply);
1665 }
1666 
OnInnerDestroy(uint32_t contextId,uint32_t agentId,AgentType agentType)1667 void WfdSinkScene::OnInnerDestroy(uint32_t contextId, uint32_t agentId, AgentType agentType)
1668 {
1669     SHARING_LOGI("HandleInnerDestroy, contextId: %{public}u, agentId: %{public}u, agentType: %{public}s.", contextId,
1670                  agentId, std::string(magic_enum::enum_name(agentType)).c_str());
1671 
1672     std::unique_lock<std::mutex> lock(mutex_);
1673     for (auto itemSurface = devSurfaceItemMap_.begin(); itemSurface != devSurfaceItemMap_.end();) {
1674         if ((itemSurface->second != nullptr) && (contextId == itemSurface->second->contextId) &&
1675             (agentId == itemSurface->second->agentId)) {
1676             itemSurface = devSurfaceItemMap_.erase(itemSurface);
1677         } else {
1678             itemSurface++;
1679         }
1680     }
1681 
1682     for (auto &item : devConnectionMap_) {
1683         if ((item.second != nullptr) && (contextId == item.second->contextId) && (agentId == item.second->agentId)) {
1684             ConnectionInfo connectionInfo;
1685             connectionInfo.ip = item.second->ip;
1686             connectionInfo.mac = item.second->mac;
1687             connectionInfo.deviceName = item.second->deviceName;
1688             connectionInfo.primaryDeviceType = item.second->primaryDeviceType;
1689             connectionInfo.secondaryDeviceType = item.second->secondaryDeviceType;
1690             connectionInfo.ctrlPort = item.second->ctrlPort;
1691             connectionInfo.state = ConnectionState::DISCONNECTED;
1692 
1693             SHARING_LOGI(
1694                 "disconnected, contextId: %{public}u, agentId: %{public}u, devMac: %{private}s, devIp: %{private}s.",
1695                 contextId, agentId, GetAnonymousMAC(connectionInfo.mac).c_str(),
1696                 GetAnonymousIp(connectionInfo.ip).c_str());
1697             OnConnectionChanged(connectionInfo);
1698 
1699             P2pRemoveClient(connectionInfo);
1700 
1701             devConnectionMap_.erase(item.second->mac);
1702             break;
1703         }
1704     }
1705 }
1706 
OnInnerEvent(SharingEvent & event)1707 void WfdSinkScene::OnInnerEvent(SharingEvent &event)
1708 {
1709     SHARING_LOGD("trace.");
1710     RETURN_IF_NULL(event.eventMsg);
1711 
1712     SHARING_LOGI("eventType: %{public}s.", std::string(magic_enum::enum_name(event.eventMsg->type)).c_str());
1713     switch (event.eventMsg->type) {
1714         case EventType::EVENT_WFD_NOTIFY_RTSP_PLAYED: {
1715             auto msg = ConvertEventMsg<WfdSceneEventMsg>(event);
1716             if (msg) {
1717                 std::unique_lock<std::mutex> lock(mutex_);
1718                 auto itConnection = devConnectionMap_.find(msg->mac);
1719                 if (itConnection == devConnectionMap_.end()) {
1720                     SHARING_LOGD("can't find dev %{private}s.", GetAnonymousMAC(msg->mac).c_str());
1721                     break;
1722                 }
1723 
1724                 itConnection->second->state = ConnectionState::PLAYING;
1725                 OnConnectionChanged(*itConnection->second);
1726             }
1727             break;
1728         }
1729         case EventType::EVENT_WFD_NOTIFY_RTSP_TEARDOWN: {
1730             auto msg = ConvertEventMsg<WfdSceneEventMsg>(event);
1731             if (msg) {
1732                 OnP2pPeerDisconnected(msg->mac);
1733             }
1734             break;
1735         }
1736         case EventType::EVENT_INTERACTION_ACCELERATION_DONE: {
1737             auto msg = ConvertEventMsg<InteractionEventMsg>(event);
1738             SHARING_LOGD("On acceleration done, contextId: %{public}d agentId: %{public}d.", msg->contextId,
1739                          msg->agentId);
1740             std::unique_lock<std::mutex> lock(mutex_);
1741             for (auto connectInfoPair : devConnectionMap_) {
1742                 if (connectInfoPair.second != nullptr && connectInfoPair.second->contextId == msg->contextId &&
1743                     connectInfoPair.second->agentId == msg->agentId) {
1744                     SHARING_LOGD("On acceleration done, device found.");
1745                     auto connectInfo = connectInfoPair.second;
1746                     connectInfo->surfaceId = msg->surfaceId;
1747 
1748                     OnDecoderAccelerationDone(*connectInfo);
1749                     break;
1750                 }
1751                 SHARING_LOGW("On acceleration done, device not found.");
1752             }
1753             break;
1754         }
1755         case EventType::EVENT_INTERACTION_STATE_REMOVE_SURFACE: {
1756             auto msg = ConvertEventMsg<InteractionEventMsg>(event);
1757             SHARING_LOGD("On state remove surface, agentId: %{public}d.", msg->agentId);
1758             std::unique_lock<std::mutex> lock(mutex_);
1759             devSurfaceItemMap_.erase(msg->surfaceId);
1760             break;
1761         }
1762         case EVENT_INTERACTION_DECODER_DIED: {
1763             auto msg = ConvertEventMsg<InteractionEventMsg>(event);
1764             auto surfaceItem = devSurfaceItemMap_.find(msg->surfaceId);
1765             if (surfaceItem != devSurfaceItemMap_.end() && surfaceItem->second != nullptr) {
1766                 auto itConnection = devConnectionMap_.find(surfaceItem->second->deviceId);
1767                 OnDecoderDied(*itConnection->second);
1768             }
1769             break;
1770         }
1771         default:
1772             SHARING_LOGI("none process case.");
1773             break;
1774     }
1775 }
1776 
OnConnectionChanged(ConnectionInfo & connectionInfo)1777 void WfdSinkScene::OnConnectionChanged(ConnectionInfo &connectionInfo)
1778 {
1779     SHARING_LOGD("trace.");
1780     auto ipcAdapter = ipcAdapter_.lock();
1781     RETURN_IF_NULL(ipcAdapter);
1782 
1783     auto msg = std::make_shared<WfdConnectionChangedMsg>();
1784     msg->ip = connectionInfo.ip;
1785     msg->mac = connectionInfo.mac;
1786     msg->state = connectionInfo.state;
1787     msg->surfaceId = connectionInfo.surfaceId;
1788     msg->deviceName = connectionInfo.deviceName;
1789     msg->primaryDeviceType = connectionInfo.primaryDeviceType;
1790     msg->secondaryDeviceType = connectionInfo.secondaryDeviceType;
1791 
1792     auto reply = std::static_pointer_cast<BaseMsg>(std::make_shared<WfdCommonRsp>());
1793     ipcAdapter->SendRequest(msg, reply);
1794 }
1795 
P2pRemoveClient(ConnectionInfo & connectionInfo)1796 void WfdSinkScene::P2pRemoveClient(ConnectionInfo &connectionInfo)
1797 {
1798     SHARING_LOGI("p2p remove client: %{private}s.", GetAnonymousMAC(connectionInfo.mac).c_str());
1799     {
1800         std::unique_lock<std::mutex> lock(currentConnectDevMutex_);
1801         currentConnectDev_.mac = "";
1802     }
1803     SetWifiScene(0);
1804     if (!p2pInstance_) {
1805         SHARING_LOGE("p2p instance is null");
1806         return;
1807     }
1808 
1809     OHOS::Wifi::GcInfo info;
1810     info.mac = connectionInfo.mac;
1811     info.ip = connectionInfo.ip;
1812     info.host = connectionInfo.deviceName;
1813 
1814     p2pInstance_->RemoveGroupClient(info);
1815 }
1816 
OnDecoderAccelerationDone(ConnectionInfo & connectionInfo)1817 void WfdSinkScene::OnDecoderAccelerationDone(ConnectionInfo &connectionInfo)
1818 {
1819     SHARING_LOGD("trace.");
1820     auto ipcAdapter = ipcAdapter_.lock();
1821     RETURN_IF_NULL(ipcAdapter);
1822 
1823     auto msg = std::make_shared<WfdDecoderAccelerationDoneMsg>();
1824     msg->surfaceId = connectionInfo.surfaceId;
1825 
1826     auto reply = std::static_pointer_cast<BaseMsg>(std::make_shared<WfdCommonRsp>());
1827     ipcAdapter->SendRequest(msg, reply);
1828     SHARING_LOGD("device ip: %{private}s, mac: %{private}s, state: %{public}s.",
1829                  GetAnonymousIp(connectionInfo.ip).c_str(), GetAnonymousMAC(connectionInfo.mac).c_str(),
1830                  std::string(magic_enum::enum_name(connectionInfo.state)).c_str());
1831 }
1832 
OnDecoderDied(ConnectionInfo & connectionInfo)1833 void WfdSinkScene::OnDecoderDied(ConnectionInfo &connectionInfo)
1834 {
1835     SHARING_LOGD("trace.");
1836     auto ipcAdapter = ipcAdapter_.lock();
1837     RETURN_IF_NULL(ipcAdapter);
1838 
1839     auto msg = std::make_shared<WfdSurfaceFailureMsg>();
1840     msg->surfaceId = connectionInfo.surfaceId;
1841     auto reply = std::static_pointer_cast<BaseMsg>(std::make_shared<WfdCommonRsp>());
1842     ipcAdapter->SendRequest(msg, reply);
1843 
1844     SHARING_LOGD("failed at device ip: %{private}s, mac: %{private}s, state: %{public}s.",
1845         GetAnonymousIp(connectionInfo.ip).c_str(), GetAnonymousMAC(connectionInfo.mac).c_str(),
1846         std::string(magic_enum::enum_name(connectionInfo.state)).c_str());
1847 }
1848 
OnRemoteDied()1849 void WfdSinkScene::OnRemoteDied()
1850 {
1851     SHARING_LOGD("trace.");
1852     auto sharingAdapter = sharingAdapter_.lock();
1853     if (sharingAdapter) {
1854         sharingAdapter->ReleaseScene(GetId());
1855     }
1856 }
1857 
1858 REGISTER_CLASS_REFLECTOR(WfdSinkScene);
1859 } // namespace Sharing
1860 } // namespace OHOS
1861