From 939b554451ced04450f54cb800ec2198b2c4c016 Mon Sep 17 00:00:00 2001 From: Thomas Jarosch Date: Thu, 26 Aug 2004 16:52:30 +0000 Subject: [PATCH] libi2ncommon: (tomj) extended IP_RANGE class with operator+ and operator- --- src/ipfunc.cpp | 33 +++++++++++++++++++++++++++++++++ src/ipfunc.hxx | 4 ++++ test/ip_range.cpp | 43 +++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 80 insertions(+), 0 deletions(-) diff --git a/src/ipfunc.cpp b/src/ipfunc.cpp index 62c8667..b02a168 100644 --- a/src/ipfunc.cpp +++ b/src/ipfunc.cpp @@ -8,6 +8,7 @@ #include #include +#include #include #include @@ -163,6 +164,13 @@ void IP_RANGE::load(type t, const std::string& ip, const std::string& mask_or_en this->ip=ia_ip1.s_addr; this->end=ia_ip2.s_addr; + + // Automatically turn IP if IP & and are swapped + if (turn_ip(this->ip) > turn_ip(this->end)) { + unsigned int tmp = this->ip; + this->ip = this->end; + this->end = tmp; + } } } @@ -206,6 +214,31 @@ bool IP_RANGE::overlapping(const IP_RANGE& a) const return false; } +IP_RANGE operator+(const IP_RANGE &base, const int &ips) +{ + IP_RANGE ret=base; + + ret.ip = ret.turn_ip(ret.turn_ip(ret.ip) + ips); + ret.end = ret.turn_ip(ret.turn_ip(ret.end) + ips); + + // Check if this is still a valid network + // If not: Convert network to range + if (ret.t == NETWORK && (ret.ip&ret.mask) != ret.ip) { + ret.t = RANGE; + ret.mask = 0; + } + + if (ret.t == RANGE && ret.turn_ip(ret.end) < ret.turn_ip(ret.ip)) + throw out_of_range("range end lower than begin"); + + return ret; +} + +int IP_RANGE::operator-(const IP_RANGE &other) +{ + return turn_ip(ip)-turn_ip(other.ip); +} + std::string IP_RANGE::to_string(void) const { struct in_addr ia_ip; diff --git a/src/ipfunc.hxx b/src/ipfunc.hxx index a4e2a24..1972846 100644 --- a/src/ipfunc.hxx +++ b/src/ipfunc.hxx @@ -17,6 +17,8 @@ class IP_RANGE { + friend IP_RANGE operator+(const IP_RANGE &base, const int &ips); + private: unsigned int ip; unsigned int mask; @@ -37,6 +39,8 @@ class IP_RANGE bool is_within(const IP_RANGE& a) const; bool overlapping(const IP_RANGE& a) const; + int operator-(const IP_RANGE &other); + // returns the complete IP_RANGE std::string to_string(void) const; diff --git a/test/ip_range.cpp b/test/ip_range.cpp index 0b17edc..6f28dab 100644 --- a/test/ip_range.cpp +++ b/test/ip_range.cpp @@ -28,6 +28,7 @@ class ip_range : public TestFixture CPPUNIT_TEST(ConstructNet2); CPPUNIT_TEST(ConstructRange1); CPPUNIT_TEST(ConstructRange2); + CPPUNIT_TEST(ConstructRangeSwap); CPPUNIT_TEST(OverlapIP); CPPUNIT_TEST(OverlapNet1); CPPUNIT_TEST(OverlapNet2); @@ -57,6 +58,10 @@ class ip_range : public TestFixture CPPUNIT_TEST(WithinRange8); CPPUNIT_TEST(WithinRange9); CPPUNIT_TEST(WithinRange10); + CPPUNIT_TEST(OperatorPlus1); + CPPUNIT_TEST(OperatorPlus2); + CPPUNIT_TEST(OperatorPlusOverflow); + CPPUNIT_TEST(OperatorMinus); CPPUNIT_TEST_SUITE_END(); @@ -105,6 +110,12 @@ class ip_range : public TestFixture CPPUNIT_ASSERT_EQUAL(string("192.168.1.5-192.168.3.1"),i.to_string()); } + void ConstructRangeSwap() + { + IP_RANGE i(ip_type::RANGE,"192.168.3.1","192.168.1.5"); + CPPUNIT_ASSERT_EQUAL(string("192.168.1.5-192.168.3.1"),i.to_string()); + } + void OverlapIP() { IP_RANGE a("192.168.1.5"); @@ -336,6 +347,38 @@ class ip_range : public TestFixture CPPUNIT_ASSERT_EQUAL(false,a.is_within(b)); } + + void OperatorPlus1() + { + IP_RANGE a("192.168.2.0/255.255.255.0"); + + a=a+256; + + CPPUNIT_ASSERT_EQUAL(string("192.168.3.0/255.255.255.0"),a.to_string()); + } + + void OperatorPlus2() + { + IP_RANGE a("192.168.2.0/255.255.255.0"); + + a=a+13; + + CPPUNIT_ASSERT_EQUAL(string("192.168.2.13-192.168.3.12"),a.to_string()); + } + + void OperatorPlusOverflow() + { + IP_RANGE a("255.255.255.0/255.255.255.0"); + CPPUNIT_ASSERT_THROW(a=a+1, std::out_of_range); + } + + void OperatorMinus() + { + IP_RANGE a("192.168.2.0/255.255.255.0"); + IP_RANGE b("192.168.1.0/255.255.255.0"); + + CPPUNIT_ASSERT_EQUAL(256,a-b); + } }; CPPUNIT_TEST_SUITE_REGISTRATION(ip_range); -- 1.7.1