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 "output/depth_data_output.h"
17 
18 #include <cstdint>
19 #include <limits>
20 #include <memory>
21 #include <utility>
22 #include <variant>
23 
24 #include "camera_device_ability_items.h"
25 #include "camera_error_code.h"
26 #include "camera_log.h"
27 #include "camera_manager.h"
28 #include "camera_metadata_operator.h"
29 #include "camera_output_capability.h"
30 #include "camera_util.h"
31 #include "hstream_depth_data_callback_stub.h"
32 #include "image_format.h"
33 #include "metadata_common_utils.h"
34 #include "pixel_map.h"
35 #include "session/capture_session.h"
36 
37 namespace OHOS {
38 namespace CameraStandard {
39 
OnDepthDataError(int32_t errorCode)40 int32_t DepthDataOutputCallbackImpl::OnDepthDataError(int32_t errorCode)
41 {
42     auto item = depthDataOutput_.promote();
43     if (item != nullptr) {
44         auto callback = item->GetApplicationCallback();
45         if (callback != nullptr) {
46             callback->OnDepthDataError(errorCode);
47         } else {
48             MEDIA_INFO_LOG("Discarding DepthDataOutputCallbackImpl::OnDepthDataError callback in depthoutput");
49         }
50     } else {
51         MEDIA_INFO_LOG("DepthDataOutputCallbackImpl::OnDepthDataError DepthDataOutput is nullptr");
52     }
53     return CAMERA_OK;
54 }
55 
DepthDataOutput(sptr<IBufferProducer> bufferProducer)56 DepthDataOutput::DepthDataOutput(sptr<IBufferProducer> bufferProducer)
57     : CaptureOutput(CAPTURE_OUTPUT_TYPE_DEPTH_DATA, StreamType::DEPTH, bufferProducer, nullptr)
58 {
59     DepthDataFormat_ = 0;
60     DepthDataSize_.height = 0;
61     DepthDataSize_.width = 0;
62 }
63 
~DepthDataOutput()64 DepthDataOutput::~DepthDataOutput()
65 {
66     MEDIA_DEBUG_LOG("Enter Into DepthDataOutput::~DepthDataOutput()");
67 }
68 
Start()69 int32_t DepthDataOutput::Start()
70 {
71     CAMERA_SYNC_TRACE;
72     SetDataAccuracy(GetDepthProfile()->GetDataAccuracy());
73     std::lock_guard<std::mutex> lock(asyncOpMutex_);
74     MEDIA_DEBUG_LOG("Enter Into DepthDataOutput::Start");
75     auto captureSession = GetSession();
76     if (captureSession == nullptr || !captureSession->IsSessionCommited()) {
77         MEDIA_ERR_LOG("DepthDataOutput Failed to Start!, session not config");
78         return CameraErrorCode::SESSION_NOT_CONFIG;
79     }
80     if (GetStream() == nullptr) {
81         MEDIA_ERR_LOG("DepthDataOutput Failed to Start!, GetStream is nullptr");
82         return CameraErrorCode::SERVICE_FATL_ERROR;
83     }
84     auto itemStream = static_cast<IStreamDepthData*>(GetStream().GetRefPtr());
85     int32_t errCode = CAMERA_UNKNOWN_ERROR;
86     if (itemStream) {
87         errCode = itemStream->Start();
88         if (errCode != CAMERA_OK) {
89             MEDIA_ERR_LOG("DepthDataOutput Failed to Start!, errCode: %{public}d", errCode);
90         }
91     } else {
92         MEDIA_ERR_LOG("DepthDataOutput::Start itemStream is nullptr");
93     }
94     return ServiceToCameraError(errCode);
95 }
96 
Stop()97 int32_t DepthDataOutput::Stop()
98 {
99     std::lock_guard<std::mutex> lock(asyncOpMutex_);
100     MEDIA_DEBUG_LOG("Enter Into DepthDataOutput::Stop");
101     if (GetStream() == nullptr) {
102         MEDIA_ERR_LOG("DepthDataOutput Failed to Stop!, GetStream is nullptr");
103         return CameraErrorCode::SERVICE_FATL_ERROR;
104     }
105     auto itemStream = static_cast<IStreamDepthData*>(GetStream().GetRefPtr());
106     int32_t errCode = CAMERA_UNKNOWN_ERROR;
107     if (itemStream) {
108         errCode = itemStream->Stop();
109         if (errCode != CAMERA_OK) {
110             MEDIA_ERR_LOG("DepthDataOutput Failed to Stop!, errCode: %{public}d", errCode);
111         }
112     } else {
113         MEDIA_ERR_LOG("DepthDataOutput::Stop itemStream is nullptr");
114     }
115     return ServiceToCameraError(errCode);
116 }
117 
SetDataAccuracy(int32_t dataAccuracy)118 int32_t DepthDataOutput::SetDataAccuracy(int32_t dataAccuracy)
119 {
120     CAMERA_SYNC_TRACE;
121     std::lock_guard<std::mutex> lock(asyncOpMutex_);
122     MEDIA_DEBUG_LOG("Enter Into DepthDataOutput::SetDataAccuracy");
123     if (GetStream() == nullptr) {
124         MEDIA_ERR_LOG("DepthDataOutput Failed to SetDataAccuracy!, GetStream is nullptr");
125         return CameraErrorCode::SERVICE_FATL_ERROR;
126     }
127     auto itemStream = static_cast<IStreamDepthData*>(GetStream().GetRefPtr());
128     int32_t errCode = CAMERA_UNKNOWN_ERROR;
129     if (itemStream) {
130         errCode = itemStream->SetDataAccuracy(dataAccuracy);
131         if (errCode != CAMERA_OK) {
132             MEDIA_ERR_LOG("DepthDataOutput Failed to SetDataAccuracy!, errCode: %{public}d", errCode);
133         }
134     } else {
135         MEDIA_ERR_LOG("DepthDataOutput::SetDataAccuracy itemStream is nullptr");
136     }
137     return ServiceToCameraError(errCode);
138 }
139 
CreateStream()140 int32_t DepthDataOutput::CreateStream()
141 {
142     MEDIA_INFO_LOG("DepthDataOutput::CreateStream enter");
143     return CameraErrorCode::SUCCESS;
144 }
145 
Release()146 int32_t DepthDataOutput::Release()
147 {
148     {
149         std::lock_guard<std::mutex> lock(outputCallbackMutex_);
150         svcCallback_ = nullptr;
151         appCallback_ = nullptr;
152     }
153     std::lock_guard<std::mutex> lock(asyncOpMutex_);
154     MEDIA_DEBUG_LOG("Enter Into DepthDataOutput::Release");
155     if (GetStream() == nullptr) {
156         MEDIA_ERR_LOG("DepthDataOutput Failed to Release!, GetStream is nullptr");
157         return CameraErrorCode::SERVICE_FATL_ERROR;
158     }
159     auto itemStream = static_cast<IStreamDepthData*>(GetStream().GetRefPtr());
160     int32_t errCode = CAMERA_UNKNOWN_ERROR;
161     if (itemStream) {
162         errCode = itemStream->Release();
163         if (errCode != CAMERA_OK) {
164             MEDIA_ERR_LOG("Failed to release DepthDataOutput!, errCode: %{public}d", errCode);
165         }
166     } else {
167         MEDIA_ERR_LOG("DepthDataOutput::Release() itemStream is nullptr");
168     }
169     CaptureOutput::Release();
170     return ServiceToCameraError(errCode);
171 }
172 
SetCallback(std::shared_ptr<DepthDataStateCallback> callback)173 void DepthDataOutput::SetCallback(std::shared_ptr<DepthDataStateCallback> callback)
174 {
175     std::lock_guard<std::mutex> lock(outputCallbackMutex_);
176     appCallback_ = callback;
177     if (appCallback_ != nullptr) {
178         if (svcCallback_ == nullptr) {
179             svcCallback_ = new (std::nothrow) DepthDataOutputCallbackImpl(this);
180             if (svcCallback_ == nullptr) {
181                 MEDIA_ERR_LOG("new DepthDataOutputCallbackImpl Failed to register callback");
182                 appCallback_ = nullptr;
183                 return;
184             }
185         }
186         if (GetStream() == nullptr) {
187             MEDIA_ERR_LOG("DepthDataOutput Failed to SetCallback!, GetStream is nullptr");
188             return;
189         }
190         auto itemStream = static_cast<IStreamDepthData*>(GetStream().GetRefPtr());
191         int32_t errorCode = CAMERA_OK;
192         if (itemStream) {
193             errorCode = itemStream->SetCallback(svcCallback_);
194         } else {
195             MEDIA_ERR_LOG("DepthDataOutput::SetCallback itemStream is nullptr");
196         }
197         if (errorCode != CAMERA_OK) {
198             MEDIA_ERR_LOG("DepthDataOutput::SetCallback Failed to register callback, errorCode: %{public}d", errorCode);
199             svcCallback_ = nullptr;
200             appCallback_ = nullptr;
201         }
202     }
203     return;
204 }
205 
GetApplicationCallback()206 std::shared_ptr<DepthDataStateCallback> DepthDataOutput::GetApplicationCallback()
207 {
208     std::lock_guard<std::mutex> lock(outputCallbackMutex_);
209     return appCallback_;
210 }
211 
CameraServerDied(pid_t pid)212 void DepthDataOutput::CameraServerDied(pid_t pid)
213 {
214     MEDIA_ERR_LOG("camera server has died, pid:%{public}d!", pid);
215     std::lock_guard<std::mutex> lock(outputCallbackMutex_);
216     if (appCallback_ != nullptr) {
217         MEDIA_DEBUG_LOG("appCallback not nullptr");
218         int32_t serviceErrorType = ServiceToCameraError(CAMERA_INVALID_STATE);
219         appCallback_->OnDepthDataError(serviceErrorType);
220     }
221 }
222 } // namespace CameraStandard
223 } // namespace OHOS
224