A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
icmpv4.cc
Go to the documentation of this file.
1/*
2 * Copyright (c) 2008 INRIA
3 *
4 * SPDX-License-Identifier: GPL-2.0-only
5 *
6 * Author: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
7 */
8
9#include "icmpv4.h"
10
11#include "ns3/log.h"
12#include "ns3/packet.h"
13
14namespace ns3
15{
16
17NS_LOG_COMPONENT_DEFINE("Icmpv4Header");
18
19/********************************************************
20 * Icmpv4Header
21 ********************************************************/
22
23NS_OBJECT_ENSURE_REGISTERED(Icmpv4Header);
24
25TypeId
27{
28 static TypeId tid = TypeId("ns3::Icmpv4Header")
30 .SetGroupName("Internet")
31 .AddConstructor<Icmpv4Header>();
32 return tid;
33}
34
36 : m_type(0),
37 m_code(0),
38 m_calcChecksum(false)
39{
40 NS_LOG_FUNCTION(this);
41}
42
47
48void
54
57{
58 NS_LOG_FUNCTION(this);
59 return GetTypeId();
60}
61
64{
65 NS_LOG_FUNCTION(this);
66 return 4;
67}
68
69void
71{
72 NS_LOG_FUNCTION(this << &start);
73 Buffer::Iterator i = start;
74 i.WriteU8(m_type);
75 i.WriteU8(m_code);
76 i.WriteHtonU16(0);
78 {
79 i = start;
80 uint16_t checksum = i.CalculateIpChecksum(i.GetSize());
81 i = start;
82 i.Next(2);
83 i.WriteU16(checksum);
84 }
85}
86
89{
90 NS_LOG_FUNCTION(this << &start);
91 m_type = start.ReadU8();
92 m_code = start.ReadU8();
93 start.Next(2); // uint16_t checksum = start.ReadNtohU16 ();
94 return 4;
95}
96
97void
98Icmpv4Header::Print(std::ostream& os) const
99{
100 NS_LOG_FUNCTION(this << &os);
101 os << "type=" << (uint32_t)m_type << ", code=" << (uint32_t)m_code;
102}
103
104void
106{
107 NS_LOG_FUNCTION(this << static_cast<uint32_t>(type));
108 m_type = type;
109}
110
111void
113{
114 NS_LOG_FUNCTION(this << static_cast<uint32_t>(code));
115 m_code = code;
116}
117
118uint8_t
120{
121 NS_LOG_FUNCTION(this);
122 return m_type;
123}
124
125uint8_t
127{
128 NS_LOG_FUNCTION(this);
129 return m_code;
130}
131
132/********************************************************
133 * Icmpv4Echo
134 ********************************************************/
135
137
138void
140{
141 NS_LOG_FUNCTION(this << id);
142 m_identifier = id;
143}
144
145void
147{
148 NS_LOG_FUNCTION(this << seq);
149 m_sequence = seq;
150}
151
152void
154{
155 NS_LOG_FUNCTION(this << *data);
156
157 uint32_t size = data->GetSize();
158 //
159 // All kinds of optimizations are possible, but let's not get carried away
160 // since this is probably a very uncommon thing in the big picture.
161 //
162 // N.B. Zero is a legal size for the alloc below even though a hardcoded zero
163 // would result in warning.
164 //
165 if (size != m_dataSize)
166 {
167 delete[] m_data;
168 m_data = new uint8_t[size];
169 m_dataSize = size;
170 }
171 data->CopyData(m_data, size);
172}
173
174uint16_t
176{
177 NS_LOG_FUNCTION(this);
178 return m_identifier;
179}
180
181uint16_t
183{
184 NS_LOG_FUNCTION(this);
185 return m_sequence;
186}
187
190{
191 NS_LOG_FUNCTION(this);
192 return m_dataSize;
193}
194
196Icmpv4Echo::GetData(uint8_t payload[]) const
197{
198 NS_LOG_FUNCTION(this << payload);
199 memcpy(payload, m_data, m_dataSize);
200 return m_dataSize;
201}
202
203TypeId
205{
206 static TypeId tid = TypeId("ns3::Icmpv4Echo")
207 .SetParent<Header>()
208 .SetGroupName("Internet")
209 .AddConstructor<Icmpv4Echo>();
210 return tid;
211}
212
214 : m_identifier(0),
215 m_sequence(0),
216 m_dataSize(0)
217{
218 NS_LOG_FUNCTION(this);
219 //
220 // After construction, m_data is always valid until destruction. This is true
221 // even if m_dataSize is zero.
222 //
223 m_data = new uint8_t[m_dataSize];
224}
225
227{
228 NS_LOG_FUNCTION(this);
229 delete[] m_data;
230 m_data = nullptr;
231 m_dataSize = 0;
232}
233
234TypeId
236{
237 NS_LOG_FUNCTION(this);
238 return GetTypeId();
239}
240
243{
244 NS_LOG_FUNCTION(this);
245 return 4 + m_dataSize;
246}
247
248void
250{
251 NS_LOG_FUNCTION(this << &start);
252 start.WriteHtonU16(m_identifier);
253 start.WriteHtonU16(m_sequence);
254 start.Write(m_data, m_dataSize);
255}
256
259{
260 NS_LOG_FUNCTION(this << &start);
261
262 uint32_t optionalPayloadSize = start.GetRemainingSize() - 4;
263 NS_ASSERT(start.GetRemainingSize() >= 4);
264
265 m_identifier = start.ReadNtohU16();
266 m_sequence = start.ReadNtohU16();
267 if (optionalPayloadSize != m_dataSize)
268 {
269 delete[] m_data;
270 m_dataSize = optionalPayloadSize;
271 m_data = new uint8_t[m_dataSize];
272 }
273 start.Read(m_data, m_dataSize);
274 return m_dataSize + 4;
275}
276
277void
278Icmpv4Echo::Print(std::ostream& os) const
279{
280 NS_LOG_FUNCTION(this << &os);
281 os << "identifier=" << m_identifier << ", sequence=" << m_sequence
282 << ", data size=" << m_dataSize;
283}
284
285/********************************************************
286 * Icmpv4DestinationUnreachable
287 ********************************************************/
288
290
291TypeId
293{
294 static TypeId tid = TypeId("ns3::Icmpv4DestinationUnreachable")
295 .SetParent<Header>()
296 .SetGroupName("Internet")
297 .AddConstructor<Icmpv4DestinationUnreachable>();
298 return tid;
299}
300
302{
303 NS_LOG_FUNCTION(this);
304 // make sure that thing is initialized to get initialized bytes
305 // when the ip payload's size is smaller than 8 bytes.
306 for (uint8_t j = 0; j < 8; j++)
307 {
308 m_data[j] = 0;
309 }
310}
311
312void
314{
315 NS_LOG_FUNCTION(this << mtu);
316 m_nextHopMtu = mtu;
317}
318
319uint16_t
325
326void
332
333void
335{
336 NS_LOG_FUNCTION(this << header);
337 m_header = header;
338}
339
340void
342{
343 NS_LOG_FUNCTION(this << payload);
344 memcpy(payload, m_data, 8);
345}
346
349{
350 NS_LOG_FUNCTION(this);
351 return m_header;
352}
353
357
358TypeId
364
371
372void
374{
375 NS_LOG_FUNCTION(this << &start);
376 start.WriteU16(0);
377 start.WriteHtonU16(m_nextHopMtu);
379 m_header.Serialize(start);
380 start.Next(size);
381 start.Write(m_data, 8);
382}
383
386{
387 NS_LOG_FUNCTION(this << &start);
388 Buffer::Iterator i = start;
389 i.Next(2);
391 uint32_t read = m_header.Deserialize(i);
392 i.Next(read);
393 for (uint8_t j = 0; j < 8; j++)
394 {
395 m_data[j] = i.ReadU8();
396 }
397 return i.GetDistanceFrom(start);
398}
399
400void
402{
403 NS_LOG_FUNCTION(this << &os);
404 m_header.Print(os);
405 os << " org data=";
406 for (uint8_t i = 0; i < 8; i++)
407 {
408 os << (uint32_t)m_data[i];
409 if (i != 8)
410 {
411 os << " ";
412 }
413 }
414}
415
416/********************************************************
417 * Icmpv4TimeExceeded
418 ********************************************************/
419
421
422TypeId
424{
425 static TypeId tid = TypeId("ns3::Icmpv4TimeExceeded")
426 .SetParent<Header>()
427 .SetGroupName("Internet")
428 .AddConstructor<Icmpv4TimeExceeded>();
429 return tid;
430}
431
433{
434 NS_LOG_FUNCTION(this);
435 // make sure that thing is initialized to get initialized bytes
436 // when the ip payload's size is smaller than 8 bytes.
437 for (uint8_t j = 0; j < 8; j++)
438 {
439 m_data[j] = 0;
440 }
441}
442
443void
449
450void
452{
453 NS_LOG_FUNCTION(this << header);
454 m_header = header;
455}
456
457void
458Icmpv4TimeExceeded::GetData(uint8_t payload[8]) const
459{
460 NS_LOG_FUNCTION(this << payload);
461 memcpy(payload, m_data, 8);
462}
463
466{
467 NS_LOG_FUNCTION(this);
468 return m_header;
469}
470
475
476TypeId
478{
479 NS_LOG_FUNCTION(this);
480 return GetTypeId();
481}
482
485{
486 NS_LOG_FUNCTION(this);
487 return 4 + m_header.GetSerializedSize() + 8;
488}
489
490void
492{
493 NS_LOG_FUNCTION(this << &start);
494 start.WriteU32(0);
496 m_header.Serialize(start);
497 start.Next(size);
498 start.Write(m_data, 8);
499}
500
503{
504 NS_LOG_FUNCTION(this << &start);
505 Buffer::Iterator i = start;
506 i.Next(4);
507 uint32_t read = m_header.Deserialize(i);
508 i.Next(read);
509 for (uint8_t j = 0; j < 8; j++)
510 {
511 m_data[j] = i.ReadU8();
512 }
513 return i.GetDistanceFrom(start);
514}
515
516void
517Icmpv4TimeExceeded::Print(std::ostream& os) const
518{
519 NS_LOG_FUNCTION(this << &os);
520 m_header.Print(os);
521 os << " org data=";
522 for (uint8_t i = 0; i < 8; i++)
523 {
524 os << (uint32_t)m_data[i];
525 if (i != 8)
526 {
527 os << " ";
528 }
529 }
530}
531
532} // namespace ns3
iterator in a Buffer instance
Definition buffer.h:89
uint16_t CalculateIpChecksum(uint16_t size)
Calculate the checksum.
Definition buffer.cc:1124
void WriteU8(uint8_t data)
Definition buffer.h:870
void WriteU16(uint16_t data)
Definition buffer.cc:848
void WriteHtonU16(uint16_t data)
Definition buffer.h:904
uint16_t ReadNtohU16()
Definition buffer.h:943
uint32_t GetDistanceFrom(const Iterator &o) const
Definition buffer.cc:769
uint32_t GetSize() const
Definition buffer.cc:1155
void Next()
go forward by one byte
Definition buffer.h:842
Protocol header serialization and deserialization.
Definition header.h:33
ICMP Destination Unreachable header.
Definition icmpv4.h:164
Ipv4Header m_header
carried IPv4 header
Definition icmpv4.h:229
uint16_t GetNextHopMtu() const
Get the next hop MTU.
Definition icmpv4.cc:320
uint16_t m_nextHopMtu
next hop MTU
Definition icmpv4.h:228
Ipv4Header GetHeader() const
Get the ICMP carried IPv4 header.
Definition icmpv4.cc:348
void GetData(uint8_t payload[8]) const
Get the ICMP carried data.
Definition icmpv4.cc:341
void SetNextHopMtu(uint16_t mtu)
Set the next hop MTU.
Definition icmpv4.cc:313
uint32_t Deserialize(Buffer::Iterator start) override
Definition icmpv4.cc:385
void Serialize(Buffer::Iterator start) const override
Definition icmpv4.cc:373
TypeId GetInstanceTypeId() const override
Get the most derived TypeId for this Object.
Definition icmpv4.cc:359
uint32_t GetSerializedSize() const override
Definition icmpv4.cc:366
void SetHeader(Ipv4Header header)
Set the ICMP carried IPv4 header.
Definition icmpv4.cc:334
void SetData(Ptr< const Packet > data)
Set the ICMP carried data.
Definition icmpv4.cc:327
static TypeId GetTypeId()
Get ICMP type.
Definition icmpv4.cc:292
uint8_t m_data[8]
carried data
Definition icmpv4.h:230
void Print(std::ostream &os) const override
Definition icmpv4.cc:401
ICMP Echo header.
Definition icmpv4.h:99
TypeId GetInstanceTypeId() const override
Get the most derived TypeId for this Object.
Definition icmpv4.cc:235
void Print(std::ostream &os) const override
Definition icmpv4.cc:278
uint16_t m_identifier
identifier
Definition icmpv4.h:152
uint16_t m_sequence
sequence number
Definition icmpv4.h:153
uint32_t GetData(uint8_t payload[]) const
Get the Echo data.
Definition icmpv4.cc:196
void SetIdentifier(uint16_t id)
Set the Echo identifier.
Definition icmpv4.cc:139
void SetData(Ptr< const Packet > data)
Set the Echo data.
Definition icmpv4.cc:153
uint32_t GetSerializedSize() const override
Definition icmpv4.cc:242
uint32_t Deserialize(Buffer::Iterator start) override
Definition icmpv4.cc:258
uint16_t GetIdentifier() const
Get the Echo identifier.
Definition icmpv4.cc:175
void Serialize(Buffer::Iterator start) const override
Definition icmpv4.cc:249
~Icmpv4Echo() override
Definition icmpv4.cc:226
static TypeId GetTypeId()
Get ICMP type.
Definition icmpv4.cc:204
uint8_t * m_data
data
Definition icmpv4.h:154
void SetSequenceNumber(uint16_t seq)
Set the Echo sequence number.
Definition icmpv4.cc:146
uint32_t GetDataSize() const
Get the Echo data size.
Definition icmpv4.cc:189
uint32_t m_dataSize
data size
Definition icmpv4.h:155
uint16_t GetSequenceNumber() const
Get the Echo sequence number.
Definition icmpv4.cc:182
Base class for all the ICMP packet headers.
Definition icmpv4.h:32
void SetCode(uint8_t code)
Set ICMP code.
Definition icmpv4.cc:112
TypeId GetInstanceTypeId() const override
Get the most derived TypeId for this Object.
Definition icmpv4.cc:56
uint32_t Deserialize(Buffer::Iterator start) override
Definition icmpv4.cc:88
bool m_calcChecksum
true if checksum is calculated
Definition icmpv4.h:90
void SetType(uint8_t type)
Set ICMP type.
Definition icmpv4.cc:105
uint8_t m_code
ICMP code.
Definition icmpv4.h:89
void EnableChecksum()
Enables ICMP Checksum calculation.
Definition icmpv4.cc:49
void Print(std::ostream &os) const override
Definition icmpv4.cc:98
uint8_t m_type
ICMP type.
Definition icmpv4.h:88
static TypeId GetTypeId()
Get the type ID.
Definition icmpv4.cc:26
uint8_t GetCode() const
Get ICMP code.
Definition icmpv4.cc:126
uint8_t GetType() const
Get ICMP type.
Definition icmpv4.cc:119
uint32_t GetSerializedSize() const override
Definition icmpv4.cc:63
~Icmpv4Header() override
Definition icmpv4.cc:43
void Serialize(Buffer::Iterator start) const override
Definition icmpv4.cc:70
ICMP Time Exceeded header.
Definition icmpv4.h:239
uint32_t Deserialize(Buffer::Iterator start) override
Definition icmpv4.cc:502
Ipv4Header m_header
carried IPv4 header
Definition icmpv4.h:286
Ipv4Header GetHeader() const
Get the ICMP carried IPv4 header.
Definition icmpv4.cc:465
void SetHeader(Ipv4Header header)
Set the ICMP carried IPv4 header.
Definition icmpv4.cc:451
uint32_t GetSerializedSize() const override
Definition icmpv4.cc:484
void GetData(uint8_t payload[8]) const
Get the ICMP carried data.
Definition icmpv4.cc:458
TypeId GetInstanceTypeId() const override
Get the most derived TypeId for this Object.
Definition icmpv4.cc:477
void Serialize(Buffer::Iterator start) const override
Definition icmpv4.cc:491
uint8_t m_data[8]
carried data
Definition icmpv4.h:287
static TypeId GetTypeId()
Get ICMP type.
Definition icmpv4.cc:423
void SetData(Ptr< const Packet > data)
Get the ICMP carried data.
Definition icmpv4.cc:444
~Icmpv4TimeExceeded() override
Definition icmpv4.cc:471
void Print(std::ostream &os) const override
Definition icmpv4.cc:517
Packet header for IPv4.
Definition ipv4-header.h:23
void Print(std::ostream &os) const override
void Serialize(Buffer::Iterator start) const override
uint32_t GetSerializedSize() const override
uint32_t Deserialize(Buffer::Iterator start) override
Smart pointer class similar to boost::intrusive_ptr.
a unique identifier for an interface.
Definition type-id.h:48
TypeId SetParent(TypeId tid)
Set the parent TypeId.
Definition type-id.cc:1001
#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_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition log.h:191
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by ",...
#define NS_OBJECT_ENSURE_REGISTERED(type)
Register an Object subclass with the TypeId system.
Definition object-base.h:35
Every class exported by the ns3 library is enclosed in the ns3 namespace.
uint8_t data[writeSize]