• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021 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 "client_trans_tcp_direct_manager.h"
17 
18 #include <securec.h>
19 
20 #include "client_trans_tcp_direct_callback.h"
21 #include "client_trans_tcp_direct_listener.h"
22 #include "softbus_adapter_mem.h"
23 #include "softbus_base_listener.h"
24 #include "softbus_def.h"
25 #include "softbus_errcode.h"
26 #include "softbus_log.h"
27 #include "softbus_tcp_socket.h"
28 #include "softbus_utils.h"
29 #include "trans_pending_pkt.h"
30 #include "trans_server_proxy.h"
31 
32 #define HEART_TIME 300
33 static SoftBusList *g_tcpDirectChannelInfoList = NULL;
34 
TransTdcGetInfoById(int32_t channelId,TcpDirectChannelInfo * info)35 TcpDirectChannelInfo *TransTdcGetInfoById(int32_t channelId, TcpDirectChannelInfo *info)
36 {
37     if (info == NULL) {
38         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s param invalid.", __func__);
39         return NULL;
40     }
41     if (SoftBusMutexLock(&g_tcpDirectChannelInfoList->lock) != SOFTBUS_OK) {
42         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s lock failed", __func__);
43         return NULL;
44     }
45 
46     TcpDirectChannelInfo *item = NULL;
47     LIST_FOR_EACH_ENTRY(item, &(g_tcpDirectChannelInfoList->list), TcpDirectChannelInfo, node) {
48         if (item->channelId == channelId) {
49             (void)memcpy_s(info, sizeof(TcpDirectChannelInfo), item, sizeof(TcpDirectChannelInfo));
50             (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
51             return item;
52         }
53     }
54 
55     (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
56     return NULL;
57 }
58 
TransTdcGetInfoByIdWithIncSeq(int32_t channelId,TcpDirectChannelInfo * info)59 TcpDirectChannelInfo *TransTdcGetInfoByIdWithIncSeq(int32_t channelId, TcpDirectChannelInfo *info)
60 {
61     if (info == NULL) {
62         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s param invalid.", __func__);
63         return NULL;
64     }
65     if (SoftBusMutexLock(&g_tcpDirectChannelInfoList->lock) != SOFTBUS_OK) {
66         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s lock failed", __func__);
67         return NULL;
68     }
69 
70     TcpDirectChannelInfo *item = NULL;
71     LIST_FOR_EACH_ENTRY(item, &(g_tcpDirectChannelInfoList->list), TcpDirectChannelInfo, node) {
72         if (item->channelId == channelId) {
73             (void)memcpy_s(info, sizeof(TcpDirectChannelInfo), item, sizeof(TcpDirectChannelInfo));
74             item->detail.sequence++;
75             (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
76             return item;
77         }
78     }
79 
80     (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
81     return NULL;
82 }
83 
TransTdcGetInfoByFd(int32_t fd,TcpDirectChannelInfo * info)84 TcpDirectChannelInfo *TransTdcGetInfoByFd(int32_t fd, TcpDirectChannelInfo *info)
85 {
86     if (info == NULL) {
87         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s param invalid.", __func__);
88         return NULL;
89     }
90     if (SoftBusMutexLock(&g_tcpDirectChannelInfoList->lock) != SOFTBUS_OK) {
91         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s lock failed", __func__);
92         return NULL;
93     }
94 
95     TcpDirectChannelInfo *item = NULL;
96     LIST_FOR_EACH_ENTRY(item, &(g_tcpDirectChannelInfoList->list), TcpDirectChannelInfo, node) {
97         if (item->detail.fd == fd) {
98             (void)memcpy_s(info, sizeof(TcpDirectChannelInfo), item, sizeof(TcpDirectChannelInfo));
99             (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
100             return item;
101         }
102     }
103 
104     (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
105     return NULL;
106 }
107 
TransTdcCheckSeq(int32_t fd,int32_t seq)108 int32_t TransTdcCheckSeq(int32_t fd, int32_t seq)
109 {
110     TcpDirectChannelInfo *item = NULL;
111     if (SoftBusMutexLock(&g_tcpDirectChannelInfoList->lock) != SOFTBUS_OK) {
112         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s lock failed", __func__);
113         return SOFTBUS_ERR;
114     }
115     LIST_FOR_EACH_ENTRY(item, &(g_tcpDirectChannelInfoList->list), TcpDirectChannelInfo, node) {
116         if (item->detail.fd == fd) {
117             if (!IsPassSeqCheck(&(item->detail.verifyInfo), seq)) {
118                 SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_WARN, "[client]fd[%d] SeqCheck is false.", fd);
119                 (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
120                 return SOFTBUS_ERR;
121             }
122             (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
123             return SOFTBUS_OK;
124         }
125     }
126 
127     (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
128     return SOFTBUS_ERR;
129 }
130 
TransTdcCloseChannel(int32_t channelId)131 void TransTdcCloseChannel(int32_t channelId)
132 {
133     SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_INFO, "[client]TransCloseTcpDirectChannel, cId [%d].", channelId);
134     if (ServerIpcCloseChannel(channelId, CHANNEL_TYPE_TCP_DIRECT) != SOFTBUS_OK) {
135         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_INFO, "[client]close server tdc channel[%d] err.", channelId);
136     }
137 
138     TcpDirectChannelInfo *item = NULL;
139     if (SoftBusMutexLock(&g_tcpDirectChannelInfoList->lock) != SOFTBUS_OK) {
140         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]TransTdcCloseChannel lock failed");
141         return;
142     }
143 
144     LIST_FOR_EACH_ENTRY(item, &(g_tcpDirectChannelInfoList->list), TcpDirectChannelInfo, node) {
145         if (item->channelId == channelId) {
146             TransTdcReleaseFd(item->detail.fd);
147             ListDelete(&item->node);
148             SoftBusFree(item);
149             item = NULL;
150             (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
151             DelPendingPacket(channelId, PENDING_TYPE_DIRECT);
152             SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_INFO, "[client]Delete chanel[%d] item success.", channelId);
153             return;
154         }
155     }
156 
157     SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]Target channel[%d] item not exist.", channelId);
158     (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
159 }
160 
TransGetNewTcpChannel(const ChannelInfo * channel)161 static TcpDirectChannelInfo *TransGetNewTcpChannel(const ChannelInfo *channel)
162 {
163     if (channel == NULL) {
164         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s param invalid", __func__);
165         return NULL;
166     }
167     TcpDirectChannelInfo *item = (TcpDirectChannelInfo *)SoftBusCalloc(sizeof(TcpDirectChannelInfo));
168     if (item == NULL) {
169         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s calloc failed", __func__);
170         return NULL;
171     }
172     item->channelId = channel->channelId;
173     item->detail.fd = channel->fd;
174     item->detail.channelType = channel->channelType;
175     if (memcpy_s(item->detail.sessionKey, SESSION_KEY_LENGTH, channel->sessionKey, SESSION_KEY_LENGTH) != EOK) {
176         SoftBusFree(item);
177         return NULL;
178     }
179     return item;
180 }
181 
ClientTransCheckTdcChannelExist(int32_t channelId)182 static int32_t ClientTransCheckTdcChannelExist(int32_t channelId)
183 {
184     if (SoftBusMutexLock(&g_tcpDirectChannelInfoList->lock) != SOFTBUS_OK) {
185         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[%s] lock failed.", __func__);
186         return SOFTBUS_ERR;
187     }
188     TcpDirectChannelInfo *item = NULL;
189     LIST_FOR_EACH_ENTRY(item, &(g_tcpDirectChannelInfoList->list), TcpDirectChannelInfo, node) {
190         if (item->channelId == channelId) {
191             SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "tcp direct channel[%d] already exist.", channelId);
192             (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
193             return SOFTBUS_ERR;
194         }
195     }
196     (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
197     return SOFTBUS_OK;
198 }
199 
ClientTransTdcOnChannelOpened(const char * sessionName,const ChannelInfo * channel)200 int32_t ClientTransTdcOnChannelOpened(const char *sessionName, const ChannelInfo *channel)
201 {
202     if (sessionName == NULL || channel == NULL) {
203         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[%s] param invalid", __func__);
204         return SOFTBUS_ERR;
205     }
206     if (ClientTransCheckTdcChannelExist(channel->channelId) != SOFTBUS_OK) {
207         return SOFTBUS_ERR;
208     }
209     if (SoftBusMutexLock(&g_tcpDirectChannelInfoList->lock) != SOFTBUS_OK) {
210         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[%s] lock failed.", __func__);
211         return SOFTBUS_ERR;
212     }
213     TcpDirectChannelInfo *item = TransGetNewTcpChannel(channel);
214     if (item == NULL) {
215         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "get new channel[%d] err.", channel->channelId);
216         goto EXIT_ERR;
217     }
218 
219     if (TransAddDataBufNode(channel->channelId, channel->fd) != SOFTBUS_OK) {
220         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR,
221             "add cId[%d] fd[%d] data buf node fail.", channel->channelId, channel->fd);
222         SoftBusFree(item);
223         goto EXIT_ERR;
224     }
225     if (TransTdcCreateListener(channel->fd) != SOFTBUS_OK) {
226         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "trans tdc fd[%d] create listener failed.", channel->fd);
227         TransDelDataBufNode(channel->channelId);
228         SoftBusFree(item);
229         goto EXIT_ERR;
230     }
231     if (ConnSetTcpKeepAlive(channel->fd, HEART_TIME) != SOFTBUS_OK) {
232         TransDelDataBufNode(channel->channelId);
233         SoftBusFree(item);
234         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "ConnSetTcpKeepAlive failed, fd[%d].", channel->fd);
235         goto EXIT_ERR;
236     }
237 
238     ListAdd(&g_tcpDirectChannelInfoList->list, &item->node);
239     (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
240 
241     if (ClientTransTdcOnSessionOpened(sessionName, channel) != SOFTBUS_OK) {
242         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "notify on session opened err.");
243         return SOFTBUS_ERR;
244     }
245     return SOFTBUS_OK;
246 EXIT_ERR:
247     (void)SoftBusMutexUnlock(&g_tcpDirectChannelInfoList->lock);
248     return SOFTBUS_ERR;
249 }
250 
TransTdcManagerInit(const IClientSessionCallBack * cb)251 int32_t TransTdcManagerInit(const IClientSessionCallBack *cb)
252 {
253     g_tcpDirectChannelInfoList = CreateSoftBusList();
254     if (g_tcpDirectChannelInfoList == NULL || TransDataListInit() != SOFTBUS_OK) {
255         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "init tcp direct channel fail.");
256         return SOFTBUS_ERR;
257     }
258     if (ClientTransTdcSetCallBack(cb) != SOFTBUS_OK) {
259         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "ClientTransTdcSetCallBack fail.");
260         return SOFTBUS_ERR;
261     }
262     if (PendingInit(PENDING_TYPE_DIRECT) == SOFTBUS_ERR) {
263         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "trans direct pending init failed.");
264         return SOFTBUS_ERR;
265     }
266     SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_INFO, "init tcp direct channel success.");
267     return SOFTBUS_OK;
268 }
269 
TransTdcManagerDeinit(void)270 void TransTdcManagerDeinit(void)
271 {
272     if (g_tcpDirectChannelInfoList == NULL) {
273         return;
274     }
275 
276     TransDataListDeinit();
277     DestroySoftBusList(g_tcpDirectChannelInfoList);
278     g_tcpDirectChannelInfoList = NULL;
279     PendingDeinit(PENDING_TYPE_DIRECT);
280 }
281 
ClientTransTdcOnChannelOpenFailed(int32_t channelId)282 int32_t ClientTransTdcOnChannelOpenFailed(int32_t channelId)
283 {
284     return ClientTransTdcOnSessionOpenFailed(channelId);
285 }
286 
TransTdcGetSessionKey(int32_t channelId,char * key,unsigned int len)287 int32_t TransTdcGetSessionKey(int32_t channelId, char *key, unsigned int len)
288 {
289     if (key == NULL) {
290         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s invalid param.", __func__);
291         return SOFTBUS_INVALID_PARAM;
292     }
293     TcpDirectChannelInfo channel;
294     if (TransTdcGetInfoById(channelId, &channel) == NULL) {
295         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "get tdc channel[%d] info failed.", channelId);
296         return SOFTBUS_ERR;
297     }
298     if (memcpy_s(key, len, channel.detail.sessionKey, SESSION_KEY_LENGTH) != EOK) {
299         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "copy session key failed.");
300         return SOFTBUS_MEM_ERR;
301     }
302     return SOFTBUS_OK;
303 }
304 
TransTdcGetHandle(int32_t channelId,int * handle)305 int32_t TransTdcGetHandle(int32_t channelId, int *handle)
306 {
307     if (handle == NULL) {
308         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "[client]%s invalid param.", __func__);
309         return SOFTBUS_INVALID_PARAM;
310     }
311     TcpDirectChannelInfo channel;
312     if (TransTdcGetInfoById(channelId, &channel) == NULL) {
313         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "get tdc channel[%d] info failed.", channelId);
314         return SOFTBUS_ERR;
315     }
316     *handle = channel.detail.fd;
317     return SOFTBUS_OK;
318 }
319 
TransDisableSessionListener(int32_t channelId)320 int32_t TransDisableSessionListener(int32_t channelId)
321 {
322     TcpDirectChannelInfo channel;
323     if (TransTdcGetInfoById(channelId, &channel) == NULL) {
324         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "get tdc channel[%d] info failed.", channelId);
325         return SOFTBUS_ERR;
326     }
327     if (channel.detail.fd < 0) {
328         SoftBusLog(SOFTBUS_LOG_TRAN, SOFTBUS_LOG_ERROR, "invalid handle.");
329         return SOFTBUS_ERR;
330     }
331     return DelTrigger(DIRECT_CHANNEL_CLIENT, channel.detail.fd, READ_TRIGGER);
332 }
333