1 /*
2 * Copyright (c) 2022-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 "trans_tcp_direct_wifi.h"
17
18 #include <securec.h>
19
20 #include "auth_interface.h"
21 #include "lnn_network_manager.h"
22 #include "softbus_adapter_hitrace.h"
23 #include "softbus_adapter_mem.h"
24 #include "softbus_errcode.h"
25 #include "softbus_socket.h"
26 #include "trans_log.h"
27 #include "trans_tcp_direct_message.h"
28 #include "trans_tcp_direct_sessionconn.h"
29 #include "trans_tcp_direct_p2p.h"
30 #include "wifi_direct_manager.h"
31
32 #define ID_OFFSET (1)
33
FreeFastTransData(AppInfo * appInfo)34 static void FreeFastTransData(AppInfo *appInfo)
35 {
36 if (appInfo != NULL && appInfo->fastTransData != NULL) {
37 SoftBusFree((void *)(appInfo->fastTransData));
38 }
39 }
40
AddTcpConnAndSessionInfo(int32_t newchannelId,int32_t fd,SessionConn * newConn,ListenerModule module)41 static int32_t AddTcpConnAndSessionInfo(int32_t newchannelId, int32_t fd, SessionConn *newConn,
42 ListenerModule module)
43 {
44 if (TransSrvAddDataBufNode(newchannelId, fd) != SOFTBUS_OK) {
45 FreeFastTransData(&(newConn->appInfo));
46 SoftBusFree(newConn);
47 TRANS_LOGE(TRANS_CTRL, "OpenTcpDirectChannel create databuf fail");
48 return SOFTBUS_MALLOC_ERR;
49 }
50
51 if (TransTdcAddSessionConn(newConn) != SOFTBUS_OK) {
52 TransSrvDelDataBufNode(newchannelId);
53 FreeFastTransData(&(newConn->appInfo));
54 SoftBusFree(newConn);
55 return SOFTBUS_TRANS_ADD_SESSION_CONN_FAILED;
56 }
57 if (AddTrigger(module, fd, WRITE_TRIGGER) != SOFTBUS_OK) {
58 TRANS_LOGE(TRANS_CTRL, "OpenTcpDirectChannel add trigger fail");
59 TransDelSessionConnById(newchannelId);
60 TransSrvDelDataBufNode(newchannelId);
61 return SOFTBUS_TRANS_ADD_TRIGGER_FAILED;
62 }
63 return SOFTBUS_OK;
64 }
65
GetMoudleType(ConnectType type,const char * peerIp)66 static ListenerModule GetMoudleType(ConnectType type, const char *peerIp)
67 {
68 ListenerModule module = UNUSE_BUTT;
69 if (type == CONNECT_P2P_REUSE) {
70 char myIp[IP_LEN] = {0};
71 struct WifiDirectManager *mgr = GetWifiDirectManager();
72 if (mgr == NULL || mgr->getLocalIpByRemoteIp == NULL) {
73 TRANS_LOGE(TRANS_CTRL, "GetWifiDirectManager failed");
74 return SOFTBUS_WIFI_DIRECT_INIT_FAILED;
75 }
76
77 int32_t ret = mgr->getLocalIpByRemoteIp(peerIp, myIp, sizeof(myIp));
78 if (ret != SOFTBUS_OK) {
79 TRANS_LOGE(TRANS_CTRL, "get Local Ip fail, ret = %{public}d", ret);
80 return module;
81 }
82
83 if (IsHmlIpAddr(myIp)) {
84 module = GetModuleByHmlIp(myIp);
85 } else {
86 module = DIRECT_CHANNEL_SERVER_P2P;
87 }
88 } else {
89 module = DIRECT_CHANNEL_SERVER_WIFI;
90 }
91 return module;
92 }
93
CopyAppInfoFastTransData(SessionConn * conn,const AppInfo * appInfo)94 static int32_t CopyAppInfoFastTransData(SessionConn *conn, const AppInfo *appInfo)
95 {
96 if (appInfo->fastTransData != NULL && appInfo->fastTransDataSize > 0) {
97 uint8_t *fastTransData = (uint8_t *)SoftBusCalloc(appInfo->fastTransDataSize);
98 if (fastTransData == NULL) {
99 return SOFTBUS_MALLOC_ERR;
100 }
101 if (memcpy_s((char *)fastTransData, appInfo->fastTransDataSize, (const char *)appInfo->fastTransData,
102 appInfo->fastTransDataSize) != EOK) {
103 SoftBusFree(fastTransData);
104 TRANS_LOGE(TRANS_CTRL, "memcpy fastTransData fail");
105 return SOFTBUS_MEM_ERR;
106 }
107 conn->appInfo.fastTransData = fastTransData;
108 }
109 return SOFTBUS_OK;
110 }
111
OpenTcpDirectChannel(const AppInfo * appInfo,const ConnectOption * connInfo,int32_t * channelId)112 int32_t OpenTcpDirectChannel(const AppInfo *appInfo, const ConnectOption *connInfo, int32_t *channelId)
113 {
114 TRANS_LOGI(TRANS_CTRL, "enter.");
115 if (appInfo == NULL || connInfo == NULL || channelId == NULL) {
116 return SOFTBUS_INVALID_PARAM;
117 }
118
119 ListenerModule module = GetMoudleType(connInfo->type, connInfo->socketOption.addr);
120 TRANS_LOGI(TRANS_CTRL, "get listener module=%{public}d!", module);
121 if (module == DIRECT_CHANNEL_SERVER_WIFI) {
122 module = LnnGetProtocolListenerModule(connInfo->socketOption.protocol, LNN_LISTENER_MODE_DIRECT);
123 }
124 if (module == UNUSE_BUTT) {
125 return SOFTBUS_TRANS_TCP_UNUSE_LISTENER_MODE;
126 }
127
128 SessionConn *newConn = CreateNewSessinConn(module, false);
129 if (newConn == NULL) {
130 return SOFTBUS_MALLOC_ERR;
131 }
132 SoftbusHitraceStart(SOFTBUS_HITRACE_ID_VALID, (uint64_t)(newConn->channelId + ID_OFFSET));
133 TRANS_LOGI(TRANS_CTRL,
134 "SoftbusHitraceChainBegin: set HitraceId=%{public}" PRIu64, (uint64_t)(newConn->channelId + ID_OFFSET));
135 int32_t newchannelId = newConn->channelId;
136 if (memcpy_s(&newConn->appInfo, sizeof(AppInfo), appInfo, sizeof(AppInfo)) != EOK) {
137 TRANS_LOGE(TRANS_CTRL, "copy appInfo fail");
138 SoftBusFree(newConn);
139 return SOFTBUS_MEM_ERR;
140 }
141 int32_t ret = CopyAppInfoFastTransData(newConn, appInfo);
142 if (ret != SOFTBUS_OK) {
143 SoftBusFree(newConn);
144 TRANS_LOGE(TRANS_CTRL, "copy appinfo fast trans data fail");
145 return ret;
146 }
147 AuthGetLatestIdByUuid(newConn->appInfo.peerData.deviceId, AUTH_LINK_TYPE_WIFI, false, &newConn->authHandle);
148 if ((newConn->authHandle.authId == AUTH_INVALID_ID) && (connInfo->type == CONNECT_P2P_REUSE)) {
149 AuthGetLatestIdByUuid(newConn->appInfo.peerData.deviceId, AUTH_LINK_TYPE_BR, false, &newConn->authHandle);
150 }
151
152 if (newConn->authHandle.authId == AUTH_INVALID_ID) {
153 FreeFastTransData(&(newConn->appInfo));
154 SoftBusFree(newConn);
155 TRANS_LOGE(TRANS_CTRL, "get authId fail");
156 return SOFTBUS_TRANS_TCP_GET_AUTHID_FAILED;
157 }
158
159 int32_t fd = ConnOpenClientSocket(connInfo, newConn->appInfo.myData.addr, true);
160 if (fd < 0) {
161 FreeFastTransData(&(newConn->appInfo));
162 SoftBusFree(newConn);
163 TRANS_LOGE(TRANS_CTRL, "connect failed. fd=%{public}d", fd);
164 return fd;
165 }
166 newConn->appInfo.fd = fd;
167
168 ret = AddTcpConnAndSessionInfo(newchannelId, fd, newConn, module);
169 if (ret != SOFTBUS_OK) {
170 return ret;
171 }
172 *channelId = newchannelId;
173 TRANS_LOGI(TRANS_CTRL,
174 "ok: channelId=%{public}d, module=%{public}d, fd=%{public}d",
175 newchannelId, (int32_t)module, fd);
176 return SOFTBUS_OK;
177 }
178