1 /*
2  * Copyright (c) 2022 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 "tlssocket_exec.h"
17 
18 #include <string>
19 #include <vector>
20 
21 #include <napi/native_api.h>
22 #include <securec.h>
23 
24 #include "context_key.h"
25 #include "event_list.h"
26 #include "napi_utils.h"
27 #include "netstack_log.h"
28 #include "socket_error.h"
29 #include "socket_exec_common.h"
30 #include "tls_socket.h"
31 
32 #ifdef IOS_PLATFORM
33 #define SO_PROTOCOL 38
34 #endif
35 
36 namespace OHOS {
37 namespace NetStack {
38 namespace TlsSocket {
39 namespace {
40 constexpr const char *CERTIFICATA_DATA = "data";
41 constexpr const char *CERTIFICATA_ENCODING_FORMAT = "encodingFormat";
42 } // namespace
43 
TLSSocketThrowException(TLSInitContext *context, int32_t errorCode)44 static inline void TLSSocketThrowException(TLSInitContext *context, int32_t errorCode)
45 {
46     context->SetNeedThrowException(true);
47     context->SetError(errorCode, MakeErrorMessage(errorCode));
48 }
49 
IsTCPSocket(int sockFD)50 static inline bool IsTCPSocket(int sockFD)
51 {
52     int optval;
53     socklen_t optlen = sizeof(optval);
54 
55     if (getsockopt(sockFD, SOL_SOCKET, SO_PROTOCOL, &optval, &optlen) != 0) {
56         return false;
57     }
58     return optval == IPPROTO_TCP;
59 }
60 
IsConnected(int sockFD)61 static inline bool IsConnected(int sockFD)
62 {
63     sockaddr_storage addr{};
64     socklen_t len = sizeof(addr);
65     return getpeername(sockFD, reinterpret_cast<sockaddr *>(&addr), &len) == 0;
66 }
67 
ExecInit(TLSInitContext *context)68 bool TLSSocketExec::ExecInit(TLSInitContext *context)
69 {
70     auto manager = context->GetManager();
71     if (manager == nullptr) {
72         NETSTACK_LOGE("manager is nullptr");
73         TLSSocketThrowException(context, SYSTEM_INTERNAL_ERROR);
74         return false;
75     }
76 
77     auto sockFd = static_cast<int>(reinterpret_cast<uint64_t>(context->extManager_->GetData()));
78     if (sockFd <= 0 || !IsTCPSocket(sockFd)) {
79         NETSTACK_LOGE("invalid tcp socket fd");
80         TLSSocketThrowException(context, TLS_ERR_SOCK_INVALID_FD);
81         return false;
82     }
83 
84     if (!IsConnected(sockFd)) {
85         NETSTACK_LOGE("tcp socket is not connected");
86         TLSSocketThrowException(context, TLS_ERR_SOCK_NOT_CONNECT);
87         return false;
88     }
89 
90     auto tlsSocket = new (std::nothrow) std::shared_ptr<TLSSocket>;
91     if (tlsSocket == nullptr) {
92         NETSTACK_LOGE("new TLSSocket failed, no enough memory");
93         TLSSocketThrowException(context, SYSTEM_INTERNAL_ERROR);
94         return false;
95     }
96     *tlsSocket = std::make_shared<TLSSocket>(sockFd);
97     manager->SetData(tlsSocket);
98 
99     std::string events[] = {EVENT_MESSAGE, EVENT_ERROR, EVENT_CONNECT, EVENT_CLOSE};
100     for (auto event : events) {
101         context->extManager_->DeleteListener(event);
102     }
103 
104     context->extManager_->SetData(reinterpret_cast<void *>(-1));
105     context->extManager_->WaitForRcvThdExit();
106     return true;
107 }
108 
ExecGetCertificate(GetCertificateContext *context)109 bool TLSSocketExec::ExecGetCertificate(GetCertificateContext *context)
110 {
111     auto manager = context->GetManager();
112     if (manager == nullptr) {
113         NETSTACK_LOGE("manager is nullptr");
114         return false;
115     }
116     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
117     if (tlsSocket == nullptr) {
118         NETSTACK_LOGE("ExecGetCertificate tlsSocket is null");
119         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
120         return false;
121     }
122     auto shared = *tlsSocket;
123     if (!shared) {
124         NETSTACK_LOGE("ExecGetCertificate tlsSocket is null");
125         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
126         return false;
127     }
128     shared->GetCertificate([&context](int32_t errorNumber, const X509CertRawData &cert) {
129         context->localCert_ = cert;
130         context->errorNumber_ = errorNumber;
131         if (errorNumber != TLSSOCKET_SUCCESS) {
132             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
133         }
134     });
135     return context->errorNumber_ == TLSSOCKET_SUCCESS;
136 }
137 
ExecConnect(TLSConnectContext *context)138 bool TLSSocketExec::ExecConnect(TLSConnectContext *context)
139 {
140     if (context == nullptr) {
141         NETSTACK_LOGE("context is nullptr");
142         return false;
143     }
144     context->connectOptions_.address_.SetRawAddress(ConvertAddressToIp(
145         context->connectOptions_.address_.GetAddress(), context->connectOptions_.address_.GetSaFamily()));
146     auto manager = context->GetManager();
147     if (manager == nullptr) {
148         NETSTACK_LOGE("manager is nullptr");
149         return false;
150     }
151     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
152     if (tlsSocket == nullptr) {
153         NETSTACK_LOGE("ExecConnect tlsSocket is null");
154         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
155         return false;
156     }
157     auto shared = *tlsSocket;
158     if (!shared) {
159         NETSTACK_LOGE("ExecConnect tlsSocket is null");
160         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
161         return false;
162     }
163     shared->Connect(context->connectOptions_, [&context](int32_t errorNumber) {
164         context->errorNumber_ = errorNumber;
165         if (errorNumber != TLSSOCKET_SUCCESS) {
166             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
167         }
168     });
169     return context->errorNumber_ == TLSSOCKET_SUCCESS;
170 }
171 
ExecGetCipherSuites(GetCipherSuitesContext *context)172 bool TLSSocketExec::ExecGetCipherSuites(GetCipherSuitesContext *context)
173 {
174     auto manager = context->GetManager();
175     if (manager == nullptr) {
176         NETSTACK_LOGE("manager is nullptr");
177         return false;
178     }
179     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
180     if (tlsSocket == nullptr) {
181         NETSTACK_LOGE("ExecGetCipherSuites tlsSocket is null");
182         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
183         return false;
184     }
185     auto shared = *tlsSocket;
186     if (!shared) {
187         NETSTACK_LOGE("ExecGetCipherSuites tlsSocket is null");
188         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
189         return false;
190     }
191     shared->GetCipherSuite([&context](int32_t errorNumber, const std::vector<std::string> &suite) {
192         context->cipherSuites_ = suite;
193         context->errorNumber_ = errorNumber;
194         if (errorNumber != TLSSOCKET_SUCCESS) {
195             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
196         }
197     });
198     return context->errorNumber_ == TLSSOCKET_SUCCESS;
199 }
200 
ExecGetRemoteCertificate(GetRemoteCertificateContext *context)201 bool TLSSocketExec::ExecGetRemoteCertificate(GetRemoteCertificateContext *context)
202 {
203     auto manager = context->GetManager();
204     if (manager == nullptr) {
205         NETSTACK_LOGE("manager is nullptr");
206         return false;
207     }
208     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
209     if (tlsSocket == nullptr) {
210         NETSTACK_LOGE("ExecGetRemoteCertificate tlsSocket is null");
211         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
212         return false;
213     }
214     auto shared = *tlsSocket;
215     if (!shared) {
216         NETSTACK_LOGE("ExecGetRemoteCertificate tlsSocket is null");
217         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
218         return false;
219     }
220     shared->GetRemoteCertificate([&context](int32_t errorNumber, const X509CertRawData &cert) {
221         context->remoteCert_ = cert;
222         context->errorNumber_ = errorNumber;
223         if (errorNumber != TLSSOCKET_SUCCESS) {
224             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
225         }
226     });
227     return context->errorNumber_ == TLSSOCKET_SUCCESS;
228 }
229 
ExecGetProtocol(GetProtocolContext *context)230 bool TLSSocketExec::ExecGetProtocol(GetProtocolContext *context)
231 {
232     auto manager = context->GetManager();
233     if (manager == nullptr) {
234         NETSTACK_LOGE("manager is nullptr");
235         return false;
236     }
237     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
238     if (tlsSocket == nullptr) {
239         NETSTACK_LOGE("ExecGetProtocol tlsSocket is null");
240         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
241         return false;
242     }
243     auto shared = *tlsSocket;
244     if (!shared) {
245         NETSTACK_LOGE("ExecGetRemoteCertificate tlsSocket is null");
246         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
247         return false;
248     }
249     shared->GetProtocol([&context](int32_t errorNumber, const std::string &protocol) {
250         context->protocol_ = protocol;
251         context->errorNumber_ = errorNumber;
252         if (errorNumber != TLSSOCKET_SUCCESS) {
253             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
254         }
255     });
256     return context->errorNumber_ == TLSSOCKET_SUCCESS;
257 }
258 
ExecGetSignatureAlgorithms(GetSignatureAlgorithmsContext *context)259 bool TLSSocketExec::ExecGetSignatureAlgorithms(GetSignatureAlgorithmsContext *context)
260 {
261     auto manager = context->GetManager();
262     if (manager == nullptr) {
263         NETSTACK_LOGE("manager is nullptr");
264         return false;
265     }
266     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
267     if (tlsSocket == nullptr) {
268         NETSTACK_LOGE("ExecGetSignatureAlgorithms tlsSocket is null");
269         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
270         return false;
271     }
272     auto shared = *tlsSocket;
273     if (!shared) {
274         NETSTACK_LOGE("ExecGetRemoteCertificate tlsSocket is null");
275         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
276         return false;
277     }
278     shared->GetSignatureAlgorithms([&context](int32_t errorNumber, const std::vector<std::string> &algorithms) {
279         context->signatureAlgorithms_ = algorithms;
280         context->errorNumber_ = errorNumber;
281         if (errorNumber != TLSSOCKET_SUCCESS) {
282             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
283         }
284     });
285     return context->errorNumber_ == TLSSOCKET_SUCCESS;
286 }
287 
ExecSend(TLSSendContext *context)288 bool TLSSocketExec::ExecSend(TLSSendContext *context)
289 {
290     auto manager = context->GetManager();
291     if (manager == nullptr) {
292         NETSTACK_LOGE("manager is nullptr");
293         return false;
294     }
295     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
296     if (tlsSocket == nullptr) {
297         NETSTACK_LOGE("ExecSend tlsSocket is null");
298         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
299         return false;
300     }
301     Socket::TCPSendOptions tcpSendOptions;
302     tcpSendOptions.SetData(context->data_);
303     auto shared = *tlsSocket;
304     if (!shared) {
305         NETSTACK_LOGE("ExecGetRemoteCertificate tlsSocket is null");
306         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
307         return false;
308     }
309     shared->Send(tcpSendOptions, [&context](int32_t errorNumber) {
310         context->errorNumber_ = errorNumber;
311         if (errorNumber != TLSSOCKET_SUCCESS) {
312             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
313         }
314     });
315     return context->errorNumber_ == TLSSOCKET_SUCCESS;
316 }
317 
ExecClose(TLSNapiContext *context)318 bool TLSSocketExec::ExecClose(TLSNapiContext *context)
319 {
320     auto manager = context->GetManager();
321     if (manager == nullptr) {
322         NETSTACK_LOGE("manager is nullptr");
323         return false;
324     }
325     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
326     if (tlsSocket == nullptr) {
327         NETSTACK_LOGE("ExecClose tlsSocket is null");
328         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
329         return false;
330     }
331     auto shared = *tlsSocket;
332     if (!shared) {
333         NETSTACK_LOGE("ExecGetRemoteCertificate tlsSocket is null");
334         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
335         return false;
336     }
337     {
338         std::lock_guard<std::mutex> lock(shared->GetCloseLock());
339         if (shared->GetCloseState()) {
340             NETSTACK_LOGE("Socket is closing");
341             return true;
342         }
343         shared->SetCloseState(true);
344     }
345     shared->Close([&context](int32_t errorNumber) {
346         context->errorNumber_ = errorNumber;
347         if (errorNumber != TLSSOCKET_SUCCESS) {
348             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
349         }
350     });
351     delete tlsSocket;
352     manager->SetData(nullptr);
353     return context->errorNumber_ == TLSSOCKET_SUCCESS;
354 }
355 
ExecBind(TLSBindContext *context)356 bool TLSSocketExec::ExecBind(TLSBindContext *context)
357 {
358     auto manager = context->GetManager();
359     if (manager == nullptr) {
360         NETSTACK_LOGE("manager is nullptr");
361         return false;
362     }
363 
364     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
365     if (tlsSocket != nullptr) {
366         NETSTACK_LOGI("TLSSocket has been constructed");
367         return true;
368     }
369 
370     tlsSocket = new (std::nothrow) std::shared_ptr<TLSSocket>;
371     if (tlsSocket == nullptr) {
372         NETSTACK_LOGE("new TLSSocket failed, no enough memory");
373         return false;
374     }
375     auto shared = std::make_shared<TLSSocket>();
376     if (!shared) {
377         return false;
378     }
379     *tlsSocket = shared;
380     shared->Bind(context->address_, [&context](int32_t errorNumber) {
381         context->errorNumber_ = errorNumber;
382         if (errorNumber != TLSSOCKET_SUCCESS) {
383             std::string errorString = MakeErrorMessage(errorNumber);
384             context->SetError(errorNumber, errorString);
385         }
386     });
387     manager->SetData(tlsSocket);
388     return context->errorNumber_ == TLSSOCKET_SUCCESS;
389 }
390 
ExecGetRemoteAddress(TLSGetRemoteAddressContext *context)391 bool TLSSocketExec::ExecGetRemoteAddress(TLSGetRemoteAddressContext *context)
392 {
393     auto manager = context->GetManager();
394     if (manager == nullptr) {
395         NETSTACK_LOGE("manager is nullptr");
396         return false;
397     }
398     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
399     if (tlsSocket == nullptr) {
400         NETSTACK_LOGE("ExecGetRemoteAddress tlsSocket is null");
401         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
402         return false;
403     }
404     auto shared = *tlsSocket;
405     if (!shared) {
406         NETSTACK_LOGE("ExecGetRemoteAddress tlsSocket is null");
407         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
408         return false;
409     }
410     shared->GetRemoteAddress([&context](int32_t errorNumber, const Socket::NetAddress address) {
411         context->address_ = address;
412         context->errorNumber_ = errorNumber;
413         if (errorNumber != TLSSOCKET_SUCCESS) {
414             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
415         }
416     });
417     return context->errorNumber_ == TLSSOCKET_SUCCESS;
418 }
419 
ExecGetLocalAddress(TLSGetLocalAddressContext *context)420 bool TLSSocketExec::ExecGetLocalAddress(TLSGetLocalAddressContext *context)
421 {
422     if (context == nullptr) {
423         return false;
424     }
425     auto manager = context->GetManager();
426     if (manager == nullptr) {
427         context->SetNeedThrowException(true);
428         context->SetError(TlsSocket::TlsSocketError::TLS_ERR_NO_BIND,
429                           TlsSocket::MakeErrorMessage(TlsSocket::TlsSocketError::TLS_ERR_NO_BIND));
430         return false;
431     }
432     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
433     if (tlsSocket == nullptr) {
434         context->SetError(TlsSocket::TlsSocketError::TLS_ERR_NO_BIND,
435                           TlsSocket::MakeErrorMessage(TlsSocket::TlsSocketError::TLS_ERR_NO_BIND));
436         return false;
437     }
438     auto shared = *tlsSocket;
439     if (!shared) {
440         context->SetError(TlsSocket::TlsSocketError::TLS_ERR_NO_BIND,
441                           TlsSocket::MakeErrorMessage(TlsSocket::TlsSocketError::TLS_ERR_NO_BIND));
442         return false;
443     }
444     auto listenSocketFD = shared->GetSocketFd();
445     struct sockaddr_storage addr {};
446     socklen_t addrLen = sizeof(addr);
447     if (getsockname(listenSocketFD, (struct sockaddr *)&addr, &addrLen) == -1) {
448         context->SetNeedThrowException(true);
449         context->SetErrorCode(errno);
450         return false;
451     }
452 
453     char ipStr[INET6_ADDRSTRLEN] = {0};
454     Socket::NetAddress localAddress;
455     if (addr.ss_family == AF_INET) {
456         auto *addr_in = (struct sockaddr_in *)&addr;
457         inet_ntop(AF_INET, &addr_in->sin_addr, ipStr, sizeof(ipStr));
458         localAddress.SetFamilyBySaFamily(AF_INET);
459         localAddress.SetRawAddress(ipStr);
460         localAddress.SetPort(ntohs(addr_in->sin_port));
461         shared->SetLocalAddress(localAddress);
462     } else if (addr.ss_family == AF_INET6) {
463         auto *addr_in6 = (struct sockaddr_in6 *)&addr;
464         inet_ntop(AF_INET6, &addr_in6->sin6_addr, ipStr, sizeof(ipStr));
465         localAddress.SetFamilyBySaFamily(AF_INET6);
466         localAddress.SetRawAddress(ipStr);
467         localAddress.SetPort(ntohs(addr_in6->sin6_port));
468         shared->SetLocalAddress(localAddress);
469     }
470     return true;
471 }
472 
ExecGetState(TLSGetStateContext *context)473 bool TLSSocketExec::ExecGetState(TLSGetStateContext *context)
474 {
475     auto manager = context->GetManager();
476     if (manager == nullptr) {
477         NETSTACK_LOGE("manager is nullptr");
478         context->SetError(TLS_ERR_SYS_EINVAL, MakeErrorMessage(TLS_ERR_SYS_EINVAL));
479         return false;
480     }
481     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
482     if (tlsSocket == nullptr) {
483         NETSTACK_LOGE("ExecGetState tlsSocket is null");
484         return true;
485     }
486     auto shared = *tlsSocket;
487     if (!shared) {
488         return true;
489     }
490     shared->GetState([&context](int32_t errorNumber, const Socket::SocketStateBase state) {
491         context->state_ = state;
492         context->errorNumber_ = errorNumber;
493         if (errorNumber != TLSSOCKET_SUCCESS) {
494             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
495         }
496     });
497     return context->errorNumber_ == TLSSOCKET_SUCCESS;
498 }
499 
ExecSetExtraOptions(TLSSetExtraOptionsContext *context)500 bool TLSSocketExec::ExecSetExtraOptions(TLSSetExtraOptionsContext *context)
501 {
502     auto manager = context->GetManager();
503     if (manager == nullptr) {
504         NETSTACK_LOGE("manager is nullptr");
505         return false;
506     }
507     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
508     if (tlsSocket == nullptr) {
509         NETSTACK_LOGE("ExecSetExtraOptions tlsSocket is null");
510         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
511         return false;
512     }
513     auto shared = *tlsSocket;
514     if (!shared) {
515         NETSTACK_LOGE("ExecSetExtraOptions tlsSocket is null");
516         context->SetError(TLS_ERR_NO_BIND, MakeErrorMessage(TLS_ERR_NO_BIND));
517         return false;
518     }
519     shared->SetExtraOptions(context->options_, [&context](int32_t errorNumber) {
520         context->errorNumber_ = errorNumber;
521         if (errorNumber != TLSSOCKET_SUCCESS) {
522             context->SetError(errorNumber, MakeErrorMessage(errorNumber));
523         }
524     });
525     return context->errorNumber_ == TLSSOCKET_SUCCESS;
526 }
527 
GetCertificateCallback(GetCertificateContext *context)528 napi_value TLSSocketExec::GetCertificateCallback(GetCertificateContext *context)
529 {
530     void *data = nullptr;
531     napi_value arrayBuffer = NapiUtils::CreateArrayBuffer(context->GetEnv(), context->localCert_.data.Length(), &data);
532     if (data != nullptr && arrayBuffer != nullptr) {
533         if (memcpy_s(data, context->localCert_.data.Length(),
534                      reinterpret_cast<const uint8_t *>(context->localCert_.data.Data()),
535                      context->localCert_.data.Length()) != EOK) {
536             NETSTACK_LOGE("memcpy_s failed!");
537             return NapiUtils::GetUndefined(context->GetEnv());
538         }
539     }
540     napi_value outData = nullptr;
541     napi_create_typedarray(context->GetEnv(), napi_uint8_array, context->localCert_.data.Length(), arrayBuffer, 0,
542                            &outData);
543     napi_value obj = NapiUtils::CreateObject(context->GetEnv());
544     if (NapiUtils::GetValueType(context->GetEnv(), obj) != napi_object) {
545         return NapiUtils::GetUndefined(context->GetEnv());
546     }
547     NapiUtils::SetNamedProperty(context->GetEnv(), obj, CERTIFICATA_DATA, outData);
548     NapiUtils::SetInt32Property(context->GetEnv(), obj, CERTIFICATA_ENCODING_FORMAT,
549                                 context->localCert_.encodingFormat);
550     return obj;
551 }
552 
ConnectCallback(TLSConnectContext *context)553 napi_value TLSSocketExec::ConnectCallback(TLSConnectContext *context)
554 {
555     return NapiUtils::GetUndefined(context->GetEnv());
556 }
557 
GetCipherSuitesCallback(GetCipherSuitesContext *context)558 napi_value TLSSocketExec::GetCipherSuitesCallback(GetCipherSuitesContext *context)
559 {
560     napi_value cipherSuites = NapiUtils::CreateArray(context->GetEnv(), 0);
561     int index = 0;
562     for (const auto &cipher : context->cipherSuites_) {
563         napi_value cipherSuite = NapiUtils::CreateStringUtf8(context->GetEnv(), cipher);
564         NapiUtils::SetArrayElement(context->GetEnv(), cipherSuites, index++, cipherSuite);
565     }
566     return cipherSuites;
567 }
568 
GetRemoteCertificateCallback(GetRemoteCertificateContext *context)569 napi_value TLSSocketExec::GetRemoteCertificateCallback(GetRemoteCertificateContext *context)
570 {
571     void *data = nullptr;
572     napi_value arrayBuffer = NapiUtils::CreateArrayBuffer(context->GetEnv(), context->remoteCert_.data.Length(), &data);
573     if (data != nullptr && arrayBuffer != nullptr) {
574         if (memcpy_s(data, context->remoteCert_.data.Length(),
575                      reinterpret_cast<const uint8_t *>(context->remoteCert_.data.Data()),
576                      context->remoteCert_.data.Length()) != EOK) {
577             NETSTACK_LOGE("memcpy_s failed!");
578             return NapiUtils::GetUndefined(context->GetEnv());
579         }
580     }
581     napi_value outData = nullptr;
582     napi_create_typedarray(context->GetEnv(), napi_uint8_array, context->remoteCert_.data.Length(), arrayBuffer, 0,
583                            &outData);
584     napi_value obj = NapiUtils::CreateObject(context->GetEnv());
585     if (NapiUtils::GetValueType(context->GetEnv(), obj) != napi_object) {
586         return NapiUtils::GetUndefined(context->GetEnv());
587     }
588     NapiUtils::SetNamedProperty(context->GetEnv(), obj, CERTIFICATA_DATA, outData);
589     NapiUtils::SetInt32Property(context->GetEnv(), obj, CERTIFICATA_ENCODING_FORMAT,
590                                 context->remoteCert_.encodingFormat);
591     return obj;
592 }
593 
GetProtocolCallback(GetProtocolContext *context)594 napi_value TLSSocketExec::GetProtocolCallback(GetProtocolContext *context)
595 {
596     return NapiUtils::CreateStringUtf8(context->GetEnv(), context->protocol_);
597 }
598 
GetSignatureAlgorithmsCallback(GetSignatureAlgorithmsContext *context)599 napi_value TLSSocketExec::GetSignatureAlgorithmsCallback(GetSignatureAlgorithmsContext *context)
600 {
601     napi_value signatureAlgorithms = NapiUtils::CreateArray(context->GetEnv(), 0);
602     int index = 0;
603     for (const auto &algorithm : context->signatureAlgorithms_) {
604         napi_value signatureAlgorithm = NapiUtils::CreateStringUtf8(context->GetEnv(), algorithm);
605         NapiUtils::SetArrayElement(context->GetEnv(), signatureAlgorithms, index++, signatureAlgorithm);
606     }
607     return signatureAlgorithms;
608 }
609 
SendCallback(TLSSendContext *context)610 napi_value TLSSocketExec::SendCallback(TLSSendContext *context)
611 {
612     return NapiUtils::GetUndefined(context->GetEnv());
613 }
614 
CloseCallback(TLSNapiContext *context)615 napi_value TLSSocketExec::CloseCallback(TLSNapiContext *context)
616 {
617     auto manager = context->GetManager();
618     if (manager != nullptr) {
619         NETSTACK_LOGD("tls socket close, delete js ref");
620         manager->DeleteEventReference(context->GetEnv());
621     }
622     return NapiUtils::GetUndefined(context->GetEnv());
623 }
624 
BindCallback(TLSBindContext *context)625 napi_value TLSSocketExec::BindCallback(TLSBindContext *context)
626 {
627     context->Emit(EVENT_LISTENING, std::make_pair(NapiUtils::GetUndefined(context->GetEnv()),
628                                                   NapiUtils::GetUndefined(context->GetEnv())));
629     return NapiUtils::GetUndefined(context->GetEnv());
630 }
631 
GetStateCallback(TLSGetStateContext *context)632 napi_value TLSSocketExec::GetStateCallback(TLSGetStateContext *context)
633 {
634     napi_value obj = NapiUtils::CreateObject(context->GetEnv());
635     if (NapiUtils::GetValueType(context->GetEnv(), obj) != napi_object) {
636         return NapiUtils::GetUndefined(context->GetEnv());
637     }
638     NapiUtils::SetBooleanProperty(context->GetEnv(), obj, KEY_IS_BOUND, context->state_.IsBound());
639     NapiUtils::SetBooleanProperty(context->GetEnv(), obj, KEY_IS_CLOSE, context->state_.IsClose());
640     NapiUtils::SetBooleanProperty(context->GetEnv(), obj, KEY_IS_CONNECTED, context->state_.IsConnected());
641     return obj;
642 }
643 
GetRemoteAddressCallback(TLSGetRemoteAddressContext *context)644 napi_value TLSSocketExec::GetRemoteAddressCallback(TLSGetRemoteAddressContext *context)
645 {
646     napi_value obj = NapiUtils::CreateObject(context->GetEnv());
647     if (NapiUtils::GetValueType(context->GetEnv(), obj) != napi_object) {
648         return NapiUtils::GetUndefined(context->GetEnv());
649     }
650     NapiUtils::SetStringPropertyUtf8(context->GetEnv(), obj, KEY_ADDRESS, context->address_.GetAddress());
651     NapiUtils::SetUint32Property(context->GetEnv(), obj, KEY_FAMILY, context->address_.GetJsValueFamily());
652     NapiUtils::SetUint32Property(context->GetEnv(), obj, KEY_PORT, context->address_.GetPort());
653     return obj;
654 }
655 
GetLocalAddressCallback(TLSGetLocalAddressContext *context)656 napi_value TLSSocketExec::GetLocalAddressCallback(TLSGetLocalAddressContext *context)
657 {
658     napi_value obj = NapiUtils::CreateObject(context->GetEnv());
659     if (NapiUtils::GetValueType(context->GetEnv(), obj) != napi_object) {
660         return NapiUtils::GetUndefined(context->GetEnv());
661     }
662     auto manager = context->GetManager();
663     if (manager == nullptr) {
664         NETSTACK_LOGE("manager is nullptr");
665         return obj;
666     }
667     auto tlsSocket = reinterpret_cast<std::shared_ptr<TLSSocket> *>(manager->GetData());
668     if (tlsSocket == nullptr) {
669         NETSTACK_LOGE("get localAddress callback tlsSocketServer is null");
670         return obj;
671     }
672     auto env = context->GetEnv();
673     auto shared = *tlsSocket;
674     if (!shared) {
675         return obj;
676     }
677     NapiUtils::SetStringPropertyUtf8(env, obj, KEY_ADDRESS, shared->GetLocalAddress().GetAddress());
678     NapiUtils::SetUint32Property(env, obj, KEY_FAMILY, shared->GetLocalAddress().GetJsValueFamily());
679     NapiUtils::SetUint32Property(env, obj, KEY_PORT, shared->GetLocalAddress().GetPort());
680     return obj;
681 }
682 
SetExtraOptionsCallback(TLSSetExtraOptionsContext *context)683 napi_value TLSSocketExec::SetExtraOptionsCallback(TLSSetExtraOptionsContext *context)
684 {
685     return NapiUtils::GetUndefined(context->GetEnv());
686 }
687 
688 } // namespace TlsSocket
689 } // namespace NetStack
690 } // namespace OHOS
691