1 /*
2 * Copyright (c) 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 #include "connect_command.h"
16
17 #include <cstring>
18
19 #include "conn_log.h"
20
21 #include "channel/auth_negotiate_channel.h"
22 #include "channel/dummy_negotiate_channel.h"
23 #include "channel/proxy_negotiate_channel.h"
24 #include "data/link_manager.h"
25 #include "event/wifi_direct_event_dispatcher.h"
26 #include "processor_selector_factory.h"
27 #include "utils/wifi_direct_anonymous.h"
28 #include "utils/wifi_direct_utils.h"
29 #include "utils/wifi_direct_dfx.h"
30 #include "wifi_direct_scheduler_factory.h"
31
32 namespace OHOS::SoftBus {
ConnectCommand(const WifiDirectConnectInfo & info,const WifiDirectConnectCallback & callback)33 ConnectCommand::ConnectCommand(const WifiDirectConnectInfo &info, const WifiDirectConnectCallback &callback)
34 : callback_(callback)
35 {
36 info_.info_ = info;
37 if (strlen(info.remoteNetworkId) != 0) {
38 remoteDeviceId_ = WifiDirectUtils::NetworkIdToUuid(info_.info_.remoteNetworkId);
39 return;
40 }
41 CONN_LOGE(CONN_WIFI_DIRECT, "remoteNetworkId empty!!");
42 }
43
GetRemoteDeviceId() const44 std::string ConnectCommand::GetRemoteDeviceId() const
45 {
46 if (!remoteDeviceId_.empty()) {
47 return remoteDeviceId_;
48 }
49 remoteDeviceId_ = WifiDirectUtils::NetworkIdToUuid(info_.info_.remoteNetworkId);
50 return remoteDeviceId_;
51 }
52
GetProcessor()53 std::shared_ptr<WifiDirectProcessor> ConnectCommand::GetProcessor()
54 {
55 CONN_LOGI(CONN_WIFI_DIRECT, "enter");
56 auto selector = ProcessorSelectorFactory::GetInstance().NewSelector();
57 if (selector == nullptr) {
58 CONN_LOGE(CONN_WIFI_DIRECT, "selector is null");
59 return nullptr;
60 }
61 return (*selector)(info_.info_);
62 }
63
GetConnectInfo()64 ConnectInfo &ConnectCommand::GetConnectInfo()
65 {
66 return info_;
67 }
68
GetConnectCallback() const69 WifiDirectConnectCallback ConnectCommand::GetConnectCallback() const
70 {
71 return callback_;
72 }
73
SetSuccessCallback(const SuccessCallback & callback)74 void ConnectCommand::SetSuccessCallback(const SuccessCallback &callback)
75 {
76 successCallback_ = callback;
77 }
78
SetFailureCallback(const FailureCallback & callback)79 void ConnectCommand::SetFailureCallback(const FailureCallback &callback)
80 {
81 failureCallback_ = callback;
82 }
83
OnSuccess(const WifiDirectLink & link) const84 void ConnectCommand::OnSuccess(const WifiDirectLink &link) const
85 {
86 CONN_LOGI(CONN_WIFI_DIRECT,
87 "requestId=%{public}u, linkId=%{public}d, localIp=%{public}s, remoteIp=%{public}s, remotePort=%{public}d, "
88 "linkType=%{public}d, isReuse=%{public}d, bw=%{public}d, channelId=%{public}d, remoteDeviceId=%{public}s",
89 info_.info_.requestId, link.linkId, WifiDirectAnonymizeIp(link.localIp).c_str(),
90 WifiDirectAnonymizeIp(link.remoteIp).c_str(), link.remotePort, link.linkType, link.isReuse, link.bandWidth,
91 link.channelId, WifiDirectAnonymizeDeviceId(remoteDeviceId_).c_str());
92 if (successCallback_ != nullptr) {
93 successCallback_(link);
94 return;
95 }
96 WifiDirectDfx::GetInstance().DfxRecord(true, SOFTBUS_OK, info_);
97 if (callback_.onConnectSuccess != nullptr) {
98 callback_.onConnectSuccess(info_.info_.requestId, &link);
99 }
100 }
101
OnFailure(int32_t reason) const102 void ConnectCommand::OnFailure(int32_t reason) const
103 {
104 CONN_LOGI(CONN_WIFI_DIRECT, "requestId=%{public}u, reason=%{public}d, remoteDeviceId=%{public}s",
105 info_.info_.requestId, reason, WifiDirectAnonymizeDeviceId(remoteDeviceId_).c_str());
106 if (reason == SOFTBUS_CONN_NEED_RENEGOTIATE && !HasRetried()) {
107 CONN_LOGI(CONN_WIFI_DIRECT, "retry");
108 WifiDirectSchedulerFactory::GetInstance().GetScheduler().ConnectDevice(info_.info_, callback_, true);
109 return;
110 }
111 if (failureCallback_ != nullptr) {
112 failureCallback_(reason);
113 return;
114 }
115 WifiDirectDfx::GetInstance().DfxRecord(false, reason, info_);
116 if (callback_.onConnectFailure != nullptr) {
117 callback_.onConnectFailure(info_.info_.requestId, reason);
118 }
119 }
120
PreferNegotiateChannel()121 void ConnectCommand::PreferNegotiateChannel()
122 {
123 auto innerLink = LinkManager::GetInstance().GetReuseLink(info_.info_.connectType, remoteDeviceId_);
124 if (remoteDeviceId_.length() != (UUID_BUF_LEN - 1) && innerLink == nullptr) {
125 innerLink = LinkManager::GetInstance().GetReuseLink(remoteDeviceId_);
126 }
127 if (innerLink == nullptr || innerLink->GetNegotiateChannel() == nullptr) {
128 if (info_.info_.negoChannel.type == NEGO_CHANNEL_AUTH) {
129 CONN_LOGI(CONN_WIFI_DIRECT, "prefer input auth channel");
130 info_.channel_ = std::make_shared<AuthNegotiateChannel>(info_.info_.negoChannel.handle.authHandle);
131 } else if (info_.info_.negoChannel.type == NEGO_CHANNEL_COC) {
132 CONN_LOGI(CONN_WIFI_DIRECT, "prefer input proxy channel");
133 info_.channel_ = std::make_shared<CoCProxyNegotiateChannel>(info_.info_.negoChannel.handle.channelId);
134 } else {
135 CONN_LOGI(CONN_WIFI_DIRECT, "prefer input null channel");
136 info_.channel_ = std::make_shared<DummyNegotiateChannel>();
137 }
138 return;
139 }
140
141 CONN_LOGI(CONN_WIFI_DIRECT, "prefer inner channel");
142 info_.channel_ = innerLink->GetNegotiateChannel();
143 }
144
IsSameCommand(const WifiDirectConnectInfo & info) const145 bool ConnectCommand::IsSameCommand(const WifiDirectConnectInfo &info) const
146 {
147 return (info.requestId == info_.info_.requestId) && (info.pid == info_.info_.pid);
148 }
149 } // namespace OHOS::SoftBus
150