Endpoint.hpp 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173
  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. #ifndef ZT_ENDPOINT_HPP
  14. #define ZT_ENDPOINT_HPP
  15. #include "Constants.hpp"
  16. #include "InetAddress.hpp"
  17. #include "Address.hpp"
  18. #include "Utils.hpp"
  19. #include "TriviallyCopyable.hpp"
  20. #include "Fingerprint.hpp"
  21. #include <cstdio>
  22. #include <cstdlib>
  23. #include <cstdint>
  24. #include <cstring>
  25. // max name size + type byte + port (for DNS name/port) + 3x 16-bit coordinate for location
  26. #define ZT_ENDPOINT_MARSHAL_SIZE_MAX (ZT_ENDPOINT_MAX_NAME_SIZE+1+2+2+2+2)
  27. namespace ZeroTier {
  28. /**
  29. * Endpoint variant specifying some form of network endpoint
  30. *
  31. * This data structure supports a number of types that are not yet actually used:
  32. * DNSNAME, URL, and ETHERNET. These are present to reserve them for future use.
  33. */
  34. class Endpoint : public TriviallyCopyable
  35. {
  36. public:
  37. /**
  38. * Endpoint type
  39. *
  40. * These are set to be the same as the IDs used for trace events in ZeroTierCore.h.
  41. */
  42. enum Type
  43. {
  44. TYPE_NIL = ZT_TRACE_EVENT_PATH_TYPE_NIL,
  45. TYPE_ZEROTIER = ZT_TRACE_EVENT_PATH_TYPE_ZEROTIER,
  46. TYPE_DNSNAME = ZT_TRACE_EVENT_PATH_TYPE_DNSNAME,
  47. TYPE_URL = ZT_TRACE_EVENT_PATH_TYPE_URL,
  48. TYPE_INETADDR_V4 = ZT_TRACE_EVENT_PATH_TYPE_INETADDR_V4,
  49. TYPE_ETHERNET = ZT_TRACE_EVENT_PATH_TYPE_ETHERNET,
  50. TYPE_INETADDR_V6 = ZT_TRACE_EVENT_PATH_TYPE_INETADDR_V6
  51. };
  52. /**
  53. * Protocol identifiers for INETADDR endpoint types
  54. *
  55. * Most of these are reserved for future use.
  56. */
  57. enum Protocol
  58. {
  59. PROTO_UDP_ZT = 0,
  60. PROTO_TCP_ZT = 1,
  61. PROTO_IP_ZT = 2
  62. };
  63. ZT_INLINE Endpoint() noexcept { memoryZero(this); }
  64. explicit Endpoint(const InetAddress &sa,const Protocol proto = PROTO_UDP_ZT) noexcept;
  65. explicit ZT_INLINE Endpoint(const Address &zt,const uint8_t identityHash[ZT_IDENTITY_HASH_SIZE]) noexcept :
  66. _t(TYPE_ZEROTIER)
  67. {
  68. _v.zt.address = zt.toInt();
  69. memcpy(_v.zt.hash,identityHash,ZT_IDENTITY_HASH_SIZE);
  70. }
  71. explicit ZT_INLINE Endpoint(const char *name,const int port) noexcept :
  72. _t(TYPE_DNSNAME)
  73. {
  74. _v.dns.port = port;
  75. Utils::scopy(_v.dns.name,sizeof(_v.dns.name),name);
  76. }
  77. explicit ZT_INLINE Endpoint(const char *url) noexcept :
  78. _t(TYPE_URL)
  79. {
  80. Utils::scopy(_v.url,sizeof(_v.url),url);
  81. }
  82. /**
  83. * @return InetAddress or NIL if not of this type
  84. */
  85. ZT_INLINE const InetAddress &inetAddr() const noexcept { return ((_t == TYPE_INETADDR_V4) || (_t == TYPE_INETADDR_V6)) ? asInetAddress(_v.in.sa) : InetAddress::NIL; }
  86. /**
  87. * @return Protocol for INETADDR types, undefined for other endpoint types
  88. */
  89. ZT_INLINE Protocol inetAddrProto() const noexcept { return (Protocol)_v.in.proto; }
  90. /**
  91. * @return DNS name or empty string if not of this type
  92. */
  93. ZT_INLINE const char *dnsName() const noexcept { return (_t == TYPE_DNSNAME) ? _v.dns.name : ""; }
  94. /**
  95. * @return Port associated with DNS name or -1 if not of this type
  96. */
  97. ZT_INLINE int dnsPort() const noexcept { return (_t == TYPE_DNSNAME) ? _v.dns.port : -1; }
  98. /**
  99. * @return ZeroTier address or NIL if not of this type
  100. */
  101. ZT_INLINE Address ztAddress() const noexcept { return Address((_t == TYPE_ZEROTIER) ? _v.zt.address : (uint64_t)0); }
  102. /**
  103. * @return 384-bit hash of identity keys or NULL if not of this type
  104. */
  105. ZT_INLINE const Fingerprint &ztFingerprint() const noexcept { return *reinterpret_cast<const Fingerprint *>(&_v.zt); }
  106. /**
  107. * @return URL or empty string if not of this type
  108. */
  109. ZT_INLINE const char *url() const noexcept { return (_t == TYPE_URL) ? _v.url : ""; }
  110. /**
  111. * @return Ethernet address or NIL if not of this type
  112. */
  113. ZT_INLINE MAC ethernet() const noexcept { return (_t == TYPE_ETHERNET) ? MAC(_v.eth) : MAC(); }
  114. /**
  115. * @return Endpoint type or NIL if unset/empty
  116. */
  117. ZT_INLINE Type type() const noexcept { return _t; }
  118. ZT_INLINE operator bool() const noexcept { return _t != TYPE_NIL; }
  119. bool operator==(const Endpoint &ep) const noexcept;
  120. ZT_INLINE bool operator!=(const Endpoint &ep) const noexcept { return (!(*this == ep)); }
  121. bool operator<(const Endpoint &ep) const noexcept;
  122. ZT_INLINE bool operator>(const Endpoint &ep) const noexcept { return (ep < *this); }
  123. ZT_INLINE bool operator<=(const Endpoint &ep) const noexcept { return !(ep < *this); }
  124. ZT_INLINE bool operator>=(const Endpoint &ep) const noexcept { return !(*this < ep); }
  125. static constexpr int marshalSizeMax() noexcept { return ZT_ENDPOINT_MARSHAL_SIZE_MAX; }
  126. int marshal(uint8_t data[ZT_ENDPOINT_MARSHAL_SIZE_MAX]) const noexcept;
  127. int unmarshal(const uint8_t *restrict data,int len) noexcept;
  128. private:
  129. Type _t;
  130. int _l[3]; // X,Y,Z location in kilometers from the nearest gravitational center of mass
  131. union {
  132. struct {
  133. sockaddr_storage sa;
  134. uint8_t proto;
  135. } in;
  136. struct {
  137. uint16_t port;
  138. char name[ZT_ENDPOINT_MAX_NAME_SIZE];
  139. } dns;
  140. ZT_Fingerprint zt;
  141. char url[ZT_ENDPOINT_MAX_NAME_SIZE];
  142. uint64_t eth;
  143. } _v;
  144. };
  145. } // namespace ZeroTier
  146. #endif