A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
tcp-option-sack.cc
Go to the documentation of this file.
1/*
2 * Copyright (c) 2011 Adrian Sai-wah Tam
3 * Copyright (c) 2015 ResiliNets, ITTC, University of Kansas
4 *
5 * SPDX-License-Identifier: GPL-2.0-only
6 *
7 * Original Author: Adrian Sai-wah Tam <adrian.sw.tam@gmail.com>
8 * Documentation, test cases: Truc Anh N. Nguyen <annguyen@ittc.ku.edu>
9 * ResiliNets Research Group https://resilinets.org/
10 * The University of Kansas
11 * James P.G. Sterbenz <jpgs@ittc.ku.edu>, director
12 */
13
14#include "tcp-option-sack.h"
15
16#include "ns3/log.h"
17
18namespace ns3
19{
20
21NS_LOG_COMPONENT_DEFINE("TcpOptionSack");
22
23NS_OBJECT_ENSURE_REGISTERED(TcpOptionSack);
24
29
33
36{
37 static TypeId tid = TypeId("ns3::TcpOptionSack")
39 .SetGroupName("Internet")
40 .AddConstructor<TcpOptionSack>();
41 return tid;
42}
43
46{
47 return GetTypeId();
48}
49
50void
51TcpOptionSack::Print(std::ostream& os) const
52{
53 os << "blocks: " << GetNumSackBlocks() << ",";
54 for (auto it = m_sackList.begin(); it != m_sackList.end(); ++it)
55 {
56 os << "[" << it->first << "," << it->second << "]";
57 }
58}
59
62{
63 NS_LOG_FUNCTION(this);
64 NS_LOG_LOGIC("Serialized size: " << 2 + GetNumSackBlocks() * 8);
65 return 2 + GetNumSackBlocks() * 8;
66}
67
68void
70{
71 NS_LOG_FUNCTION(this);
72 Buffer::Iterator i = start;
73 i.WriteU8(GetKind()); // Kind
74 auto length = static_cast<uint8_t>(GetNumSackBlocks() * 8 + 2);
75 i.WriteU8(length); // Length
76
77 for (auto it = m_sackList.begin(); it != m_sackList.end(); ++it)
78 {
79 SequenceNumber32 leftEdge = it->first;
80 SequenceNumber32 rightEdge = it->second;
81 i.WriteHtonU32(leftEdge.GetValue()); // Left edge of the block
82 i.WriteHtonU32(rightEdge.GetValue()); // Right edge of the block
83 }
84}
85
88{
89 NS_LOG_FUNCTION(this);
90 Buffer::Iterator i = start;
91 uint8_t readKind = i.ReadU8();
92 if (readKind != GetKind())
93 {
94 NS_LOG_WARN("Malformed SACK option, wrong type");
95 return 0;
96 }
97
98 uint8_t size = i.ReadU8();
99 NS_LOG_LOGIC("Size: " << static_cast<uint32_t>(size));
100 m_sackList.clear();
101 uint8_t sackCount = (size - 2) / 8;
102 while (sackCount)
103 {
104 SequenceNumber32 leftEdge(i.ReadNtohU32());
105 SequenceNumber32 rightEdge(i.ReadNtohU32());
106 SackBlock s(leftEdge, rightEdge);
107 AddSackBlock(s);
108 sackCount--;
109 }
110
111 return GetSerializedSize();
112}
113
114uint8_t
116{
117 return TcpOption::SACK;
118}
119
120void
122{
123 NS_LOG_FUNCTION(this);
124 m_sackList.push_back(s);
125}
126
129{
130 NS_LOG_FUNCTION(this);
131 NS_LOG_LOGIC("Number of SACK blocks appended: " << m_sackList.size());
132 return static_cast<uint32_t>(m_sackList.size());
133}
134
135void
140
143{
144 NS_LOG_FUNCTION(this);
145 return m_sackList;
146}
147
148std::ostream&
149operator<<(std::ostream& os, const TcpOptionSack& sackOption)
150{
151 std::stringstream ss;
152 ss << "{";
153 for (auto it = sackOption.m_sackList.begin(); it != sackOption.m_sackList.end(); ++it)
154 {
155 ss << *it;
156 }
157 ss << "}";
158 os << ss.str();
159 return os;
160}
161
162std::ostream&
163operator<<(std::ostream& os, const TcpOptionSack::SackBlock& sackBlock)
164{
165 std::stringstream ss;
166 ss << "[" << sackBlock.first << ";" << sackBlock.second << "]";
167 os << ss.str();
168 return os;
169}
170
171} // namespace ns3
iterator in a Buffer instance
Definition buffer.h:89
void WriteU8(uint8_t data)
Definition buffer.h:870
uint32_t ReadNtohU32()
Definition buffer.h:967
void WriteHtonU32(uint32_t data)
Definition buffer.h:922
NUMERIC_TYPE GetValue() const
Extracts the numeric value of the sequence number.
Base class for all kinds of TCP options.
Definition tcp-option.h:27
Defines the TCP option of kind 5 (selective acknowledgment option) as in RFC 2018
void ClearSackList()
Clear the SACK list.
std::list< SackBlock > SackList
SACK list definition.
uint32_t GetNumSackBlocks() const
Count the total number of SACK blocks.
uint8_t GetKind() const override
Get the ‘kind’ (as in RFC 793 ) of this option.
void Print(std::ostream &os) const override
Print the Option contents.
void Serialize(Buffer::Iterator start) const override
Serialize the Option to a buffer iterator.
std::pair< SequenceNumber32, SequenceNumber32 > SackBlock
SACK block definition.
TypeId GetInstanceTypeId() const override
Get the most derived TypeId for this Object.
static TypeId GetTypeId()
Get the type ID.
void AddSackBlock(SackBlock s)
Add a SACK block.
uint32_t Deserialize(Buffer::Iterator start) override
Deserialize the Option from a buffer iterator.
uint32_t GetSerializedSize() const override
Returns number of bytes required for Option serialization.
SackList m_sackList
the list of SACK blocks
SackList GetSackList() const
Get the SACK list.
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_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition log.h:191
#define NS_LOG_LOGIC(msg)
Use NS_LOG to output a message of level LOG_LOGIC.
Definition log.h:271
#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:250
#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.
std::ostream & operator<<(std::ostream &os, const Angles &a)
Definition angles.cc:148