mirror of
https://github.com/espressif/openthread.git
synced 2026-09-12 12:10:07 +00:00
[net] add Ip4::Address class (#6334)
This commit adds IPv4 address definitions in OpenThread: - Adds `Ip4::Address` class. - Adds methods to convert IPv4 address to/from string. - Updates the `Ip6::Address::FromString()` to use the IPv4 `FromString()` for the case where the IPv6 address contains an embedded IPv4 address. - Renames unit test to `test_ip_address` and updates it to cover the behavior of newly added IPv4 definitions in addition to IPv6 related tests.
This commit is contained in:
@@ -269,6 +269,7 @@ LOCAL_SRC_FILES := \
|
|||||||
src/core/net/dns_types.cpp \
|
src/core/net/dns_types.cpp \
|
||||||
src/core/net/dnssd_server.cpp \
|
src/core/net/dnssd_server.cpp \
|
||||||
src/core/net/icmp6.cpp \
|
src/core/net/icmp6.cpp \
|
||||||
|
src/core/net/ip4_address.cpp \
|
||||||
src/core/net/ip6.cpp \
|
src/core/net/ip6.cpp \
|
||||||
src/core/net/ip6_address.cpp \
|
src/core/net/ip6_address.cpp \
|
||||||
src/core/net/ip6_filter.cpp \
|
src/core/net/ip6_filter.cpp \
|
||||||
|
|||||||
@@ -492,6 +492,8 @@ openthread_core_files = [
|
|||||||
"net/dnssd_server.hpp",
|
"net/dnssd_server.hpp",
|
||||||
"net/icmp6.cpp",
|
"net/icmp6.cpp",
|
||||||
"net/icmp6.hpp",
|
"net/icmp6.hpp",
|
||||||
|
"net/ip4_address.cpp",
|
||||||
|
"net/ip4_address.hpp",
|
||||||
"net/ip6.cpp",
|
"net/ip6.cpp",
|
||||||
"net/ip6.hpp",
|
"net/ip6.hpp",
|
||||||
"net/ip6_address.cpp",
|
"net/ip6_address.cpp",
|
||||||
|
|||||||
@@ -145,6 +145,7 @@ set(COMMON_SOURCES
|
|||||||
net/dns_types.cpp
|
net/dns_types.cpp
|
||||||
net/dnssd_server.cpp
|
net/dnssd_server.cpp
|
||||||
net/icmp6.cpp
|
net/icmp6.cpp
|
||||||
|
net/ip4_address.cpp
|
||||||
net/ip6.cpp
|
net/ip6.cpp
|
||||||
net/ip6_address.cpp
|
net/ip6_address.cpp
|
||||||
net/ip6_filter.cpp
|
net/ip6_filter.cpp
|
||||||
|
|||||||
@@ -222,6 +222,7 @@ SOURCES_COMMON = \
|
|||||||
net/dns_types.cpp \
|
net/dns_types.cpp \
|
||||||
net/dnssd_server.cpp \
|
net/dnssd_server.cpp \
|
||||||
net/icmp6.cpp \
|
net/icmp6.cpp \
|
||||||
|
net/ip4_address.cpp \
|
||||||
net/ip6.cpp \
|
net/ip6.cpp \
|
||||||
net/ip6_address.cpp \
|
net/ip6_address.cpp \
|
||||||
net/ip6_filter.cpp \
|
net/ip6_filter.cpp \
|
||||||
@@ -476,6 +477,7 @@ HEADERS_COMMON = \
|
|||||||
net/dns_types.hpp \
|
net/dns_types.hpp \
|
||||||
net/dnssd_server.hpp \
|
net/dnssd_server.hpp \
|
||||||
net/icmp6.hpp \
|
net/icmp6.hpp \
|
||||||
|
net/ip4_address.hpp \
|
||||||
net/ip6.hpp \
|
net/ip6.hpp \
|
||||||
net/ip6_address.hpp \
|
net/ip6_address.hpp \
|
||||||
net/ip6_filter.hpp \
|
net/ip6_filter.hpp \
|
||||||
|
|||||||
@@ -0,0 +1,95 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2021, The OpenThread Authors.
|
||||||
|
* All rights reserved.
|
||||||
|
*
|
||||||
|
* Redistribution and use in source and binary forms, with or without
|
||||||
|
* modification, are permitted provided that the following conditions are met:
|
||||||
|
* 1. Redistributions of source code must retain the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer.
|
||||||
|
* 2. Redistributions in binary form must reproduce the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer in the
|
||||||
|
* documentation and/or other materials provided with the distribution.
|
||||||
|
* 3. Neither the name of the copyright holder nor the
|
||||||
|
* names of its contributors may be used to endorse or promote products
|
||||||
|
* derived from this software without specific prior written permission.
|
||||||
|
*
|
||||||
|
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||||
|
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||||
|
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||||
|
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||||
|
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||||
|
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||||
|
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||||
|
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||||
|
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||||
|
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||||
|
* POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @file
|
||||||
|
* This file implements IPv4 address related functionality.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "ip4_address.hpp"
|
||||||
|
|
||||||
|
#include "common/code_utils.hpp"
|
||||||
|
#include "common/numeric_limits.hpp"
|
||||||
|
|
||||||
|
namespace ot {
|
||||||
|
namespace Ip4 {
|
||||||
|
|
||||||
|
Error Address::FromString(const char *aString)
|
||||||
|
{
|
||||||
|
enum : char
|
||||||
|
{
|
||||||
|
kSeperatorChar = '.',
|
||||||
|
kNullChar = '\0',
|
||||||
|
};
|
||||||
|
|
||||||
|
Error error = kErrorParse;
|
||||||
|
|
||||||
|
for (uint8_t index = 0;; index++)
|
||||||
|
{
|
||||||
|
uint16_t value = 0;
|
||||||
|
uint8_t hasFirstDigit = false;
|
||||||
|
|
||||||
|
for (char digitChar = *aString;; ++aString, digitChar = *aString)
|
||||||
|
{
|
||||||
|
if ((digitChar < '0') || (digitChar > '9'))
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
value = static_cast<uint16_t>((value * 10) + static_cast<uint8_t>(digitChar - '0'));
|
||||||
|
VerifyOrExit(value <= NumericLimits<uint8_t>::Max());
|
||||||
|
hasFirstDigit = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
VerifyOrExit(hasFirstDigit);
|
||||||
|
|
||||||
|
mBytes[index] = static_cast<uint8_t>(value);
|
||||||
|
|
||||||
|
if (index == sizeof(Address) - 1)
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
VerifyOrExit(*aString == kSeperatorChar);
|
||||||
|
aString++;
|
||||||
|
}
|
||||||
|
|
||||||
|
VerifyOrExit(*aString == kNullChar);
|
||||||
|
error = kErrorNone;
|
||||||
|
|
||||||
|
exit:
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
|
||||||
|
Address::InfoString Address::ToString(void) const
|
||||||
|
{
|
||||||
|
return InfoString("%d.%d.%d.%d", mBytes[0], mBytes[1], mBytes[2], mBytes[3]);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace Ip4
|
||||||
|
} // namespace ot
|
||||||
@@ -0,0 +1,115 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2021, The OpenThread Authors.
|
||||||
|
* All rights reserved.
|
||||||
|
*
|
||||||
|
* Redistribution and use in source and binary forms, with or without
|
||||||
|
* modification, are permitted provided that the following conditions are met:
|
||||||
|
* 1. Redistributions of source code must retain the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer.
|
||||||
|
* 2. Redistributions in binary form must reproduce the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer in the
|
||||||
|
* documentation and/or other materials provided with the distribution.
|
||||||
|
* 3. Neither the name of the copyright holder nor the
|
||||||
|
* names of its contributors may be used to endorse or promote products
|
||||||
|
* derived from this software without specific prior written permission.
|
||||||
|
*
|
||||||
|
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||||
|
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||||
|
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||||
|
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||||
|
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||||
|
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||||
|
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||||
|
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||||
|
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||||
|
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||||
|
* POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @file
|
||||||
|
* This file includes definitions for IPv4 addresses.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef IP4_ADDRESS_HPP_
|
||||||
|
#define IP4_ADDRESS_HPP_
|
||||||
|
|
||||||
|
#include "openthread-core-config.h"
|
||||||
|
|
||||||
|
#include "common/clearable.hpp"
|
||||||
|
#include "common/equatable.hpp"
|
||||||
|
#include "common/error.hpp"
|
||||||
|
#include "common/string.hpp"
|
||||||
|
|
||||||
|
namespace ot {
|
||||||
|
namespace Ip4 {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class represents an IPv4 address.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
OT_TOOL_PACKED_BEGIN
|
||||||
|
class Address : public Equatable<Address>, public Clearable<Address>
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
enum : uint8_t
|
||||||
|
{
|
||||||
|
kSize = 4, ///< Size of an IPv4 Address (in bytes).
|
||||||
|
kAddressStringSize = 17, ///< String size used by `ToString()`.
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This type defines the fixed-length `String` object returned from `ToString()`.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
typedef String<kAddressStringSize> InfoString;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This method gets the IPv4 address as a pointer to a byte array.
|
||||||
|
*
|
||||||
|
* @returns A pointer to a byte array containing the IPv4 address.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
const uint8_t *GetBytes(void) const { return mBytes; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This method sets the IPv4 address from a given byte array.
|
||||||
|
*
|
||||||
|
* @param[in] aBuffer Pointer to an array containing the IPv4 address. `kSize` bytes from the buffer
|
||||||
|
* are copied to form the IPv4 address.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
void SetBytes(const uint8_t *aBuffer) { memcpy(mBytes, aBuffer, kSize); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This method parses an IPv4 address string.
|
||||||
|
*
|
||||||
|
* The string MUST follow the quad-dotted notation of four decimal values (ranging from 0 to 255 each). For
|
||||||
|
* example, "127.0.0.1"
|
||||||
|
*
|
||||||
|
* @param[in] aString A pointer to the null-terminated string.
|
||||||
|
*
|
||||||
|
* @retval kErrorNone Successfully parsed the IPv4 address string.
|
||||||
|
* @retval kErrorParse Failed to parse the IPv4 address string.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
Error FromString(const char *aString);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This method converts the IPv4 address to a string.
|
||||||
|
*
|
||||||
|
* The string format uses quad-dotted notation of four bytes in the address (e.g., "127.0.0.1").
|
||||||
|
*
|
||||||
|
* @returns An `InfoString` representing the IPv4 address.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
InfoString ToString(void) const;
|
||||||
|
|
||||||
|
private:
|
||||||
|
uint8_t mBytes[kSize];
|
||||||
|
} OT_TOOL_PACKED_END;
|
||||||
|
|
||||||
|
} // namespace Ip4
|
||||||
|
} // namespace ot
|
||||||
|
|
||||||
|
#endif // IP4_ADDRESS_HPP_
|
||||||
@@ -39,6 +39,7 @@
|
|||||||
#include "common/encoding.hpp"
|
#include "common/encoding.hpp"
|
||||||
#include "common/instance.hpp"
|
#include "common/instance.hpp"
|
||||||
#include "common/random.hpp"
|
#include "common/random.hpp"
|
||||||
|
#include "net/ip4_address.hpp"
|
||||||
#include "net/netif.hpp"
|
#include "net/netif.hpp"
|
||||||
|
|
||||||
using ot::Encoding::BigEndian::HostSwap32;
|
using ot::Encoding::BigEndian::HostSwap32;
|
||||||
@@ -509,7 +510,7 @@ Error Address::FromString(const char *aBuf)
|
|||||||
hasIp4 = true;
|
hasIp4 = true;
|
||||||
|
|
||||||
// Do not count bytes of the embedded IPv4 address.
|
// Do not count bytes of the embedded IPv4 address.
|
||||||
endp -= kIp4AddressSize;
|
endp -= Ip4::Address::kSize;
|
||||||
|
|
||||||
VerifyOrExit(dst <= endp, error = kErrorParse);
|
VerifyOrExit(dst <= endp, error = kErrorParse);
|
||||||
|
|
||||||
@@ -539,40 +540,10 @@ Error Address::FromString(const char *aBuf)
|
|||||||
|
|
||||||
if (hasIp4)
|
if (hasIp4)
|
||||||
{
|
{
|
||||||
val = 0;
|
Ip4::Address ip4Addr;
|
||||||
|
|
||||||
// Reset the start and end pointers.
|
SuccessOrExit(error = ip4Addr.FromString(colonc));
|
||||||
dst = reinterpret_cast<uint8_t *>(mFields.m8 + 12);
|
memcpy(mFields.m8 + 12, ip4Addr.GetBytes(), Ip4::Address::kSize);
|
||||||
endp = reinterpret_cast<uint8_t *>(mFields.m8 + 15);
|
|
||||||
|
|
||||||
for (;;)
|
|
||||||
{
|
|
||||||
ch = *colonc++;
|
|
||||||
|
|
||||||
if (ch == '.' || ch == '\0' || ch == ' ')
|
|
||||||
{
|
|
||||||
VerifyOrExit(dst <= endp, error = kErrorParse);
|
|
||||||
|
|
||||||
*dst++ = static_cast<uint8_t>(val);
|
|
||||||
val = 0;
|
|
||||||
|
|
||||||
if (ch == '\0' || ch == ' ')
|
|
||||||
{
|
|
||||||
// Check if embedded IPv4 address had exactly four parts.
|
|
||||||
VerifyOrExit(dst == endp + 1, error = kErrorParse);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
VerifyOrExit('0' <= ch && ch <= '9', error = kErrorParse);
|
|
||||||
|
|
||||||
val = (10 * val) + (ch & 0xf);
|
|
||||||
|
|
||||||
// Single part of IPv4 address has to fit in one byte.
|
|
||||||
VerifyOrExit(val <= 0xff, error = kErrorParse);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
exit:
|
exit:
|
||||||
|
|||||||
@@ -38,6 +38,8 @@
|
|||||||
|
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
|
||||||
|
#include <openthread/ip6.h>
|
||||||
|
|
||||||
#include "common/clearable.hpp"
|
#include "common/clearable.hpp"
|
||||||
#include "common/encoding.hpp"
|
#include "common/encoding.hpp"
|
||||||
#include "common/equatable.hpp"
|
#include "common/equatable.hpp"
|
||||||
@@ -906,10 +908,7 @@ public:
|
|||||||
* @retval false The IPv6 address is larger than or equal to @p aOther.
|
* @retval false The IPv6 address is larger than or equal to @p aOther.
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
bool operator<(const Ip6::Address &aOther) const
|
bool operator<(const Address &aOther) const { return memcmp(mFields.m8, aOther.mFields.m8, sizeof(Address)) < 0; }
|
||||||
{
|
|
||||||
return memcmp(mFields.m8, aOther.mFields.m8, sizeof(Ip6::Address)) < 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void SetPrefix(uint8_t aOffset, const uint8_t *aPrefix, uint8_t aPrefixLength);
|
void SetPrefix(uint8_t aOffset, const uint8_t *aPrefix, uint8_t aPrefixLength);
|
||||||
@@ -923,7 +922,6 @@ private:
|
|||||||
|
|
||||||
enum
|
enum
|
||||||
{
|
{
|
||||||
kIp4AddressSize = 4, ///< Size of the IPv4 address.
|
|
||||||
kMulticastNetworkPrefixLengthOffset = 3, ///< Prefix-Based Multicast Address (RFC3306).
|
kMulticastNetworkPrefixLengthOffset = 3, ///< Prefix-Based Multicast Address (RFC3306).
|
||||||
kMulticastNetworkPrefixOffset = 4, ///< Prefix-Based Multicast Address (RFC3306).
|
kMulticastNetworkPrefixOffset = 4, ///< Prefix-Based Multicast Address (RFC3306).
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -306,26 +306,26 @@ target_link_libraries(test-hmac-sha256
|
|||||||
|
|
||||||
add_test(NAME test-hmac-sha256 COMMAND test-hmac-sha256)
|
add_test(NAME test-hmac-sha256 COMMAND test-hmac-sha256)
|
||||||
|
|
||||||
add_executable(test-ip6-address
|
add_executable(test-ip-address
|
||||||
test_ip6_address.cpp
|
test_ip_address.cpp
|
||||||
)
|
)
|
||||||
|
|
||||||
target_include_directories(test-ip6-address
|
target_include_directories(test-ip-address
|
||||||
PRIVATE
|
PRIVATE
|
||||||
${COMMON_INCLUDES}
|
${COMMON_INCLUDES}
|
||||||
)
|
)
|
||||||
|
|
||||||
target_compile_options(test-ip6-address
|
target_compile_options(test-ip-address
|
||||||
PRIVATE
|
PRIVATE
|
||||||
${COMMON_COMPILE_OPTIONS}
|
${COMMON_COMPILE_OPTIONS}
|
||||||
)
|
)
|
||||||
|
|
||||||
target_link_libraries(test-ip6-address
|
target_link_libraries(test-ip-address
|
||||||
PRIVATE
|
PRIVATE
|
||||||
${COMMON_LIBS}
|
${COMMON_LIBS}
|
||||||
)
|
)
|
||||||
|
|
||||||
add_test(NAME test-ip6-address COMMAND test-ip6-address)
|
add_test(NAME test-ip-address COMMAND test-ip-address)
|
||||||
|
|
||||||
add_executable(test-link-quality
|
add_executable(test-link-quality
|
||||||
test_link_quality.cpp
|
test_link_quality.cpp
|
||||||
@@ -720,7 +720,7 @@ set_target_properties(
|
|||||||
test-heap
|
test-heap
|
||||||
test-hkdf-sha256
|
test-hkdf-sha256
|
||||||
test-hmac-sha256
|
test-hmac-sha256
|
||||||
test-ip6-address
|
test-ip-address
|
||||||
test-link-quality
|
test-link-quality
|
||||||
test-linked-list
|
test-linked-list
|
||||||
test-lookup-table
|
test-lookup-table
|
||||||
|
|||||||
@@ -117,7 +117,7 @@ check_PROGRAMS += \
|
|||||||
test-heap \
|
test-heap \
|
||||||
test-hkdf-sha256 \
|
test-hkdf-sha256 \
|
||||||
test-hmac-sha256 \
|
test-hmac-sha256 \
|
||||||
test-ip6-address \
|
test-ip-address \
|
||||||
test-link-quality \
|
test-link-quality \
|
||||||
test-linked-list \
|
test-linked-list \
|
||||||
test-lookup-table \
|
test-lookup-table \
|
||||||
@@ -212,8 +212,8 @@ test_hkdf_sha256_SOURCES = $(COMMON_SOURCES) test_hkdf_sha256.cpp
|
|||||||
test_hmac_sha256_LDADD = $(COMMON_LDADD)
|
test_hmac_sha256_LDADD = $(COMMON_LDADD)
|
||||||
test_hmac_sha256_SOURCES = $(COMMON_SOURCES) test_hmac_sha256.cpp
|
test_hmac_sha256_SOURCES = $(COMMON_SOURCES) test_hmac_sha256.cpp
|
||||||
|
|
||||||
test_ip6_address_LDADD = $(COMMON_LDADD)
|
test_ip_address_LDADD = $(COMMON_LDADD)
|
||||||
test_ip6_address_SOURCES = $(COMMON_SOURCES) test_ip6_address.cpp
|
test_ip_address_SOURCES = $(COMMON_SOURCES) test_ip_address.cpp
|
||||||
|
|
||||||
test_link_quality_LDADD = $(COMMON_LDADD)
|
test_link_quality_LDADD = $(COMMON_LDADD)
|
||||||
test_link_quality_SOURCES = $(COMMON_SOURCES) test_link_quality.cpp
|
test_link_quality_SOURCES = $(COMMON_SOURCES) test_link_quality.cpp
|
||||||
|
|||||||
@@ -29,6 +29,7 @@
|
|||||||
#include <limits.h>
|
#include <limits.h>
|
||||||
|
|
||||||
#include "common/encoding.hpp"
|
#include "common/encoding.hpp"
|
||||||
|
#include "net/ip4_address.hpp"
|
||||||
#include "net/ip6_address.hpp"
|
#include "net/ip6_address.hpp"
|
||||||
#include "net/ip6_headers.hpp"
|
#include "net/ip6_headers.hpp"
|
||||||
|
|
||||||
@@ -36,32 +37,39 @@
|
|||||||
|
|
||||||
using ot::Encoding::BigEndian::ReadUint16;
|
using ot::Encoding::BigEndian::ReadUint16;
|
||||||
|
|
||||||
struct Ip6AddressStringTestVector
|
template <typename AddressType> struct TestVector
|
||||||
{
|
{
|
||||||
const char * mString;
|
const char * mString;
|
||||||
const uint8_t mAddr[OT_IP6_ADDRESS_SIZE];
|
const uint8_t mAddr[sizeof(AddressType)];
|
||||||
ot::Error mError;
|
ot::Error mError;
|
||||||
};
|
};
|
||||||
|
|
||||||
static void checkAddressFromString(Ip6AddressStringTestVector *aTestVector)
|
template <typename AddressType> static void checkAddressFromString(TestVector<AddressType> *aTestVector)
|
||||||
{
|
{
|
||||||
ot::Error error;
|
ot::Error error;
|
||||||
ot::Ip6::Address address;
|
AddressType address;
|
||||||
|
|
||||||
|
address.Clear();
|
||||||
|
|
||||||
error = address.FromString(aTestVector->mString);
|
error = address.FromString(aTestVector->mString);
|
||||||
|
|
||||||
VerifyOrQuit(error == aTestVector->mError, "Ip6::Address::FromString returned unexpected error code");
|
printf("%-42s -> %-42s\n", aTestVector->mString,
|
||||||
|
(error == ot::kErrorNone) ? address.ToString().AsCString() : "(parse error)");
|
||||||
|
|
||||||
|
VerifyOrQuit(error == aTestVector->mError, "Address::FromString returned unexpected error code");
|
||||||
|
|
||||||
if (error == ot::kErrorNone)
|
if (error == ot::kErrorNone)
|
||||||
{
|
{
|
||||||
VerifyOrQuit(0 == memcmp(address.mFields.m8, aTestVector->mAddr, OT_IP6_ADDRESS_SIZE),
|
VerifyOrQuit(0 == memcmp(address.GetBytes(), aTestVector->mAddr, sizeof(AddressType)),
|
||||||
"Ip6::Address::FromString parsing failed");
|
"Address::FromString parsing failed");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void TestIp6AddressFromString(void)
|
void TestIp6AddressFromString(void)
|
||||||
{
|
{
|
||||||
Ip6AddressStringTestVector testVectors[] = {
|
typedef TestVector<ot::Ip6::Address> Ip6AddressTestVector;
|
||||||
|
|
||||||
|
Ip6AddressTestVector testVectors[] = {
|
||||||
// Valid full IPv6 address.
|
// Valid full IPv6 address.
|
||||||
{"0102:0304:0506:0708:090a:0b0c:0d0e:0f00",
|
{"0102:0304:0506:0708:090a:0b0c:0d0e:0f00",
|
||||||
{0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x00},
|
{0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x00},
|
||||||
@@ -134,7 +142,33 @@ void TestIp6AddressFromString(void)
|
|||||||
{":f:0:0:c:0:f:f:.", {0}, ot::kErrorParse},
|
{":f:0:0:c:0:f:f:.", {0}, ot::kErrorParse},
|
||||||
};
|
};
|
||||||
|
|
||||||
for (Ip6AddressStringTestVector &testVector : testVectors)
|
for (Ip6AddressTestVector &testVector : testVectors)
|
||||||
|
{
|
||||||
|
checkAddressFromString(&testVector);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void TestIp4AddressFromString(void)
|
||||||
|
{
|
||||||
|
typedef TestVector<ot::Ip4::Address> Ip4AddressTestVector;
|
||||||
|
|
||||||
|
Ip4AddressTestVector testVectors[] = {
|
||||||
|
{"0.0.0.0", {0, 0, 0, 0}, ot::kErrorNone},
|
||||||
|
{"255.255.255.255", {255, 255, 255, 255}, ot::kErrorNone},
|
||||||
|
{"127.0.0.1", {127, 0, 0, 1}, ot::kErrorNone},
|
||||||
|
{"1.2.3.4", {1, 2, 3, 4}, ot::kErrorNone},
|
||||||
|
{"001.002.003.004", {1, 2, 3, 4}, ot::kErrorNone},
|
||||||
|
{"00000127.000.000.000001", {127, 0, 0, 1}, ot::kErrorNone},
|
||||||
|
{"123.231.0.256", {0}, ot::kErrorParse}, // Invalid byte value.
|
||||||
|
{"100123.231.0.256", {0}, ot::kErrorParse}, // Invalid byte value.
|
||||||
|
{"1.22.33", {0}, ot::kErrorParse}, // Too few bytes.
|
||||||
|
{"1.22.33.44.5", {0}, ot::kErrorParse}, // Too many bytes.
|
||||||
|
{"a.b.c.d", {0}, ot::kErrorParse}, // Wrong digit char.
|
||||||
|
{"123.23.45 .12", {0}, ot::kErrorParse}, // Extra space.
|
||||||
|
{".", {0}, ot::kErrorParse}, // Invalid.
|
||||||
|
};
|
||||||
|
|
||||||
|
for (Ip4AddressTestVector &testVector : testVectors)
|
||||||
{
|
{
|
||||||
checkAddressFromString(&testVector);
|
checkAddressFromString(&testVector);
|
||||||
}
|
}
|
||||||
@@ -360,6 +394,7 @@ void TestIp6Header(void)
|
|||||||
int main(void)
|
int main(void)
|
||||||
{
|
{
|
||||||
TestIp6AddressSetPrefix();
|
TestIp6AddressSetPrefix();
|
||||||
|
TestIp4AddressFromString();
|
||||||
TestIp6AddressFromString();
|
TestIp6AddressFromString();
|
||||||
TestIp6Prefix();
|
TestIp6Prefix();
|
||||||
TestIp6Header();
|
TestIp6Header();
|
||||||
Reference in New Issue
Block a user