more improvements/redesign, mostly Windows related

This commit is contained in:
Aleksandar Fabijanic 2012-08-13 01:58:35 +00:00
Родитель 20d5b2d2fb
Коммит 273b9c92f8
6 изменённых файлов: 288 добавлений и 117 удалений

Просмотреть файл

@ -89,7 +89,9 @@ public:
IPv4_OR_IPv6 /// Return interfaces with IPv4 or IPv6 address
};
NetworkInterface(unsigned index = 0);
static const unsigned NO_INDEX = ~0;
NetworkInterface(unsigned index = NO_INDEX);
/// Creates a NetworkInterface representing the
/// default interface.
///
@ -129,8 +131,11 @@ public:
///
/// On other platforms this is the same as name().
const IPAddress& address(unsigned index = 0) const;
/// Returns the IP address bound to the interface.
const IPAddress& findFirstAddress(IPAddress::Family family) const;
/// Returns the first IP address bound to the interface.
const IPAddress& address(unsigned index) const;
/// Returns the IP address bound to the interface at index position.
void addAddress(const IPAddress& address);
/// Adds address to the interface.
@ -141,13 +146,13 @@ public:
const AddressList& addressList() const;
/// Returns the list of IP addresses bound to the interface.
const IPAddress& subnetMask(unsigned index = 0) const;
const IPAddress& subnetMask(unsigned index) const;
/// Returns the subnet mask for this network interface.
const IPAddress& broadcastAddress(unsigned index = 0) const;
const IPAddress& broadcastAddress(unsigned index) const;
/// Returns the broadcast address for this network interface.
const IPAddress& destAddress(unsigned index = 0) const;
const IPAddress& destAddress(unsigned index) const;
/// Returns the IPv4 point-to-point destiation address for this network interface.
const MacAddress& macAddress() const;
@ -217,26 +222,50 @@ public:
/// with the given index does not exist (or IPv6 is not
/// available).
static Map map();
/// Returns a map with all network interfaces
/// on the system. Map is keyed by interface system
/// indices.
static List list(bool ipOnly = true, bool upOnly = true);
/// Returns a list with all network interfaces
/// on the system.
///
/// If ipOnly is true, only interfaces supporting IP
/// are returned. Otherwise, all system network interfaces
/// are returned.
///
/// If upOnly is true, only interfaces being up are returned.
/// Otherwise, both interfaces being up and down are returned.
///
/// If there are multiple addresses bound to one interface,
/// multiple NetworkInterface entries are listed for
/// the same interface.
static Map map(bool ipOnly = true, bool upOnly = true);
/// Returns a map containing system network interfaces
/// Map is keyed by interface system indices.
///
/// If ipOnly is true, only interfaces supporting IP
/// are returned. Otherwise, all system network interfaces
/// are returned.
///
/// If upOnly is true, only interfaces being up are returned.
/// Otherwise, both interfaces being up and down are returned.
///
/// If there are multiple addresses bound to one interface,
/// they are contained within the NetworkInterface (second)
/// member of the pair.
protected:
NetworkInterface(const std::string& name, const std::string& displayName, const IPAddress& address, unsigned index = 0);
NetworkInterface(const std::string& name, const std::string& displayName, const IPAddress& address, unsigned index);
/// Creates the NetworkInterface.
NetworkInterface(const std::string& name, const std::string& displayName, const IPAddress& address, const IPAddress& subnetMask, const IPAddress& broadcastAddress, unsigned index = 0);
NetworkInterface(const std::string& name, const std::string& displayName, unsigned index);
/// Creates the NetworkInterface.
NetworkInterface(const std::string& name, const IPAddress& address, unsigned index = 0);
NetworkInterface(const std::string& name, const IPAddress& address, unsigned index);
/// Creates the NetworkInterface.
NetworkInterface(const std::string& name, const IPAddress& address, const IPAddress& subnetMask, const IPAddress& broadcastAddress, unsigned index = 0);
NetworkInterface(const std::string& name, const std::string& displayName, const IPAddress& address, const IPAddress& subnetMask, const IPAddress& broadcastAddress, unsigned index);
/// Creates the NetworkInterface.
NetworkInterface(const std::string& name, const IPAddress& address, const IPAddress& subnetMask, const IPAddress& broadcastAddress, unsigned index);
/// Creates the NetworkInterface.
IPAddress interfaceNameToAddress(const std::string& interfaceName) const;

Просмотреть файл

@ -99,7 +99,7 @@ void MulticastSocket::setInterface(const NetworkInterface& interfc)
{
if (!interfc.supportsIPv6())
{
impl()->setOption(IPPROTO_IP, IP_MULTICAST_IF, interfc.address());
impl()->setOption(IPPROTO_IP, IP_MULTICAST_IF, interfc.findFirstAddress(IPAddress::IPv4));
}
else
{
@ -217,7 +217,7 @@ void MulticastSocket::joinGroup(const IPAddress& groupAddress, const NetworkInte
{
struct ip_mreq mr;
std::memcpy(&mr.imr_multiaddr, groupAddress.addr(), groupAddress.length());
std::memcpy(&mr.imr_interface, interfc.address().addr(), interfc.address().length());
std::memcpy(&mr.imr_interface, interfc.findFirstAddress(IPAddress::IPv4).addr(), interfc.findFirstAddress(IPAddress::IPv4).length());
impl()->setRawOption(IPPROTO_IP, IP_ADD_MEMBERSHIP, &mr, sizeof(mr));
}
else
@ -245,7 +245,7 @@ void MulticastSocket::leaveGroup(const IPAddress& groupAddress, const NetworkInt
{
struct ip_mreq mr;
std::memcpy(&mr.imr_multiaddr, groupAddress.addr(), groupAddress.length());
std::memcpy(&mr.imr_interface, interfc.address().addr(), interfc.address().length());
std::memcpy(&mr.imr_interface, interfc.findFirstAddress(IPAddress::IPv4).addr(), interfc.findFirstAddress(IPAddress::IPv4).length());
impl()->setRawOption(IPPROTO_IP, IP_DROP_MEMBERSHIP, &mr, sizeof(mr));
}
else

Просмотреть файл

@ -70,20 +70,22 @@ public:
typedef NetworkInterface::AddressTuple AddressTuple;
typedef NetworkInterface::AddressList AddressList;
NetworkInterfaceImpl(unsigned index = 0);
NetworkInterfaceImpl(const std::string& name, const std::string& displayName, const IPAddress& address, unsigned index = 0);
NetworkInterfaceImpl(const std::string& name, const std::string& displayName, const IPAddress& address, const IPAddress& subnetMask, const IPAddress& broadcastAddress, unsigned index = 0);
NetworkInterfaceImpl(unsigned index);
NetworkInterfaceImpl(const std::string& name, const std::string& displayName, const IPAddress& address, unsigned index);
NetworkInterfaceImpl(const std::string& name, const std::string& displayName, unsigned index = 0);
NetworkInterfaceImpl(const std::string& name, const std::string& displayName, const IPAddress& address, const IPAddress& subnetMask, const IPAddress& broadcastAddress, unsigned index);
unsigned index() const;
const std::string& name() const;
const std::string& displayName() const;
const IPAddress& findFirstAddress(IPAddress::Family family) const;
void addAddress(const AddressTuple& address);
const IPAddress& address(unsigned index = 0) const;
const IPAddress& address(unsigned index) const;
const NetworkInterface::AddressList& addressList() const;
bool hasAddress(const IPAddress& address) const;
const IPAddress& subnetMask(unsigned index = 0) const;
const IPAddress& broadcastAddress(unsigned index = 0) const;
const IPAddress& destAddress(unsigned index = 0) const;
const IPAddress& subnetMask(unsigned index) const;
const IPAddress& broadcastAddress(unsigned index) const;
const IPAddress& destAddress(unsigned index) const;
const NetworkInterface::MacAddress& macAddress() const;
bool supportsIPv4() const;
bool supportsIPv6() const;
@ -137,7 +139,7 @@ private:
NetworkInterface::MacAddress _macAddress;
friend NetworkInterface::Map NetworkInterface::map();
friend NetworkInterface::Map NetworkInterface::map(bool, bool);
};
@ -166,6 +168,23 @@ NetworkInterfaceImpl::NetworkInterfaceImpl(const std::string& name, const std::s
}
NetworkInterfaceImpl::NetworkInterfaceImpl(const std::string& name, const std::string& displayName, unsigned index):
_name(name),
_displayName(displayName),
_index(index),
_broadcast(false),
_loopback(false),
_multicast(false),
_pointToPoint(false),
_up(false),
_running(false),
_mtu(0)
{
getPhyParams();
if (_pointToPoint) getPeerAddress();
}
NetworkInterfaceImpl::NetworkInterfaceImpl(const std::string& name, const std::string& displayName, const IPAddress& address, const IPAddress& subnetMask, const IPAddress& broadcastAddress, unsigned index):
_name(name),
_displayName(displayName),
@ -275,6 +294,23 @@ inline const std::string& NetworkInterfaceImpl::displayName() const
}
const IPAddress& NetworkInterfaceImpl::findFirstAddress(IPAddress::Family family) const
{
if (!supportsIPv4() && !supportsIPv6())
throw NotImplementedException("Unknown or unsupported family.");
AddressList::const_iterator it = _addressList.begin();
AddressList::const_iterator end = _addressList.end();
for (;it != end; ++it)
{
const IPAddress& addr = it->get<NetworkInterface::IP_ADDRESS>();
if (addr.family() == family) return addr;
}
throw NotFoundException(format("%s family address not found.", family == IPAddress::IPv4 ? "IPv4" : "IPv6"));
}
inline void NetworkInterfaceImpl::addAddress(const AddressTuple& address)
{
_addressList.push_back(address);
@ -514,8 +550,8 @@ NetworkInterface::NetworkInterface(const std::string& name, const std::string& d
}
NetworkInterface::NetworkInterface(const std::string& name, const std::string& displayName, const IPAddress& address, const IPAddress& subnetMask, const IPAddress& broadcastAddress, unsigned index):
_pImpl(new NetworkInterfaceImpl(name, displayName, address, subnetMask, broadcastAddress, index))
NetworkInterface::NetworkInterface(const std::string& name, const std::string& displayName, unsigned index):
_pImpl(new NetworkInterfaceImpl(name, displayName, index))
{
}
@ -526,6 +562,12 @@ NetworkInterface::NetworkInterface(const std::string& name, const IPAddress& add
}
NetworkInterface::NetworkInterface(const std::string& name, const std::string& displayName, const IPAddress& address, const IPAddress& subnetMask, const IPAddress& broadcastAddress, unsigned index):
_pImpl(new NetworkInterfaceImpl(name, displayName, address, subnetMask, broadcastAddress, index))
{
}
NetworkInterface::NetworkInterface(const std::string& name, const IPAddress& address, const IPAddress& subnetMask, const IPAddress& broadcastAddress, unsigned index):
_pImpl(new NetworkInterfaceImpl(name, name, address, subnetMask, broadcastAddress, index))
{
@ -571,6 +613,12 @@ const std::string& NetworkInterface::displayName() const
}
const IPAddress& NetworkInterface::findFirstAddress(IPAddress::Family family) const
{
return _pImpl->findFirstAddress(family);
}
void NetworkInterface::addAddress(const IPAddress& address)
{
_pImpl->addAddress(AddressTuple(address, IPAddress(), IPAddress()));
@ -741,48 +789,55 @@ NetworkInterface NetworkInterface::forAddress(const IPAddress& addr)
NetworkInterface NetworkInterface::forIndex(unsigned i)
{
if (i != 0)
if (i != NetworkInterface::NO_INDEX)
{
Map map = NetworkInterface::map();
Map::const_iterator it = map.find(i);
if (it != map.end())
return it->second;
else
throw InterfaceNotFoundException("#" + NumberFormatter::format(i));
}
throw InterfaceNotFoundException("#" + NumberFormatter::format(i));
}
#if (POCO_OS == POCO_OS_LINUX)
#include <net/if_arp.h>
static unsigned arphrdToIfType(unsigned arphrd)
NetworkInterface::List NetworkInterface::list(bool ipOnly, bool upOnly)
{
switch (arphrd) {
case ARPHRD_ETHER:
return 6; // IF_TYPE_ETHERNET_CSMACD
case ARPHRD_IEEE802:
return 9; // IF_TYPE_ISO88025_TOKENRING
case ARPHRD_DLCI:
return 32; // IF_TYPE_FRAMERELAY
case ARPHRD_PPP:
return 512; // IF_TYPE_PPP
case ARPHRD_LOOPBACK:
return 24; // IF_TYPE_SOFTWARE_LOOPBACK
case ARPHRD_ATM:
return 37; // IF_TYPE_ATM
case ARPHRD_IEEE80211:
return 71; // IF_TYPE_IEEE80211
case ARPHRD_TUNNEL:
case ARPHRD_TUNNEL6:
return 131; // IF_TYPE_TUNNEL
case ARPHRD_IEEE1394:
return 144; // IF_TYPE_IEEE1394
default:
return 1; // IF_TYPE_OTHER
List list;
Map m = map(ipOnly, upOnly);
NetworkInterface::Map::const_iterator it = m.begin();
NetworkInterface::Map::const_iterator end = m.end();
for (; it != end; ++it)
{
int index = it->second.index();
std::string name = it->second.name();
std::string displayName = it->second.displayName();
typedef NetworkInterface::AddressList List;
const List& ipList = it->second.addressList();
List::const_iterator ipIt = ipList.begin();
List::const_iterator ipEnd = ipList.end();
for (int counter = 0; ipIt != ipEnd; ++ipIt, ++counter)
{
IPAddress addr = ipIt->get<NetworkInterface::IP_ADDRESS>();
IPAddress mask = ipIt->get<NetworkInterface::SUBNET_MASK>();
NetworkInterface ni;
if (mask.isWildcard())
ni = NetworkInterface(name, displayName, addr, index);
else
{
IPAddress broadcast = ipIt->get<NetworkInterface::BROADCAST_ADDRESS>();
ni = NetworkInterface(name, displayName, addr, mask, broadcast, index);
}
list.push_back(ni);
}
}
return list;
}
#endif
} } // namespace Poco::Net
@ -860,7 +915,7 @@ std::string getErrorMessage(DWORD errorCode)
} /// namespace
NetworkInterface::Map NetworkInterface::map()
NetworkInterface::Map NetworkInterface::map(bool ipOnly, bool upOnly)
{
FastMutex::ScopedLock lock(_mutex);
Map result;
@ -897,67 +952,72 @@ NetworkInterface::Map NetworkInterface::map()
IPAddress subnetMask;
IPAddress broadcastAddress;
unsigned ifIndex = 0;
//
// Create interface even if it has an empty list of addresses; also, set
// physical attributes which are protocol independent (name, media type,
// MAC address, MTU, operational status, etc).
//
Map::iterator ifIt = result.insert(Map::value_type(ifInex, NetworkInterface(name, displayName, ifIndex);
ifIt->second.impl().setFlags(pAddress->Flags, pAddress->IfType);
ifIt->second.impl().setMtu(pAddress->Mtu);
ifIt->second.impl().setUp(pAddress->OperStatus == IfOperStatusUp);
ifIt->second.impl().setMacAddress(pAddress->PhysicalAddress, pAddress->PhysicalAddressLength);
ifIt->second.impl().setHWType(pAddress->IfType);
#if defined(POCO_HAVE_IPv6)
poco_assert (pAddress->Ipv6IfIndex == pAddress->IfIndex);
if (pAddress->Flags & IP_ADAPTER_IPV6_ENABLED) ifIndex = pAddress->Ipv6IfIndex;
else
#endif
if (pAddress->Flags & IP_ADAPTER_IPV4_ENABLED) ifIndex = pAddress->IfIndex;
for (PIP_ADAPTER_UNICAST_ADDRESS pUniAddr = pAddress->FirstUnicastAddress;
pUniAddr;
pUniAddr = pUniAddr->Next)
{
std::string name(pAddress->AdapterName);
std::string displayName;
std::string name(pAddress->AdapterName);
std::string displayName;
#ifdef POCO_WIN32_UTF8
Poco::UnicodeConverter::toUTF8(pAddress->FriendlyName, displayName);
Poco::UnicodeConverter::toUTF8(pAddress->FriendlyName, displayName);
#else
char displayNameBuffer[1024];
int rc = WideCharToMultiByte(CP_ACP, WC_DEFAULTCHAR, pAddress->FriendlyName, -1, displayNameBuffer, sizeof(displayNameBuffer), NULL, NULL);
if (rc) displayName = displayNameBuffer;
char displayNameBuffer[1024];
int rc = WideCharToMultiByte(CP_ACP, WC_DEFAULTCHAR, pAddress->FriendlyName, -1, displayNameBuffer, sizeof(displayNameBuffer), NULL, NULL);
if (rc) displayName = displayNameBuffer;
#endif
UINT8 prefixLength = pUniAddr->OnLinkPrefixLength;
address = IPAddress(pUniAddr->Address);
ADDRESS_FAMILY family = pUniAddr->Address.lpSockaddr->sa_family;
switch (family)
bool isUp = (pAddress->OperStatus == IfOperStatusUp);
bool isIP = (0 != pAddress->FirstUnicastAddress);
if (((ipOnly && isIP) || !ipOnly) && ((upOnly && isUp) || !upOnly))
{
NetworkInterface ni(name, displayName, ifIndex);
// Create interface even if it has an empty list of addresses; also, set
// physical attributes which are protocol independent (name, media type,
// MAC address, MTU, operational status, etc).
Map::iterator ifIt = result.find(ifIndex);
if (ifIt == result.end())
ifIt = result.insert(Map::value_type(ifIndex, ni)).first;
ifIt->second.impl().setFlags(pAddress->Flags, pAddress->IfType);
ifIt->second.impl().setMtu(pAddress->Mtu);
ifIt->second.impl().setUp(pAddress->OperStatus == IfOperStatusUp);
ifIt->second.impl().setHWType(pAddress->IfType);
if (pAddress->PhysicalAddressLength)
ifIt->second.impl().setMacAddress(pAddress->PhysicalAddress, pAddress->PhysicalAddressLength);
for (PIP_ADAPTER_UNICAST_ADDRESS pUniAddr = pAddress->FirstUnicastAddress;
pUniAddr;
pUniAddr = pUniAddr->Next)
{
case AF_INET:
UINT8 prefixLength = pUniAddr->OnLinkPrefixLength;
address = IPAddress(pUniAddr->Address);
ADDRESS_FAMILY family = pUniAddr->Address.lpSockaddr->sa_family;
switch (family)
{
// Windows lists broadcast address on localhost
bool hasBroadcast = (pAddress->IfType == IF_TYPE_ETHERNET_CSMACD) || (pAddress->IfType == IF_TYPE_SOFTWARE_LOOPBACK);
// On Windows, a valid broadcast address will be all 1's (== address | ~subnetMask); we go an extra mile here in order to
// make sure we reflect the actual value held by system and protect against misconfiguration (e.g. bad DHCP config entry)
broadcastAddress = getBroadcastAddress(pAddress->FirstPrefix, address);
subnetMask = prefixLength ? IPAddress(prefixLength, IPAddress::IPv4) : IPAddress();
if (hasBroadcast)
ifIt->second.addAddress(address, subnetMask, broadcastAddress);
else
case AF_INET:
{
// Windows lists broadcast address on localhost
bool hasBroadcast = (pAddress->IfType == IF_TYPE_ETHERNET_CSMACD) || (pAddress->IfType == IF_TYPE_SOFTWARE_LOOPBACK);
// On Windows, a valid broadcast address will be all 1's (== address | ~subnetMask); we go an extra mile here in order to
// make sure we reflect the actual value held by system and protect against misconfiguration (e.g. bad DHCP config entry)
broadcastAddress = getBroadcastAddress(pAddress->FirstPrefix, address);
subnetMask = prefixLength ? IPAddress(prefixLength, IPAddress::IPv4) : IPAddress();
if (hasBroadcast)
ifIt->second.addAddress(address, subnetMask, broadcastAddress);
else
ifIt->second.addAddress(address);
} break;
#if defined(POCO_HAVE_IPv6)
case AF_INET6:
ifIt->second.addAddress(address);
} break;
#if defined(POCO_HAVE_IPv6)
case AF_INET6:
{
ifIt->second.addAddress(address);
} break;
#endif
} // switch family
} // for addresses
break;
#endif
} // switch family
} // for addresses
} // if ipOnly/upOnly
} // for adapters
return result;
}
@ -1035,7 +1095,7 @@ namespace Poco {
namespace Net {
NetworkInterface::Map NetworkInterface::map()
NetworkInterface::Map NetworkInterface::map(bool ipOnly, bool upOnly)
{
FastMutex::ScopedLock lock(_mutex);
Map result;
@ -1134,13 +1194,46 @@ NetworkInterface::Map NetworkInterface::map()
#include <ifaddrs.h>
#include <linux/if.h>
#include <linux/if_packet.h>
#include <net/if_arp.h>
namespace Poco {
namespace Net {
NetworkInterface::Map NetworkInterface::map()
namespace {
static unsigned arphrdToIfType(unsigned arphrd)
{
switch (arphrd) {
case ARPHRD_ETHER:
return 6; // IF_TYPE_ETHERNET_CSMACD
case ARPHRD_IEEE802:
return 9; // IF_TYPE_ISO88025_TOKENRING
case ARPHRD_DLCI:
return 32; // IF_TYPE_FRAMERELAY
case ARPHRD_PPP:
return 512; // IF_TYPE_PPP
case ARPHRD_LOOPBACK:
return 24; // IF_TYPE_SOFTWARE_LOOPBACK
case ARPHRD_ATM:
return 37; // IF_TYPE_ATM
case ARPHRD_IEEE80211:
return 71; // IF_TYPE_IEEE80211
case ARPHRD_TUNNEL:
case ARPHRD_TUNNEL6:
return 131; // IF_TYPE_TUNNEL
case ARPHRD_IEEE1394:
return 144; // IF_TYPE_IEEE1394
default:
return 1; // IF_TYPE_OTHER
}
}
}
NetworkInterface::Map NetworkInterface::map(bool ipOnly, bool upOnly)
{
FastMutex::ScopedLock lock(_mutex);
Map result;

Просмотреть файл

@ -107,11 +107,16 @@ const NetworkInterface& MulticastEchoServer::interfc() const
Poco::Net::NetworkInterface MulticastEchoServer::findInterface()
{
NetworkInterface::Map map = NetworkInterface::map();
for (NetworkInterface::Map::const_iterator it = map.begin(); it != map.end(); ++it)
NetworkInterface::Map m = NetworkInterface::map();
for (NetworkInterface::Map::const_iterator it = m.begin(); it != m.end(); ++it)
{
if (it->second.supportsIPv4() && it->second.address().isUnicast() && !it->second.isLoopback() && it->second.isPointToPoint())
if (it->second.supportsIPv4() &&
it->second.findFirstAddress(IPAddress::IPv4).isUnicast() &&
!it->second.isLoopback() &&
!it->second.isPointToPoint())
{
return it->second;
}
}
return NetworkInterface();
}

Просмотреть файл

@ -41,6 +41,7 @@
using Poco::Net::NetworkInterface;
using Poco::Net::IPAddress;
using Poco::NotFoundException;
NetworkInterfaceTest::NetworkInterfaceTest(const std::string& name): CppUnit::TestCase(name)
@ -55,9 +56,9 @@ NetworkInterfaceTest::~NetworkInterfaceTest()
void NetworkInterfaceTest::testMap()
{
NetworkInterface::Map map = NetworkInterface::map();
assert (!map.empty());
for (NetworkInterface::Map::const_iterator it = map.begin(); it != map.end(); ++it)
NetworkInterface::Map m = NetworkInterface::map(false, false);
assert (!m.empty());
for (NetworkInterface::Map::const_iterator it = m.begin(); it != m.end(); ++it)
{
std::cout << std::endl << "=============" << std::endl;
@ -71,7 +72,7 @@ void NetworkInterfaceTest::testMap()
std::cout << "Mac Address: (" << it->second.hwType() << ")";
for (unsigned i = 0; i < mac.size(); ++i)
std::cout << ((i == 0) ? ' ' : ':') << std::hex << std::setw(2) << std::setfill('0') << (unsigned)mac[i];
std::cout << std::endl;
std::cout << std::dec << std::endl;
}
typedef NetworkInterface::AddressList List;
@ -95,6 +96,36 @@ void NetworkInterfaceTest::testMap()
}
void NetworkInterfaceTest::testList()
{
NetworkInterface::List list = NetworkInterface::list();
assert (!list.empty());
for (NetworkInterface::NetworkInterfaceList::const_iterator it = list.begin(); it != list.end(); ++it)
{
std::cout << "==============" << std::endl;
std::cout << "Index: " << it->index() << std::endl;
std::cout << "Name: " << it->name() << std::endl;
std::cout << "DisplayName: " << it->displayName() << std::endl;
typedef NetworkInterface::AddressList List;
const List& ipList = it->addressList();
List::const_iterator ipIt = ipList.begin();
List::const_iterator ipEnd = ipList.end();
for (int counter = 0; ipIt != ipEnd; ++ipIt, ++counter)
{
std::cout << "IP Address: " << ipIt->get<NetworkInterface::IP_ADDRESS>().toString() << std::endl;
IPAddress addr = ipIt->get<NetworkInterface::SUBNET_MASK>();
if (!addr.isWildcard()) std::cout << "Subnet: " << ipIt->get<NetworkInterface::SUBNET_MASK>().toString() << std::endl;
addr = ipIt->get<NetworkInterface::BROADCAST_ADDRESS>();
if (!addr.isWildcard()) std::cout << "Broadcast: " << ipIt->get<NetworkInterface::BROADCAST_ADDRESS>().toString() << std::endl;
}
std::cout << "==============" << std::endl << std::endl;
}
}
void NetworkInterfaceTest::testForName()
{
NetworkInterface::Map map = NetworkInterface::map();
@ -112,11 +143,22 @@ void NetworkInterfaceTest::testForAddress()
for (NetworkInterface::Map::const_iterator it = map.begin(); it != map.end(); ++it)
{
// not all interfaces have IP configured
if (it->second.addressList().empty())
continue;
if (it->second.addressList().empty()) continue;
NetworkInterface ifc = NetworkInterface::forAddress(it->second.address());
assert (ifc.address() == it->second.address());
if (it->second.supportsIPv4())
{
NetworkInterface ifc = NetworkInterface::forAddress(it->second.findFirstAddress(IPAddress::IPv4));
assert (ifc.findFirstAddress(IPAddress::IPv4) == it->second.findFirstAddress(IPAddress::IPv4));
}
else
{
try
{
it->second.findFirstAddress(IPAddress::IPv4);
fail ("must throw");
}
catch (NotFoundException&) { }
}
}
}
@ -146,6 +188,7 @@ CppUnit::Test* NetworkInterfaceTest::suite()
{
CppUnit::TestSuite* pSuite = new CppUnit::TestSuite("NetworkInterfaceTest");
CppUnit_addTest(pSuite, NetworkInterfaceTest, testList);
CppUnit_addTest(pSuite, NetworkInterfaceTest, testMap);
CppUnit_addTest(pSuite, NetworkInterfaceTest, testForName);
CppUnit_addTest(pSuite, NetworkInterfaceTest, testForAddress);

Просмотреть файл

@ -47,6 +47,7 @@ public:
~NetworkInterfaceTest();
void testMap();
void testList();
void testForName();
void testForAddress();
void testForIndex();