IPv6Address Class Reference

#include <IPv6Address.h>

List of all members.


Detailed Description

Stores an IPv6 address. Compliant to RFC 3513 - Internet Protocol Version 6 (IPv6) Addressing Architecture.

Storage is efficient: an object occupies size of an IPv6 address (128bits=16 bytes).


Public Types

 UNSPECIFIED
 LOOPBACK
 MULTICAST
 LINK
 SITE
 GLOBAL
enum  Scope {
  UNSPECIFIED, LOOPBACK, MULTICAST, LINK,
  SITE, GLOBAL
}

Public Member Functions

 IPv6Address ()
 IPv6Address (uint32 segment0, uint32 segment1, uint32 segment2, uint32 segment3)
 IPv6Address (const char *addr)
bool operator< (const IPv6Address &addr) const
bool operator> (const IPv6Address &addr) const
bool operator== (const IPv6Address &addr) const
bool operator!= (const IPv6Address &addr) const
int compare (const IPv6Address &addr) const
bool tryParse (const char *addr)
bool tryParseAddrWithPrefix (const char *addr, int &prefixLen)
void set (const char *addr)
std::string str () const
void set (uint32 d0, uint32 d1, uint32 d2, uint32 d3)
uint32words ()
Scope scope () const
IPv6Address getPrefix (int prefixLength) const
IPv6Address getSuffix (int prefixLength) const
const IPv6AddresssetPrefix (const IPv6Address &fromAddr, int prefixLength)
const IPv6AddresssetSuffix (const IPv6Address &fromAddr, int prefixLength)
IPv6Address formSolicitedNodeMulticastAddress () const
IPv6Address formSubnetRouterAnycastAddress (int prefixLength) const
bool matches (const IPv6Address &prefix, int prefixLength) const
bool isUnspecified () const
bool isMulticast () const
bool isUnicast () const
bool isLoopback () const
bool isLinkLocal () const
bool isSiteLocal () const
bool isGlobal () const
int multicastScope () const

Static Public Member Functions

static const char * scopeName (Scope s)
static void constructMask (int prefixLength, uint32 *mask)
static IPv6Address formLinkLocalAddress (const InterfaceToken &ident)

Static Public Attributes

Predefined addresses
static const IPv6Address UNSPECIFIED_ADDRESS
static const IPv6Address LOOPBACK_ADDRESS
static const IPv6Address ALL_NODES_1
static const IPv6Address ALL_NODES_2
static const IPv6Address ALL_ROUTERS_1
static const IPv6Address ALL_ROUTERS_2
static const IPv6Address ALL_ROUTERS_5
static const IPv6Address SOLICITED_NODE_PREFIX
static const IPv6Address LINKLOCAL_PREFIX

Protected Member Functions

bool doTryParse (const char *&addr)

Private Attributes

uint32 d [4]


Member Enumeration Documentation

enum IPv6Address::Scope

IPv6 address scope (RFC 3513)

Enumerator:
UNSPECIFIED 
LOOPBACK 
MULTICAST 
LINK 
SITE 
GLOBAL 
00054         {
00055             UNSPECIFIED,
00056             LOOPBACK,
00057             MULTICAST,
00058             LINK,
00059             SITE,
00060             GLOBAL
00061         };


Constructor & Destructor Documentation

IPv6Address::IPv6Address (  )  [inline]

Constructor Set all 128 bits of the IPv6 address to '0'. 0:0:0:0:0:0:0:0

00098                        {
00099             d[0]=d[1]=d[2]=d[3]=0;
00100         }

IPv6Address::IPv6Address ( uint32  segment0,
uint32  segment1,
uint32  segment2,
uint32  segment3 
) [inline]

Constructor Construct an IPv6 Address based on 4 given segments.

00106                                                                                          {
00107             d[0] = segment0;
00108             d[1] = segment1;
00109             d[2] = segment2;
00110             d[3] = segment3;
00111         }

IPv6Address::IPv6Address ( const char *  addr  )  [inline]

Constructor. Sets the address from the given text representation. See documentation of tryParse() for supported syntax.

00117 {set(addr);}


Member Function Documentation

int IPv6Address::compare ( const IPv6Address addr  )  const [inline]

Returns -1, 0 or 1.

00129                                                     {
00130             return d[0]<addr.d[0] ? -1 : d[0]>addr.d[0] ? 1 :
00131                    d[1]<addr.d[1] ? -1 : d[1]>addr.d[1] ? 1 :
00132                    d[2]<addr.d[2] ? -1 : d[2]>addr.d[2] ? 1 :
00133                    d[3]<addr.d[3] ? -1 : d[3]>addr.d[3] ? 1 : 0;
00134         }

void IPv6Address::constructMask ( int  prefixLength,
uint32 mask 
) [static]

Construct a 128 bit mask based on the prefix length. Mask should point to an array of four 32-bit unsigned integers.

00261 {
00262     ASSERT(prefixLength>=0 && prefixLength<=128 && mask!=NULL);
00263 
00264     // create a mask based on the prefix length.
00265     if (prefixLength==0)
00266     {
00267         mask[0] = mask[1] = mask[2] = mask[3] = 0x00000000;
00268     }
00269     else if (prefixLength<=32)
00270     {
00271         int num_of_shifts = 32 - prefixLength;
00272         mask[0] = 0xFFFFFFFFU << num_of_shifts;
00273         mask[1] = 0x00000000;
00274         mask[2] = 0x00000000;
00275         mask[3] = 0x00000000;
00276     }
00277     else if (prefixLength<=64)
00278     {
00279         int num_of_shifts = 64 - prefixLength;
00280         mask[0] = 0xFFFFFFFFU;
00281         mask[1] = 0xFFFFFFFFU << num_of_shifts;
00282         mask[2] = 0x00000000;
00283         mask[3] = 0x00000000;
00284     }
00285     else if (prefixLength<=96)
00286     {
00287         int num_of_shifts = 96 - prefixLength;
00288         mask[0] = 0xFFFFFFFFU;
00289         mask[1] = 0xFFFFFFFFU;
00290         mask[2] = 0xFFFFFFFFU << num_of_shifts;
00291         mask[3] = 0x00000000;
00292     }
00293     else
00294     {
00295         int num_of_shifts = 128 - prefixLength;
00296         mask[0] = 0xFFFFFFFFU;
00297         mask[1] = 0xFFFFFFFFU;
00298         mask[2] = 0xFFFFFFFFU;
00299         mask[3] = 0xFFFFFFFFU << num_of_shifts;
00300     }
00301 }

bool IPv6Address::doTryParse ( const char *&  addr  )  [protected]

00072 {
00073     if (!strcmp(addr,"<unspec>"))
00074     {
00075         addr += 8;
00076         d[0] = d[1] = d[2] = d[3] = 0;
00077         return true;
00078     }
00079 
00080     // parse and store 16-bit units
00081     int octals[8];
00082     int numOctals = parseOctals(addr, octals);
00083 
00084     // if address string contains "::", parse and store second half too
00085     if (*addr==':' && *(addr+1)==':')
00086     {
00087         addr += 2;
00088         int suffixOctals[8];
00089         int numSuffixOctals = parseOctals(addr, suffixOctals);
00090 
00091         // merge suffixOctals[] into octals[]
00092         if (numOctals+numSuffixOctals>8)
00093             return false; // too many
00094         for (int i=numOctals; i<8; i++) {
00095             int j = i-8+numSuffixOctals;
00096             octals[i] = j<0 ? 0 : suffixOctals[j];
00097         }
00098         numOctals = 8;
00099     }
00100 
00101     if (numOctals!=8)
00102         return false; // too few
00103 
00104     // copy octets to d[]
00105     for (unsigned int i=0; i<4; i++)
00106         d[i] = (octals[i*2]<<16) + octals[2*i + 1];
00107 
00108     return true;
00109 }

IPv6Address IPv6Address::formLinkLocalAddress ( const InterfaceToken ident  )  [static]

Forms a link-local address using the given interface identifier.

00354 {
00355     IPv6Address suffix(0, 0, ident.normal(), ident.low());
00356     IPv6Address linkLocalAddr = IPv6Address::LINKLOCAL_PREFIX;
00357     linkLocalAddr.setSuffix(suffix, 128-ident.length());
00358     return linkLocalAddr;
00359 }

IPv6Address IPv6Address::formSolicitedNodeMulticastAddress (  )  const [inline]

Create solicited-node multicast address for this address. This function replaces the prefix with FF02:0:0:0:0:1:FF00:0/104.

00219                                                               {
00220             return IPv6Address(*this).setPrefix(SOLICITED_NODE_PREFIX, 104);
00221         };

IPv6Address IPv6Address::formSubnetRouterAnycastAddress ( int  prefixLength  )  const [inline]

RFC 3513: Section 2.6.1 The Subnet-Router anycast address is predefined. Its format is as follows:

 |                         n bits                 |   128-n bits   |
 +------------------------------------------------+----------------+
 |                   subnet prefix                | 00000000000000 |
 +------------------------------------------------+----------------+
 
00235                                                                            {
00236             return IPv6Address(*this).setSuffix(UNSPECIFIED_ADDRESS, prefixLength);
00237         }

IPv6Address IPv6Address::getPrefix ( int  prefixLength  )  const

Get the IPv6 first prefixLength bits of the address, with the rest set to zero.

00304 {
00305     // First we construct a mask.
00306     uint32 mask[4];
00307     constructMask(prefixLength, mask);
00308 
00309     // Now we mask each IPv6 address segment and create a new IPv6 Address!
00310     return IPv6Address(d[0]&mask[0],d[1]&mask[1],d[2]&mask[2],d[3]&mask[3] );
00311 }

IPv6Address IPv6Address::getSuffix ( int  prefixLength  )  const

Get the last 128-prefixLength bits of the address, with the first bits set to zero.

00314 {
00315     // First we construct a mask.
00316     uint32 mask[4];
00317     constructMask(prefixLength, mask);
00318 
00319     // Now we mask each IPv6 address segment, inverse it
00320     // and create a new IPv6 Address!
00321     return IPv6Address(d[0]&~mask[0],d[1]&~mask[1],d[2]&~mask[2],d[3]&~mask[3] );
00322 }

bool IPv6Address::isGlobal (  )  const [inline]

Utility function based on scope()

00270 {return scope()==GLOBAL;}

bool IPv6Address::isLinkLocal (  )  const [inline]

Utility function based on scope()

00264 {return scope()==LINK;}

bool IPv6Address::isLoopback (  )  const [inline]

Utility function based on scope()

00261 {return scope()==LOOPBACK;}

bool IPv6Address::isMulticast (  )  const [inline]

Utility function based on scope()

00255 {return scope()==MULTICAST;}

bool IPv6Address::isSiteLocal (  )  const [inline]

Utility function based on scope()

00267 {return scope()==SITE;}

bool IPv6Address::isUnicast (  )  const [inline]

Utility function based on scope()

00258 {return scope()!=MULTICAST && scope()!=UNSPECIFIED;}

bool IPv6Address::isUnspecified (  )  const [inline]

Check if the IPv6 Address is undefined.

00252 {return (d[0]|d[1]|d[2]|d[3])==0;}

bool IPv6Address::matches ( const IPv6Address prefix,
int  prefixLength 
) const

Returns true if the address matches the given prefix.

00362 {
00363     // first we construct a mask.
00364     uint32 mask[4];
00365     constructMask(prefixLength, mask);
00366 
00367     // xor the bits of the 2 addresses, and the result should be zero wherever
00368     // the mask has 1 bits
00369     return (((d[0]^prefix.d[0])&mask[0]) | ((d[1]^prefix.d[1])&mask[1]) |
00370             ((d[2]^prefix.d[2])&mask[2]) | ((d[3]^prefix.d[3])&mask[3]))==0;
00371 }

int IPv6Address::multicastScope (  )  const

Get the 4-bit scope field of an IPv6 multicast address.

00374 {
00375     if ((d[0] & MULTICAST_MASK)!=MULTICAST_PREFIX)
00376         throw cRuntimeError("IPv6Address::multicastScope(): %s is not a multicast address", str().c_str());
00377     return (d[0] >> 16) & 0x0F;
00378 }

bool IPv6Address::operator!= ( const IPv6Address addr  )  const [inline]

00124 {return !operator==(addr);}

bool IPv6Address::operator< ( const IPv6Address addr  )  const [inline]

00119 {return compare(addr)<0;}

bool IPv6Address::operator== ( const IPv6Address addr  )  const [inline]

00121                                                        {
00122             return d[3]==addr.d[3] && d[0]==addr.d[0] && d[1]==addr.d[1] && d[2]==addr.d[2]; // d[3] differs most often, compare it first
00123         }

bool IPv6Address::operator> ( const IPv6Address addr  )  const [inline]

00120 {return compare(addr)>0;}

IPv6Address::Scope IPv6Address::scope (  )  const

Get the IPv6 address scope.

00208 {
00209     //Mask the given IPv6 address with the different mask types
00210     //to get only the IPv6 address scope. Compare the masked
00211     //address with the different prefixes.
00212 
00213     if ((d[0] & LINK_LOCAL_MASK) == LINK_LOCAL_PREFIX )
00214     {
00215         return LINK;
00216     }
00217     else if ((d[0] & SITE_LOCAL_MASK) == SITE_LOCAL_PREFIX )
00218     {
00219         return SITE;
00220     }
00221     else if ((d[0] & MULTICAST_MASK) == MULTICAST_PREFIX )
00222     {
00223         return MULTICAST;
00224     }
00225     else if (d[0] == 0x00000000 && d[1] == 0x00000000 && d[2] == 0x00000000)
00226     {
00227         if (d[3] == 0x00000000)
00228         {
00229             return UNSPECIFIED;
00230         }
00231         else if (d[3] == 0x00000001)
00232         {
00233             return LOOPBACK;
00234         }
00235         else
00236         {
00237             return GLOBAL; // actually an "IPv4-compatible IPv6 address"
00238         }
00239     }
00240     else
00241     {
00242         return GLOBAL;
00243     }
00244 }

const char * IPv6Address::scopeName ( Scope  s  )  [static]

Return the string representation of the given scope.

00247 {
00248     switch (scope)
00249     {
00250         case UNSPECIFIED:        return "unspec";
00251         case LOOPBACK:           return "loopback";
00252         case MULTICAST:          return "mcast";
00253         case LINK:               return "link";
00254         case SITE:               return "site";
00255         case GLOBAL:             return "global";
00256         default:                 return "???";
00257     }
00258 }

void IPv6Address::set ( uint32  d0,
uint32  d1,
uint32  d2,
uint32  d3 
) [inline]

Set the address to the given four 32-bit integers.

00163                                                              {
00164             d[0]=d0; d[1]=d1; d[2]=d2; d[3]=d3;
00165         }

void IPv6Address::set ( const char *  addr  ) 

Sets the IPv6 address. Given a string.

00145 {
00146     if (!tryParse(addr))
00147         throw new cRuntimeError("IPv6Address: cannot interpret address string `%s'", addr);
00148 }

const IPv6Address & IPv6Address::setPrefix ( const IPv6Address fromAddr,
int  prefixLength 
)

Overwrites the first prefixLength bits of the address with the bits from the address passed as argument. Return value is the object itself.

00325 {
00326     // first we construct a mask.
00327     uint32 mask[4];
00328     constructMask(prefixLength, mask);
00329 
00330     // combine the addresses
00331     d[0] = (d[0]&~mask[0]) | (fromAddr.d[0]&mask[0]);
00332     d[1] = (d[1]&~mask[1]) | (fromAddr.d[1]&mask[1]);
00333     d[2] = (d[2]&~mask[2]) | (fromAddr.d[2]&mask[2]);
00334     d[3] = (d[3]&~mask[3]) | (fromAddr.d[3]&mask[3]);
00335     return *this;
00336 }

const IPv6Address & IPv6Address::setSuffix ( const IPv6Address fromAddr,
int  prefixLength 
)

Overwrites the last 128-prefixLength bits of the address with the bits from address passed as argument. Return value is the object itself.

00340 {
00341     // first we construct a mask.
00342     uint32 mask[4];
00343     constructMask(prefixLength, mask);
00344 
00345     // combine the addresses
00346     d[0] = (d[0]&mask[0]) | (fromAddr.d[0]&~mask[0]);
00347     d[1] = (d[1]&mask[1]) | (fromAddr.d[1]&~mask[1]);
00348     d[2] = (d[2]&mask[2]) | (fromAddr.d[2]&~mask[2]);
00349     d[3] = (d[3]&mask[3]) | (fromAddr.d[3]&~mask[3]);
00350     return *this;
00351 }

std::string IPv6Address::str (  )  const

Get the IPv6 address as a "standard string".

00179 {
00180     if (isUnspecified())
00181         return std::string("<unspec>");
00182 
00183     // convert to 16-bit octals
00184     int octals[8] = {
00185         (d[0]>>16), (d[0]&0xffff), (d[1]>>16), (d[1]&0xffff),
00186         (d[2]>>16), (d[2]&0xffff), (d[3]>>16), (d[3]&0xffff)
00187     };
00188 
00189     // find longest sequence of zeros in octals[]
00190     int start, end;
00191     findGap(octals, start, end);
00192     if (start==0 && end==8)
00193         return "::0";  // the unspecified address is a special case
00194 
00195     // print octals, replacing gap with "::"
00196     std::stringstream os;
00197     os << std::hex;
00198     for (int i=0; i<start; i++)
00199         os << (i==0?"":":") << octals[i];
00200     if (start!=end)
00201         os << "::";
00202     for (int j=end; j<8; j++)
00203         os << (j==end?"":":") << octals[j];
00204     return os.str();
00205 }

bool IPv6Address::tryParse ( const char *  addr  ) 

Try parsing an IPv6 address. Return true if the string contained a well-formed IPv6 address, and false otherwise.

TBD: explain syntax (refer to RFC?)

00112 {
00113     if (!addr)
00114         return false;
00115     if (!doTryParse(addr))
00116         return false;
00117     if (*addr!=0)
00118         return false; // illegal trailing character
00119     return true;
00120 }

bool IPv6Address::tryParseAddrWithPrefix ( const char *  addr,
int &  prefixLen 
)

FIXME

00123 {
00124     if (!addr)
00125         return false;
00126     if (!doTryParse(addr))
00127         return false;
00128     if (*addr!='/')
00129         return false; // no '/' after address
00130     addr++;
00131 
00132     // parse prefix
00133     char *e;
00134     prefixLen = strtoul(addr,&e,10);
00135     if (addr==e)
00136         return false; // no number after '/'
00137     if (*e!=0)
00138         return false; // garbage after number
00139     if (prefixLen<0 || prefixLen>128)
00140         return false; // wrong len value
00141     return true;
00142 }

uint32* IPv6Address::words (  )  [inline]

Returns pointer to internal binary representation of address, four 32-bit unsigned integers.

00171 {return d;}


Member Data Documentation

const IPv6Address IPv6Address::ALL_NODES_1 [static]

All-nodes multicast address, scope 1 (interface-local)

const IPv6Address IPv6Address::ALL_NODES_2 [static]

All-nodes multicast address, scope 2 (link-local)

const IPv6Address IPv6Address::ALL_ROUTERS_1 [static]

All-routers multicast address, scope 1 (interface-local)

const IPv6Address IPv6Address::ALL_ROUTERS_2 [static]

All-routers multicast address, scope 2 (link-local)

const IPv6Address IPv6Address::ALL_ROUTERS_5 [static]

All-routers multicast address, scope 5 (site-local)

uint32 IPv6Address::d[4] [private]

const IPv6Address IPv6Address::LINKLOCAL_PREFIX [static]

The link-local prefix (fe80::)

const IPv6Address IPv6Address::LOOPBACK_ADDRESS [static]

The loopback address

const IPv6Address IPv6Address::SOLICITED_NODE_PREFIX [static]

The solicited-node multicast address prefix (prefix length = 104)

const IPv6Address IPv6Address::UNSPECIFIED_ADDRESS [static]

The unspecified address


The documentation for this class was generated from the following files:
Generated on Wed Apr 4 13:20:21 2007 for INET Framework for OMNeT++/OMNEST by  doxygen 1.4.7