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_stream_data_process.h"
17
18 #include "anonymous_string.h"
19 #include "distributed_camera_constants.h"
20 #include "distributed_camera_errno.h"
21 #include "distributed_hardware_log.h"
22
23 #include "dcamera_pipeline_source.h"
24 #include "dcamera_stream_data_process_pipeline_listener.h"
25
26 namespace OHOS {
27 namespace DistributedHardware {
DCameraStreamDataProcess(std::string devId,std::string dhId,DCStreamType streamType)28 DCameraStreamDataProcess::DCameraStreamDataProcess(std::string devId, std::string dhId, DCStreamType streamType)
29 : devId_(devId), dhId_(dhId), streamType_(streamType)
30 {
31 DHLOGI("DCameraStreamDataProcess Constructor devId %{public}s dhId %{public}s", GetAnonyString(devId_).c_str(),
32 GetAnonyString(dhId_).c_str());
33 pipeline_ = nullptr;
34 listener_ = nullptr;
35 }
36
~DCameraStreamDataProcess()37 DCameraStreamDataProcess::~DCameraStreamDataProcess()
38 {
39 DHLOGI("DCameraStreamDataProcess Destructor devId %{public}s dhId %{public}s streamType: %{public}d",
40 GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamType_);
41 streamIds_.clear();
42 producers_.clear();
43 if (pipeline_ != nullptr) {
44 pipeline_->DestroyDataProcessPipeline();
45 }
46 }
47
FeedStream(std::shared_ptr<DataBuffer> & buffer)48 void DCameraStreamDataProcess::FeedStream(std::shared_ptr<DataBuffer>& buffer)
49 {
50 for (auto streamId : streamIds_) {
51 uint64_t buffersSize = static_cast<uint64_t>(buffer->Size());
52 DHLOGD("FeedStream devId %{public}s dhId %{public}s streamId %{public}d streamType %{public}d streamSize: "
53 "%{public}" PRIu64, GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamId,
54 streamType_, buffersSize);
55 }
56 switch (streamType_) {
57 case SNAPSHOT_FRAME: {
58 FeedStreamToSnapShot(buffer);
59 break;
60 }
61 case CONTINUOUS_FRAME: {
62 FeedStreamToContinue(buffer);
63 break;
64 }
65 default:
66 break;
67 }
68 }
69
ConfigStreams(std::shared_ptr<DCameraStreamConfig> & dstConfig,std::set<int32_t> & streamIds)70 void DCameraStreamDataProcess::ConfigStreams(std::shared_ptr<DCameraStreamConfig>& dstConfig,
71 std::set<int32_t>& streamIds)
72 {
73 CHECK_AND_RETURN_LOG(dstConfig == nullptr, "dstConfig is nullptr");
74 for (auto streamId : streamIds) {
75 DHLOGI("ConfigStreams devId %{public}s dhId %{public}s streamId %{public}d, width: %{public}d, height: "
76 "%{public}d, format: %{public}d, dataspace: %{public}d, encodeType: %{public}d, streamType: %{public}d",
77 GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamId, dstConfig->width_,
78 dstConfig->height_, dstConfig->format_, dstConfig->dataspace_, dstConfig->encodeType_, dstConfig->type_);
79 }
80 dstConfig_ = dstConfig;
81 streamIds_ = streamIds;
82 }
83
ReleaseStreams(std::set<int32_t> & streamIds)84 void DCameraStreamDataProcess::ReleaseStreams(std::set<int32_t>& streamIds)
85 {
86 for (auto streamId : streamIds) {
87 DHLOGI("ReleaseStreams devId %{public}s dhId %{public}s streamId %{public}d streamType %{public}d",
88 GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamId, streamType_);
89 }
90 std::lock_guard<std::mutex> autoLock(producerMutex_);
91 for (auto iter = streamIds.begin(); iter != streamIds.end(); iter++) {
92 int32_t streamId = *iter;
93 DHLOGI("ReleaseStreams devId %{public}s dhId %{public}s streamId: %{public}d", GetAnonyString(devId_).c_str(),
94 GetAnonyString(dhId_).c_str(), streamId);
95 streamIds_.erase(streamId);
96 auto producerIter = producers_.find(streamId);
97 if (producerIter == producers_.end()) {
98 continue;
99 }
100 producerIter->second->Stop();
101 producers_.erase(streamId);
102 }
103 }
104
StartCapture(std::shared_ptr<DCameraStreamConfig> & srcConfig,std::set<int32_t> & streamIds)105 void DCameraStreamDataProcess::StartCapture(std::shared_ptr<DCameraStreamConfig>& srcConfig,
106 std::set<int32_t>& streamIds)
107 {
108 CHECK_AND_RETURN_LOG(srcConfig == nullptr, "srcConfig is nullptr");
109 for (auto iter = streamIds.begin(); iter != streamIds.end(); iter++) {
110 DHLOGI("StartCapture devId %{public}s dhId %{public}s streamType: %{public}d streamId: %{public}d, "
111 "srcConfig: width: %{public}d, height: %{public}d, format: %{public}d, dataspace: %{public}d, "
112 "streamType: %{public}d, encodeType: %{public}d",
113 GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamType_, *iter,
114 srcConfig->width_, srcConfig->height_, srcConfig->format_, srcConfig->dataspace_,
115 srcConfig->type_, srcConfig->encodeType_);
116 }
117 srcConfig_ = srcConfig;
118 if (streamType_ == CONTINUOUS_FRAME) {
119 CreatePipeline();
120 }
121 {
122 std::lock_guard<std::mutex> autoLock(producerMutex_);
123 for (auto iter = streamIds_.begin(); iter != streamIds_.end(); iter++) {
124 uint32_t streamId = *iter;
125 DHLOGI("StartCapture streamId: %{public}d", streamId);
126 if (streamIds.find(streamId) == streamIds.end()) {
127 continue;
128 }
129
130 DHLOGI("StartCapture findProducer devId %{public}s dhId %{public}s streamType: %{public}d streamId: "
131 "%{public}d", GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamType_, streamId);
132 auto producerIter = producers_.find(streamId);
133 if (producerIter != producers_.end()) {
134 continue;
135 }
136 DHLOGI("StartCapture CreateProducer devId %{public}s dhId %{public}s streamType: %{public}d streamId: "
137 "%{public}d", GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamType_, streamId);
138 producers_[streamId] =
139 std::make_shared<DCameraStreamDataProcessProducer>(devId_, dhId_, streamId, streamType_);
140 producers_[streamId]->Start();
141 }
142 }
143 }
144
StopCapture(std::set<int32_t> & streamIds)145 void DCameraStreamDataProcess::StopCapture(std::set<int32_t>& streamIds)
146 {
147 for (auto iter = streamIds.begin(); iter != streamIds.end(); iter++) {
148 DHLOGI("StopCapture devId %{public}s dhId %{public}s streamType: %{public}d streamId: %{public}d",
149 GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamType_, *iter);
150 }
151 {
152 std::lock_guard<std::mutex> autoLock(producerMutex_);
153 for (auto iter = streamIds_.begin(); iter != streamIds_.end(); iter++) {
154 uint32_t streamId = *iter;
155 DHLOGI("StopCapture streamId: %{public}d", streamId);
156 if (streamIds.find(streamId) == streamIds.end()) {
157 continue;
158 }
159
160 DHLOGI("StopCapture findProducer devId %{public}s dhId %{public}s streamType: %{public}d streamId: "
161 "%{public}d", GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamType_, streamId);
162 auto producerIter = producers_.find(streamId);
163 if (producerIter == producers_.end()) {
164 DHLOGE("StopCapture no producer, devId %{public}s dhId %{public}s streamType: %{public}d streamId: "
165 "%{public}d", GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamType_, streamId);
166 continue;
167 }
168 DHLOGI("StopCapture stop producer, devId %{public}s dhId %{public}s streamType: %{public}d streamId: "
169 "%{public}d", GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamType_, streamId);
170 producerIter->second->Stop();
171 producerIter = producers_.erase(producerIter);
172 }
173 }
174 }
175
GetAllStreamIds(std::set<int32_t> & streamIds)176 void DCameraStreamDataProcess::GetAllStreamIds(std::set<int32_t>& streamIds)
177 {
178 streamIds = streamIds_;
179 }
180
GetProducerSize()181 int32_t DCameraStreamDataProcess::GetProducerSize()
182 {
183 DHLOGI("DCameraStreamDataProcess GetProducerSize devId %{public}s dhId %{public}s",
184 GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str());
185 std::lock_guard<std::mutex> autoLock(producerMutex_);
186 return producers_.size();
187 }
188
FeedStreamToSnapShot(const std::shared_ptr<DataBuffer> & buffer)189 void DCameraStreamDataProcess::FeedStreamToSnapShot(const std::shared_ptr<DataBuffer>& buffer)
190 {
191 CHECK_AND_RETURN_LOG(buffer == nullptr, "buffer is nullptr.");
192 uint64_t buffersSize = static_cast<uint64_t>(buffer->Size());
193 DHLOGD("DCameraStreamDataProcess FeedStreamToSnapShot devId %{public}s dhId %{public}s streamType %{public}d "
194 "streamSize: %{public}" PRIu64, GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(),
195 streamType_, buffersSize);
196 std::lock_guard<std::mutex> autoLock(producerMutex_);
197 for (auto iter = producers_.begin(); iter != producers_.end(); iter++) {
198 iter->second->FeedStream(buffer);
199 }
200 }
201
FeedStreamToContinue(const std::shared_ptr<DataBuffer> & buffer)202 void DCameraStreamDataProcess::FeedStreamToContinue(const std::shared_ptr<DataBuffer>& buffer)
203 {
204 CHECK_AND_RETURN_LOG(buffer == nullptr, "buffer is nullptr.");
205 uint64_t buffersSize = static_cast<uint64_t>(buffer->Size());
206 DHLOGD("DCameraStreamDataProcess FeedStreamToContinue devId %{public}s dhId %{public}s streamType %{public}d "
207 "streamSize: %{public}" PRIu64, GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(),
208 streamType_, buffersSize);
209 std::lock_guard<std::mutex> autoLock(pipelineMutex_);
210 std::vector<std::shared_ptr<DataBuffer>> buffers;
211 buffers.push_back(buffer);
212 if (pipeline_ == nullptr) {
213 buffersSize = static_cast<uint64_t>(buffer->Size());
214 DHLOGE("pipeline null devId %{public}s dhId %{public}s type: %{public}d streamSize: %{public}" PRIu64,
215 GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(), streamType_, buffersSize);
216 return;
217 }
218 int32_t ret = pipeline_->ProcessData(buffers);
219 if (ret != DCAMERA_OK) {
220 DHLOGE("pipeline ProcessData failed, ret: %{public}d", ret);
221 }
222 }
223
OnProcessedVideoBuffer(const std::shared_ptr<DataBuffer> & videoResult)224 void DCameraStreamDataProcess::OnProcessedVideoBuffer(const std::shared_ptr<DataBuffer>& videoResult)
225 {
226 CHECK_AND_LOG(videoResult == nullptr, "videoResult is nullptr.");
227 uint64_t resultSize = static_cast<uint64_t>(videoResult->Size());
228 DHLOGI("DCameraStreamDataProcess OnProcessedVideoBuffer devId %{public}s dhId %{public}s streamType: %{public}d "
229 "streamSize: %{public}" PRIu64, GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str(),
230 streamType_, resultSize);
231 std::lock_guard<std::mutex> autoLock(producerMutex_);
232 for (auto iter = producers_.begin(); iter != producers_.end(); iter++) {
233 iter->second->FeedStream(videoResult);
234 }
235 }
236
OnError(const DataProcessErrorType errorType)237 void DCameraStreamDataProcess::OnError(const DataProcessErrorType errorType)
238 {
239 DHLOGE("DCameraStreamDataProcess OnError pipeline errorType: %{public}d", errorType);
240 }
241
CreatePipeline()242 void DCameraStreamDataProcess::CreatePipeline()
243 {
244 DHLOGI("DCameraStreamDataProcess CreatePipeline devId %{public}s dhId %{public}s",
245 GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str());
246 std::lock_guard<std::mutex> autoLock(pipelineMutex_);
247 if (pipeline_ != nullptr) {
248 DHLOGI("DCameraStreamDataProcess CreatePipeline already exist, devId %{public}s dhId %{public}s",
249 GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str());
250 return;
251 }
252 pipeline_ = std::make_shared<DCameraPipelineSource>();
253 auto process = std::shared_ptr<DCameraStreamDataProcess>(shared_from_this());
254 listener_ = std::make_shared<DCameraStreamDataProcessPipelineListener>(process);
255 VideoConfigParams srcParams(GetPipelineCodecType(srcConfig_->encodeType_), GetPipelineFormat(srcConfig_->format_),
256 DCAMERA_PRODUCER_FPS_DEFAULT, srcConfig_->width_, srcConfig_->height_);
257 VideoConfigParams dstParams(GetPipelineCodecType(dstConfig_->encodeType_), GetPipelineFormat(dstConfig_->format_),
258 DCAMERA_PRODUCER_FPS_DEFAULT, dstConfig_->width_, dstConfig_->height_);
259 int32_t ret = pipeline_->CreateDataProcessPipeline(PipelineType::VIDEO, srcParams, dstParams, listener_);
260 if (ret != DCAMERA_OK) {
261 DHLOGE("DCameraStreamDataProcess CreateDataProcessPipeline type: %{public}d failed, ret: %{public}d",
262 PipelineType::VIDEO, ret);
263 }
264 }
265
DestroyPipeline()266 void DCameraStreamDataProcess::DestroyPipeline()
267 {
268 DHLOGI("DCameraStreamDataProcess DestroyPipeline devId %{public}s dhId %{public}s",
269 GetAnonyString(devId_).c_str(), GetAnonyString(dhId_).c_str());
270 std::lock_guard<std::mutex> autoLock(pipelineMutex_);
271 if (pipeline_ == nullptr) {
272 return;
273 }
274 pipeline_->DestroyDataProcessPipeline();
275 pipeline_ = nullptr;
276 }
277
GetPipelineCodecType(DCEncodeType encodeType)278 VideoCodecType DCameraStreamDataProcess::GetPipelineCodecType(DCEncodeType encodeType)
279 {
280 VideoCodecType codecType;
281 switch (encodeType) {
282 case ENCODE_TYPE_H264:
283 codecType = VideoCodecType::CODEC_H264;
284 break;
285 case ENCODE_TYPE_H265:
286 codecType = VideoCodecType::CODEC_H265;
287 break;
288 case ENCODE_TYPE_MPEG4_ES:
289 codecType = VideoCodecType::CODEC_MPEG4_ES;
290 break;
291 default:
292 codecType = VideoCodecType::NO_CODEC;
293 break;
294 }
295 return codecType;
296 }
297
GetPipelineFormat(int32_t format)298 Videoformat DCameraStreamDataProcess::GetPipelineFormat(int32_t format)
299 {
300 Videoformat videoFormat;
301 switch (format) {
302 case OHOS_CAMERA_FORMAT_RGBA_8888:
303 videoFormat = Videoformat::RGBA_8888;
304 break;
305 default:
306 videoFormat = Videoformat::NV21;
307 break;
308 }
309 return videoFormat;
310 }
311 } // namespace DistributedHardware
312 } // namespace OHOS
313