proxygen
IPAddressV4.h
Go to the documentation of this file.
1 /*
2  * Copyright 2014-present Facebook, Inc.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #pragma once
18 
19 #include <cstring>
20 
21 #include <array>
22 #include <functional>
23 #include <iosfwd>
24 
25 #include <folly/Expected.h>
26 #include <folly/FBString.h>
28 #include <folly/Range.h>
29 #include <folly/detail/IPAddress.h>
30 #include <folly/hash/Hash.h>
31 
32 namespace folly {
33 
34 class IPAddress;
35 class IPAddressV4;
37 
41 typedef std::pair<IPAddressV4, uint8_t> CIDRNetworkV4;
42 
46 typedef std::array<uint8_t, 4> ByteArray4;
47 
58 class IPAddressV4 {
59  public:
60  // Max size of std::string returned by toFullyQualified.
61  static constexpr size_t kMaxToFullyQualifiedSize =
62  4 /*words*/ * 3 /*max chars per word*/ + 3 /*separators*/;
63 
64  // returns true iff the input string can be parsed as an ipv4-address
65  static bool validate(StringPiece ip) noexcept;
66 
67  // create an IPAddressV4 instance from a uint32_t (network byte order)
68  static IPAddressV4 fromLong(uint32_t src);
69  // same as above but host byte order
70  static IPAddressV4 fromLongHBO(uint32_t src);
71 
77 
84 
91 
95  ByteRange toBinary() const {
96  return ByteRange((const unsigned char*)&addr_.inAddr_.s_addr, 4);
97  }
98 
104  static IPAddressV4 fromInverseArpaName(const std::string& arpaname);
105 
111  static uint32_t toLong(StringPiece ip);
112  // Same as above, but in host byte order.
113  // This is slightly slower than toLong.
114  static uint32_t toLongHBO(StringPiece ip);
115 
121  IPAddressV4();
122 
123  // Create an IPAddressV4 from a string
124  // @throws IPAddressFormatException
125  explicit IPAddressV4(StringPiece ip);
126 
127  // ByteArray4 constructor
128  explicit IPAddressV4(const ByteArray4& src) noexcept;
129 
130  // in_addr constructor
131  explicit IPAddressV4(const in_addr src) noexcept;
132 
133  // Return the V6 mapped representation of the address.
134  IPAddressV6 createIPv6() const;
135 
139  IPAddressV6 getIPv6For6To4() const;
140 
141  // Return the long (network byte order) representation of the address.
142  uint32_t toLong() const {
143  return toAddr().s_addr;
144  }
145 
146  // Return the long (host byte order) representation of the address.
147  // This is slightly slower than toLong.
148  uint32_t toLongHBO() const {
149  return ntohl(toLong());
150  }
151 
156  static constexpr size_t bitCount() {
157  return 32;
158  }
159 
163  std::string toJson() const;
164 
165  size_t hash() const {
166  static const uint32_t seed = AF_INET;
167  uint32_t hashed = hash::fnv32_buf(&addr_, 4);
168  return hash::hash_combine(seed, hashed);
169  }
170 
171  // @see IPAddress#inSubnet
172  // @throws IPAddressFormatException if string doesn't contain a V4 address
173  bool inSubnet(StringPiece cidrNetwork) const;
174 
175  // return true if address is in subnet
176  bool inSubnet(const IPAddressV4& subnet, uint8_t cidr) const {
177  return inSubnetWithMask(subnet, fetchMask(cidr));
178  }
179  bool inSubnetWithMask(const IPAddressV4& subnet, const ByteArray4 mask) const;
180 
181  // @see IPAddress#isLoopback
182  bool isLoopback() const;
183 
184  // @see IPAddress#isLinkLocal
185  bool isLinkLocal() const;
186 
187  // @see IPAddress#isNonroutable
188  bool isNonroutable() const;
189 
190  // @see IPAddress#isPrivate
191  bool isPrivate() const;
192 
193  // @see IPAddress#isMulticast
194  bool isMulticast() const;
195 
196  // @see IPAddress#isZero
197  bool isZero() const {
198  constexpr auto zero = ByteArray4{{}};
199  return 0 == std::memcmp(bytes(), zero.data(), zero.size());
200  }
201 
202  bool isLinkLocalBroadcast() const {
203  return (INADDR_BROADCAST == toLongHBO());
204  }
205 
206  // @see IPAddress#mask
207  IPAddressV4 mask(size_t numBits) const;
208 
209  // @see IPAddress#str
210  std::string str() const;
211 
213 
214  // return underlying in_addr structure
215  in_addr toAddr() const {
216  return addr_.inAddr_;
217  }
218 
219  sockaddr_in toSockAddr() const {
220  sockaddr_in addr;
221  memset(&addr, 0, sizeof(sockaddr_in));
222  addr.sin_family = AF_INET;
223  memcpy(&addr.sin_addr, &addr_.inAddr_, sizeof(in_addr));
224  return addr;
225  }
226 
227  ByteArray4 toByteArray() const {
228  ByteArray4 ba{{0}};
229  std::memcpy(ba.data(), bytes(), 4);
230  return ba;
231  }
232 
233  // @see IPAddress#toFullyQualified
235  return str();
236  }
237 
238  // @see IPAddress#toFullyQualifiedAppend
239  void toFullyQualifiedAppend(std::string& out) const;
240 
241  // @see IPAddress#version
242  uint8_t version() const {
243  return 4;
244  }
245 
254  static const ByteArray4 fetchMask(size_t numBits);
255 
256  // Given 2 IPAddressV4, mask pairs extract the longest common IPAddress,
257  // mask pair
258  static CIDRNetworkV4 longestCommonPrefix(
259  const CIDRNetworkV4& one,
260  const CIDRNetworkV4& two);
261  // Number of bytes in the address representation.
262  static size_t byteCount() {
263  return 4;
264  }
265  // get nth most significant bit - 0 indexed
266  bool getNthMSBit(size_t bitIndex) const {
267  return detail::getNthMSBitImpl(*this, bitIndex, AF_INET);
268  }
269  // get nth most significant byte - 0 indexed
270  uint8_t getNthMSByte(size_t byteIndex) const;
271  // get nth bit - 0 indexed
272  bool getNthLSBit(size_t bitIndex) const {
273  return getNthMSBit(bitCount() - bitIndex - 1);
274  }
275  // get nth byte - 0 indexed
276  uint8_t getNthLSByte(size_t byteIndex) const {
277  return getNthMSByte(byteCount() - byteIndex - 1);
278  }
279 
280  const unsigned char* bytes() const {
281  return addr_.bytes_.data();
282  }
283 
284  private:
286  static_assert(
287  sizeof(in_addr) == sizeof(ByteArray4),
288  "size of in_addr and ByteArray4 are different");
289  in_addr inAddr_;
290  ByteArray4 bytes_;
292  std::memset(this, 0, sizeof(AddressStorage));
293  }
294  explicit AddressStorage(const ByteArray4 bytes) : bytes_(bytes) {}
295  explicit AddressStorage(const in_addr addr) : inAddr_(addr) {}
296  } addr_;
297 
304 };
305 
306 // boost::hash uses hash_value() so this allows boost::hash to work
307 // automatically for IPAddressV4
308 size_t hash_value(const IPAddressV4& addr);
309 std::ostream& operator<<(std::ostream& os, const IPAddressV4& addr);
310 // Define toAppend() to allow IPAddressV4 to be used with to<string>
311 void toAppend(IPAddressV4 addr, std::string* result);
312 void toAppend(IPAddressV4 addr, fbstring* result);
313 
317 inline bool operator==(const IPAddressV4& addr1, const IPAddressV4& addr2) {
318  return (addr1.toLong() == addr2.toLong());
319 }
320 // Return true if addr1 < addr2
321 inline bool operator<(const IPAddressV4& addr1, const IPAddressV4& addr2) {
322  return (addr1.toLongHBO() < addr2.toLongHBO());
323 }
324 // Derived operators
325 inline bool operator!=(const IPAddressV4& a, const IPAddressV4& b) {
326  return !(a == b);
327 }
328 inline bool operator>(const IPAddressV4& a, const IPAddressV4& b) {
329  return b < a;
330 }
331 inline bool operator<=(const IPAddressV4& a, const IPAddressV4& b) {
332  return !(a > b);
333 }
334 inline bool operator>=(const IPAddressV4& a, const IPAddressV4& b) {
335  return !(a < b);
336 }
337 
338 } // namespace folly
339 
340 namespace std {
341 template <>
343  size_t operator()(const folly::IPAddressV4 addr) const {
344  return addr.hash();
345  }
346 };
347 } // namespace std
IPAddressV4 mask(size_t numBits) const
bool getNthMSBitImpl(const IPAddrType &ip, size_t bitIndex, sa_family_t family)
Definition: IPAddress.h:49
static uint32_t toLong(StringPiece ip)
Definition: IPAddressV4.cpp:65
bool operator>(const Expected< Value, Error > &lhs, const Expected< Value, Error > &rhs)
Definition: Expected.h:1349
std::string toInverseArpaName() const
size_t operator()(const folly::IPAddressV4 addr) const
Definition: IPAddressV4.h:343
static CIDRNetworkV4 longestCommonPrefix(const CIDRNetworkV4 &one, const CIDRNetworkV4 &two)
char b
std::string toFullyQualified() const
Definition: IPAddressV4.h:234
bool isNonroutable() const
bool isLinkLocal() const
static const int seed
static constexpr size_t kMaxToFullyQualifiedSize
Definition: IPAddressV4.h:61
static size_t byteCount()
Definition: IPAddressV4.h:262
STL namespace.
static IPAddressV4 fromBinary(ByteRange bytes)
bool isLoopback() const
—— Concurrent Priority Queue Implementation ——
Definition: AtomicBitSet.h:29
uint8_t getNthMSByte(size_t byteIndex) const
requires E e noexcept(noexcept(s.error(std::move(e))))
ByteRange toBinary() const
Definition: IPAddressV4.h:95
AddressStorage(const ByteArray4 bytes)
Definition: IPAddressV4.h:294
static Expected< IPAddressV4, IPAddressFormatError > tryFromString(StringPiece str) noexcept
Definition: IPAddressV4.cpp:96
uint8_t version() const
Definition: IPAddressV4.h:242
ByteArray4 toByteArray() const
Definition: IPAddressV4.h:227
sockaddr_in toSockAddr() const
Definition: IPAddressV4.h:219
static Expected< IPAddressV4, IPAddressFormatError > tryFromBinary(ByteRange bytes) noexcept
union folly::IPAddressV4::AddressStorage addr_
bool operator!=(const Unexpected< Error > &lhs, const Unexpected< Error > &rhs)
Definition: Expected.h:766
bool isPrivate() const
bool inSubnetWithMask(const IPAddressV4 &subnet, const ByteArray4 mask) const
uint32_t fnv32_buf(const void *buf, size_t n, uint32_t hash=FNV_32_HASH_START) noexcept
Definition: Hash.h:163
static IPAddressV4 fromLong(uint32_t src)
Definition: IPAddressV4.cpp:52
size_t hash_combine(const T &t, const Ts &...ts) noexcept(noexcept(hash_combine_generic(StdHasher{}, t, ts...)))
Definition: Hash.h:669
size_t hash() const
Definition: IPAddressV4.h:165
in_addr toAddr() const
Definition: IPAddressV4.h:215
static const ByteArray4 fetchMask(size_t numBits)
IPAddressV6 getIPv6For6To4() const
size_t hash_value(const IPAddress &addr)
Definition: IPAddress.cpp:34
uint32_t toLong() const
Definition: IPAddressV4.h:142
const unsigned char * bytes() const
Definition: IPAddressV4.h:280
std::pair< IPAddressV4, uint8_t > CIDRNetworkV4
Definition: IPAddressV4.h:36
char a
void toFullyQualifiedAppend(std::string &out) const
bool getNthMSBit(size_t bitIndex) const
Definition: IPAddressV4.h:266
void toAppend(char value, Tgt *result)
Definition: Conv.h:406
Expected< Unit, IPAddressFormatError > trySetFromBinary(ByteRange bytes) noexcept
bool operator>=(const Expected< Value, Error > &lhs, const Expected< Value, Error > &rhs)
Definition: Expected.h:1358
bool getNthLSBit(size_t bitIndex) const
Definition: IPAddressV4.h:272
std::string toJson() const
bool isZero() const
Definition: IPAddressV4.h:197
bool operator==(const Unexpected< Error > &lhs, const Unexpected< Error > &rhs)
Definition: Expected.h:758
uint32_t toLongHBO() const
Definition: IPAddressV4.h:148
const char * string
Definition: Conv.cpp:212
bool operator<=(const Expected< Value, Error > &lhs, const Expected< Value, Error > &rhs)
Definition: Expected.h:1340
Range< const unsigned char * > ByteRange
Definition: Range.h:1163
static IPAddressV4 fromLongHBO(uint32_t src)
Definition: IPAddressV4.cpp:58
static bool validate(StringPiece ip) noexcept
Definition: IPAddressV4.cpp:47
bool inSubnet(StringPiece cidrNetwork) const
std::string str() const
uint8_t getNthLSByte(size_t byteIndex) const
Definition: IPAddressV4.h:276
static uint32_t toLongHBO(StringPiece ip)
Definition: IPAddressV4.cpp:76
std::array< uint8_t, 4 > ByteArray4
Definition: IPAddressV4.h:46
static constexpr size_t bitCount()
Definition: IPAddressV4.h:156
bool isLinkLocalBroadcast() const
Definition: IPAddressV4.h:202
static IPAddressV4 fromInverseArpaName(const std::string &arpaname)
bool isMulticast() const
ThreadPoolListHook * addr
IPAddressV6 createIPv6() const
bool inSubnet(const IPAddressV4 &subnet, uint8_t cidr) const
Definition: IPAddressV4.h:176
std::enable_if< IsLessThanComparable< Value >::value, bool >::type operator<(const Expected< Value, Error > &lhs, const Expected< Value, Error > &rhs)
Definition: Expected.h:1321
AddressStorage(const in_addr addr)
Definition: IPAddressV4.h:295
std::ostream & operator<<(std::ostream &out, dynamic const &d)
Definition: dynamic-inl.h:1158