1 /*
2  * Copyright (c) 2021-2022 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 "hstream_depth_data.h"
17 
18 #include <cstdint>
19 
20 #include "camera_device_ability_items.h"
21 #include "camera_log.h"
22 #include "camera_metadata_operator.h"
23 #include "camera_service_ipc_interface_code.h"
24 #include "display_manager.h"
25 #include "camera_util.h"
26 #include "hstream_common.h"
27 #include "ipc_skeleton.h"
28 #include "istream_depth_data_callback.h"
29 #include "metadata_utils.h"
30 #include "camera_report_uitls.h"
31 
32 namespace OHOS {
33 namespace CameraStandard {
34 using namespace OHOS::HDI::Camera::V1_0;
HStreamDepthData( sptr<OHOS::IBufferProducer> producer, int32_t format, int32_t width, int32_t height)35 HStreamDepthData::HStreamDepthData(
36     sptr<OHOS::IBufferProducer> producer, int32_t format, int32_t width, int32_t height)
37     : HStreamCommon(StreamType::DEPTH, producer, format, width, height)
38 {
39     MEDIA_INFO_LOG("HStreamDepthData::HStreamDepthData construct, format:%{public}d, size:%{public}dx%{public}d, "
40         "streamId:%{public}d",
41         format, width, height, GetFwkStreamId());
42 }
43 
~HStreamDepthData()44 HStreamDepthData::~HStreamDepthData()
45 {
46     MEDIA_INFO_LOG("HStreamDepthData::~HStreamDepthData deconstruct, format:%{public}d size:%{public}dx%{public}d "
47                    "streamId:%{public}d, hdiStreamId:%{public}d",
48         format_, width_, height_, GetFwkStreamId(), GetHdiStreamId());
49 }
50 
LinkInput(sptr<OHOS::HDI::Camera::V1_0::IStreamOperator> streamOperator, std::shared_ptr<OHOS::Camera::CameraMetadata> cameraAbility)51 int32_t HStreamDepthData::LinkInput(sptr<OHOS::HDI::Camera::V1_0::IStreamOperator> streamOperator,
52     std::shared_ptr<OHOS::Camera::CameraMetadata> cameraAbility)
53 {
54     MEDIA_INFO_LOG("HStreamDepthData::LinkInput streamId:%{public}d", GetFwkStreamId());
55     int32_t ret = HStreamCommon::LinkInput(streamOperator, cameraAbility);
56     if (ret != CAMERA_OK) {
57         MEDIA_ERR_LOG("HStreamDepthData::LinkInput err, streamId:%{public}d ,err:%{public}d", GetFwkStreamId(), ret);
58         return ret;
59     }
60     return CAMERA_OK;
61 }
62 
SetStreamInfo(StreamInfo_V1_1& streamInfo)63 void HStreamDepthData::SetStreamInfo(StreamInfo_V1_1& streamInfo)
64 {
65     HStreamCommon::SetStreamInfo(streamInfo);
66     streamInfo.v1_0.intent_ =
67         static_cast<OHOS::HDI::Camera::V1_0::StreamIntent>(OHOS::HDI::Camera::V1_3::StreamType::STREAM_TYPE_DEPTH);
68 }
69 
SetDataAccuracy(int32_t accuracy)70 int32_t HStreamDepthData::SetDataAccuracy(int32_t accuracy)
71 {
72     MEDIA_INFO_LOG("HStreamDepthData::SetDataAccuracy accuracy: %{public}d", accuracy);
73     streamDepthDataAccuracy_ = {accuracy};
74     std::vector<uint8_t> ability;
75     std::vector<uint8_t> depthSettings;
76     {
77         std::lock_guard<std::mutex> lock(cameraAbilityLock_);
78         OHOS::Camera::MetadataUtils::ConvertMetadataToVec(cameraAbility_, ability);
79         std::shared_ptr<OHOS::Camera::CameraMetadata> dynamicSetting = nullptr;
80         OHOS::Camera::MetadataUtils::ConvertVecToMetadata(ability, dynamicSetting);
81         camera_metadata_item_t item;
82         CHECK_AND_RETURN_RET_LOG(dynamicSetting != nullptr, CAMERA_INVALID_ARG,
83             "HStreamDepthData::SetDataAccuracy dynamicSetting is nullptr.");
84         int ret = OHOS::Camera::FindCameraMetadataItem(dynamicSetting->get(), OHOS_CONTROL_DEPTH_DATA_ACCURACY, &item);
85         bool status = false;
86         if (ret == CAM_META_ITEM_NOT_FOUND) {
87             MEDIA_DEBUG_LOG("HStreamDepthData::SetDataAccuracy Failed to find data accuracy");
88             status = dynamicSetting->addEntry(
89                 OHOS_CONTROL_DEPTH_DATA_ACCURACY, streamDepthDataAccuracy_.data(), streamDepthDataAccuracy_.size());
90         } else if (ret == CAM_META_SUCCESS) {
91             MEDIA_DEBUG_LOG("HStreamDepthData::SetDataAccuracy success to find data accuracy");
92             status = dynamicSetting->updateEntry(
93                 OHOS_CONTROL_DEPTH_DATA_ACCURACY, streamDepthDataAccuracy_.data(), streamDepthDataAccuracy_.size());
94         }
95         if (!status) {
96             MEDIA_ERR_LOG("HStreamDepthData::SetDataAccuracy Failed to set data accuracy");
97         }
98         OHOS::Camera::MetadataUtils::ConvertMetadataToVec(dynamicSetting, depthSettings);
99     }
100 
101     auto streamOperator = GetStreamOperator();
102 
103     CamRetCode rc = HDI::Camera::V1_0::NO_ERROR;
104     if (streamOperator != nullptr) {
105         std::lock_guard<std::mutex> startStopLock(streamStartStopLock_);
106         CaptureInfo captureInfo;
107         captureInfo.streamIds_ = {GetHdiStreamId()};
108         captureInfo.captureSetting_ = depthSettings;
109         captureInfo.enableShutterCallback_ = false;
110         int32_t currentCaptureId = GetPreparedCaptureId();
111         MEDIA_INFO_LOG("HStreamDepthData::SetDataAccuracy stream:%{public}d, with settingCapture ID:%{public}d",
112             GetFwkStreamId(), currentCaptureId);
113         rc = (CamRetCode)(streamOperator->Capture(currentCaptureId, captureInfo, true));
114         if (rc != HDI::Camera::V1_0::NO_ERROR) {
115             MEDIA_ERR_LOG("HStreamDepthData::SetDataAccuracy Failed with error Code:%{public}d", rc);
116         }
117     }
118     return rc;
119 }
120 
Start()121 int32_t HStreamDepthData::Start()
122 {
123     CAMERA_SYNC_TRACE;
124     auto streamOperator = GetStreamOperator();
125     if (streamOperator == nullptr) {
126         return CAMERA_INVALID_STATE;
127     }
128 
129     auto preparedCaptureId = GetPreparedCaptureId();
130     if (preparedCaptureId != CAPTURE_ID_UNSET) {
131         MEDIA_ERR_LOG("HStreamDepthData::Start, Already started with captureID: %{public}d", preparedCaptureId);
132         return CAMERA_INVALID_STATE;
133     }
134 
135     int32_t ret = PrepareCaptureId();
136     preparedCaptureId = GetPreparedCaptureId();
137     if (ret != CAMERA_OK || preparedCaptureId == CAPTURE_ID_UNSET) {
138         MEDIA_ERR_LOG("HStreamDepthData::Start Failed to allocate a captureId");
139         return ret;
140     }
141 
142     std::vector<uint8_t> ability;
143     {
144         std::lock_guard<std::mutex> lock(cameraAbilityLock_);
145         OHOS::Camera::MetadataUtils::ConvertMetadataToVec(cameraAbility_, ability);
146     }
147 
148     CaptureInfo captureInfo;
149     captureInfo.streamIds_ = { GetHdiStreamId() };
150     captureInfo.captureSetting_ = ability;
151     captureInfo.enableShutterCallback_ = false;
152     MEDIA_INFO_LOG("HStreamDepthData::Start streamId:%{public}d hdiStreamId:%{public}d With capture ID: %{public}d",
153         GetFwkStreamId(), GetHdiStreamId(), preparedCaptureId);
154 
155     std::lock_guard<std::mutex> startStopLock(streamStartStopLock_);
156     HStreamCommon::PrintCaptureDebugLog(cameraAbility_);
157     CamRetCode rc = (CamRetCode)(streamOperator->Capture(preparedCaptureId, captureInfo, true));
158     if (rc != HDI::Camera::V1_0::NO_ERROR) {
159         ResetCaptureId();
160         MEDIA_ERR_LOG("HStreamDepthData::Start Failed with error Code:%{public}d", rc);
161         CameraReportUtils::ReportCameraError(
162             "HStreamDepthData::Start", rc, true, CameraReportUtils::GetCallerInfo());
163         ret = HdiToServiceError(rc);
164     } else {
165         depthDataStreamStatus_ = DepthDataStreamStatus::STARTED;
166     }
167 
168     return ret;
169 }
170 
Stop()171 int32_t HStreamDepthData::Stop()
172 {
173     CAMERA_SYNC_TRACE;
174     auto streamOperator = GetStreamOperator();
175     if (streamOperator == nullptr) {
176         MEDIA_INFO_LOG("HStreamDepthData::Stop streamOperator is null");
177         return CAMERA_INVALID_STATE;
178     }
179     auto preparedCaptureId = GetPreparedCaptureId();
180     MEDIA_INFO_LOG("HStreamDepthData::Start streamId:%{public}d hdiStreamId:%{public}d With capture ID: %{public}d",
181         GetFwkStreamId(), GetHdiStreamId(), preparedCaptureId);
182     if (preparedCaptureId == CAPTURE_ID_UNSET) {
183         MEDIA_ERR_LOG("HStreamDepthData::Stop, Stream not started yet");
184         return CAMERA_INVALID_STATE;
185     }
186     int32_t ret = CAMERA_OK;
187     {
188         std::lock_guard<std::mutex> startStopLock(streamStartStopLock_);
189         ret = StopStream();
190         if (ret != CAMERA_OK) {
191             MEDIA_ERR_LOG("HStreamDepthData::Stop Failed with errorCode:%{public}d, curCaptureID_: %{public}d",
192                           ret, preparedCaptureId);
193         } else {
194             depthDataStreamStatus_ = DepthDataStreamStatus::STOPED;
195         }
196     }
197     return ret;
198 }
199 
Release()200 int32_t HStreamDepthData::Release()
201 {
202     return ReleaseStream(false);
203 }
204 
ReleaseStream(bool isDelay)205 int32_t HStreamDepthData::ReleaseStream(bool isDelay)
206 {
207     {
208         std::lock_guard<std::mutex> lock(callbackLock_);
209         streamDepthDataCallback_ = nullptr;
210     }
211     return HStreamCommon::ReleaseStream(isDelay);
212 }
213 
SetCallback(sptr<IStreamDepthDataCallback>& callback)214 int32_t HStreamDepthData::SetCallback(sptr<IStreamDepthDataCallback>& callback)
215 {
216     if (callback == nullptr) {
217         MEDIA_ERR_LOG("HStreamDepthData::SetCallback callback is null");
218         return CAMERA_INVALID_ARG;
219     }
220     std::lock_guard<std::mutex> lock(callbackLock_);
221     streamDepthDataCallback_ = callback;
222     return CAMERA_OK;
223 }
224 
OnDepthDataError(int32_t errorType)225 int32_t HStreamDepthData::OnDepthDataError(int32_t errorType)
226 {
227     std::lock_guard<std::mutex> lock(callbackLock_);
228     if (streamDepthDataCallback_ != nullptr) {
229         int32_t depthDataErrorCode;
230         if (errorType == BUFFER_LOST) {
231             depthDataErrorCode = CAMERA_STREAM_BUFFER_LOST;
232         } else {
233             depthDataErrorCode = CAMERA_UNKNOWN_ERROR;
234         }
235         CAMERA_SYSEVENT_FAULT(CreateMsg("Depth OnDepthDataError! errorCode:%d", depthDataErrorCode));
236         streamDepthDataCallback_->OnDepthDataError(depthDataErrorCode);
237     }
238     return CAMERA_OK;
239 }
240 
DumpStreamInfo(CameraInfoDumper& infoDumper)241 void HStreamDepthData::DumpStreamInfo(CameraInfoDumper& infoDumper)
242 {
243     infoDumper.Title("depth stream");
244     HStreamCommon::DumpStreamInfo(infoDumper);
245 }
246 
OperatePermissionCheck(uint32_t interfaceCode)247 int32_t HStreamDepthData::OperatePermissionCheck(uint32_t interfaceCode)
248 {
249     switch (static_cast<StreamDepthDataInterfaceCode>(interfaceCode)) {
250         case StreamDepthDataInterfaceCode::CAMERA_STREAM_DEPTH_DATA_START: {
251             auto callerToken = IPCSkeleton::GetCallingTokenID();
252             if (callerToken_ != callerToken) {
253                 MEDIA_ERR_LOG("HStreamDepthData::OperatePermissionCheck fail, callerToken invalid!");
254                 return CAMERA_OPERATION_NOT_ALLOWED;
255             }
256             break;
257         }
258         default:
259             break;
260     }
261     return CAMERA_OK;
262 }
263 } // namespace CameraStandard
264 } // namespace OHOS
265