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