Commit 6644b370 authored by Yedidya Feldblum's avatar Yedidya Feldblum Committed by Facebook Github Bot 1

IPAddressV[46]::validate

Summary:[Folly] `IPAddressV[46]::validate(StringPiece)`.

Just perform the check without allocations or throws.

Reviewed By: meyering

Differential Revision: D3103545

fb-gh-sync-id: 2918c1398935738f597b9045cf7dadbe42da2527
fbshipit-source-id: 2918c1398935738f597b9045cf7dadbe42da2527
parent 03afacaf
......@@ -44,6 +44,15 @@ void toAppend(IPAddressV4 addr, fbstring* result) {
result->append(addr.str());
}
bool IPAddressV4::validate(StringPiece ip) {
constexpr size_t kStrMaxLen = INET_ADDRSTRLEN;
std::array<char, kStrMaxLen + 1> ip_cstr;
const size_t len = std::min(ip.size(), kStrMaxLen);
std::memcpy(ip_cstr.data(), ip.data(), len);
ip_cstr[len] = 0;
struct in_addr addr;
return 1 == inet_pton(AF_INET, ip_cstr.data(), &addr);
}
// public static
IPAddressV4 IPAddressV4::fromLong(uint32_t src) {
......
......@@ -53,6 +53,8 @@ typedef std::array<uint8_t, 4> ByteArray4;
*/
class IPAddressV4 : boost::totally_ordered<IPAddressV4> {
public:
static bool validate(StringPiece ip);
// create an IPAddressV4 instance from a uint32_t (network byte order)
static IPAddressV4 fromLong(uint32_t src);
// same as above but host byte order
......
......@@ -48,6 +48,20 @@ void toAppend(IPAddressV6 addr, fbstring* result) {
result->append(addr.str());
}
bool IPAddressV6::validate(StringPiece ip) {
if (ip.size() > 0 && ip.front() == '[' && ip.back() == ']') {
ip = ip.subpiece(1, ip.size() - 2);
}
constexpr size_t kStrMaxLen = INET6_ADDRSTRLEN;
std::array<char, kStrMaxLen + 1> ip_cstr;
const size_t len = std::min(ip.size(), kStrMaxLen);
std::memcpy(ip_cstr.data(), ip.data(), len);
ip_cstr[len] = 0;
struct in6_addr addr;
return 1 == inet_pton(AF_INET6, ip_cstr.data(), &addr);
}
// public default constructor
IPAddressV6::IPAddressV6() {
}
......
......@@ -86,6 +86,8 @@ class IPAddressV6 : boost::totally_ordered<IPAddressV6> {
static constexpr size_t kToFullyQualifiedSize =
8 /*words*/ * 4 /*hex chars per word*/ + 7 /*separators*/;
static bool validate(StringPiece ip);
/**
* Create a new IPAddress instance from the provided binary data.
* @throws IPAddressFormatException if the input length is not 16 bytes.
......
......@@ -219,6 +219,22 @@ TEST(IPAddress, CtorDefault) {
EXPECT_EQ(IPAddressV6("::0"), v6);
}
TEST(IPAddressV4, validate) {
EXPECT_TRUE(IPAddressV4::validate("0.0.0.0"));
EXPECT_FALSE(IPAddressV4::validate("0.0.0."));
EXPECT_TRUE(IPAddressV4::validate("127.127.127.127"));
}
TEST(IPAddressV6, validate) {
EXPECT_TRUE(IPAddressV6::validate("2620:0:1cfe:face:b00c::3"));
EXPECT_FALSE(IPAddressV6::validate("0.0.0.0"));
EXPECT_TRUE(IPAddressV6::validate("[2620:0:1cfe:face:b00c::3]"));
EXPECT_TRUE(IPAddressV6::validate("::ffff:0.1.1.1"));
EXPECT_TRUE(IPAddressV6::validate("2620:0000:1cfe:face:b00c:0000:0000:0003"));
EXPECT_TRUE(
IPAddressV6::validate("2620:0000:1cfe:face:b00c:0000:127.127.127.127"));
}
// Test addresses constructed using a in[6]_addr value
TEST_P(IPAddressTest, CtorAddress) {
AddressData param = GetParam();
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment