1 /*
2 * Copyright (c) 2024-2025 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 <chrono>
17 #include <sys/prctl.h>
18 #include <thread>
19
20 #include "dsched_collab.h"
21
22 #include "ability_connection_wrapper_stub.h"
23 #include "ability_manager_client.h"
24 #include "bool_wrapper.h"
25 #include "bundle/bundle_manager_internal.h"
26 #include "distributed_sched_permission.h"
27 #include "dsched_collab_manager.h"
28 #include "dsched_transport_softbus_adapter.h"
29 #include "dtbschedmgr_device_info_storage.h"
30 #include "ipc_skeleton.h"
31 #include "iservice_registry.h"
32 #include "parcel_helper.h"
33 #ifdef DMS_CHECK_SCREENLOCK
34 #include "screenlock_manager.h"
35 #endif
36 #include "string_wrapper.h"
37 #include "system_ability_definition.h"
38
39 namespace OHOS {
40 namespace DistributedSchedule {
41 using namespace AAFwk;
42 namespace {
43 const std::string TAG = "DSchedCollab";
44 const std::string DMS_VERSION_ID = "dmsVersion";
45 const std::u16string NAPI_COLLAB_CALLBACK_INTERFACE_TOKEN = u"OHOS.DistributedCollab.IAbilityConnectionManager";
46
47 constexpr int32_t DSCHED_COLLAB_PROTOCOL_VERSION = 1;
48 constexpr int32_t NOTIFY_COLLAB_PREPARE_RESULT = 0;
49 constexpr int32_t NOTIFY_COLLAB_DISCONNECT = 1;
50 constexpr int32_t NOTIFY_WIFI_OPEN = 2;
51 constexpr int32_t NOTIFY_PEER_COLLAB_VERSION = 3;
52 constexpr int32_t DMS_VERSION = 6;
53 std::map<int32_t, std::string> CMDDATA = {
54 {MIN_CMD, "MIN_CMD"},
55 {SINK_GET_VERSION_CMD, "SINK_GET_VERSION_CMD"},
56 {SOURCE_GET_VERSION_CMD, "SOURCE_GET_VERSION_CMD"},
57 {SINK_START_CMD, "SINK_START_CMD"},
58 {NOTIFY_RESULT_CMD, "NOTIFY_RESULT_CMD"},
59 {DISCONNECT_CMD, "DISCONNECT_CMD"},
60 {MAX_CMD, "MAX_CMD"},
61 };
62 std::map<int32_t, std::string> EVENTDATA = {
63 {SOURCE_GET_PEER_VERSION_EVENT, "SOURCE_GET_PEER_VERSION_EVENT"},
64 {SOURCE_START_EVENT, "SOURCE_START_EVENT"},
65 {NOTIFY_RESULT_EVENT, "NOTIFY_RESULT_EVENT"},
66 {GET_SINK_VERSION_EVENT, "GET_SINK_VERSION_EVENT"},
67 {START_ABILITY_EVENT, "START_ABILITY_EVENT"},
68 {NOTIFY_PREPARE_RESULT_EVENT, "NOTIFY_PREPARE_RESULT_EVENT"},
69 {ERR_END_EVENT, "ERR_END_EVENT"},
70 {END_EVENT, "END_EVENT"},
71 };
72 std::map<int32_t, std::string> STATEDATA = {
73 {SOURCE_GET_PEER_VERSION_STATE, "SOURCE_GET_PEER_VERSION_STATE"},
74 {SOURCE_START_STATE, "SOURCE_START_STATE"},
75 {SOURCE_WAIT_RESULT_STATE, "SOURCE_WAIT_RESULT_STATE"},
76 {SOURCE_WAIT_END_STATE, "SOURCE_WAIT_END_STATE"},
77 {SINK_GET_VERSION_STATE, "SINK_GET_VERSION_STATE"},
78 {SINK_START_STATE, "SINK_START_STATE"},
79 {SINK_CONNECT_STATE, "SINK_CONNECT_STATE"},
80 {SINK_WAIT_END_STATE, "SINK_WAIT_END_STATE"},
81 };
82 }
83
DSchedCollab(const std::string & collabToken,const DSchedCollabInfo & info)84 DSchedCollab::DSchedCollab(const std::string &collabToken, const DSchedCollabInfo &info)
85 {
86 HILOGI("create");
87 collabInfo_ = info;
88 collabInfo_.collabToken_ = collabToken;
89 collabInfo_.srcCollabVersion_ = DSCHED_COLLAB_PROTOCOL_VERSION;
90 HILOGI("created successfully. collabInfo: %{public}s", collabInfo_.ToString().c_str());
91 }
92
DSchedCollab(std::shared_ptr<GetSinkCollabVersionCmd> startCmd,const int32_t & softbusSessionId)93 DSchedCollab::DSchedCollab(std::shared_ptr<GetSinkCollabVersionCmd> startCmd, const int32_t &softbusSessionId)
94 {
95 HILOGI("create by recvCmd");
96 if (startCmd == nullptr) {
97 HILOGE("startCmd is null");
98 return;
99 }
100 collabInfo_.srcCollabSessionId_ = startCmd->srcCollabSessionId_;
101 collabInfo_.collabToken_ = startCmd->collabToken_;
102 collabInfo_.srcInfo_.pid_ = startCmd->srcPid_;
103 collabInfo_.srcInfo_.uid_ = startCmd->srcUid_;
104 collabInfo_.srcInfo_.accessToken_ = startCmd->srcAccessToken_;
105 collabInfo_.direction_ = COLLAB_SINK;
106 softbusSessionId_ = softbusSessionId;
107 HILOGI("created successfully. collabInfo: %{public}s", collabInfo_.ToString().c_str());
108 }
109
SetSrcCollabInfo(DSchedCollabInfo & info)110 void DSchedCollab::SetSrcCollabInfo(DSchedCollabInfo &info)
111 {
112 HILOGI("called");
113 info.srcClientCB_ = collabInfo_.srcClientCB_;
114 collabInfo_ = info;
115 HILOGI("end");
116 }
117
SetSinkCollabInfo(std::shared_ptr<SinkStartCmd> startCmd)118 void DSchedCollab::SetSinkCollabInfo(std::shared_ptr<SinkStartCmd> startCmd)
119 {
120 HILOGI("called");
121 if (startCmd == nullptr) {
122 HILOGE("startCmd is null");
123 return;
124 }
125 collabInfo_.srcCollabVersion_ = startCmd->collabVersion_;
126 collabInfo_.srcOpt_.needSendBigData_ = startCmd->needSendBigData_;
127 collabInfo_.srcOpt_.needSendStream_ = startCmd->needSendStream_;
128 collabInfo_.srcOpt_.needRecvStream_ = startCmd->needRecvStream_;
129 collabInfo_.srcOpt_.startParams_ = startCmd->startParams_;
130 collabInfo_.srcOpt_.messageParams_ = startCmd->messageParams_;
131 collabInfo_.srcInfo_.deviceId_ = startCmd->srcDeviceId_;
132 collabInfo_.srcInfo_.bundleName_ = startCmd->srcBundleName_;
133 collabInfo_.srcInfo_.abilityName_ = startCmd->srcAbilityName_;
134 collabInfo_.srcInfo_.moduleName_ = startCmd->srcModuleName_;
135 collabInfo_.srcInfo_.serverId_ = startCmd->srcServerId_;
136 collabInfo_.srcInfo_.pid_ = startCmd->srcPid_;
137 collabInfo_.srcInfo_.uid_ = startCmd->srcUid_;
138 collabInfo_.srcInfo_.accessToken_ = startCmd->srcAccessToken_;
139 collabInfo_.sinkInfo_.deviceId_ = startCmd->sinkDeviceId_;
140 collabInfo_.sinkInfo_.bundleName_ = startCmd->sinkBundleName_;
141 collabInfo_.sinkInfo_.abilityName_ = startCmd->sinkAbilityName_;
142 collabInfo_.srcAppVersion_ = startCmd->appVersion_;
143 collabInfo_.callerInfo_ = startCmd->callerInfo_;
144 collabInfo_.callerInfo_.accessToken = static_cast<uint32_t>(collabInfo_.srcInfo_.accessToken_);
145 collabInfo_.srcAccountInfo_ = startCmd->accountInfo_;
146
147 #ifdef OS_ACCOUNT_PART
148 std::vector<int32_t> ids;
149 int32_t ret = AccountSA::OsAccountManager::QueryActiveOsAccountIds(ids);
150 if (ret != ERR_OK || ids.empty()) {
151 HILOGE("Get userId from active Os AccountIds fail, ret : %{public}d", ret);
152 return;
153 }
154 collabInfo_.sinkUserId_ = ids[0];
155 #endif
156 HILOGI("created successfully. collabInfo: %{public}s", collabInfo_.ToString().c_str());
157 }
158
~DSchedCollab()159 DSchedCollab::~DSchedCollab()
160 {
161 HILOGI("delete enter");
162 UnregisterAbilityLifecycleObserver();
163 UnInit();
164 HILOGI("delete end");
165 }
166
Init()167 int32_t DSchedCollab::Init()
168 {
169 HILOGI("called");
170 if (eventHandler_ != nullptr) {
171 HILOGI("already inited, end.");
172 return ERR_OK;
173 }
174 auto dCollab = std::shared_ptr<DSchedCollab>(shared_from_this());
175 stateMachine_ = std::make_shared<DSchedCollabStateMachine>(dCollab);
176
177 eventThread_ = std::thread(&DSchedCollab::StartEventHandler, this);
178 std::unique_lock<std::mutex> lock(eventMutex_);
179 eventCon_.wait(lock, [this] {
180 return eventHandler_ != nullptr;
181 });
182 HILOGI("end");
183 return ERR_OK;
184 }
185
UnInit()186 int32_t DSchedCollab::UnInit()
187 {
188 HILOGI("called");
189 if ((eventHandler_ != nullptr) && (eventHandler_->GetEventRunner() != nullptr)) {
190 eventHandler_->GetEventRunner()->Stop();
191 }
192 if (eventThread_.joinable()) {
193 HILOGI("start calling join");
194 eventThread_.join();
195 HILOGI("call join completed");
196 }
197 eventHandler_ = nullptr;
198 HILOGI("end");
199 return ERR_OK;
200 }
201
StartEventHandler()202 void DSchedCollab::StartEventHandler()
203 {
204 HILOGI("called");
205 std::string eventThreadName = "DSchedCollab_EventHandler";
206 prctl(PR_SET_NAME, eventThreadName.c_str());
207 auto runner = AppExecFwk::EventRunner::Create(false);
208 if (runner == nullptr) {
209 HILOGE("continue start eventHandler failed.");
210 return;
211 }
212 {
213 std::lock_guard<std::mutex> lock(eventMutex_);
214 eventHandler_ = std::make_shared<DSchedCollabEventHandler>(runner, shared_from_this());
215 }
216 eventCon_.notify_one();
217 runner->Run();
218 }
219
PostSrcGetPeerVersionTask()220 int32_t DSchedCollab::PostSrcGetPeerVersionTask()
221 {
222 HILOGI("called");
223 if (eventHandler_ == nullptr) {
224 HILOGE("eventHandler is nullptr");
225 return INVALID_PARAMETERS_ERR;
226 }
227 DSchedCollabEventType eventType = SOURCE_GET_PEER_VERSION_EVENT;
228 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType);
229 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
230 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
231 return COLLAB_SEND_EVENT_FAILED;
232 }
233 return ERR_OK;
234 }
235
PostSrcGetVersionTask()236 int32_t DSchedCollab::PostSrcGetVersionTask()
237 {
238 HILOGI("called");
239 if (eventHandler_ == nullptr) {
240 HILOGE("eventHandler is nullptr");
241 return INVALID_PARAMETERS_ERR;
242 }
243 DSchedCollabEventType eventType = SOURCE_GET_VERSION_EVENT;
244 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType);
245 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
246 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
247 return COLLAB_SEND_EVENT_FAILED;
248 }
249 return ERR_OK;
250 }
251
PostSrcStartTask()252 int32_t DSchedCollab::PostSrcStartTask()
253 {
254 HILOGI("called");
255 if (eventHandler_ == nullptr) {
256 HILOGE("eventHandler is nullptr");
257 return INVALID_PARAMETERS_ERR;
258 }
259 DSchedCollabEventType eventType = SOURCE_START_EVENT;
260 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType);
261 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
262 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
263 return COLLAB_SEND_EVENT_FAILED;
264 }
265 return ERR_OK;
266 }
267
PostSinkGetVersionTask()268 int32_t DSchedCollab::PostSinkGetVersionTask()
269 {
270 HILOGI("called");
271 if (eventHandler_ == nullptr) {
272 HILOGE("eventHandler is nullptr");
273 return INVALID_PARAMETERS_ERR;
274 }
275 DSchedCollabEventType eventType = GET_SINK_VERSION_EVENT;
276 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType);
277 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
278 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
279 return COLLAB_SEND_EVENT_FAILED;
280 }
281 return ERR_OK;
282 }
283
PostSinkStartTask(const std::string & peerDeviceId)284 int32_t DSchedCollab::PostSinkStartTask(const std::string &peerDeviceId)
285 {
286 HILOGI("called");
287 if (eventHandler_ == nullptr) {
288 HILOGE("eventHandler is nullptr");
289 return INVALID_PARAMETERS_ERR;
290 }
291 DSchedCollabEventType eventType = START_ABILITY_EVENT;
292 auto data = std::make_shared<std::string>(peerDeviceId);
293 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType, data, 0);
294 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
295 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
296 return COLLAB_SEND_EVENT_FAILED;
297 }
298 return ERR_OK;
299 }
300
PostSinkPrepareResultTask(const int32_t & result,const DSchedCollabInfo & dSchedCollabInfo)301 int32_t DSchedCollab::PostSinkPrepareResultTask(const int32_t &result, const DSchedCollabInfo &dSchedCollabInfo)
302 {
303 HILOGI("called");
304 if (eventHandler_ == nullptr) {
305 HILOGE("eventHandler is nullptr");
306 return INVALID_PARAMETERS_ERR;
307 }
308 collabInfo_.sinkCollabSessionId_ = dSchedCollabInfo.sinkCollabSessionId_;
309 collabInfo_.sinkInfo_.socketName_ = dSchedCollabInfo.sinkInfo_.socketName_;
310 collabInfo_.sinkClientCB_ = dSchedCollabInfo.sinkClientCB_;
311 collabInfo_.sinkInfo_.uid_ = dSchedCollabInfo.sinkInfo_.uid_;
312 collabInfo_.sinkInfo_.pid_ = dSchedCollabInfo.sinkInfo_.pid_;
313 collabInfo_.sinkInfo_.accessToken_ = dSchedCollabInfo.sinkInfo_.accessToken_;
314 auto data = std::make_shared<int32_t>(result);
315 DSchedCollabEventType eventType = NOTIFY_PREPARE_RESULT_EVENT;
316 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType, data, 0);
317 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
318 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
319 return COLLAB_SEND_EVENT_FAILED;
320 }
321 HILOGI("end");
322 return ERR_OK;
323 }
324
PostSrcResultTask(std::shared_ptr<NotifyResultCmd> notifyResultCmd)325 int32_t DSchedCollab::PostSrcResultTask(std::shared_ptr<NotifyResultCmd> notifyResultCmd)
326 {
327 HILOGI("called, collabInfo %{public}s", collabInfo_.ToString().c_str());
328 if (eventHandler_ == nullptr) {
329 HILOGE("eventHandler is nullptr");
330 return INVALID_PARAMETERS_ERR;
331 }
332 if (!notifyResultCmd->abilityRejectReason_.empty()) {
333 DSchedCollabEventType eventType = ABILITY_REJECT_EVENT;
334 auto data = std::make_shared<std::string>(notifyResultCmd->abilityRejectReason_);
335 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType, data, 0);
336 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
337 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
338 return COLLAB_SEND_EVENT_FAILED;
339 }
340 return ERR_OK;
341 }
342 collabInfo_.sinkCollabSessionId_ = notifyResultCmd->sinkCollabSessionId_;
343 collabInfo_.sinkInfo_.socketName_ = notifyResultCmd->sinkSocketName_;
344 collabInfo_.sinkInfo_.pid_ = notifyResultCmd->sinkPid_;
345 collabInfo_.sinkInfo_.accessToken_ = notifyResultCmd->sinkAccessToken_;
346 collabInfo_.sinkUserId_ = notifyResultCmd->sinkUserId_;
347 collabInfo_.sinkAccountId_ = notifyResultCmd->sinkAccountId_;
348 collabInfo_.sinkUdid_ = DtbschedmgrDeviceInfoStorage::GetInstance().GetUdidByNetworkId(
349 collabInfo_.sinkInfo_.deviceId_);
350 collabInfo_.srcUdid_ = DtbschedmgrDeviceInfoStorage::GetInstance().GetUdidByNetworkId(
351 collabInfo_.srcInfo_.deviceId_);
352 DSchedCollabEventType eventType = NOTIFY_RESULT_EVENT;
353 auto data = std::make_shared<int32_t>(notifyResultCmd->result_);
354 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType, data, 0);
355 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
356 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
357 return COLLAB_SEND_EVENT_FAILED;
358 }
359 return ERR_OK;
360 }
361
PostErrEndTask(const int32_t & result)362 int32_t DSchedCollab::PostErrEndTask(const int32_t &result)
363 {
364 HILOGI("called, collabInfo %{public}s", collabInfo_.ToString().c_str());
365 if (eventHandler_ == nullptr) {
366 HILOGE("eventHandler is nullptr");
367 return INVALID_PARAMETERS_ERR;
368 }
369 DSchedCollabEventType eventType = ERR_END_EVENT;
370 auto data = std::make_shared<int32_t>(result);
371 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType, data, 0);
372 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
373 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
374 return COLLAB_SEND_EVENT_FAILED;
375 }
376 return ERR_OK;
377 }
378
PostAbilityRejectTask(const std::string & reason)379 int32_t DSchedCollab::PostAbilityRejectTask(const std::string &reason)
380 {
381 HILOGI("called, reason: %{public}s", reason.c_str());
382 if (eventHandler_ == nullptr) {
383 HILOGE("eventHandler is nullptr");
384 return INVALID_PARAMETERS_ERR;
385 }
386 DSchedCollabEventType eventType = ABILITY_REJECT_EVENT;
387 auto data = std::make_shared<std::string>(reason);
388 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType, data, 0);
389 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
390 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
391 return COLLAB_SEND_EVENT_FAILED;
392 }
393 return ERR_OK;
394 }
395
PostEndTask()396 int32_t DSchedCollab::PostEndTask()
397 {
398 HILOGI("called, collabInfo %{public}s", collabInfo_.ToString().c_str());
399 if (eventHandler_ == nullptr) {
400 HILOGE("eventHandler is nullptr");
401 return INVALID_PARAMETERS_ERR;
402 }
403 DSchedCollabEventType eventType = END_EVENT;
404 auto msgEvent = AppExecFwk::InnerEvent::Get(eventType);
405 if (!eventHandler_->SendEvent(msgEvent, 0, AppExecFwk::EventQueue::Priority::IMMEDIATE)) {
406 HILOGE("send event type %{public}s fail", EVENTDATA[eventType].c_str());
407 return COLLAB_SEND_EVENT_FAILED;
408 }
409 HILOGI("end");
410 return ERR_OK;
411 }
412
ProcessEvent(const AppExecFwk::InnerEvent::Pointer & event)413 void DSchedCollab::ProcessEvent(const AppExecFwk::InnerEvent::Pointer &event)
414 {
415 HILOGI("called");
416 if (event == nullptr || stateMachine_ == nullptr) {
417 HILOGE("event or state machine is null");
418 return;
419 }
420 auto eventId = event->GetInnerEventId();
421 HILOGI("process event: %{public}s with state %{public}s",
422 EVENTDATA[eventId].c_str(), STATEDATA[stateMachine_->GetStateType()].c_str());
423 int32_t ret = stateMachine_->Execute(event);
424 if (ret != ERR_OK) {
425 HILOGE("event %{public}s execute failed, ret %{public}d", EVENTDATA[eventId].c_str(), ret);
426 PostErrEndTask(ret);
427 }
428 HILOGI("end");
429 return;
430 }
431
ExeSrcGetPeerVersion()432 int32_t DSchedCollab::ExeSrcGetPeerVersion()
433 {
434 HILOGI("called");
435 const std::string sinkDeviceId = collabInfo_.sinkInfo_.deviceId_;
436 int32_t ret = DSchedTransportSoftbusAdapter::GetInstance().ConnectDevice(sinkDeviceId,
437 softbusSessionId_, SERVICE_TYPE_COLLAB);
438 if (ret != ERR_OK) {
439 HILOGE("connect peer device failed, ret %{public}d", ret);
440 return ret;
441 }
442 HILOGI("this bind is successful, softbusSessionId %{public}d", softbusSessionId_);
443
444 auto getPeerVersionCmd = std::make_shared<GetSinkCollabVersionCmd>();
445 ret = PackGetPeerVersionCmd(getPeerVersionCmd);
446 if (ret != ERR_OK) {
447 HILOGE("pack failed, ret %{public}d", ret);
448 return ret;
449 }
450 ret = SendCommand(getPeerVersionCmd);
451 if (ret != ERR_OK) {
452 HILOGE("send failed, ret %{public}d", ret);
453 return ret;
454 }
455
456 HILOGI("end");
457 return ERR_OK;
458 }
459
ExeSrcGetVersion()460 int32_t DSchedCollab::ExeSrcGetVersion()
461 {
462 HILOGI("called");
463 int32_t ret = SrcPeerVersionNotify();
464 if (ret != ERR_OK) {
465 HILOGE("failed, ret: %{public}d", ret);
466 return PostErrEndTask(ret);
467 }
468 HILOGI("end");
469 return ERR_OK;
470 }
471
ExeSrcStart()472 int32_t DSchedCollab::ExeSrcStart()
473 {
474 HILOGI("called");
475 auto startCmd = std::make_shared<SinkStartCmd>();
476 int32_t ret = PackStartCmd(startCmd);
477 if (ret != ERR_OK) {
478 HILOGE("pack startCmd failed, ret %{public}d", ret);
479 return ret;
480 }
481 ret = SendCommand(startCmd);
482 if (ret != ERR_OK) {
483 HILOGE("send startCmd failed, ret %{public}d", ret);
484 return ret;
485 }
486
487 UpdateState(SOURCE_WAIT_RESULT_STATE);
488 RegisterAbilityLifecycleObserver(collabInfo_.srcInfo_.bundleName_);
489 HILOGI("end");
490 return ERR_OK;
491 }
492
PackGetPeerVersionCmd(std::shared_ptr<GetSinkCollabVersionCmd> & cmd)493 int32_t DSchedCollab::PackGetPeerVersionCmd(std::shared_ptr<GetSinkCollabVersionCmd>& cmd)
494 {
495 if (cmd == nullptr) {
496 HILOGE("cmd or is null");
497 return INVALID_PARAMETERS_ERR;
498 }
499 cmd->command_ = SINK_GET_VERSION_CMD;
500 cmd->srcCollabSessionId_ = collabInfo_.srcCollabSessionId_;
501 cmd->collabToken_ = collabInfo_.collabToken_;
502 cmd->sinkDeviceId_ = collabInfo_.sinkInfo_.deviceId_;
503 cmd->srcDeviceId_ = collabInfo_.srcInfo_.deviceId_;
504 return ERR_OK;
505 }
506
PackSinkCollabVersionCmd(std::shared_ptr<GetSinkCollabVersionCmd> & cmd)507 int32_t DSchedCollab::PackSinkCollabVersionCmd(std::shared_ptr<GetSinkCollabVersionCmd>& cmd)
508 {
509 if (cmd == nullptr) {
510 HILOGE("cmd or is null");
511 return INVALID_PARAMETERS_ERR;
512 }
513 cmd->command_ = SOURCE_GET_VERSION_CMD;
514 cmd->collabToken_ = collabInfo_.collabToken_;
515 cmd->sinkCollabVersion_ = DSCHED_COLLAB_PROTOCOL_VERSION;
516 cmd->srcDeviceId_ = collabInfo_.srcInfo_.deviceId_;
517 cmd->sinkDeviceId_ = collabInfo_.sinkInfo_.deviceId_;
518 return ERR_OK;
519 }
520
PackStartCmd(std::shared_ptr<SinkStartCmd> & cmd)521 int32_t DSchedCollab::PackStartCmd(std::shared_ptr<SinkStartCmd>& cmd)
522 {
523 if (cmd == nullptr) {
524 HILOGE("cmd or is null");
525 return INVALID_PARAMETERS_ERR;
526 }
527 cmd->collabVersion_ = collabInfo_.srcCollabVersion_;
528 cmd->dmsVersion_ = DMS_VERSION;
529 cmd->command_ = SINK_START_CMD;
530 cmd->srcCollabSessionId_ = collabInfo_.srcCollabSessionId_;
531 cmd->collabToken_ = collabInfo_.collabToken_;
532 cmd->srcPid_ = collabInfo_.srcInfo_.pid_;
533 cmd->srcUid_ = collabInfo_.srcInfo_.uid_;
534 cmd->srcAccessToken_ = collabInfo_.srcInfo_.accessToken_;
535 cmd->srcServerId_ = collabInfo_.srcInfo_.serverId_;
536 cmd->sinkServerId_ = collabInfo_.sinkInfo_.serverId_;
537 cmd->srcDeviceId_ = collabInfo_.srcInfo_.deviceId_;
538 cmd->sinkDeviceId_ = collabInfo_.sinkInfo_.deviceId_;
539 cmd->srcBundleName_ = collabInfo_.srcInfo_.bundleName_;
540 cmd->sinkBundleName_ = collabInfo_.sinkInfo_.bundleName_;
541 cmd->srcAbilityName_ = collabInfo_.srcInfo_.abilityName_;
542 cmd->sinkAbilityName_ = collabInfo_.sinkInfo_.abilityName_;
543 cmd->srcModuleName_ = collabInfo_.srcInfo_.moduleName_;
544 cmd->sinkModuleName_ = collabInfo_.sinkInfo_.moduleName_;
545 cmd->needSendBigData_ = collabInfo_.srcOpt_.needSendBigData_;
546 cmd->needSendStream_ = collabInfo_.srcOpt_.needSendStream_;
547 cmd->needRecvStream_ = collabInfo_.srcOpt_.needRecvStream_;
548 cmd->startParams_ = collabInfo_.srcOpt_.startParams_;
549 cmd->startParams_.SetParam(DMS_IS_CALLER_FOREGROUND, AAFwk::Boolean::Box(
550 DistributedSchedPermission::GetInstance().IsAbilityForeground(collabInfo_.srcInfo_.accessToken_)));
551 cmd->messageParams_ = collabInfo_.srcOpt_.messageParams_;
552 return PackPartCmd(cmd);
553 }
554
PackPartCmd(std::shared_ptr<SinkStartCmd> & cmd)555 int32_t DSchedCollab::PackPartCmd(std::shared_ptr<SinkStartCmd>& cmd)
556 {
557 AppExecFwk::BundleInfo localBundleInfo;
558 int32_t ret = BundleManagerInternal::GetLocalBundleInfoV9(cmd->srcBundleName_, localBundleInfo);
559 if (ret != ERR_OK) {
560 HILOGE("pack start cmd failed, the bundle is not installed on local device.");
561 return ret;
562 }
563 cmd->appVersion_ = static_cast<int32_t>(localBundleInfo.versionCode);
564 CallerInfo callerInfo;
565 callerInfo.sourceDeviceId = collabInfo_.srcInfo_.deviceId_;
566 callerInfo.uid = collabInfo_.srcInfo_.uid_;
567 callerInfo.accessToken = static_cast<uint32_t>(collabInfo_.srcInfo_.accessToken_);
568 if (!BundleManagerInternal::GetCallerAppIdFromBms(callerInfo.uid, callerInfo.callerAppId)) {
569 HILOGE("GetCallerAppIdFromBms failed");
570 return GET_APPID_ERR;
571 }
572 if (!BundleManagerInternal::GetBundleNameListFromBms(callerInfo.uid, callerInfo.bundleNames)) {
573 HILOGE("GetBundleNameListFromBms failed");
574 return GET_BUNDLENAMELIST_ERR;
575 }
576 callerInfo.extraInfoJson[DMS_VERSION_ID] = DMS_VERSION;
577 AccountInfo accountInfo;
578 ret = DistributedSchedPermission::GetInstance().GetAccountInfo(collabInfo_.sinkInfo_.deviceId_,
579 callerInfo, accountInfo);
580 if (ret != ERR_OK) {
581 HILOGE("get or check accountInfo failed");
582 return GET_ACCOUNT_INFO_ERR;
583 }
584 if (!DistributedSchedPermission::GetInstance().CheckSrcBackgroundPermission(collabInfo_.srcInfo_.accessToken_)) {
585 HILOGE("check source backgroundPermission failed");
586 return DMS_START_CONTROL_PERMISSION_DENIED;
587 }
588 cmd->callerInfo_ = callerInfo;
589 collabInfo_.callerInfo_ = callerInfo;
590 cmd->accountInfo_ = accountInfo;
591 collabInfo_.srcAccountInfo_ = accountInfo;
592 return ERR_OK;
593 }
594
ExeStartAbility(const std::string & peerDeviceId)595 int32_t DSchedCollab::ExeStartAbility(const std::string &peerDeviceId)
596 {
597 HILOGI("called, peerDeviceId: %{public}s", GetAnonymStr(peerDeviceId).c_str());
598 if (collabInfo_.callerInfo_.sourceDeviceId != peerDeviceId) {
599 HILOGE("Irrecognized srcDeviceId!");
600 return INVALID_PARAMETERS_ERR;
601 }
602 AAFwk::Want want = GenerateCollabWant();
603 int32_t ret = DistributedSchedService::GetInstance().CheckCollabStartPermission(want, collabInfo_.callerInfo_,
604 collabInfo_.srcAccountInfo_, false);
605 want.RemoveParam(DMS_IS_CALLER_FOREGROUND);
606 if (ret != ERR_OK) {
607 HILOGE("CheckTargetPermission failed!");
608 return ret;
609 }
610
611 HILOGI("flag is %{public}d", want.GetFlags());
612 ret = AAFwk::AbilityManagerClient::GetInstance()->Connect();
613 if (ret != ERR_OK) {
614 HILOGE("connect ability server failed %{public}d", ret);
615 return ret;
616 }
617 sptr<IRemoteObject> callbackWrapper = sptr<AbilityConnectionWrapperStub>(new AbilityConnectionWrapperStub());
618 ret = AAFwk::AbilityManagerClient::GetInstance()->StartAbilityByCall(want,
619 iface_cast<AAFwk::IAbilityConnection>(callbackWrapper));
620 if (ret != ERR_OK) {
621 HILOGE("startAbilityByCall failed! ret: %{public}d", ret);
622 ret = PostErrEndTask(ret);
623 return ret;
624 }
625
626 UpdateState(SINK_CONNECT_STATE);
627 RegisterAbilityLifecycleObserver(collabInfo_.sinkInfo_.bundleName_);
628 HILOGI("end");
629 return ERR_OK;
630 }
631
GenerateCollabWant()632 AAFwk::Want DSchedCollab::GenerateCollabWant()
633 {
634 HILOGI("called");
635 AAFwk::Want want;
636 want.AddFlags(want.FLAG_ABILITY_ON_COLLABORATE);
637 want.SetParam("deviceId", collabInfo_.sinkInfo_.deviceId_);
638 want.SetElementName(collabInfo_.sinkInfo_.deviceId_, collabInfo_.sinkInfo_.bundleName_,
639 collabInfo_.sinkInfo_.abilityName_);
640
641 AAFwk::WantParams peerInfoParams;
642 peerInfoParams.SetParam("deviceId", AAFwk::String::Box(collabInfo_.srcInfo_.deviceId_));
643 peerInfoParams.SetParam("bundleName", AAFwk::String::Box(collabInfo_.srcInfo_.bundleName_));
644 peerInfoParams.SetParam("moduleName", AAFwk::String::Box(collabInfo_.srcInfo_.moduleName_));
645 peerInfoParams.SetParam("abilityName", AAFwk::String::Box(collabInfo_.srcInfo_.abilityName_));
646 peerInfoParams.SetParam("serverId", AAFwk::String::Box(collabInfo_.srcInfo_.serverId_));
647
648 AAFwk::WantParams optParams;
649 optParams.SetParam("needSendData", AAFwk::Boolean::Box(collabInfo_.srcOpt_.needSendBigData_));
650 optParams.SetParam("needSendStream", AAFwk::Boolean::Box(collabInfo_.srcOpt_.needSendStream_));
651 optParams.SetParam("needReceiveStream", AAFwk::Boolean::Box(collabInfo_.srcOpt_.needRecvStream_));
652 optParams.SetParam("parameters", AAFwk::WantParamWrapper::Box(collabInfo_.srcOpt_.messageParams_));
653
654 AAFwk::WantParams collabParams;
655 collabParams.SetParam("PeerInfo", AAFwk::WantParamWrapper::Box(peerInfoParams));
656 collabParams.SetParam("ConnectOption", AAFwk::WantParamWrapper::Box(optParams));
657 collabParams.SetParam("ohos.dms.collabToken", AAFwk::String::Box(collabInfo_.collabToken_));
658
659 AAFwk::WantParams wantParams;
660 SetScreenLockParameters(wantParams);
661 wantParams.SetParam("ohos.extra.param.key.supportCollaborateIndex", AAFwk::WantParamWrapper::Box(collabParams));
662 HILOGI("ohos.aafwk.param.callAbilityToForeground is %{public}d", IsStartForeground());
663 wantParams.SetParam("ohos.aafwk.param.callAbilityToForeground", AAFwk::Boolean::Box(IsStartForeground()));
664 bool isCallerForeground = collabInfo_.srcOpt_.startParams_.GetParam(DMS_IS_CALLER_FOREGROUND);
665 want.SetParam(DMS_IS_CALLER_FOREGROUND, isCallerForeground);
666 want.SetParams(wantParams);
667 return want;
668 }
669
SetScreenLockParameters(AAFwk::WantParams & wantParams)670 void DSchedCollab::SetScreenLockParameters(AAFwk::WantParams& wantParams)
671 {
672 #ifdef DMS_CHECK_SCREENLOCK
673 bool isSecureMode = OHOS::ScreenLock::ScreenLockManager::GetInstance()->GetSecure();
674 bool isLocked = false;
675 OHOS::ScreenLock::ScreenLockManager::GetInstance()->IsLocked(isLocked);
676 HILOGI("isSecureMode is %{public}d, isLocked is %{public}d", isSecureMode, isLocked);
677 wantParams.SetParam("isSecureMode", AAFwk::Boolean::Box(isSecureMode));
678 wantParams.SetParam("isFromScreenLock", AAFwk::Boolean::Box(isLocked));
679 #endif
680 }
681
IsStartForeground()682 bool DSchedCollab::IsStartForeground()
683 {
684 auto value = collabInfo_.srcOpt_.startParams_.GetParam(KEY_START_OPTION);
685 IString *ao = IString::Query(value);
686 if (ao != nullptr) {
687 std::string startOpt = AAFwk::String::Unbox(ao);
688 HILOGI("startOpt is: %{public}s", startOpt.c_str());
689 return (startOpt == VALUE_START_OPTION_BACKGROUND) ? false : true;
690 }
691 return true;
692 }
693
SaveSinkAbilityData(const std::string & collabToken,const int32_t & result,const int32_t & sinkPid,const int32_t & sinkUid,const int32_t & sinkAccessTokenId)694 int32_t DSchedCollab::SaveSinkAbilityData(const std::string& collabToken, const int32_t &result,
695 const int32_t &sinkPid, const int32_t &sinkUid, const int32_t &sinkAccessTokenId)
696 {
697 HILOGI("called, pid: %{public}d, uid: %{public}d, accessTokenId: %{public}d", sinkPid, sinkUid, sinkAccessTokenId);
698 collabInfo_.sinkInfo_.pid_ = sinkPid;
699 collabInfo_.sinkInfo_.uid_ = sinkUid;
700 collabInfo_.sinkInfo_.accessToken_ = sinkAccessTokenId;
701 HILOGI("end, continueInfo %{public}s", collabInfo_.ToString().c_str());
702 return ERR_OK;
703 }
704
ExeAbilityRejectError(const std::string & reason)705 int32_t DSchedCollab::ExeAbilityRejectError(const std::string &reason)
706 {
707 HILOGI("called");
708 auto cmd = std::make_shared<NotifyResultCmd>();
709 PackNotifyResultCmd(cmd, COLLAB_ABILITY_REJECT_ERR, reason);
710 SendCommand(cmd);
711 CleanUpSession();
712 HILOGI("end");
713 return ERR_OK;
714 }
715
ExeSinkPrepareResult(const int32_t & result)716 int32_t DSchedCollab::ExeSinkPrepareResult(const int32_t &result)
717 {
718 HILOGI("called");
719 if (result != ERR_OK && result != COLLAB_ABILITY_REJECT_ERR) {
720 HILOGE("failed %{public}d", result);
721 return PostErrEndTask(result);
722 }
723 auto notifyResCmd = std::make_shared<NotifyResultCmd>();
724 PackNotifyResultCmd(notifyResCmd, result);
725 int32_t ret = SendCommand(notifyResCmd);
726 if (ret != ERR_OK) {
727 HILOGE("send notifyResCmd failed, ret %{public}d", ret);
728 return ret;
729 }
730 UpdateState(SINK_WAIT_END_STATE);
731 collabInfo_.srcUdid_ = DtbschedmgrDeviceInfoStorage::GetInstance().GetUdidByNetworkId(
732 collabInfo_.srcInfo_.deviceId_);
733 collabInfo_.sinkUdid_ = DtbschedmgrDeviceInfoStorage::GetInstance().GetUdidByNetworkId(
734 collabInfo_.sinkInfo_.deviceId_);
735 HILOGI("end, info: %{public}s.", collabInfo_.ToString().c_str());
736 return ERR_OK;
737 }
738
PackNotifyResultCmd(std::shared_ptr<NotifyResultCmd> cmd,const int32_t & result,const std::string & abilityRejectReason)739 int32_t DSchedCollab::PackNotifyResultCmd(std::shared_ptr<NotifyResultCmd> cmd, const int32_t &result,
740 const std::string &abilityRejectReason)
741 {
742 if (cmd == nullptr) {
743 HILOGE("cmd is null");
744 return INVALID_PARAMETERS_ERR;
745 }
746 cmd->command_ = NOTIFY_RESULT_CMD;
747 cmd->result_ = result;
748 cmd->collabToken_ = collabInfo_.collabToken_;
749 cmd->sinkSocketName_ = collabInfo_.sinkInfo_.socketName_;
750 cmd->sinkCollabSessionId_ = collabInfo_.sinkCollabSessionId_;
751 cmd->abilityRejectReason_ = abilityRejectReason;
752 cmd->sinkPid_ = collabInfo_.sinkInfo_.pid_;
753 cmd->sinkAccessToken_ = collabInfo_.sinkInfo_.accessToken_;
754 cmd->sinkUserId_ = collabInfo_.sinkUserId_;
755 cmd->sinkAccountId_ = collabInfo_.sinkAccountId_;
756 return ERR_OK;
757 }
758
ExeSrcCollabResult(const int32_t & result,const std::string reason)759 int32_t DSchedCollab::ExeSrcCollabResult(const int32_t &result, const std::string reason)
760 {
761 HILOGI("called, collabInfo: %{public}s", collabInfo_.ToString().c_str());
762 if (result != ERR_OK && result != COLLAB_ABILITY_REJECT_ERR) {
763 HILOGE("failed, result: %{public}d", result);
764 return PostErrEndTask(result);
765 }
766 int32_t ret = ExeSrcClientNotify(result, reason);
767 if (!reason.empty()) {
768 HILOGE("reason: %{public}s", reason.c_str());
769 return CleanUpSession();
770 }
771 if (ret != ERR_OK) {
772 HILOGE("failed, ret: %{public}d", ret);
773 return PostErrEndTask(result);
774 }
775 UpdateState(SOURCE_WAIT_END_STATE);
776 HILOGI("end");
777 return ERR_OK;
778 }
779
CleanUpSession()780 int32_t DSchedCollab::CleanUpSession()
781 {
782 if (collabInfo_.direction_ == COLLAB_SOURCE) {
783 const std::string peerDeviceId = collabInfo_.sinkInfo_.deviceId_;
784 HILOGI("disconnect peer device %{public}s", GetAnonymStr(peerDeviceId).c_str());
785 DSchedTransportSoftbusAdapter::GetInstance().DisconnectDevice(peerDeviceId);
786 }
787 ExeClientDisconnectNotify();
788 return DSchedCollabManager::GetInstance().CleanUpSession(collabInfo_.collabToken_);
789 }
790
SrcPeerVersionNotify()791 int32_t DSchedCollab::SrcPeerVersionNotify()
792 {
793 HILOGI("called");
794 MessageParcel data;
795 if (!data.WriteInterfaceToken(NAPI_COLLAB_CALLBACK_INTERFACE_TOKEN)) {
796 HILOGE("write token failed");
797 return INVALID_PARAMETERS_ERR;
798 }
799 PARCEL_WRITE_HELPER(data, Int32, collabInfo_.srcCollabSessionId_);
800 PARCEL_WRITE_HELPER(data, Int32, collabInfo_.sinkCollabVersion_);
801 MessageParcel reply;
802 MessageOption option;
803 int32_t ret = collabInfo_.srcClientCB_->SendRequest(NOTIFY_PEER_COLLAB_VERSION, data, reply, option);
804 return ret;
805 }
806
ExeSrcClientNotify(const int32_t & result,const std::string reason)807 int32_t DSchedCollab::ExeSrcClientNotify(const int32_t &result, const std::string reason)
808 {
809 HILOGI("called, result: %{public}d, collabInfo: %{public}s", result, collabInfo_.ToString().c_str());
810 if (collabInfo_.srcClientCB_ == nullptr) {
811 HILOGW("callback object null.");
812 return INVALID_PARAMETERS_ERR;
813 }
814
815 MessageParcel data;
816 if (!data.WriteInterfaceToken(NAPI_COLLAB_CALLBACK_INTERFACE_TOKEN)) {
817 HILOGE("write token failed");
818 return INVALID_PARAMETERS_ERR;
819 }
820 PARCEL_WRITE_HELPER(data, Int32, collabInfo_.srcCollabSessionId_);
821 PARCEL_WRITE_HELPER(data, Int32, result);
822 PARCEL_WRITE_HELPER(data, String, collabInfo_.sinkInfo_.socketName_);
823 PARCEL_WRITE_HELPER(data, String, collabInfo_.collabToken_);
824 PARCEL_WRITE_HELPER(data, String, reason);
825 MessageParcel reply;
826 MessageOption option;
827 int32_t ret = collabInfo_.srcClientCB_->SendRequest(NOTIFY_COLLAB_PREPARE_RESULT, data, reply, option);
828 if (ret != ERR_OK) {
829 HILOGE("send request failed, ret: %{public}d", ret);
830 }
831 HILOGI("end");
832 return ret;
833 }
834
ExeClientDisconnectNotify()835 int32_t DSchedCollab::ExeClientDisconnectNotify()
836 {
837 HILOGI("called");
838 int32_t collabSessionId;
839 sptr<IRemoteObject> clientCB;
840 if (collabInfo_.direction_ == COLLAB_SOURCE) {
841 if (collabInfo_.srcClientCB_ == nullptr) {
842 HILOGW("srcClientCB object null.");
843 return ERR_NULL_OBJECT;
844 }
845 collabSessionId = collabInfo_.srcCollabSessionId_;
846 clientCB = collabInfo_.srcClientCB_;
847 } else {
848 if (collabInfo_.sinkClientCB_ == nullptr) {
849 HILOGW("sinkClientCB object null.");
850 return ERR_NULL_OBJECT;
851 }
852 collabSessionId = collabInfo_.sinkCollabSessionId_;
853 clientCB = collabInfo_.sinkClientCB_;
854 }
855
856 MessageParcel data;
857 if (!data.WriteInterfaceToken(NAPI_COLLAB_CALLBACK_INTERFACE_TOKEN)) {
858 HILOGE("write token failed");
859 return SEND_REQUEST_DEF_FAIL;
860 }
861 PARCEL_WRITE_HELPER(data, Int32, collabSessionId);
862 MessageParcel reply;
863 MessageOption option;
864 int32_t ret = clientCB->SendRequest(NOTIFY_COLLAB_DISCONNECT, data, reply, option);
865 if (ret != ERR_OK) {
866 HILOGE("send request failed, ret: %{public}d", ret);
867 return SEND_REQUEST_DEF_FAIL;
868 }
869 HILOGI("end");
870 return ERR_OK;
871 }
872
NotifyWifiOpen()873 int32_t DSchedCollab::NotifyWifiOpen()
874 {
875 HILOGI("called");
876 int32_t collabSessionId;
877 sptr<IRemoteObject> clientCB;
878 if (collabInfo_.direction_ == COLLAB_SOURCE) {
879 if (collabInfo_.srcClientCB_ == nullptr) {
880 HILOGW("srcClientCB object null.");
881 return ERR_NULL_OBJECT;
882 }
883 collabSessionId = collabInfo_.srcCollabSessionId_;
884 clientCB = collabInfo_.srcClientCB_;
885 } else {
886 if (collabInfo_.sinkClientCB_ == nullptr) {
887 HILOGW("sinkClientCB object null.");
888 return ERR_NULL_OBJECT;
889 }
890 collabSessionId = collabInfo_.sinkCollabSessionId_;
891 clientCB = collabInfo_.sinkClientCB_;
892 }
893
894 MessageParcel data;
895 if (!data.WriteInterfaceToken(NAPI_COLLAB_CALLBACK_INTERFACE_TOKEN)) {
896 HILOGE("write token failed");
897 return SEND_REQUEST_DEF_FAIL;
898 }
899 PARCEL_WRITE_HELPER(data, Int32, collabSessionId);
900 MessageParcel reply;
901 MessageOption option;
902 int32_t ret = clientCB->SendRequest(NOTIFY_WIFI_OPEN, data, reply, option);
903 if (ret != ERR_OK) {
904 HILOGE("send request failed, ret: %{public}d", ret);
905 return SEND_REQUEST_DEF_FAIL;
906 }
907 HILOGI("end");
908 return ERR_OK;
909 }
910
ExeSrcGetPeerVersionError(const int32_t & result)911 int32_t DSchedCollab::ExeSrcGetPeerVersionError(const int32_t &result)
912 {
913 HILOGE("called, reason: %{public}d", result);
914 ExeSrcClientNotify(result);
915 CleanUpSession();
916 HILOGI("end");
917 return ERR_OK;
918 }
919
ExeSrcStartError(const int32_t & result)920 int32_t DSchedCollab::ExeSrcStartError(const int32_t &result)
921 {
922 HILOGE("called, reason: %{public}d", result);
923 ExeSrcClientNotify(result);
924 CleanUpSession();
925 HILOGI("end");
926 return ERR_OK;
927 }
928
ExeSrcWaitResultError(const int32_t & result)929 int32_t DSchedCollab::ExeSrcWaitResultError(const int32_t &result)
930 {
931 HILOGE("called, reason: %{public}d", result);
932 auto cmd = std::make_shared<DisconnectCmd>();
933 PackDisconnectCmd(cmd);
934 SendCommand(cmd);
935 ExeSrcClientNotify(result);
936 CleanUpSession();
937 HILOGI("end");
938 return ERR_OK;
939 }
940
ExeSinkGetVersion()941 int32_t DSchedCollab::ExeSinkGetVersion()
942 {
943 HILOGI("end");
944 auto sinkCollabVersionCmd = std::make_shared<GetSinkCollabVersionCmd>();
945 PackSinkCollabVersionCmd(sinkCollabVersionCmd);
946 SendCommand(sinkCollabVersionCmd);
947 UpdateState(SINK_START_STATE);
948 return ERR_OK;
949 }
950
ExeSinkError(const int32_t & result)951 int32_t DSchedCollab::ExeSinkError(const int32_t &result)
952 {
953 HILOGE("called, reason: %{public}d", result);
954 auto cmd = std::make_shared<NotifyResultCmd>();
955 PackNotifyResultCmd(cmd, result);
956 SendCommand(cmd);
957 CleanUpSession();
958 HILOGI("end");
959 return ERR_OK;
960 }
961
ExeSinkGetVersionError(const int32_t & result)962 int32_t DSchedCollab::ExeSinkGetVersionError(const int32_t &result)
963 {
964 HILOGE("called, reason: %{public}d", result);
965 auto cmd = std::make_shared<NotifyResultCmd>();
966 PackNotifyResultCmd(cmd, result);
967 SendCommand(cmd);
968 CleanUpSession();
969 HILOGI("end");
970 return ERR_OK;
971 }
972
ExeSinkStartError(const int32_t & result)973 int32_t DSchedCollab::ExeSinkStartError(const int32_t &result)
974 {
975 HILOGE("called, reason: %{public}d", result);
976 auto cmd = std::make_shared<NotifyResultCmd>();
977 PackNotifyResultCmd(cmd, result);
978 SendCommand(cmd);
979 CleanUpSession();
980 HILOGI("end");
981 return ERR_OK;
982 }
983
ExeSinkConnectError(const int32_t & result)984 int32_t DSchedCollab::ExeSinkConnectError(const int32_t &result)
985 {
986 HILOGE("called, reason: %{public}d", result);
987 auto cmd = std::make_shared<NotifyResultCmd>();
988 PackNotifyResultCmd(cmd, result);
989 SendCommand(cmd);
990 CleanUpSession();
991 HILOGI("end");
992 return ERR_OK;
993 }
994
ExeDisconnect()995 int32_t DSchedCollab::ExeDisconnect()
996 {
997 HILOGI("called");
998 auto cmd = std::make_shared<DisconnectCmd>();
999 PackDisconnectCmd(cmd);
1000 SendCommand(cmd);
1001 CleanUpSession();
1002 HILOGI("end");
1003 return ERR_OK;
1004 }
1005
PackDisconnectCmd(std::shared_ptr<DisconnectCmd> cmd)1006 int32_t DSchedCollab::PackDisconnectCmd(std::shared_ptr<DisconnectCmd> cmd)
1007 {
1008 if (cmd == nullptr) {
1009 HILOGE("cmd is null");
1010 return INVALID_PARAMETERS_ERR;
1011 }
1012 cmd->command_ = DISCONNECT_CMD;
1013 cmd->collabToken_ = collabInfo_.collabToken_;
1014 return ERR_OK;
1015 }
1016
SendCommand(std::shared_ptr<BaseCmd> cmd)1017 int32_t DSchedCollab::SendCommand(std::shared_ptr<BaseCmd> cmd)
1018 {
1019 if (cmd == nullptr) {
1020 HILOGE("cmd is null");
1021 return INVALID_PARAMETERS_ERR;
1022 }
1023 HILOGI("called, cmd %{public}s", CMDDATA[cmd->command_].c_str());
1024 std::string jsonStr;
1025 int32_t ret = cmd->Marshal(jsonStr);
1026 if (ret != ERR_OK) {
1027 HILOGE("marshal cmd %{public}s failed, ret %{public}d", CMDDATA[cmd->command_].c_str(), ret);
1028 return ret;
1029 }
1030 auto buffer = std::make_shared<DSchedDataBuffer>(jsonStr.length() + 1);
1031 ret = memcpy_s(buffer->Data(), buffer->Capacity(), jsonStr.c_str(), jsonStr.length());
1032 if (ret != ERR_OK) {
1033 HILOGE("memcpy_s failed, cmd %{public}s, ret %{public}d", CMDDATA[cmd->command_].c_str(), ret);
1034 return ret;
1035 }
1036 ret = DSchedTransportSoftbusAdapter::GetInstance().SendData(softbusSessionId_, SERVICE_TYPE_COLLAB, buffer);
1037 if (ret != ERR_OK) {
1038 HILOGE("send data failed, cmd %{public}s, ret %{public}d", CMDDATA[cmd->command_].c_str(), ret);
1039 return ret;
1040 }
1041 HILOGI("end");
1042 return ERR_OK;
1043 }
1044
GetSoftbusSessionId()1045 int32_t DSchedCollab::GetSoftbusSessionId()
1046 {
1047 return softbusSessionId_;
1048 }
1049
GetCollabInfo()1050 DSchedCollabInfo DSchedCollab::GetCollabInfo()
1051 {
1052 return collabInfo_;
1053 }
1054
OnDataRecv(const std::string & peerDeviceId,int32_t command,std::shared_ptr<DSchedDataBuffer> dataBuffer)1055 void DSchedCollab::OnDataRecv(const std::string &peerDeviceId, int32_t command,
1056 std::shared_ptr<DSchedDataBuffer> dataBuffer)
1057 {
1058 if (dataBuffer == nullptr) {
1059 HILOGE("dataBuffer is null");
1060 return;
1061 }
1062 int32_t ret = 0;
1063 uint8_t *data = dataBuffer->Data();
1064 std::string jsonStr(reinterpret_cast<const char *>(data), dataBuffer->Capacity());
1065 switch (command) {
1066 case SOURCE_GET_VERSION_CMD: {
1067 auto getSinkCollabVersionCmd = std::make_shared<GetSinkCollabVersionCmd>();
1068 ret = getSinkCollabVersionCmd->Unmarshal(jsonStr);
1069 if (ret != ERR_OK) {
1070 PostErrEndTask(ret);
1071 return;
1072 }
1073 collabInfo_.sinkCollabVersion_ = getSinkCollabVersionCmd->sinkCollabVersion_;
1074 PostSrcGetVersionTask();
1075 break;
1076 }
1077 case SINK_START_CMD: {
1078 auto startCmd = std::make_shared<SinkStartCmd>();
1079 ret = startCmd->Unmarshal(jsonStr);
1080 if (ret != ERR_OK) {
1081 PostErrEndTask(ret);
1082 return;
1083 }
1084 SetSinkCollabInfo(startCmd);
1085 PostSinkStartTask(peerDeviceId);
1086 break;
1087 }
1088 case NOTIFY_RESULT_CMD: {
1089 auto notifyResultCmd = std::make_shared<NotifyResultCmd>();
1090 ret = notifyResultCmd->Unmarshal(jsonStr);
1091 if (ret != ERR_OK) {
1092 PostErrEndTask(ret);
1093 return;
1094 }
1095 PostSrcResultTask(notifyResultCmd);
1096 break;
1097 }
1098 case DISCONNECT_CMD: {
1099 CleanUpSession();
1100 break;
1101 }
1102 default:
1103 break;
1104 }
1105 }
1106
UpdateState(CollabStateType stateType)1107 void DSchedCollab::UpdateState(CollabStateType stateType)
1108 {
1109 HILOGI("called");
1110 if (stateMachine_ == nullptr) {
1111 HILOGE("stateMachine is null");
1112 return;
1113 }
1114 stateMachine_->UpdateState(stateType);
1115 }
1116
RegisterAbilityLifecycleObserver(const std::string & bundleName)1117 bool DSchedCollab::RegisterAbilityLifecycleObserver(const std::string &bundleName)
1118 {
1119 HILOGI("called");
1120 sptr<AppExecFwk::IAppMgr> appObject = GetAppManager();
1121 if (appObject == nullptr) {
1122 HILOGE("failed to get app manager service");
1123 return false;
1124 }
1125 std::vector<std::string> bundleNameList = {bundleName};
1126 appStateObserver_ = sptr<AbilityLifecycleObserver>(new (std::nothrow) AbilityLifecycleObserver());
1127 int ret = appObject->RegisterApplicationStateObserver(appStateObserver_, bundleNameList);
1128 if (ret != ERR_OK) {
1129 HILOGE("failed to register observer, ret = %{public}d", ret);
1130 return false;
1131 }
1132 HILOGI("success");
1133 return true;
1134 }
1135
UnregisterAbilityLifecycleObserver()1136 void DSchedCollab::UnregisterAbilityLifecycleObserver()
1137 {
1138 HILOGI("called");
1139 if (appStateObserver_ == nullptr) {
1140 HILOGW("no need to unregister");
1141 return;
1142 }
1143 sptr<AppExecFwk::IAppMgr> appObject = GetAppManager();
1144 if (appObject == nullptr) {
1145 HILOGE("failed to get app manager service");
1146 return;
1147 }
1148 int ret = appObject->UnregisterApplicationStateObserver(appStateObserver_);
1149 if (ret != ERR_OK) {
1150 HILOGE("failed to unregister observer, ret = %{public}d", ret);
1151 return;
1152 }
1153 HILOGI("success");
1154 }
1155
GetAppManager()1156 sptr<AppExecFwk::IAppMgr> DSchedCollab::GetAppManager()
1157 {
1158 auto samgr = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
1159 if (samgr == nullptr) {
1160 HILOGE("system ability manager is nullptr.");
1161 return nullptr;
1162 }
1163
1164 sptr<AppExecFwk::IAppMgr> appObject =
1165 iface_cast<AppExecFwk::IAppMgr>(samgr->GetSystemAbility(APP_MGR_SERVICE_ID));
1166 if (appObject == nullptr) {
1167 HILOGE("failed to get app manager service");
1168 return nullptr;
1169 }
1170 return appObject;
1171 }
1172
OnShutDown()1173 void DSchedCollab::OnShutDown()
1174 {
1175 }
1176
OnBind()1177 void DSchedCollab::OnBind()
1178 {
1179 }
1180 } // namespace DistributedSchedule
1181 } // namespace OHOS
1182