GoGlue.cpp 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729
  1. /*
  2. * Copyright (c)2013-2020 ZeroTier, Inc.
  3. *
  4. * Use of this software is governed by the Business Source License included
  5. * in the LICENSE.TXT file in the project's root directory.
  6. *
  7. * Change Date: 2024-01-01
  8. *
  9. * On the date above, in accordance with the Business Source License, use
  10. * of this software will be governed by version 2.0 of the Apache License.
  11. */
  12. /****/
  13. #include "GoGlue.h"
  14. #include "../core/Constants.hpp"
  15. #include "../core/InetAddress.hpp"
  16. #include "../core/Node.hpp"
  17. #include "../core/Utils.hpp"
  18. #include "../core/MAC.hpp"
  19. #include "../core/Address.hpp"
  20. #include "../core/Containers.hpp"
  21. #include "../osdep/OSUtils.hpp"
  22. #include "../osdep/EthernetTap.hpp"
  23. #ifndef __WINDOWS__
  24. #include <unistd.h>
  25. #include <sys/socket.h>
  26. #include <sys/un.h>
  27. #include <sys/types.h>
  28. #include <sys/ioctl.h>
  29. #include <ifaddrs.h>
  30. #include <net/if.h>
  31. #include <netinet/in.h>
  32. #ifdef __BSD__
  33. #include <netinet6/in6_var.h>
  34. #endif
  35. #include <arpa/inet.h>
  36. #include <errno.h>
  37. #ifdef __LINUX__
  38. #ifndef IPV6_DONTFRAG
  39. #define IPV6_DONTFRAG 62
  40. #endif
  41. #endif
  42. #endif // !__WINDOWS__
  43. #include <thread>
  44. #include <mutex>
  45. #include <memory>
  46. #include <atomic>
  47. #ifdef __WINDOWS__
  48. #define SETSOCKOPT_FLAG_TYPE BOOL
  49. #define SETSOCKOPT_FLAG_TRUE TRUE
  50. #define SETSOCKOPT_FLAG_FALSE FALSE
  51. #else
  52. #define SETSOCKOPT_FLAG_TYPE int
  53. #define SETSOCKOPT_FLAG_TRUE 1
  54. #define SETSOCKOPT_FLAG_FALSE 0
  55. #endif
  56. #ifndef MSG_DONTWAIT
  57. #define MSG_DONTWAIT 0
  58. #endif
  59. using namespace ZeroTier;
  60. struct ZT_GoNodeThread
  61. {
  62. String ip;
  63. int port;
  64. int af;
  65. bool primary;
  66. std::atomic< bool > run;
  67. std::thread thr;
  68. };
  69. struct ZT_GoNode_Impl
  70. {
  71. void *goUserPtr;
  72. Node *node;
  73. volatile int64_t nextBackgroundTaskDeadline;
  74. String path;
  75. std::atomic< bool > run;
  76. Map< ZT_SOCKET, ZT_GoNodeThread > threads;
  77. Map< uint64_t, std::shared_ptr< EthernetTap > > taps;
  78. std::mutex threads_l;
  79. std::mutex taps_l;
  80. std::thread backgroundTaskThread;
  81. };
  82. static const String defaultHomePath(OSUtils::platformDefaultHomePath());
  83. const char *const ZT_PLATFORM_DEFAULT_HOMEPATH = defaultHomePath.c_str();
  84. // These are implemented in Go code.
  85. extern "C" int goPathCheckFunc(void *, const ZT_Identity *, int, const void *, int);
  86. extern "C" int goPathLookupFunc(void *, uint64_t, int, const ZT_Identity *, int *, uint8_t [16], int *);
  87. extern "C" void goStateObjectPutFunc(void *, int, const uint64_t [2], const void *, int);
  88. extern "C" int goStateObjectGetFunc(void *, int, const uint64_t [2], void **);
  89. extern "C" void goVirtualNetworkConfigFunc(void *, ZT_GoTap *, uint64_t, int, const ZT_VirtualNetworkConfig *);
  90. extern "C" void goZtEvent(void *, int, const void *);
  91. extern "C" void goHandleTapAddedMulticastGroup(void *, ZT_GoTap *, uint64_t, uint64_t, uint32_t);
  92. extern "C" void goHandleTapRemovedMulticastGroup(void *, ZT_GoTap *, uint64_t, uint64_t, uint32_t);
  93. static void ZT_GoNode_VirtualNetworkConfigFunction(
  94. ZT_Node *node,
  95. void *uptr,
  96. void *tptr,
  97. uint64_t nwid,
  98. void **nptr,
  99. enum ZT_VirtualNetworkConfigOperation op,
  100. const ZT_VirtualNetworkConfig *cfg)
  101. {
  102. goVirtualNetworkConfigFunc(reinterpret_cast<ZT_GoNode *>(uptr)->goUserPtr, reinterpret_cast<ZT_GoTap *>(*nptr), nwid, op, cfg);
  103. }
  104. static void ZT_GoNode_VirtualNetworkFrameFunction(
  105. ZT_Node *node,
  106. void *uptr,
  107. void *tptr,
  108. uint64_t nwid,
  109. void **nptr,
  110. uint64_t srcMac,
  111. uint64_t destMac,
  112. unsigned int etherType,
  113. unsigned int vlanId,
  114. const void *data,
  115. unsigned int len)
  116. {
  117. if (*nptr)
  118. reinterpret_cast<EthernetTap *>(*nptr)->put(MAC(srcMac), MAC(destMac), etherType, data, len);
  119. }
  120. static void ZT_GoNode_EventCallback(
  121. ZT_Node *node,
  122. void *uptr,
  123. void *tptr,
  124. enum ZT_Event et,
  125. const void *data)
  126. {
  127. goZtEvent(reinterpret_cast<ZT_GoNode *>(uptr)->goUserPtr, et, data);
  128. }
  129. static void ZT_GoNode_StatePutFunction(
  130. ZT_Node *node,
  131. void *uptr,
  132. void *tptr,
  133. enum ZT_StateObjectType objType,
  134. const uint64_t id[2],
  135. const void *data,
  136. int len)
  137. {
  138. goStateObjectPutFunc(
  139. reinterpret_cast<ZT_GoNode *>(uptr)->goUserPtr,
  140. objType,
  141. id,
  142. data,
  143. len);
  144. }
  145. static void _freeFunc(void *p)
  146. { if (p) free(p); }
  147. static int ZT_GoNode_StateGetFunction(
  148. ZT_Node *node,
  149. void *uptr,
  150. void *tptr,
  151. enum ZT_StateObjectType objType,
  152. const uint64_t id[2],
  153. void **data,
  154. void (**freeFunc)(void *))
  155. {
  156. *freeFunc = &_freeFunc;
  157. return goStateObjectGetFunc(
  158. reinterpret_cast<ZT_GoNode *>(uptr)->goUserPtr,
  159. (int)objType,
  160. id,
  161. data);
  162. }
  163. static ZT_INLINE void doUdpSend(ZT_SOCKET sock, const struct sockaddr_storage *addr, const void *data, const unsigned int len, const unsigned int ipTTL)
  164. {
  165. switch (addr->ss_family) {
  166. case AF_INET:
  167. if (unlikely((ipTTL > 0) && (ipTTL < 255))) {
  168. #ifdef __WINDOWS__
  169. DWORD tmp = (DWORD)ipTTL;
  170. #else
  171. int tmp = (int)ipTTL;
  172. #endif
  173. setsockopt(sock, IPPROTO_IP, IP_TTL, &tmp, sizeof(tmp));
  174. sendto(sock, data, len, MSG_DONTWAIT, (const sockaddr *)addr, sizeof(struct sockaddr_in));
  175. tmp = 255;
  176. setsockopt(sock, IPPROTO_IP, IP_TTL, &tmp, sizeof(tmp));
  177. } else {
  178. sendto(sock, data, len, MSG_DONTWAIT, (const sockaddr *)addr, sizeof(struct sockaddr_in));
  179. }
  180. break;
  181. case AF_INET6:
  182. // The ipTTL option isn't currently used with IPv6. It's only used
  183. // with IPv4 "firewall opener" / "NAT buster" preamble packets as part
  184. // of IPv4 NAT traversal.
  185. sendto(sock, data, len, MSG_DONTWAIT, (const sockaddr *)addr, sizeof(struct sockaddr_in6));
  186. break;
  187. }
  188. }
  189. static int ZT_GoNode_WirePacketSendFunction(
  190. ZT_Node *node,
  191. void *uptr,
  192. void *tptr,
  193. int64_t localSocket,
  194. const struct sockaddr_storage *addr,
  195. const void *data,
  196. unsigned int len,
  197. unsigned int ipTTL)
  198. {
  199. if (likely(localSocket > 0)) {
  200. doUdpSend((ZT_SOCKET)localSocket, addr, data, len, ipTTL);
  201. } else {
  202. ZT_GoNode *const gn = reinterpret_cast<ZT_GoNode *>(uptr);
  203. std::lock_guard< std::mutex > l(gn->threads_l);
  204. for (auto t = gn->threads.begin(); t != gn->threads.end(); ++t) {
  205. if ((t->second.af == addr->ss_family) && (t->second.primary)) {
  206. doUdpSend(t->first, addr, data, len, ipTTL);
  207. break;
  208. }
  209. }
  210. }
  211. return 0;
  212. }
  213. static int ZT_GoNode_PathCheckFunction(
  214. ZT_Node *node,
  215. void *uptr,
  216. void *tptr,
  217. uint64_t ztAddress,
  218. const ZT_Identity *id,
  219. int64_t localSocket,
  220. const struct sockaddr_storage *sa)
  221. {
  222. switch (sa->ss_family) {
  223. case AF_INET:
  224. return goPathCheckFunc(
  225. reinterpret_cast<ZT_GoNode *>(uptr)->goUserPtr,
  226. id,
  227. AF_INET,
  228. &(reinterpret_cast<const struct sockaddr_in *>(sa)->sin_addr.s_addr),
  229. Utils::ntoh((uint16_t)reinterpret_cast<const struct sockaddr_in *>(sa)->sin_port));
  230. case AF_INET6:
  231. return goPathCheckFunc(
  232. reinterpret_cast<ZT_GoNode *>(uptr)->goUserPtr,
  233. id,
  234. AF_INET6,
  235. reinterpret_cast<const struct sockaddr_in6 *>(sa)->sin6_addr.s6_addr,
  236. Utils::ntoh((uint16_t)reinterpret_cast<const struct sockaddr_in6 *>(sa)->sin6_port));
  237. }
  238. return 0;
  239. }
  240. static int ZT_GoNode_PathLookupFunction(
  241. ZT_Node *node,
  242. void *uptr,
  243. void *tptr,
  244. uint64_t ztAddress,
  245. const ZT_Identity *id,
  246. int desiredAddressFamily,
  247. struct sockaddr_storage *sa)
  248. {
  249. int family = 0;
  250. uint8_t ip[16];
  251. int port = 0;
  252. const int result = goPathLookupFunc(
  253. reinterpret_cast<ZT_GoNode *>(uptr)->goUserPtr,
  254. ztAddress,
  255. desiredAddressFamily,
  256. id,
  257. &family,
  258. ip,
  259. &port
  260. );
  261. if (result != 0) {
  262. switch (family) {
  263. case AF_INET:
  264. reinterpret_cast<struct sockaddr_in *>(sa)->sin_family = AF_INET;
  265. memcpy(&(reinterpret_cast<struct sockaddr_in *>(sa)->sin_addr.s_addr), ip, 4);
  266. reinterpret_cast<struct sockaddr_in *>(sa)->sin_port = Utils::hton((uint16_t)port);
  267. return 1;
  268. case AF_INET6:
  269. reinterpret_cast<struct sockaddr_in6 *>(sa)->sin6_family = AF_INET6;
  270. memcpy(reinterpret_cast<struct sockaddr_in6 *>(sa)->sin6_addr.s6_addr, ip, 16);
  271. reinterpret_cast<struct sockaddr_in6 *>(sa)->sin6_port = Utils::hton((uint16_t)port);
  272. return 1;
  273. }
  274. }
  275. return 0;
  276. }
  277. extern "C" ZT_GoNode *ZT_GoNode_new(const char *workingPath, uintptr_t userPtr)
  278. {
  279. try {
  280. struct ZT_Node_Callbacks cb;
  281. cb.statePutFunction = &ZT_GoNode_StatePutFunction;
  282. cb.stateGetFunction = &ZT_GoNode_StateGetFunction;
  283. cb.wirePacketSendFunction = &ZT_GoNode_WirePacketSendFunction;
  284. cb.virtualNetworkFrameFunction = &ZT_GoNode_VirtualNetworkFrameFunction;
  285. cb.virtualNetworkConfigFunction = &ZT_GoNode_VirtualNetworkConfigFunction;
  286. cb.eventCallback = &ZT_GoNode_EventCallback;
  287. cb.pathCheckFunction = &ZT_GoNode_PathCheckFunction;
  288. cb.pathLookupFunction = &ZT_GoNode_PathLookupFunction;
  289. ZT_GoNode_Impl *gn = new ZT_GoNode_Impl;
  290. const int64_t now = OSUtils::now();
  291. gn->goUserPtr = reinterpret_cast<void *>(userPtr);
  292. gn->node = new Node(reinterpret_cast<void *>(gn), nullptr, &cb, now);
  293. gn->nextBackgroundTaskDeadline = now;
  294. gn->path = workingPath;
  295. gn->run = true;
  296. gn->backgroundTaskThread = std::thread([gn] {
  297. int64_t lastCheckedTaps = 0;
  298. while (gn->run) {
  299. std::this_thread::sleep_for(std::chrono::milliseconds(500));
  300. const int64_t now = OSUtils::now();
  301. if (now >= gn->nextBackgroundTaskDeadline)
  302. gn->node->processBackgroundTasks(nullptr, now, &(gn->nextBackgroundTaskDeadline));
  303. if ((now - lastCheckedTaps) > 10000) {
  304. lastCheckedTaps = now;
  305. std::vector< MulticastGroup > added, removed;
  306. std::lock_guard< std::mutex > tl(gn->taps_l);
  307. for (auto t = gn->taps.begin(); t != gn->taps.end(); ++t) {
  308. added.clear();
  309. removed.clear();
  310. t->second->scanMulticastGroups(added, removed);
  311. for (auto g = added.begin(); g != added.end(); ++g)
  312. goHandleTapAddedMulticastGroup(gn, (ZT_GoTap *)t->second.get(), t->first, g->mac().toInt(), g->adi());
  313. for (auto g = removed.begin(); g != removed.end(); ++g)
  314. goHandleTapRemovedMulticastGroup(gn, (ZT_GoTap *)t->second.get(), t->first, g->mac().toInt(), g->adi());
  315. }
  316. }
  317. }
  318. });
  319. return gn;
  320. } catch (...) {
  321. fprintf(stderr, "FATAL: unable to create new instance of Node (out of memory?)" ZT_EOL_S);
  322. exit(1);
  323. }
  324. }
  325. extern "C" void ZT_GoNode_delete(ZT_GoNode *gn)
  326. {
  327. gn->run = false;
  328. gn->threads_l.lock();
  329. for (auto t = gn->threads.begin(); t != gn->threads.end(); ++t) {
  330. t->second.run = false;
  331. shutdown(t->first, SHUT_RDWR);
  332. close(t->first);
  333. t->second.thr.join();
  334. }
  335. gn->threads_l.unlock();
  336. gn->taps_l.lock();
  337. for (auto t = gn->taps.begin(); t != gn->taps.end(); ++t)
  338. gn->node->leave(t->first, nullptr, nullptr);
  339. gn->taps.clear();
  340. gn->taps_l.unlock();
  341. gn->backgroundTaskThread.join();
  342. gn->node->shutdown(nullptr);
  343. delete gn->node;
  344. delete gn;
  345. }
  346. extern "C" ZT_Node *ZT_GoNode_getNode(ZT_GoNode *gn)
  347. {
  348. return gn->node;
  349. }
  350. static void setCommonUdpSocketSettings(ZT_SOCKET udpSock, const char *dev)
  351. {
  352. int bufSize = 1048576;
  353. while (bufSize > 131072) {
  354. if (setsockopt(udpSock, SOL_SOCKET, SO_RCVBUF, (const char *)&bufSize, sizeof(bufSize)) == 0)
  355. break;
  356. bufSize -= 131072;
  357. }
  358. bufSize = 1048576;
  359. while (bufSize > 131072) {
  360. if (setsockopt(udpSock, SOL_SOCKET, SO_SNDBUF, (const char *)&bufSize, sizeof(bufSize)) == 0)
  361. break;
  362. bufSize -= 131072;
  363. }
  364. SETSOCKOPT_FLAG_TYPE fl;
  365. #ifdef SO_REUSEPORT
  366. fl = SETSOCKOPT_FLAG_TRUE;
  367. setsockopt(udpSock, SOL_SOCKET, SO_REUSEPORT, (void *)&fl, sizeof(fl));
  368. #endif
  369. #ifndef __LINUX__ // linux wants just SO_REUSEPORT
  370. fl = SETSOCKOPT_FLAG_TRUE;
  371. setsockopt(udpSock, SOL_SOCKET, SO_REUSEADDR, (void *)&fl, sizeof(fl));
  372. #endif
  373. fl = SETSOCKOPT_FLAG_TRUE;
  374. setsockopt(udpSock, SOL_SOCKET, SO_BROADCAST, (void *)&fl, sizeof(fl));
  375. #ifdef IP_DONTFRAG
  376. fl = SETSOCKOPT_FLAG_FALSE;
  377. setsockopt(udpSock,IPPROTO_IP,IP_DONTFRAG,(void *)&fl,sizeof(fl));
  378. #endif
  379. #ifdef IP_MTU_DISCOVER
  380. fl = SETSOCKOPT_FLAG_FALSE;
  381. setsockopt(udpSock,IPPROTO_IP,IP_MTU_DISCOVER,(void *)&fl,sizeof(fl));
  382. #endif
  383. #ifdef SO_BINDTODEVICE
  384. if ((dev)&&(strlen(dev)))
  385. setsockopt(udpSock,SOL_SOCKET,SO_BINDTODEVICE,dev,strlen(dev));
  386. #endif
  387. #if defined(__BSD__) && defined(IP_BOUND_IF)
  388. if ((dev) && (strlen(dev))) {
  389. int idx = if_nametoindex(dev);
  390. if (idx != 0)
  391. setsockopt(udpSock, IPPROTO_IP, IP_BOUND_IF, (void *)&idx, sizeof(idx));
  392. }
  393. #endif
  394. }
  395. extern "C" int ZT_GoNode_phyStartListen(ZT_GoNode *gn, const char *dev, const char *ip, const int port, const int primary)
  396. {
  397. if (strchr(ip, ':')) {
  398. struct sockaddr_in6 in6;
  399. memset(&in6, 0, sizeof(in6));
  400. in6.sin6_family = AF_INET6;
  401. if (inet_pton(AF_INET6, ip, &(in6.sin6_addr)) <= 0)
  402. return errno;
  403. in6.sin6_port = htons((uint16_t)port);
  404. ZT_SOCKET udpSock = socket(AF_INET6, SOCK_DGRAM, 0);
  405. if (udpSock == ZT_INVALID_SOCKET)
  406. return errno;
  407. setCommonUdpSocketSettings(udpSock, dev);
  408. SETSOCKOPT_FLAG_TYPE fl = SETSOCKOPT_FLAG_TRUE;
  409. setsockopt(udpSock, IPPROTO_IPV6, IPV6_V6ONLY, (const char *)&fl, sizeof(fl));
  410. #ifdef IPV6_DONTFRAG
  411. fl = SETSOCKOPT_FLAG_FALSE;
  412. setsockopt(udpSock,IPPROTO_IPV6,IPV6_DONTFRAG,&fl,sizeof(fl));
  413. #endif
  414. if (bind(udpSock, reinterpret_cast<const struct sockaddr *>(&in6), sizeof(in6)) != 0)
  415. return errno;
  416. {
  417. std::lock_guard< std::mutex > l(gn->threads_l);
  418. ZT_GoNodeThread &gnt = gn->threads[udpSock];
  419. gnt.ip = ip;
  420. gnt.port = port;
  421. gnt.af = AF_INET6;
  422. gnt.primary = (primary != 0);
  423. gnt.run = true;
  424. gnt.thr = std::thread([udpSock, gn, &gnt] {
  425. struct sockaddr_in6 in6;
  426. socklen_t salen;
  427. while (gnt.run) {
  428. salen = sizeof(in6);
  429. void *buf = ZT_getBuffer();
  430. if (buf) {
  431. int s = (int)recvfrom(udpSock, buf, 16384, 0, reinterpret_cast<struct sockaddr *>(&in6), &salen);
  432. if (s > 0) {
  433. ZT_Node_processWirePacket(
  434. reinterpret_cast<ZT_Node *>(gn->node),
  435. nullptr,
  436. OSUtils::now(),
  437. (int64_t)udpSock,
  438. reinterpret_cast<const struct sockaddr_storage *>(&in6),
  439. buf,
  440. (unsigned int)s,
  441. 1,
  442. &(gn->nextBackgroundTaskDeadline));
  443. } else {
  444. ZT_freeBuffer(buf);
  445. std::this_thread::sleep_for(std::chrono::milliseconds(10));
  446. }
  447. }
  448. }
  449. });
  450. }
  451. } else {
  452. struct sockaddr_in in;
  453. memset(&in, 0, sizeof(in));
  454. in.sin_family = AF_INET;
  455. if (inet_pton(AF_INET, ip, &(in.sin_addr)) <= 0)
  456. return errno;
  457. in.sin_port = htons((uint16_t)port);
  458. ZT_SOCKET udpSock = socket(AF_INET, SOCK_DGRAM, 0);
  459. if (udpSock == ZT_INVALID_SOCKET)
  460. return errno;
  461. setCommonUdpSocketSettings(udpSock, dev);
  462. #ifdef SO_NO_CHECK
  463. SETSOCKOPT_FLAG_TYPE fl = SETSOCKOPT_FLAG_TRUE;
  464. setsockopt(udpSock,SOL_SOCKET,SO_NO_CHECK,&fl,sizeof(fl));
  465. #endif
  466. if (bind(udpSock, reinterpret_cast<const struct sockaddr *>(&in), sizeof(in)) != 0)
  467. return errno;
  468. {
  469. std::lock_guard< std::mutex > l(gn->threads_l);
  470. ZT_GoNodeThread &gnt = gn->threads[udpSock];
  471. gnt.ip = ip;
  472. gnt.port = port;
  473. gnt.af = AF_INET6;
  474. gnt.primary = (primary != 0);
  475. gnt.run = true;
  476. gnt.thr = std::thread([udpSock, gn, &gnt] {
  477. struct sockaddr_in in4;
  478. socklen_t salen;
  479. while (gnt.run) {
  480. salen = sizeof(in4);
  481. void *buf = ZT_getBuffer();
  482. if (buf) {
  483. int s = (int)recvfrom(udpSock, buf, sizeof(buf), 0, reinterpret_cast<struct sockaddr *>(&in4), &salen);
  484. if (s > 0) {
  485. ZT_Node_processWirePacket(
  486. reinterpret_cast<ZT_Node *>(gn->node),
  487. nullptr,
  488. OSUtils::now(),
  489. (int64_t)udpSock,
  490. reinterpret_cast<const struct sockaddr_storage *>(&in4),
  491. buf,
  492. (unsigned int)s,
  493. 1,
  494. &(gn->nextBackgroundTaskDeadline));
  495. } else {
  496. ZT_freeBuffer(buf);
  497. std::this_thread::sleep_for(std::chrono::milliseconds(10));
  498. }
  499. }
  500. }
  501. });
  502. }
  503. }
  504. return 0;
  505. }
  506. extern "C" int ZT_GoNode_phyStopListen(ZT_GoNode *gn, const char *dev, const char *ip, const int port)
  507. {
  508. {
  509. std::lock_guard< std::mutex > l(gn->threads_l);
  510. for (auto t = gn->threads.begin(); t != gn->threads.end();) {
  511. if ((t->second.ip == ip) && (t->second.port == port)) {
  512. t->second.run = false;
  513. shutdown(t->first, SHUT_RDWR);
  514. close(t->first);
  515. t->second.thr.join();
  516. gn->threads.erase(t++);
  517. } else ++t;
  518. }
  519. }
  520. return 0;
  521. }
  522. static void tapFrameHandler(void *uptr, void *tptr, uint64_t nwid, const MAC &from, const MAC &to, unsigned int etherType, unsigned int vlanId, const void *data, unsigned int len)
  523. {
  524. ZT_Node_processVirtualNetworkFrame(
  525. reinterpret_cast<ZT_Node *>(reinterpret_cast<ZT_GoNode *>(uptr)->node),
  526. tptr,
  527. OSUtils::now(),
  528. nwid,
  529. from.toInt(),
  530. to.toInt(),
  531. etherType,
  532. vlanId,
  533. data,
  534. len,
  535. 0,
  536. &(reinterpret_cast<ZT_GoNode *>(uptr)->nextBackgroundTaskDeadline));
  537. }
  538. extern "C" ZT_GoTap *ZT_GoNode_join(ZT_GoNode *gn, uint64_t nwid, const ZT_Fingerprint *const controllerFingerprint)
  539. {
  540. try {
  541. std::lock_guard< std::mutex > l(gn->taps_l);
  542. auto existingTap = gn->taps.find(nwid);
  543. if (existingTap != gn->taps.end())
  544. return (ZT_GoTap *)existingTap->second.get();
  545. char tmp[256];
  546. OSUtils::ztsnprintf(tmp, sizeof(tmp), "ZeroTier Network %.16llx", (unsigned long long)nwid);
  547. std::shared_ptr< EthernetTap > tap(EthernetTap::newInstance(nullptr, gn->path.c_str(), MAC(Address(gn->node->address()), nwid), ZT_DEFAULT_MTU, 0, nwid, tmp, &tapFrameHandler, gn));
  548. if (!tap)
  549. return nullptr;
  550. gn->taps[nwid] = tap;
  551. gn->node->join(nwid, controllerFingerprint, tap.get(), nullptr);
  552. return (ZT_GoTap *)tap.get();
  553. } catch (...) {
  554. return nullptr;
  555. }
  556. }
  557. extern "C" void ZT_GoNode_leave(ZT_GoNode *gn, uint64_t nwid)
  558. {
  559. std::lock_guard< std::mutex > l(gn->taps_l);
  560. auto existingTap = gn->taps.find(nwid);
  561. if (existingTap != gn->taps.end()) {
  562. gn->node->leave(nwid, nullptr, nullptr);
  563. gn->taps.erase(existingTap);
  564. }
  565. }
  566. extern "C" void ZT_GoTap_setEnabled(ZT_GoTap *tap, int enabled)
  567. {
  568. reinterpret_cast<EthernetTap *>(tap)->setEnabled(enabled != 0);
  569. }
  570. extern "C" int ZT_GoTap_addIp(ZT_GoTap *tap, int af, const void *ip, int netmaskBits)
  571. {
  572. switch (af) {
  573. case AF_INET:
  574. return (reinterpret_cast<EthernetTap *>(tap)->addIp(InetAddress(ip, 4, (unsigned int)netmaskBits)) ? 1 : 0);
  575. case AF_INET6:
  576. return (reinterpret_cast<EthernetTap *>(tap)->addIp(InetAddress(ip, 16, (unsigned int)netmaskBits)) ? 1 : 0);
  577. }
  578. return 0;
  579. }
  580. extern "C" int ZT_GoTap_removeIp(ZT_GoTap *tap, int af, const void *ip, int netmaskBits)
  581. {
  582. switch (af) {
  583. case AF_INET:
  584. return (reinterpret_cast<EthernetTap *>(tap)->removeIp(InetAddress(ip, 4, (unsigned int)netmaskBits)) ? 1 : 0);
  585. case AF_INET6:
  586. return (reinterpret_cast<EthernetTap *>(tap)->removeIp(InetAddress(ip, 16, (unsigned int)netmaskBits)) ? 1 : 0);
  587. }
  588. return 0;
  589. }
  590. extern "C" int ZT_GoTap_ips(ZT_GoTap *tap, void *buf, unsigned int bufSize)
  591. {
  592. auto ips = reinterpret_cast<EthernetTap *>(tap)->ips();
  593. unsigned int p = 0;
  594. uint8_t *const b = reinterpret_cast<uint8_t *>(buf);
  595. for (auto ip = ips.begin(); ip != ips.end(); ++ip) {
  596. if ((p + 6) > bufSize)
  597. break;
  598. const uint8_t *const ipd = reinterpret_cast<const uint8_t *>(ip->rawIpData());
  599. if (ip->isV4()) {
  600. b[p++] = AF_INET;
  601. b[p++] = ipd[0];
  602. b[p++] = ipd[1];
  603. b[p++] = ipd[2];
  604. b[p++] = ipd[3];
  605. b[p++] = (uint8_t)ip->netmaskBits();
  606. } else if (ip->isV6()) {
  607. if ((p + 18) <= bufSize) {
  608. b[p++] = AF_INET6;
  609. for (int j = 0; j < 16; ++j)
  610. b[p++] = ipd[j];
  611. b[p++] = (uint8_t)ip->netmaskBits();
  612. }
  613. }
  614. }
  615. return (int)p;
  616. }
  617. extern "C" void ZT_GoTap_deviceName(ZT_GoTap *tap, char nbuf[256])
  618. {
  619. Utils::scopy(nbuf, 256, reinterpret_cast<EthernetTap *>(tap)->deviceName().c_str());
  620. }
  621. extern "C" void ZT_GoTap_setFriendlyName(ZT_GoTap *tap, const char *friendlyName)
  622. {
  623. reinterpret_cast<EthernetTap *>(tap)->setFriendlyName(friendlyName);
  624. }
  625. extern "C" void ZT_GoTap_setMtu(ZT_GoTap *tap, unsigned int mtu)
  626. {
  627. reinterpret_cast<EthernetTap *>(tap)->setMtu(mtu);
  628. }
  629. #if defined(IFA_F_SECONDARY) && !defined(IFA_F_TEMPORARY)
  630. #define IFA_F_TEMPORARY IFA_F_SECONDARY
  631. #endif
  632. extern "C" int ZT_isTemporaryV6Address(const char *ifname, const struct sockaddr_storage *a)
  633. {
  634. #if defined(IN6_IFF_TEMPORARY) && defined(SIOCGIFAFLAG_IN6)
  635. static ZT_SOCKET s_tmpV6Socket = ZT_INVALID_SOCKET;
  636. static std::mutex s_lock;
  637. std::lock_guard< std::mutex > l(s_lock);
  638. if (s_tmpV6Socket == ZT_INVALID_SOCKET) {
  639. s_tmpV6Socket = socket(AF_INET6, SOCK_DGRAM, 0);
  640. if (s_tmpV6Socket <= 0)
  641. return 0;
  642. }
  643. struct in6_ifreq ifr;
  644. memset(&ifr, 0, sizeof(ifr));
  645. strncpy(ifr.ifr_name, ifname, sizeof(ifr.ifr_name));
  646. memcpy(&(ifr.ifr_addr), a, sizeof(sockaddr_in6));
  647. if (ioctl(s_tmpV6Socket, SIOCGIFAFLAG_IN6, &ifr) < 0) {
  648. return 0;
  649. }
  650. return ((ifr.ifr_ifru.ifru_flags6 & IN6_IFF_TEMPORARY) != 0) ? 1 : 0;
  651. #else
  652. return 0;
  653. #endif
  654. }
  655. extern "C" void *ZT_malloc(unsigned long s)
  656. { return (void *)malloc((size_t)s); }