1 /*
2 * Copyright (c) 2021-2023 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 "distributed_camera_sink_service.h"
17
18 #include "if_system_ability_manager.h"
19 #include "ipc_skeleton.h"
20 #include "ipc_types.h"
21 #include "iservice_registry.h"
22 #include "string_ex.h"
23 #include "system_ability_definition.h"
24
25 #include "anonymous_string.h"
26 #include "dcamera_handler.h"
27 #include "dcamera_hisysevent_adapter.h"
28 #include "dcamera_sink_service_ipc.h"
29 #include "distributed_camera_errno.h"
30 #include "distributed_hardware_log.h"
31
32 namespace OHOS {
33 namespace DistributedHardware {
34 REGISTER_SYSTEM_ABILITY_BY_ID(DistributedCameraSinkService, DISTRIBUTED_HARDWARE_CAMERA_SINK_SA_ID, true);
35
36 static CameraDumpInfo g_camDump;
37 DistributedCameraSinkService* DistributedCameraSinkService::dcSinkService;
DistributedCameraSinkService(int32_t saId,bool runOnCreate)38 DistributedCameraSinkService::DistributedCameraSinkService(int32_t saId, bool runOnCreate)
39 : SystemAbility(saId, runOnCreate)
40 {
41 dcSinkService = this;
42 }
43
OnStart()44 void DistributedCameraSinkService::OnStart()
45 {
46 DHLOGI("DistributedCameraSinkService OnStart");
47 if (state_ == DCameraServiceState::DCAMERA_SRV_STATE_RUNNING) {
48 DHLOGI("DistributedCameraSinkService has already started.");
49 return;
50 }
51
52 if (!Init()) {
53 DHLOGE("DistributedCameraSinkService init failed");
54 return;
55 }
56 state_ = DCameraServiceState::DCAMERA_SRV_STATE_RUNNING;
57 DHLOGI("DCameraServiceState OnStart service success.");
58 }
59
Init()60 bool DistributedCameraSinkService::Init()
61 {
62 DHLOGI("DistributedCameraSinkService start init");
63 DCameraSinkServiceIpc::GetInstance().Init();
64 if (!registerToService_) {
65 bool ret = Publish(this);
66 if (!ret) {
67 DHLOGE("DistributedCameraSinkService Publish service failed");
68 return false;
69 }
70 registerToService_ = true;
71 }
72 DHLOGI("DistributedCameraSinkService init success");
73 return true;
74 }
75
OnStop()76 void DistributedCameraSinkService::OnStop()
77 {
78 DHLOGI("DistributedCameraSinkService OnStop service");
79 state_ = DCameraServiceState::DCAMERA_SRV_STATE_NOT_START;
80 registerToService_ = false;
81 DCameraSinkServiceIpc::GetInstance().UnInit();
82 }
83
InitSink(const std::string & params)84 int32_t DistributedCameraSinkService::InitSink(const std::string& params)
85 {
86 DHLOGI("start");
87 sinkVer_ = params;
88 g_camDump.version = sinkVer_;
89 int32_t ret = DCameraHandler::GetInstance().Initialize();
90 if (ret != DCAMERA_OK) {
91 DHLOGE("handler initialize failed, ret: %d", ret);
92 return ret;
93 }
94
95 std::vector<std::string> cameras = DCameraHandler::GetInstance().GetCameras();
96 if (cameras.empty()) {
97 DHLOGE("no camera device");
98 return DCAMERA_BAD_VALUE;
99 }
100 g_camDump.camNumber = static_cast<int32_t>(cameras.size());
101 for (auto& dhId : cameras) {
102 std::shared_ptr<DCameraSinkDev> sinkDevice = std::make_shared<DCameraSinkDev>(dhId);
103 ret = sinkDevice->Init();
104 if (ret != DCAMERA_OK) {
105 DHLOGE("sink device init failed, ret: %d", ret);
106 return ret;
107 }
108 {
109 std::lock_guard<std::mutex> lock(mapMutex_);
110 camerasMap_.emplace(dhId, sinkDevice);
111 }
112 }
113 DHLOGI("success");
114 return DCAMERA_OK;
115 }
116
ReleaseSink()117 int32_t DistributedCameraSinkService::ReleaseSink()
118 {
119 DHLOGI("enter");
120 {
121 std::lock_guard<std::mutex> lock(mapMutex_);
122 for (auto iter = camerasMap_.begin(); iter != camerasMap_.end(); iter++) {
123 std::shared_ptr<DCameraSinkDev> sinkDevice = iter->second;
124 int32_t ret = sinkDevice->UnInit();
125 if (ret != DCAMERA_OK) {
126 DHLOGE("release sink device failed, ret: %d", ret);
127 }
128 }
129 camerasMap_.clear();
130 }
131
132 auto systemAbilityMgr = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
133 if (systemAbilityMgr == nullptr) {
134 DHLOGE("sink systemAbilityMgr is null");
135 return DCAMERA_BAD_VALUE;
136 }
137 int32_t ret = systemAbilityMgr->UnloadSystemAbility(DISTRIBUTED_HARDWARE_CAMERA_SINK_SA_ID);
138 if (ret != DCAMERA_OK) {
139 DHLOGE("sink systemAbilityMgr UnLoadSystemAbility failed, ret: %d", ret);
140 return DCAMERA_BAD_VALUE;
141 }
142 DHLOGI("sink systemAbilityMgr UnLoadSystemAbility success");
143 return DCAMERA_OK;
144 }
145
SubscribeLocalHardware(const std::string & dhId,const std::string & parameters)146 int32_t DistributedCameraSinkService::SubscribeLocalHardware(const std::string& dhId, const std::string& parameters)
147 {
148 DHLOGI("dhId: %s", GetAnonyString(dhId).c_str());
149 std::shared_ptr<DCameraSinkDev> sinkDevice = nullptr;
150 {
151 std::lock_guard<std::mutex> lock(mapMutex_);
152 auto iter = camerasMap_.find(dhId);
153 if (iter == camerasMap_.end()) {
154 DHLOGE("device not found");
155 return DCAMERA_NOT_FOUND;
156 }
157 sinkDevice = iter->second;
158 }
159
160 int32_t ret = sinkDevice->SubscribeLocalHardware(parameters);
161 if (ret != DCAMERA_OK) {
162 DHLOGE("SubscribeLocalHardware failed, ret: %d", ret);
163 return ret;
164 }
165 DHLOGI("SubscribeLocalHardware success");
166 return DCAMERA_OK;
167 }
168
UnsubscribeLocalHardware(const std::string & dhId)169 int32_t DistributedCameraSinkService::UnsubscribeLocalHardware(const std::string& dhId)
170 {
171 DHLOGI("dhId: %s", GetAnonyString(dhId).c_str());
172 std::shared_ptr<DCameraSinkDev> sinkDevice = nullptr;
173 {
174 std::lock_guard<std::mutex> lock(mapMutex_);
175 auto iter = camerasMap_.find(dhId);
176 if (iter == camerasMap_.end()) {
177 DHLOGE("device not found");
178 return DCAMERA_NOT_FOUND;
179 }
180 sinkDevice = iter->second;
181 }
182
183 int32_t ret = sinkDevice->UnsubscribeLocalHardware();
184 if (ret != DCAMERA_OK) {
185 DHLOGE("UnsubscribeLocalHardware failed, ret: %d", ret);
186 return ret;
187 }
188 DHLOGI("UnsubscribeLocalHardware success");
189 return DCAMERA_OK;
190 }
191
StopCapture(const std::string & dhId)192 int32_t DistributedCameraSinkService::StopCapture(const std::string& dhId)
193 {
194 DHLOGI("dhId: %s", GetAnonyString(dhId).c_str());
195 std::shared_ptr<DCameraSinkDev> sinkDevice = nullptr;
196 {
197 std::lock_guard<std::mutex> lock(mapMutex_);
198 auto iter = camerasMap_.find(dhId);
199 if (iter == camerasMap_.end()) {
200 DHLOGE("device not found");
201 return DCAMERA_NOT_FOUND;
202 }
203 sinkDevice = iter->second;
204 }
205
206 int32_t ret = sinkDevice->StopCapture();
207 if (ret != DCAMERA_OK) {
208 DHLOGE("StopCapture failed, ret: %d", ret);
209 return ret;
210 }
211 DHLOGI("StopCapture success");
212 return DCAMERA_OK;
213 }
214
ChannelNeg(const std::string & dhId,std::string & channelInfo)215 int32_t DistributedCameraSinkService::ChannelNeg(const std::string& dhId, std::string& channelInfo)
216 {
217 DHLOGI("dhId: %s", GetAnonyString(dhId).c_str());
218 std::shared_ptr<DCameraSinkDev> sinkDevice = nullptr;
219 {
220 std::lock_guard<std::mutex> lock(mapMutex_);
221 auto iter = camerasMap_.find(dhId);
222 if (iter == camerasMap_.end()) {
223 DHLOGE("device not found");
224 return DCAMERA_NOT_FOUND;
225 }
226 sinkDevice = iter->second;
227 }
228
229 int32_t ret = sinkDevice->ChannelNeg(channelInfo);
230 if (ret != DCAMERA_OK) {
231 DHLOGE("ChannelNeg failed, ret: %d", ret);
232 return ret;
233 }
234 DHLOGI("ChannelNeg success");
235 return DCAMERA_OK;
236 }
237
GetCameraInfo(const std::string & dhId,std::string & cameraInfo)238 int32_t DistributedCameraSinkService::GetCameraInfo(const std::string& dhId, std::string& cameraInfo)
239 {
240 DHLOGI("dhId: %s", GetAnonyString(dhId).c_str());
241 std::shared_ptr<DCameraSinkDev> sinkDevice = nullptr;
242 {
243 std::lock_guard<std::mutex> lock(mapMutex_);
244 auto iter = camerasMap_.find(dhId);
245 if (iter == camerasMap_.end()) {
246 DHLOGE("device not found");
247 return DCAMERA_NOT_FOUND;
248 }
249 sinkDevice = iter->second;
250 }
251
252 int32_t ret = sinkDevice->GetCameraInfo(cameraInfo);
253 if (ret != DCAMERA_OK) {
254 DHLOGE("GetCameraInfo failed, ret: %d", ret);
255 return ret;
256 }
257 DHLOGI("GetCameraInfo success");
258 return DCAMERA_OK;
259 }
260
OpenChannel(const std::string & dhId,std::string & openInfo)261 int32_t DistributedCameraSinkService::OpenChannel(const std::string& dhId, std::string& openInfo)
262 {
263 DHLOGI("dhId: %s", GetAnonyString(dhId).c_str());
264 std::shared_ptr<DCameraSinkDev> sinkDevice = nullptr;
265 {
266 std::lock_guard<std::mutex> lock(mapMutex_);
267 auto iter = camerasMap_.find(dhId);
268 if (iter == camerasMap_.end()) {
269 DHLOGE("device not found");
270 return DCAMERA_NOT_FOUND;
271 }
272 sinkDevice = iter->second;
273 }
274
275 int32_t ret = sinkDevice->OpenChannel(openInfo);
276 if (ret != DCAMERA_OK) {
277 DHLOGE("OpenChannel failed, ret: %d", ret);
278 ReportDcamerOptFail(DCAMERA_OPT_FAIL, DCAMERA_SINK_OPEN_CAM_ERROR,
279 CreateMsg("sink service open channel failed, dhId: %s", GetAnonyString(dhId).c_str()));
280 return ret;
281 }
282 DHLOGI("OpenChannel success");
283 return DCAMERA_OK;
284 }
285
CloseChannel(const std::string & dhId)286 int32_t DistributedCameraSinkService::CloseChannel(const std::string& dhId)
287 {
288 DHLOGI("dhId: %s", GetAnonyString(dhId).c_str());
289 std::shared_ptr<DCameraSinkDev> sinkDevice = nullptr;
290 {
291 std::lock_guard<std::mutex> lock(mapMutex_);
292 auto iter = camerasMap_.find(dhId);
293 if (iter == camerasMap_.end()) {
294 DHLOGE("device not found");
295 return DCAMERA_NOT_FOUND;
296 }
297 sinkDevice = iter->second;
298 }
299
300 int32_t ret = sinkDevice->CloseChannel();
301 if (ret != DCAMERA_OK) {
302 DHLOGE("CloseChannel failed, ret: %d", ret);
303 return ret;
304 }
305 DHLOGI("CloseChannel success");
306 return DCAMERA_OK;
307 }
308
Dump(int32_t fd,const std::vector<std::u16string> & args)309 int DistributedCameraSinkService::Dump(int32_t fd, const std::vector<std::u16string>& args)
310 {
311 DHLOGI("DistributedCameraSinkService Dump.");
312 if (args.size() > DUMP_MAX_SIZE) {
313 DHLOGE("DistributedCameraSinkService Dump input is invalid");
314 return DCAMERA_BAD_VALUE;
315 }
316 std::string result;
317 std::vector<std::string> argsStr;
318 for (auto item : args) {
319 argsStr.emplace_back(Str16ToStr8(item));
320 }
321
322 if (!DcameraSinkHidumper::GetInstance().Dump(argsStr, result)) {
323 DHLOGE("Hidump error");
324 return DCAMERA_BAD_VALUE;
325 }
326
327 int ret = dprintf(fd, "%s\n", result.c_str());
328 if (ret < 0) {
329 DHLOGE("dprintf error");
330 return DCAMERA_BAD_VALUE;
331 }
332
333 return DCAMERA_OK;
334 }
335
GetCamIds()336 void DistributedCameraSinkService::GetCamIds()
337 {
338 std::vector<std::string> camIds;
339 {
340 std::lock_guard<std::mutex> lock(mapMutex_);
341 for (auto it = camerasMap_.begin(); it != camerasMap_.end(); it++) {
342 camIds.push_back(it->second->GetDhid());
343 }
344 }
345 g_camDump.camIds = camIds;
346 }
347
GetCamDumpInfo(CameraDumpInfo & camDump)348 void DistributedCameraSinkService::GetCamDumpInfo(CameraDumpInfo& camDump)
349 {
350 dcSinkService->GetCamIds();
351 camDump = g_camDump;
352 }
353 } // namespace DistributedHardware
354 } // namespace OHOS