1 /*
2 * Copyright (c) 2021-2024 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "dcamera_sink_controller.h"
17
18 #include <securec.h>
19 #include <thread>
20
21 #include "anonymous_string.h"
22 #include "dcamera_channel_sink_impl.h"
23 #include "dcamera_client.h"
24 #include "dcamera_metadata_setting_cmd.h"
25 #include "dcamera_protocol.h"
26 #include "dcamera_utils_tools.h"
27
28 #include "dcamera_sink_access_control.h"
29 #include "dcamera_sink_controller_channel_listener.h"
30 #include "dcamera_sink_controller_state_callback.h"
31 #include "dcamera_sink_output.h"
32 #include "dcamera_sink_service_ipc.h"
33
34 #include "distributed_camera_constants.h"
35 #include "distributed_camera_errno.h"
36 #include "distributed_hardware_log.h"
37 #ifdef DEVICE_SECURITY_LEVEL_ENABLE
38 #include "device_security_defines.h"
39 #include "device_security_info.h"
40 #endif
41 #include "ffrt_inner.h"
42 #include "idistributed_camera_source.h"
43 #include "ipc_skeleton.h"
44 #include "dcamera_low_latency.h"
45 #include <sys/prctl.h>
46
47 namespace OHOS {
48 namespace DistributedHardware {
49 const int DEFAULT_DEVICE_SECURITY_LEVEL = -1;
50 const std::string PAGE_SUBTYPE = "camera";
51
DCameraSinkController(std::shared_ptr<ICameraSinkAccessControl>& accessControl, const sptr<IDCameraSinkCallback> &sinkCallback)52 DCameraSinkController::DCameraSinkController(std::shared_ptr<ICameraSinkAccessControl>& accessControl,
53 const sptr<IDCameraSinkCallback> &sinkCallback)
54 : isInit_(false), sessionState_(DCAMERA_CHANNEL_STATE_DISCONNECTED), accessControl_(accessControl),
55 sinkCallback_(sinkCallback)
56 {
57 }
58
~DCameraSinkController()59 DCameraSinkController::~DCameraSinkController()
60 {
61 if (isInit_) {
62 UnInit();
63 }
64 }
65
StartCapture(std::vector<std::shared_ptr<DCameraCaptureInfo>>& captureInfos, int32_t sceneMode)66 int32_t DCameraSinkController::StartCapture(std::vector<std::shared_ptr<DCameraCaptureInfo>>& captureInfos,
67 int32_t sceneMode)
68 {
69 DHLOGI("StartCapture dhId: %{public}s, mode: %{public}d", GetAnonyString(dhId_).c_str(), sceneMode);
70 std::string accessType = "";
71 CHECK_AND_RETURN_RET_LOG(accessControl_ == nullptr, DCAMERA_BAD_VALUE, "accessControl_ is null.");
72 if ((accessControl_->IsSensitiveSrcAccess(SRC_TYPE)) &&
73 (accessControl_->GetAccessControlType(accessType) == DCAMERA_SAME_ACCOUNT)) {
74 int32_t ret = StartCaptureInner(captureInfos);
75 if (ret == DCAMERA_OK) {
76 accessControl_->NotifySensitiveSrc(SRC_TYPE);
77 }
78 return ret;
79 } else {
80 std::shared_ptr<std::string> param = std::make_shared<std::string>("");
81 std::shared_ptr<std::vector<std::shared_ptr<DCameraCaptureInfo>>> infos =
82 std::make_shared<std::vector<std::shared_ptr<DCameraCaptureInfo>>>(captureInfos);
83 CHECK_AND_RETURN_RET_LOG(sinkCotrEventHandler_ == nullptr, DCAMERA_BAD_VALUE, "sinkCotrEventHandler_ is null.");
84 AppExecFwk::InnerEvent::Pointer triggerEvent =
85 AppExecFwk::InnerEvent::Get(EVENT_FRAME_TRIGGER, param, 0);
86 AppExecFwk::InnerEvent::Pointer authorizationEvent =
87 AppExecFwk::InnerEvent::Get(EVENT_AUTHORIZATION, infos, 0);
88 sinkCotrEventHandler_->SendEvent(triggerEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE);
89 sinkCotrEventHandler_->SendEvent(authorizationEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE);
90 }
91 return DCAMERA_OK;
92 }
93
StopCapture()94 int32_t DCameraSinkController::StopCapture()
95 {
96 DHLOGI("StopCapture dhId: %{public}s", GetAnonyString(dhId_).c_str());
97 std::lock_guard<std::mutex> autoLock(captureLock_);
98 if (operator_ == nullptr) {
99 return DCAMERA_BAD_VALUE;
100 }
101 int32_t ret = operator_->StopCapture();
102 if (ret != DCAMERA_OK) {
103 DHLOGE("client stop capture failed, dhId: %{public}s, ret: %{public}d",
104 GetAnonyString(dhId_).c_str(), ret);
105 DCameraNotifyInner(DCAMERA_MESSAGE, DCAMERA_EVENT_DEVICE_ERROR, std::string("operator stop capture failed."));
106 return ret;
107 }
108 if (output_ == nullptr) {
109 return DCAMERA_BAD_VALUE;
110 }
111 ret = output_->StopCapture();
112 if (ret != DCAMERA_OK) {
113 DHLOGE("output stop capture failed, dhId: %{public}s, ret: %{public}d",
114 GetAnonyString(dhId_).c_str(), ret);
115 DCameraNotifyInner(DCAMERA_MESSAGE, DCAMERA_EVENT_DEVICE_ERROR, std::string("output stop capture failed"));
116 return ret;
117 }
118 DHLOGI("StopCapture %{public}s success", GetAnonyString(dhId_).c_str());
119 return DCAMERA_OK;
120 }
121
ChannelNeg(std::shared_ptr<DCameraChannelInfo>& info)122 int32_t DCameraSinkController::ChannelNeg(std::shared_ptr<DCameraChannelInfo>& info)
123 {
124 DHLOGI("ChannelNeg dhId: %{public}s", GetAnonyString(dhId_).c_str());
125 int32_t ret = output_->OpenChannel(info);
126 if (ret != DCAMERA_OK) {
127 DHLOGE("channel negotiate failed, dhId: %{public}s, ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
128 return ret;
129 }
130
131 DHLOGI("ChannelNeg %{public}s success", GetAnonyString(dhId_).c_str());
132 return DCAMERA_OK;
133 }
134
DCameraNotify(std::shared_ptr<DCameraEvent>& events)135 int32_t DCameraSinkController::DCameraNotify(std::shared_ptr<DCameraEvent>& events)
136 {
137 DHLOGI("DCameraNotify dhId: %{public}s", GetAnonyString(dhId_).c_str());
138 CHECK_AND_RETURN_RET_LOG(srcDevId_.empty(), DCAMERA_BAD_VALUE, "source deviceId is empty");
139
140 DCameraEventCmd eventCmd;
141 std::string jsonStr = "";
142 eventCmd.type_ = DCAMERA_PROTOCOL_TYPE_MESSAGE;
143 eventCmd.dhId_ = dhId_;
144 eventCmd.command_ = DCAMERA_PROTOCOL_CMD_STATE_NOTIFY;
145 eventCmd.value_ = events;
146 int32_t ret = eventCmd.Marshal(jsonStr);
147 if (ret != DCAMERA_OK) {
148 DHLOGE("DCameraEventCmd marshal failed, dhId: %{public}s, ret: %{public}d",
149 GetAnonyString(dhId_).c_str(), ret);
150 return ret;
151 }
152
153 if (ManageSelectChannel::GetInstance().GetSinkConnect()) {
154 std::shared_ptr<DataBuffer> buffer = std::make_shared<DataBuffer>(jsonStr.length() + 1);
155 ret = memcpy_s(buffer->Data(), buffer->Capacity(),
156 reinterpret_cast<uint8_t *>(const_cast<char *>(jsonStr.c_str())), jsonStr.length());
157 CHECK_AND_RETURN_RET_LOG(ret != EOK, DCAMERA_BAD_VALUE, "DCameraNotify memcpy_s failed, ret: %{public}d", ret);
158 ret = channel_->SendData(buffer);
159 if (ret != DCAMERA_OK) {
160 DHLOGE("DCameraNotify channel send data failed, dhId: %{public}s ret: %{public}d",
161 GetAnonyString(dhId_).c_str(), ret);
162 return DCAMERA_BAD_VALUE;
163 }
164 } else {
165 std::string sinkDevId;
166 ret = GetLocalDeviceNetworkId(sinkDevId);
167 if (ret != DCAMERA_OK) {
168 DHLOGE("GetLocalDeviceNetworkId failed, devId: %{public}s, dhId: %{public}s, ret: %{public}d",
169 GetAnonyString(sinkDevId).c_str(), GetAnonyString(dhId_).c_str(), ret);
170 return ret;
171 }
172
173 sptr<IDistributedCameraSource> sourceSA = DCameraSinkServiceIpc::GetInstance().GetSourceRemoteCamSrv(srcDevId_);
174 CHECK_AND_RETURN_RET_LOG(sourceSA == nullptr, DCAMERA_BAD_VALUE, "sourceSA is null");
175 ret = sourceSA->DCameraNotify(sinkDevId, dhId_, jsonStr);
176 if (ret != DCAMERA_OK) {
177 DHLOGE("SourceSA notify failed, srcId: %{public}s, sinkId: %{public}s, dhId: %{public}s, ret: %{public}d",
178 GetAnonyString(srcDevId_).c_str(), GetAnonyString(sinkDevId).c_str(),
179 GetAnonyString(dhId_).c_str(), ret);
180 return ret;
181 }
182 }
183
184 DHLOGI("DCameraNotify %{public}s success", GetAnonyString(dhId_).c_str());
185 return DCAMERA_OK;
186 }
187
UpdateSettings(std::vector<std::shared_ptr<DCameraSettings>>& settings)188 int32_t DCameraSinkController::UpdateSettings(std::vector<std::shared_ptr<DCameraSettings>>& settings)
189 {
190 DHLOGI("UpdateSettings dhId: %{public}s", GetAnonyString(dhId_).c_str());
191 if (!CheckPermission()) {
192 DHLOGE("DCameraSinkController UpdateSettings fail, CheckPermission fail");
193 return DCAMERA_WRONG_STATE;
194 }
195 int32_t ret = operator_->UpdateSettings(settings);
196 if (ret != DCAMERA_OK) {
197 DHLOGE("UpdateSettings failed, dhId: %{public}s, ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
198 return ret;
199 }
200
201 DHLOGI("UpdateSettings %{public}s success", GetAnonyString(dhId_).c_str());
202 return DCAMERA_OK;
203 }
204
GetCameraInfo(std::shared_ptr<DCameraInfo>& camInfo)205 int32_t DCameraSinkController::GetCameraInfo(std::shared_ptr<DCameraInfo>& camInfo)
206 {
207 DHLOGI("GetCameraInfo dhId: %{public}s, session state: %{public}d", GetAnonyString(dhId_).c_str(), sessionState_);
208 camInfo->state_ = sessionState_;
209 return DCAMERA_OK;
210 }
211
CheckSensitive()212 int32_t DCameraSinkController::CheckSensitive()
213 {
214 if (sinkCallback_ == nullptr) {
215 DHLOGE("check sensitive callback is nullptr.");
216 return DCAMERA_BAD_VALUE;
217 }
218 int32_t ret = sinkCallback_->OnNotifyResourceInfo(ResourceEventType::EVENT_TYPE_QUERY_RESOURCE, PAGE_SUBTYPE,
219 srcDevId_, isSensitive_, isSameAccount_);
220 CHECK_AND_RETURN_RET_LOG(ret != DCAMERA_OK, ret, "Query resource failed, ret: %{public}d", ret);
221 DHLOGI("OpenChannel isSensitive: %{public}d, isSameAccout: %{public}d", isSensitive_, isSameAccount_);
222 if (isSensitive_ && !isSameAccount_) {
223 DHLOGE("Privacy resource must be logged in with the same account.");
224 return DCAMERA_BAD_VALUE;
225 }
226
227 if (isCheckSecLevel_) {
228 std::string sinkDevId;
229 ret = GetLocalDeviceNetworkId(sinkDevId);
230 CHECK_AND_RETURN_RET_LOG(ret != DCAMERA_OK, ret, "GetLocalDeviceNetworkId failed, ret: %{public}d", ret);
231 if (isSensitive_ && !CheckDeviceSecurityLevel(srcDevId_, sinkDevId)) {
232 DHLOGE("Check device security level failed!");
233 return DCAMERA_BAD_VALUE;
234 }
235 }
236 return DCAMERA_OK;
237 }
238
OpenChannel(std::shared_ptr<DCameraOpenInfo>& openInfo)239 int32_t DCameraSinkController::OpenChannel(std::shared_ptr<DCameraOpenInfo>& openInfo)
240 {
241 DHLOGI("DCameraSinkController OpenChannel Start, dhId: %{public}s", GetAnonyString(dhId_).c_str());
242 ManageSelectChannel::GetInstance().SetSinkConnect(false);
243 if (!CheckPermission()) {
244 DHLOGE("DCameraSinkController OpenChannel fail, CheckPermission fail");
245 return DCAMERA_WRONG_STATE;
246 }
247 if (sessionState_ != DCAMERA_CHANNEL_STATE_DISCONNECTED) {
248 DHLOGE("wrong state, dhId: %{public}s, sessionState: %{public}d", GetAnonyString(dhId_).c_str(), sessionState_);
249 return DCAMERA_WRONG_STATE;
250 }
251 srcDevId_ = openInfo->sourceDevId_;
252 int32_t ret = CheckSensitive();
253 if (ret != DCAMERA_OK) {
254 DHLOGE("check sensitive error, ret %{public}d", ret);
255 return ret;
256 }
257 std::vector<DCameraIndex> indexs;
258 indexs.push_back(DCameraIndex(srcDevId_, dhId_));
259 auto controller = std::shared_ptr<DCameraSinkController>(shared_from_this());
260 std::shared_ptr<ICameraChannelListener> listener =
261 std::make_shared<DCameraSinkControllerChannelListener>(controller);
262 ret = channel_->CreateSession(indexs, SESSION_FLAG, DCAMERA_SESSION_MODE_CTRL, listener);
263 if (ret != DCAMERA_OK) {
264 DHLOGE("channel create session failed, dhId: %{public}s, ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
265 return ret;
266 }
267 ret = PullUpPage();
268 CHECK_AND_RETURN_RET_LOG(ret != DCAMERA_OK, ret, "PullUpPage failed");
269 DHLOGI("DCameraSinkController OpenChannel %{public}s success", GetAnonyString(dhId_).c_str());
270 return DCAMERA_OK;
271 }
272
PullUpPage()273 int32_t DCameraSinkController::PullUpPage()
274 {
275 if (isSensitive_) {
276 bool isSensitive = false;
277 bool isSameAccout = false;
278 int32_t ret = sinkCallback_->OnNotifyResourceInfo(ResourceEventType::EVENT_TYPE_PULL_UP_PAGE, PAGE_SUBTYPE,
279 srcDevId_, isSensitive, isSameAccout);
280 if (ret != DCAMERA_OK) {
281 DHLOGE("pull up page failed, ret %{public}d", ret);
282 return ret;
283 }
284 isPageStatus_.store(true);
285 }
286 return DCAMERA_OK;
287 }
288
CloseChannel()289 int32_t DCameraSinkController::CloseChannel()
290 {
291 DHLOGI("DCameraSinkController CloseChannel Start, dhId: %{public}s", GetAnonyString(dhId_).c_str());
292 std::lock_guard<std::mutex> autoLock(channelLock_);
293 if (!ManageSelectChannel::GetInstance().GetSinkConnect()) {
294 DCameraSinkServiceIpc::GetInstance().DeleteSourceRemoteCamSrv(srcDevId_);
295 if (channel_ == nullptr) {
296 DHLOGE("DCameraSinkController CloseChannel channel_ is nullptr");
297 return DCAMERA_BAD_VALUE;
298 }
299 int32_t ret = channel_->ReleaseSession();
300 if (ret != DCAMERA_OK) {
301 DHLOGE("DCameraSinkController release channel failed, dhId: %{public}s, ret: %{public}d",
302 GetAnonyString(dhId_).c_str(), ret);
303 }
304
305 ret = output_->CloseChannel();
306 if (ret != DCAMERA_OK) {
307 DHLOGE("DCameraSinkController CloseChannel failed, dhId: %{public}s, ret: %{public}d",
308 GetAnonyString(dhId_).c_str(), ret);
309 }
310 }
311 srcDevId_.clear();
312 sessionState_ = DCAMERA_CHANNEL_STATE_DISCONNECTED;
313 if (isPageStatus_.load()) {
314 bool isSensitive = false;
315 bool isSameAccout = false;
316 int32_t ret = sinkCallback_->OnNotifyResourceInfo(ResourceEventType::EVENT_TYPE_CLOSE_PAGE, PAGE_SUBTYPE,
317 srcDevId_, isSensitive, isSameAccout);
318 if (ret != DCAMERA_OK) {
319 DHLOGE("close page failed, ret: %{public}d", ret);
320 }
321 }
322 isPageStatus_.store(false);
323 ManageSelectChannel::GetInstance().SetSinkConnect(false);
324 DHLOGI("DCameraSinkController CloseChannel %{public}s success", GetAnonyString(dhId_).c_str());
325 return DCAMERA_OK;
326 }
327
Init(std::vector<DCameraIndex>& indexs)328 int32_t DCameraSinkController::Init(std::vector<DCameraIndex>& indexs)
329 {
330 DHLOGI("DCameraSinkController Init");
331 dhId_ = indexs[0].dhId_;
332 operator_ = std::make_shared<DCameraClient>(dhId_);
333 output_ = std::make_shared<DCameraSinkOutput>(dhId_, operator_);
334 int32_t ret = output_->Init();
335 if (ret != DCAMERA_OK) {
336 DHLOGE("output init failed, dhId: %{public}s, ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
337 return ret;
338 }
339
340 auto controller = std::shared_ptr<DCameraSinkController>(shared_from_this());
341 std::shared_ptr<StateCallback> stateCallback = std::make_shared<DCameraSinkControllerStateCallback>(controller);
342 operator_->SetStateCallback(stateCallback);
343 ret = operator_->Init();
344 if (ret != DCAMERA_OK) {
345 DHLOGE("operator init failed, dhId: %{public}s, ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
346 return ret;
347 }
348
349 channel_ = std::make_shared<DCameraChannelSinkImpl>();
350 std::shared_ptr<AppExecFwk::EventRunner> runner = AppExecFwk::EventRunner::Create(true);
351 sinkCotrEventHandler_ =
352 std::make_shared<DCameraSinkController::DCameraSinkContrEventHandler>(runner, shared_from_this());
353 isInit_ = true;
354 initCallback_ = std::make_shared<DeviceInitCallback>();
355 ManageSelectChannel::GetInstance().SetSinkConnect(true);
356 ret = CreateCtrlSession();
357 if (ret != DCAMERA_OK) {
358 DHLOGE("CreateCtrlSessiion init failed, dhId: %{public}s, ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
359 return ret;
360 }
361 std::shared_ptr<DCameraChannelInfo> info = std::make_shared<DCameraChannelInfo>();
362 info->sourceDevId_ = "";
363 DCameraChannelDetail continueChInfo(CONTINUE_SESSION_FLAG, CONTINUOUS_FRAME);
364 DCameraChannelDetail snapShotChInfo(SNAP_SHOT_SESSION_FLAG, SNAPSHOT_FRAME);
365 info->detail_.push_back(continueChInfo);
366 info->detail_.push_back(snapShotChInfo);
367 ret = ChannelNeg(info);
368 if (ret != DCAMERA_OK) {
369 DHLOGE("ChannelNeg init failed, dhId: %{public}s, ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
370 return ret;
371 }
372 DHLOGI("DCameraSinkController Init %{public}s success", GetAnonyString(dhId_).c_str());
373 return DCAMERA_OK;
374 }
375
CreateCtrlSession()376 int32_t DCameraSinkController::CreateCtrlSession()
377 {
378 DHLOGI("DCameraSinkController CreateCtrlSessiion Start, dhId: %{public}s", GetAnonyString(dhId_).c_str());
379 if (sessionState_ != DCAMERA_CHANNEL_STATE_DISCONNECTED) {
380 DHLOGE("wrong state, dhId: %{public}s, sessionState: %{public}d", GetAnonyString(dhId_).c_str(), sessionState_);
381 return DCAMERA_WRONG_STATE;
382 }
383 DCameraLowLatency::GetInstance().EnableLowLatency();
384 std::vector<DCameraIndex> indexs;
385 indexs.push_back(DCameraIndex("", dhId_));
386 auto controller = std::shared_ptr<DCameraSinkController>(shared_from_this());
387 std::shared_ptr<ICameraChannelListener> listener =
388 std::make_shared<DCameraSinkControllerChannelListener>(controller);
389 int32_t ret = channel_->CreateSession(indexs, SESSION_FLAG, DCAMERA_SESSION_MODE_CTRL, listener);
390 if (ret != DCAMERA_OK) {
391 DHLOGE("channel create session failed, dhId: %{public}s, ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
392 return ret;
393 }
394 DHLOGI("DCameraSinkController CreateCtrlSessiion %{public}s success", GetAnonyString(dhId_).c_str());
395 return DCAMERA_OK;
396 }
397
UnInit()398 int32_t DCameraSinkController::UnInit()
399 {
400 DHLOGI("DCameraSinkController UnInit dhId: %{public}s", GetAnonyString(dhId_).c_str());
401 std::lock_guard<std::mutex> autoLock(autoLock_);
402 int32_t ret = StopCapture();
403 if (ret != DCAMERA_OK) {
404 DHLOGE("DCameraSinkController UnInit %{public}s stop capture failed, ret: %{public}d",
405 GetAnonyString(dhId_).c_str(), ret);
406 }
407
408 ret = CloseChannel();
409 if (ret != DCAMERA_OK) {
410 DHLOGE("DCameraSinkController UnInit %{public}s close channel failed, ret: %{public}d",
411 GetAnonyString(dhId_).c_str(), ret);
412 }
413
414 DCameraLowLatency::GetInstance().DisableLowLatency();
415 if (ManageSelectChannel::GetInstance().GetSinkConnect()) {
416 if (channel_ != nullptr) {
417 ret = channel_->ReleaseSession();
418 if (ret != DCAMERA_OK) {
419 DHLOGE("DCameraSinkController release channel failed, dhId: %{public}s, ret: %{public}d",
420 GetAnonyString(dhId_).c_str(), ret);
421 }
422 }
423 if (output_ != nullptr) {
424 ret = output_->CloseChannel();
425 if (ret != DCAMERA_OK) {
426 DHLOGE("DCameraSinkController output CloseChannel failed, dhId: %{public}s, ret: %{public}d",
427 GetAnonyString(dhId_).c_str(), ret);
428 }
429 }
430 }
431
432 if (output_ != nullptr) {
433 ret = output_->UnInit();
434 if (ret != DCAMERA_OK) {
435 DHLOGE("DCameraSinkController release output failed, dhId: %{public}s, ret: %{public}d",
436 GetAnonyString(dhId_).c_str(), ret);
437 }
438 }
439
440 if (operator_ != nullptr) {
441 ret = operator_->UnInit();
442 if (ret != DCAMERA_OK) {
443 DHLOGE("DCameraSinkController release operator failed, dhId: %{public}s, ret: %{public}d",
444 GetAnonyString(dhId_).c_str(), ret);
445 }
446 }
447
448 isInit_ = false;
449 DHLOGI("DCameraSinkController UnInit %{public}s success", GetAnonyString(dhId_).c_str());
450 return DCAMERA_OK;
451 }
452
DCameraSinkContrEventHandler( const std::shared_ptr<AppExecFwk::EventRunner> &runner, std::shared_ptr<DCameraSinkController> sinkContrPtr)453 DCameraSinkController::DCameraSinkContrEventHandler::DCameraSinkContrEventHandler(
454 const std::shared_ptr<AppExecFwk::EventRunner> &runner, std::shared_ptr<DCameraSinkController> sinkContrPtr)
455 : AppExecFwk::EventHandler(runner), sinkContrWPtr_(sinkContrPtr)
456 {
457 DHLOGI("Ctor DCameraSinkContrEventHandler.");
458 }
459
ProcessEvent(const AppExecFwk::InnerEvent::Pointer &event)460 void DCameraSinkController::DCameraSinkContrEventHandler::ProcessEvent(const AppExecFwk::InnerEvent::Pointer &event)
461 {
462 CHECK_AND_RETURN_LOG(event, "event is nullptr.");
463 uint32_t eventId = event->GetInnerEventId();
464 auto sinkContr = sinkContrWPtr_.lock();
465 if (sinkContr == nullptr) {
466 DHLOGE("Can not get strong self ptr");
467 return;
468 }
469 switch (eventId) {
470 case EVENT_FRAME_TRIGGER:
471 sinkContr->ProcessFrameTrigger(event);
472 break;
473 case EVENT_AUTHORIZATION:
474 sinkContr->ProcessPostAuthorization(event);
475 break;
476 default:
477 DHLOGE("event is undefined, id is %d", eventId);
478 break;
479 }
480 }
481
ProcessFrameTrigger(const AppExecFwk::InnerEvent::Pointer &event)482 void DCameraSinkController::ProcessFrameTrigger(const AppExecFwk::InnerEvent::Pointer &event)
483 {
484 DHLOGD("Receive frame trigger event then start process data in sink controller.");
485 std::shared_ptr<std::string> param = event->GetSharedObject<std::string>();
486 CHECK_AND_RETURN_LOG(param == nullptr, "ProcessFrameTrigger get param is null");
487 accessControl_->TriggerFrame(*param);
488 }
489
ProcessPostAuthorization(const AppExecFwk::InnerEvent::Pointer &event)490 void DCameraSinkController::ProcessPostAuthorization(const AppExecFwk::InnerEvent::Pointer &event)
491 {
492 DHLOGD("Receive post authorization event then start process data in sink controller.");
493 std::shared_ptr<std::vector<std::shared_ptr<DCameraCaptureInfo>>> captureInfos =
494 event->GetSharedObject<std::vector<std::shared_ptr<DCameraCaptureInfo>>>();
495 CHECK_AND_RETURN_LOG(captureInfos == nullptr, "ProcessPostAuthorization get captureInfos is null");
496 PostAuthorization(*captureInfos);
497 }
498
OnStateChanged(std::shared_ptr<DCameraEvent>& event)499 void DCameraSinkController::OnStateChanged(std::shared_ptr<DCameraEvent>& event)
500 {
501 DHLOGI("DCameraSinkController::OnStateChanged dhId: %{public}s, result: %{public}d",
502 GetAnonyString(dhId_).c_str(), event->eventResult_);
503 if (event->eventResult_ == DCAMERA_EVENT_DEVICE_PREEMPT) {
504 DCameraNotifyInner(DCAMERA_MESSAGE, DCAMERA_EVENT_DEVICE_PREEMPT, std::string("camera device preempted"));
505 } else {
506 DCameraNotifyInner(DCAMERA_MESSAGE, DCAMERA_EVENT_DEVICE_ERROR, std::string("camera error"));
507 }
508 }
509
OnMetadataResult(std::vector<std::shared_ptr<DCameraSettings>>& settings)510 void DCameraSinkController::OnMetadataResult(std::vector<std::shared_ptr<DCameraSettings>>& settings)
511 {
512 DHLOGI("DCameraSinkController::OnMetadataResult dhId: %{public}s", GetAnonyString(dhId_).c_str());
513 if (settings.empty()) {
514 DHLOGE("camera settings is empty");
515 return;
516 }
517 DCameraMetadataSettingCmd cmd;
518 cmd.type_ = DCAMERA_PROTOCOL_TYPE_MESSAGE;
519 cmd.dhId_ = dhId_;
520 cmd.command_ = DCAMERA_PROTOCOL_CMD_METADATA_RESULT;
521 cmd.value_.assign(settings.begin(), settings.end());
522 std::string jsonStr;
523 int32_t ret = cmd.Marshal(jsonStr);
524 if (ret != DCAMERA_OK) {
525 DHLOGE("Marshal metadata settings failed, dhId: %{public}s ret: %{public}d",
526 GetAnonyString(dhId_).c_str(), ret);
527 return;
528 }
529 std::shared_ptr<DataBuffer> buffer = std::make_shared<DataBuffer>(jsonStr.length() + 1);
530 ret = memcpy_s(buffer->Data(), buffer->Capacity(), reinterpret_cast<uint8_t *>(const_cast<char *>(jsonStr.c_str())),
531 jsonStr.length());
532 if (ret != EOK) {
533 DHLOGE("memcpy_s failed, dhId: %{public}s ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
534 return;
535 }
536 ret = channel_->SendData(buffer);
537 if (ret != DCAMERA_OK) {
538 DHLOGE("channel send data failed, dhId: %{public}s ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
539 return;
540 }
541 DHLOGI("DCameraSinkController::OnMetadataResult dhId: %{public}s success", GetAnonyString(dhId_).c_str());
542 }
543
OnSessionState(int32_t state, std::string networkId)544 void DCameraSinkController::OnSessionState(int32_t state, std::string networkId)
545 {
546 DHLOGI("DCameraSinkController::OnSessionState dhId: %{public}s, state: %{public}d",
547 GetAnonyString(dhId_).c_str(), state);
548 sessionState_ = state;
549 switch (state) {
550 case DCAMERA_CHANNEL_STATE_CONNECTING:
551 DHLOGI("channel is connecting");
552 break;
553 case DCAMERA_CHANNEL_STATE_CONNECTED: {
554 DHLOGI("channel is connected");
555 if (!ManageSelectChannel::GetInstance().GetSinkConnect()) {
556 break;
557 }
558 srcDevId_ = networkId;
559 int32_t ret = CheckSensitive();
560 if (ret != DCAMERA_OK) {
561 DHLOGE("Check sensitive error. ret %{public}d.", ret);
562 return;
563 }
564 ret = PullUpPage();
565 CHECK_AND_RETURN_LOG(ret != DCAMERA_OK, "PullUpPage failed");
566 break;
567 }
568 case DCAMERA_CHANNEL_STATE_DISCONNECTED:
569 DHLOGI("channel is disconnected");
570 ffrt::submit([this]() {
571 DHLOGI("DCameraSinkController::OnSessionState %{public}s new thread session state: %{public}d",
572 GetAnonyString(dhId_).c_str(), sessionState_);
573 prctl(PR_SET_NAME, CHANNEL_DISCONNECTED.c_str());
574 std::lock_guard<std::mutex> autoLock(autoLock_);
575 int32_t ret = CloseChannel();
576 if (ret != DCAMERA_OK) {
577 DHLOGE("session state: %{public}d, %{public}s close channel failed, ret: %{public}d",
578 sessionState_, GetAnonyString(dhId_).c_str(), ret);
579 }
580 ret = StopCapture();
581 if (ret != DCAMERA_OK) {
582 DHLOGE("session state: %{public}d, %{public}s stop capture failed, ret: %{public}d",
583 sessionState_, GetAnonyString(dhId_).c_str(), ret);
584 }
585 });
586 break;
587 default:
588 DHLOGE("unknown session state");
589 break;
590 }
591 }
592
OnSessionError(int32_t eventType, int32_t eventReason, std::string detail)593 void DCameraSinkController::OnSessionError(int32_t eventType, int32_t eventReason, std::string detail)
594 {
595 DHLOGI("DCameraSinkController::OnSessionError dhId: %{public}s, eventType: %{public}d, eventReason: %{public}d,"
596 " detail: %{public}s", GetAnonyString(dhId_).c_str(), eventType, eventReason, detail.c_str());
597 }
598
OnDataReceived(std::vector<std::shared_ptr<DataBuffer>>& buffers)599 void DCameraSinkController::OnDataReceived(std::vector<std::shared_ptr<DataBuffer>>& buffers)
600 {
601 DHLOGI("OnReceivedData %{public}s control channel receive data", GetAnonyString(dhId_).c_str());
602 for (auto& buffer : buffers) {
603 if (buffer->Size() <= 0 || buffer->Size() > DATABUFF_MAX_SIZE) {
604 DHLOGI("buffer is invalid");
605 return;
606 }
607 HandleReceivedData(buffer);
608 }
609 }
610
PostAuthorization(std::vector<std::shared_ptr<DCameraCaptureInfo>>& captureInfos)611 void DCameraSinkController::PostAuthorization(std::vector<std::shared_ptr<DCameraCaptureInfo>>& captureInfos)
612 {
613 DHLOGI("DCameraSinkController::PostAuthorization dhId: %{public}s", GetAnonyString(dhId_).c_str());
614 int32_t ret = StartCaptureInner(captureInfos);
615 if (ret == DCAMERA_OK) {
616 accessControl_->NotifySensitiveSrc(SRC_TYPE);
617 }
618 }
619
StartCaptureInner(std::vector<std::shared_ptr<DCameraCaptureInfo>>& captureInfos)620 int32_t DCameraSinkController::StartCaptureInner(std::vector<std::shared_ptr<DCameraCaptureInfo>>& captureInfos)
621 {
622 DHLOGI("StartCaptureInner dhId: %{public}s", GetAnonyString(dhId_).c_str());
623 std::lock_guard<std::mutex> autoLock(captureLock_);
624 int32_t ret = output_->StartCapture(captureInfos);
625 if (ret != DCAMERA_OK) {
626 DHLOGE("output start capture failed, dhId: %{public}s, ret: %{public}d", GetAnonyString(dhId_).c_str(), ret);
627 DCameraNotifyInner(DCAMERA_MESSAGE, DCAMERA_EVENT_DEVICE_ERROR, std::string("output start capture failed"));
628 return ret;
629 }
630 PropertyCarrier carrier;
631 ret = output_->GetProperty(SURFACE, carrier);
632 if (ret != DCAMERA_OK) {
633 DHLOGD("StartCaptureInner: get property fail.");
634 return DCAMERA_BAD_VALUE;
635 }
636 ret = operator_->StartCapture(captureInfos, carrier.surface_, sceneMode_);
637 if (ret != DCAMERA_OK) {
638 DHLOGE("camera client start capture failed, dhId: %{public}s, ret: %{public}d",
639 GetAnonyString(dhId_).c_str(), ret);
640 if (ret == DCAMERA_ALLOC_ERROR) {
641 DCameraNotifyInner(DCAMERA_MESSAGE, DCAMERA_EVENT_NO_PERMISSION,
642 std::string("operator start capture permission denial."));
643 } else if (ret == DCAMERA_DEVICE_BUSY) {
644 DCameraNotifyInner(DCAMERA_MESSAGE, DCAMERA_EVENT_DEVICE_IN_USE,
645 std::string("operator start capture in used."));
646 }
647 return ret;
648 }
649
650 DCameraNotifyInner(DCAMERA_MESSAGE, DCAMERA_EVENT_CAMERA_SUCCESS, std::string("operator start capture success"));
651 DHLOGI("DCameraSinkController::StartCaptureInner %{public}s success", GetAnonyString(dhId_).c_str());
652 return DCAMERA_OK;
653 }
654
DCameraNotifyInner(int32_t type, int32_t result, std::string reason)655 int32_t DCameraSinkController::DCameraNotifyInner(int32_t type, int32_t result, std::string reason)
656 {
657 std::shared_ptr<DCameraEvent> event = std::make_shared<DCameraEvent>();
658 event->eventType_ = type;
659 event->eventResult_ = result;
660 event->eventContent_ = reason;
661 return DCameraNotify(event);
662 }
663
HandleReceivedData(std::shared_ptr<DataBuffer>& dataBuffer)664 int32_t DCameraSinkController::HandleReceivedData(std::shared_ptr<DataBuffer>& dataBuffer)
665 {
666 DHLOGI("DCameraSinkController::HandleReceivedData dhId: %{public}s", GetAnonyString(dhId_).c_str());
667 uint8_t *data = dataBuffer->Data();
668 std::string jsonStr(reinterpret_cast<const char *>(data), dataBuffer->Capacity());
669 cJSON *rootValue = cJSON_Parse(jsonStr.c_str());
670 if (rootValue == nullptr) {
671 return DCAMERA_BAD_VALUE;
672 }
673 cJSON *comvalue = cJSON_GetObjectItemCaseSensitive(rootValue, "Command");
674 if (comvalue == nullptr || !cJSON_IsString(comvalue) || (comvalue->valuestring == nullptr)) {
675 cJSON_Delete(rootValue);
676 DHLOGE("parse command failed");
677 return DCAMERA_BAD_VALUE;
678 }
679 std::string command = std::string(comvalue->valuestring);
680 cJSON_Delete(rootValue);
681 if ((!command.empty()) && (command.compare(DCAMERA_PROTOCOL_CMD_CAPTURE) == 0)) {
682 DCameraCaptureInfoCmd captureInfoCmd;
683 int32_t ret = captureInfoCmd.Unmarshal(jsonStr);
684 if (ret != DCAMERA_OK) {
685 DHLOGE("Capture Info Unmarshal failed, dhId: %{public}s ret: %{public}d",
686 GetAnonyString(dhId_).c_str(), ret);
687 return ret;
688 }
689 sceneMode_ = captureInfoCmd.sceneMode_;
690 return StartCapture(captureInfoCmd.value_, sceneMode_);
691 } else if ((!command.empty()) && (command.compare(DCAMERA_PROTOCOL_CMD_UPDATE_METADATA) == 0)) {
692 DCameraMetadataSettingCmd metadataSettingCmd;
693 int32_t ret = metadataSettingCmd.Unmarshal(jsonStr);
694 if (ret != DCAMERA_OK) {
695 DHLOGE("Metadata Setting Unmarshal failed, dhId: %{public}s ret: %{public}d",
696 GetAnonyString(dhId_).c_str(), ret);
697 return ret;
698 }
699 return UpdateSettings(metadataSettingCmd.value_);
700 } else if ((!command.empty()) && (command.compare(DCAMERA_PROTOCOL_CMD_STOP_CAPTURE) == 0)) {
701 return StopCapture();
702 }
703 return DCAMERA_BAD_VALUE;
704 }
705
PauseDistributedHardware(const std::string &networkId)706 int32_t DCameraSinkController::PauseDistributedHardware(const std::string &networkId)
707 {
708 DHLOGI("Pause distributed hardware dhId: %{public}s", GetAnonyString(dhId_).c_str());
709 if (networkId.empty()) {
710 DHLOGE("networkId is empty");
711 return DCAMERA_BAD_VALUE;
712 }
713 if (operator_ == nullptr) {
714 DHLOGE("operator_ is nullptr.");
715 return DCAMERA_BAD_VALUE;
716 }
717 int32_t ret = operator_->PauseCapture();
718 if (ret != DCAMERA_OK) {
719 DHLOGE("Pause distributed hardware failed, dhId: %{public}s, ret: %{public}d",
720 GetAnonyString(dhId_).c_str(), ret);
721 }
722 return ret;
723 }
724
ResumeDistributedHardware(const std::string &networkId)725 int32_t DCameraSinkController::ResumeDistributedHardware(const std::string &networkId)
726 {
727 DHLOGI("Resume distributed hardware dhId: %{public}s", GetAnonyString(dhId_).c_str());
728 if (networkId.empty()) {
729 DHLOGE("networkId is empty");
730 return DCAMERA_BAD_VALUE;
731 }
732 if (operator_ == nullptr) {
733 DHLOGE("operator_ is nullptr.");
734 return DCAMERA_BAD_VALUE;
735 }
736 int32_t ret = operator_->ResumeCapture();
737 if (ret != DCAMERA_OK) {
738 DHLOGE("Resume distributed hardware failed, dhId: %{public}s, ret: %{public}d",
739 GetAnonyString(dhId_).c_str(), ret);
740 }
741 return ret;
742 }
743
StopDistributedHardware(const std::string &networkId)744 int32_t DCameraSinkController::StopDistributedHardware(const std::string &networkId)
745 {
746 DHLOGI("Stop distributed hardware dhId: %{public}s", GetAnonyString(dhId_).c_str());
747 if (networkId.empty()) {
748 DHLOGE("networkId is empty");
749 return DCAMERA_BAD_VALUE;
750 }
751
752 isPageStatus_.store(false);
753 return DCameraNotifyInner(DCAMERA_SINK_STOP, DCAMERA_EVENT_SINK_STOP, std::string("sink stop dcamera business"));
754 }
755
CheckDeviceSecurityLevel(const std::string &srcDeviceId, const std::string &dstDeviceId)756 bool DCameraSinkController::CheckDeviceSecurityLevel(const std::string &srcDeviceId, const std::string &dstDeviceId)
757 {
758 DHLOGD("CheckDeviceSecurityLevel srcDeviceId %{public}s, dstDeviceId %{public}s.",
759 GetAnonyString(srcDeviceId).c_str(), GetAnonyString(dstDeviceId).c_str());
760 std::string srcUdid = GetUdidByNetworkId(srcDeviceId);
761 if (srcUdid.empty()) {
762 DHLOGE("src udid is empty");
763 return false;
764 }
765 std::string dstUdid = GetUdidByNetworkId(dstDeviceId);
766 if (dstUdid.empty()) {
767 DHLOGE("dst udid is empty");
768 return false;
769 }
770 DHLOGD("CheckDeviceSecurityLevel srcUdid %{public}s, dstUdid %{public}s.",
771 GetAnonyString(srcUdid).c_str(), GetAnonyString(dstUdid).c_str());
772 int32_t srcDeviceSecurityLevel = GetDeviceSecurityLevel(srcUdid);
773 int32_t dstDeviceSecurityLevel = GetDeviceSecurityLevel(dstUdid);
774 DHLOGI("srcDeviceSecurityLevel is %{public}d, dstDeviceSecurityLevel is %{public}d.",
775 srcDeviceSecurityLevel, dstDeviceSecurityLevel);
776 if (srcDeviceSecurityLevel == DEFAULT_DEVICE_SECURITY_LEVEL ||
777 srcDeviceSecurityLevel < dstDeviceSecurityLevel) {
778 DHLOGE("The device security of source device is lower.");
779 return false;
780 }
781 return true;
782 }
783
GetDeviceSecurityLevel(const std::string &udid)784 int32_t DCameraSinkController::GetDeviceSecurityLevel(const std::string &udid)
785 {
786 #ifdef DEVICE_SECURITY_LEVEL_ENABLE
787 DeviceIdentify devIdentify;
788 devIdentify.length = DEVICE_ID_MAX_LEN;
789 int32_t ret = memcpy_s(devIdentify.identity, DEVICE_ID_MAX_LEN, udid.c_str(), DEVICE_ID_MAX_LEN);
790 if (ret != 0) {
791 DHLOGE("str copy failed %{public}d", ret);
792 return DEFAULT_DEVICE_SECURITY_LEVEL;
793 }
794 DeviceSecurityInfo *info = nullptr;
795 ret = RequestDeviceSecurityInfo(&devIdentify, nullptr, &info);
796 if (ret != SUCCESS) {
797 DHLOGE("Request device security info failed %{public}d", ret);
798 FreeDeviceSecurityInfo(info);
799 info = nullptr;
800 return DEFAULT_DEVICE_SECURITY_LEVEL;
801 }
802 #endif
803 int32_t level = 0;
804 #ifdef DEVICE_SECURITY_LEVEL_ENABLE
805 ret = GetDeviceSecurityLevelValue(info, &level);
806 DHLOGD("Get device security level, level is %{public}d", level);
807 FreeDeviceSecurityInfo(info);
808 info = nullptr;
809 if (ret != SUCCESS) {
810 DHLOGE("Get device security level failed %{public}d", ret);
811 return DEFAULT_DEVICE_SECURITY_LEVEL;
812 }
813 #endif
814 return level;
815 }
816
GetUdidByNetworkId(const std::string &networkId)817 std::string DCameraSinkController::GetUdidByNetworkId(const std::string &networkId)
818 {
819 if (networkId.empty()) {
820 DHLOGE("networkId is empty!");
821 return "";
822 }
823 int32_t ret = DeviceManager::GetInstance().InitDeviceManager(DCAMERA_PKG_NAME, initCallback_);
824 if (ret != DCAMERA_OK) {
825 DHLOGE("InitDeviceManager failed ret = %{public}d", ret);
826 return "";
827 }
828 std::string udid = "";
829 ret = DeviceManager::GetInstance().GetUdidByNetworkId(DCAMERA_PKG_NAME, networkId, udid);
830 if (ret != DCAMERA_OK) {
831 DHLOGE("GetUdidByNetworkId failed ret = %{public}d", ret);
832 return "";
833 }
834 return udid;
835 }
836
CheckPermission()837 bool DCameraSinkController::CheckPermission()
838 {
839 DHLOGI("DCameraSinkController CheckPermission Start");
840 auto uid = IPCSkeleton::GetCallingUid();
841 return uid == DCAMERA_UID;
842 }
843
OnRemoteDied()844 void DeviceInitCallback::OnRemoteDied()
845 {
846 DHLOGI("DeviceInitCallback OnRemoteDied");
847 }
848 } // namespace DistributedHardware
849 } // namespace OHOS