A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
ipv4-address.cc
Go to the documentation of this file.
1/*
2 * Copyright (c) 2005 INRIA
3 *
4 * SPDX-License-Identifier: GPL-2.0-only
5 *
6 * Author: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
7 */
8
9#include "ipv4-address.h"
10
11#include "ns3/assert.h"
12#include "ns3/log.h"
13
14#include <cstdlib>
15
16#ifdef __WIN32__
17#include <WS2tcpip.h>
18#else
19#include <arpa/inet.h>
20#include <sys/socket.h>
21#endif
22
23namespace ns3
24{
25
26NS_LOG_COMPONENT_DEFINE("Ipv4Address");
27
29 : m_mask(mask)
30{
31 NS_LOG_FUNCTION(this << mask);
32}
33
34Ipv4Mask::Ipv4Mask(const char* mask)
35{
36 NS_LOG_FUNCTION(this << mask);
37 if (*mask == '/')
38 {
39 auto plen = static_cast<uint32_t>(std::atoi(++mask));
40 NS_ASSERT(plen <= 32);
41 if (plen > 0)
42 {
43 m_mask = 0xffffffff << (32 - plen);
44 }
45 else
46 {
47 m_mask = 0;
48 }
49 }
50 else
51 {
52 if (inet_pton(AF_INET, mask, &m_mask) <= 0)
53 {
54 NS_ABORT_MSG("Error, can not build an IPv4 mask from an invalid string: " << mask);
55 }
56 m_mask = ntohl(m_mask);
57 }
58}
59
60bool
62{
63 NS_LOG_FUNCTION(this << a << b);
64 return (a.Get() & m_mask) == (b.Get() & m_mask);
65}
66
69{
70 NS_LOG_FUNCTION(this);
71 return m_mask;
72}
73
74void
76{
77 NS_LOG_FUNCTION(this << mask);
78 m_mask = mask;
79}
80
83{
84 NS_LOG_FUNCTION(this);
85 return ~m_mask;
86}
87
88void
89Ipv4Mask::Print(std::ostream& os) const
90{
91 NS_LOG_FUNCTION(this << &os);
92 os << ((m_mask >> 24) & 0xff) << "." << ((m_mask >> 16) & 0xff) << "." << ((m_mask >> 8) & 0xff)
93 << "." << ((m_mask >> 0) & 0xff);
94}
95
98{
100 static Ipv4Mask loopback("255.0.0.0");
101 return loopback;
102}
103
106{
108 static Ipv4Mask zero("0.0.0.0");
109 return zero;
110}
111
114{
116 static Ipv4Mask ones("255.255.255.255");
117 return ones;
118}
119
120uint16_t
122{
123 NS_LOG_FUNCTION(this);
124 uint16_t tmp = 0;
125 uint32_t mask = m_mask;
126 while (mask != 0)
127 {
128 mask = mask << 1;
129 tmp++;
130 }
131 return tmp;
132}
133
135{
136 NS_LOG_FUNCTION(this << address);
137 m_address = address;
138}
139
140Ipv4Address::Ipv4Address(const char* address)
141{
142 NS_LOG_FUNCTION(this << address);
143
144 if (inet_pton(AF_INET, address, &m_address) <= 0)
145 {
146 NS_ABORT_MSG("Error, can not build an IPv4 address from an invalid string: " << address);
147 return;
148 }
149 m_address = ntohl(m_address);
150}
151
152bool
153Ipv4Address::CheckCompatible(const std::string& addressStr)
154{
155 NS_LOG_FUNCTION(addressStr);
156
157 uint32_t buffer;
158
159 if (inet_pton(AF_INET, addressStr.c_str(), &buffer) <= 0)
160 {
161 NS_LOG_WARN("Error, can not build an IPv4 address from an invalid string: " << addressStr);
162 return false;
163 }
164 return true;
165}
166
169{
170 NS_LOG_FUNCTION(this);
171 return m_address;
172}
173
174void
176{
177 NS_LOG_FUNCTION(this << address);
178 m_address = address;
179}
180
181void
182Ipv4Address::Set(const char* address)
183{
184 NS_LOG_FUNCTION(this << address);
185 if (inet_pton(AF_INET, address, &m_address) <= 0)
186 {
187 NS_ABORT_MSG("Error, can not build an IPv4 address from an invalid string: " << address);
188 return;
189 }
190 m_address = ntohl(m_address);
191}
192
195{
196 NS_LOG_FUNCTION(this << mask);
197 return Ipv4Address(Get() & mask.Get());
198}
199
202{
203 NS_LOG_FUNCTION(this << mask);
204 if (mask == Ipv4Mask::GetOnes())
205 {
206 NS_ASSERT_MSG(false,
207 "Trying to get subnet-directed broadcast address with an all-ones netmask");
208 }
209 return Ipv4Address(Get() | mask.GetInverse());
210}
211
212bool
214{
215 NS_LOG_FUNCTION(this << mask);
216 if (mask == Ipv4Mask::GetOnes())
217 {
218 // If the mask is 255.255.255.255, there is no subnet directed
219 // broadcast for this address.
220 return false;
221 }
222 return ((Get() | mask.Get()) == Ipv4Address::GetBroadcast().Get());
223}
224
225bool
227{
228 NS_LOG_FUNCTION(this);
229 return true;
230}
231
232bool
234{
235 NS_LOG_FUNCTION(this);
236 return (m_address == 0x00000000U);
237}
238
239bool
241{
242 NS_LOG_FUNCTION(this);
243 return (m_address == 0x7f000001U);
244}
245
246bool
248{
249 NS_LOG_FUNCTION(this);
250 return (m_address == 0xffffffffU);
251}
252
253bool
255{
256 //
257 // Multicast addresses are defined as ranging from 224.0.0.0 through
258 // 239.255.255.255 (which is E0000000 through EFFFFFFF in hex).
259 //
260 NS_LOG_FUNCTION(this);
261 return (m_address >= 0xe0000000 && m_address <= 0xefffffff);
262}
263
264bool
266{
267 NS_LOG_FUNCTION(this);
268 // Link-Local multicast address is 224.0.0.0/24
269 return (m_address & 0xffffff00) == 0xe0000000;
270}
271
272bool
274{
275 NS_LOG_FUNCTION(this);
276 // Link-Local address is 169.254.0.0/16
277 return (m_address & 0xffff0000) == 0xa9fe0000;
278}
279
280void
281Ipv4Address::Serialize(uint8_t buf[4]) const
282{
283 NS_LOG_FUNCTION(this << &buf);
284 buf[0] = (m_address >> 24) & 0xff;
285 buf[1] = (m_address >> 16) & 0xff;
286 buf[2] = (m_address >> 8) & 0xff;
287 buf[3] = (m_address >> 0) & 0xff;
288}
289
291Ipv4Address::Deserialize(const uint8_t buf[4])
292{
293 NS_LOG_FUNCTION(&buf);
294 Ipv4Address ipv4;
295 ipv4.m_address = 0;
296 ipv4.m_address |= buf[0];
297 ipv4.m_address <<= 8;
298 ipv4.m_address |= buf[1];
299 ipv4.m_address <<= 8;
300 ipv4.m_address |= buf[2];
301 ipv4.m_address <<= 8;
302 ipv4.m_address |= buf[3];
303
304 return ipv4;
305}
306
307void
308Ipv4Address::Print(std::ostream& os) const
309{
310 NS_LOG_FUNCTION(this);
311 os << ((m_address >> 24) & 0xff) << "." << ((m_address >> 16) & 0xff) << "."
312 << ((m_address >> 8) & 0xff) << "." << ((m_address >> 0) & 0xff);
313}
314
315bool
317{
318 NS_LOG_FUNCTION(&address);
319 return address.CheckCompatible(GetType(), 4);
320}
321
322Ipv4Address::
323operator Address() const
324{
325 return ConvertTo();
326}
327
330{
331 NS_LOG_FUNCTION(this);
332 uint8_t buf[4];
333 Serialize(buf);
334 return Address(GetType(), buf, 4);
335}
336
339{
340 NS_LOG_FUNCTION(&address);
341 NS_ASSERT(address.CheckCompatible(GetType(), 4));
342 uint8_t buf[4];
343 address.CopyTo(buf);
344 return Deserialize(buf);
345}
346
347uint8_t
349{
351 static uint8_t type = Address::Register("IpAddress", 4);
352 return type;
353}
354
357{
359 static Ipv4Address zero("0.0.0.0");
360 return zero;
361}
362
365{
367 static Ipv4Address any("0.0.0.0");
368 return any;
369}
370
373{
375 static Ipv4Address broadcast("255.255.255.255");
376 return broadcast;
377}
378
381{
383 Ipv4Address loopback("127.0.0.1");
384 return loopback;
385}
386
387size_t
389{
390 return std::hash<uint32_t>()(x.Get());
391}
392
393std::ostream&
394operator<<(std::ostream& os, const Ipv4Address& address)
395{
396 address.Print(os);
397 return os;
398}
399
400std::ostream&
401operator<<(std::ostream& os, const Ipv4Mask& mask)
402{
403 mask.Print(os);
404 return os;
405}
406
407std::istream&
408operator>>(std::istream& is, Ipv4Address& address)
409{
410 std::string str;
411 is >> str;
412 address = Ipv4Address(str.c_str());
413 return is;
414}
415
416std::istream&
417operator>>(std::istream& is, Ipv4Mask& mask)
418{
419 std::string str;
420 is >> str;
421 mask = Ipv4Mask(str.c_str());
422 return is;
423}
424
427
428} // namespace ns3
cairo_uint64_t x
_cairo_uint_96by64_32x64_divrem:
a polymophic address class
Definition address.h:114
static uint8_t Register(const std::string &kind, uint8_t length)
Allocate a new type id for a new type of address.
Definition address.cc:130
size_t operator()(const Ipv4Address &x) const
Returns the hash of an IPv4 address.
Ipv4 addresses are stored in host order in this class.
void Print(std::ostream &os) const
Print this address to the given output stream.
static Ipv4Address GetLoopback()
Ipv4Address GetSubnetDirectedBroadcast(const Ipv4Mask &mask) const
Generate subnet-directed broadcast address corresponding to mask.
bool IsMulticast() const
static Ipv4Address ConvertFrom(const Address &address)
static Ipv4Address GetZero()
static bool IsMatchingType(const Address &address)
void Set(uint32_t address)
input address is in host order.
Ipv4Address()=default
bool IsSubnetDirectedBroadcast(const Ipv4Mask &mask) const
Generate subnet-directed broadcast address corresponding to mask.
bool IsLocalhost() const
static Ipv4Address GetBroadcast()
void Serialize(uint8_t buf[4]) const
Serialize this address to a 4-byte buffer.
Ipv4Address CombineMask(const Ipv4Mask &mask) const
Combine this address with a network mask.
bool IsAny() const
uint32_t Get() const
Get the host-order 32-bit IP address.
static Ipv4Address Deserialize(const uint8_t buf[4])
static uint8_t GetType()
Get the underlying address type (automatically assigned).
uint32_t m_address
IPv4 address.
Address ConvertTo() const
Convert to an Address type.
bool IsBroadcast() const
static Ipv4Address GetAny()
static bool CheckCompatible(const std::string &addressStr)
Checks if the string contains an Ipv4Address.
bool IsInitialized() const
bool IsLocalMulticast() const
bool IsLinkLocal() const
If the IPv4 address is an APIPA address (169.254/16).
a class to represent an Ipv4 address mask
uint32_t m_mask
IP mask.
static Ipv4Mask GetOnes()
void Set(uint32_t mask)
input mask is in host order.
Ipv4Mask()=default
Will initialize to a zero-length mask, which will match any address.
uint16_t GetPrefixLength() const
uint32_t Get() const
Get the host-order 32-bit IP mask.
void Print(std::ostream &os) const
Print this mask to the given output stream.
uint32_t GetInverse() const
Return the inverse mask in host order.
bool IsMatch(Ipv4Address a, Ipv4Address b) const
static Ipv4Mask GetLoopback()
static Ipv4Mask GetZero()
#define NS_ASSERT(condition)
At runtime, in debugging builds, if this condition is not true, the program prints the source file,...
Definition assert.h:55
#define NS_ASSERT_MSG(condition, message)
At runtime, in debugging builds, if this condition is not true, the program prints the message to out...
Definition assert.h:75
#define ATTRIBUTE_HELPER_CPP(type)
Define the attribute value, accessor and checkers for class type.
#define NS_ABORT_MSG(msg)
Unconditional abnormal program termination with a message.
Definition abort.h:38
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition log.h:194
#define NS_LOG_FUNCTION_NOARGS()
Output the name of the function.
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by ",...
#define NS_LOG_WARN(msg)
Use NS_LOG to output a message of level LOG_WARN.
Definition log.h:253
Every class exported by the ns3 library is enclosed in the ns3 namespace.
std::ostream & operator<<(std::ostream &os, const Angles &a)
Definition angles.cc:148
std::istream & operator>>(std::istream &is, Angles &a)
Definition angles.cc:172