A Discrete-Event Network Simulator
API
tcp-bic-test.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2015 Natale Patriciello, <natale.patriciello@gmail.com>
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License version 2 as
7  * published by the Free Software Foundation;
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17  *
18  */
19 
20 #include "ns3/test.h"
21 #include "ns3/log.h"
22 #include "ns3/tcp-congestion-ops.h"
23 #include "ns3/tcp-socket-base.h"
24 #include "ns3/tcp-bic.h"
25 
26 using namespace ns3;
27 
28 NS_LOG_COMPONENT_DEFINE ("TcpBicTestSuite");
29 
37 {
38 public:
48  TcpBicIncrementTest (uint32_t cWnd,
49  uint32_t segmentSize,
50  uint32_t ssThresh,
51  uint32_t segmentsAcked,
52  uint32_t lastMaxCwnd,
53  const std::string &name);
54 
55 private:
56  virtual void DoRun (void);
57 
63  uint32_t Update (Ptr<TcpSocketState> tcb);
64 
68  void ExecuteTest (void);
69 
70  uint32_t m_cWnd;
71  uint32_t m_segmentSize;
72  uint32_t m_ssThresh;
73  uint32_t m_segmentsAcked;
74  uint32_t m_lastMaxCwnd;
76 };
77 
79  uint32_t segmentSize,
80  uint32_t ssThresh,
81  uint32_t segmentsAcked,
82  uint32_t lastMaxCwnd,
83  const std::string &name)
84  : TestCase (name),
85  m_cWnd (cWnd),
86  m_segmentSize (segmentSize),
87  m_ssThresh (ssThresh),
88  m_segmentsAcked (segmentsAcked),
89  m_lastMaxCwnd (lastMaxCwnd)
90 {
91 }
92 
93 void
95 {
96  m_state = CreateObject<TcpSocketState> ();
97 
101 
102  Simulator::Schedule (Seconds (0.0), &TcpBicIncrementTest::ExecuteTest, this);
103  Simulator::Run ();
104  Simulator::Destroy ();
105 }
106 
107 void
109 {
110  uint32_t segCwnd = m_cWnd / m_segmentSize;
111 
112  uint32_t ackCnt = Update (m_state);
113 
114  if (m_segmentsAcked > ackCnt)
115  {
117  "Bic has not increment cWnd");
118  /* NS_TEST_ASSERT_MSG_EQ (m_state->m_cWnd.Get (), 27000,
119  "Bic has not increment cWnd");*/
120  }
121  else
122  {
124  "Bic has modified cWnd");
125  }
126 }
127 
128 uint32_t
130 {
131  uint32_t segCwnd = tcb->m_cWnd / tcb->m_segmentSize;
132  Ptr<TcpBic> cong = CreateObject <TcpBic> ();
134  UintegerValue lowWindow, bsCoeff, wMax;
135  UintegerValue smoothPart;
136  cong->GetAttribute ("LowWnd", lowWindow);
137  cong->GetAttribute ("BinarySearchCoefficient", bsCoeff);
138  cong->GetAttribute ("MaxIncr", wMax);
139  cong->GetAttribute ("SmoothPart", smoothPart);
140 
142 
143  uint32_t ackCnt = 0;
144 
145  if (segCwnd < lowWindow.Get ())
146  {
147  ackCnt = segCwnd;
148  return ackCnt;
149  }
150  if (segCwnd < m_lastMaxCwnd)
151  {
152  double midPt = (m_lastMaxCwnd - segCwnd) / bsCoeff.Get ();
153  if (midPt > wMax.Get ())
154  {
155  //Linear increase
156  ackCnt = segCwnd / wMax.Get ();
157  }
158  else if (midPt <= 1)
159  {
160  ackCnt = (segCwnd * smoothPart.Get ()) / bsCoeff.Get ();
161  }
162  else
163  {
164  //Binary search increase
165  ackCnt = segCwnd / midPt;
166  }
167  }
168  else
169  {
170  if (segCwnd < m_lastMaxCwnd + bsCoeff.Get ())
171  {
172  /* slow start AMD linear increase */
173  ackCnt = (segCwnd * smoothPart.Get ()) / bsCoeff.Get ();
174  }
175  else if (segCwnd < m_lastMaxCwnd + wMax.Get () * (bsCoeff.Get () - 1))
176  {
177  /* slow start */
178  ackCnt = (segCwnd * (bsCoeff.Get () - 1)) / (segCwnd - m_lastMaxCwnd);
179  }
180  else
181  {
182  /* linear increase */
183  ackCnt = segCwnd / wMax.Get ();
184 
185  }
186  }
187  return ackCnt;
188 
189 }
190 
198 {
199 public:
208  TcpBicDecrementTest (uint32_t cWnd,
209  uint32_t segmentSize,
210  BooleanValue fastConvergence,
211  uint32_t lastMaxCwnd,
212  const std::string &name);
213 
214 private:
215  virtual void DoRun (void);
216 
220  void ExecuteTest (void);
221 
222  uint32_t m_cWnd;
223  uint32_t m_segmentSize;
225  uint32_t m_lastMaxCwnd;
227 };
228 
230  uint32_t segmentSize,
231  BooleanValue fastConvergence,
232  uint32_t lastMaxCwnd,
233  const std::string &name)
234  : TestCase (name),
235  m_cWnd (cWnd),
236  m_segmentSize (segmentSize),
237  m_fastConvergence (fastConvergence),
238  m_lastMaxCwnd (lastMaxCwnd)
239 {
240 }
241 
242 void
244 {
245  m_state = CreateObject<TcpSocketState> ();
246 
247  m_state->m_cWnd = m_cWnd;
249 
250  Simulator::Schedule (Seconds (0.0), &TcpBicDecrementTest::ExecuteTest, this);
251  Simulator::Run ();
252  Simulator::Destroy ();
253 }
254 
255 void
257 {
258  Ptr<TcpBic> cong = CreateObject <TcpBic> ();
260  cong->SetAttribute ("FastConvergence", m_fastConvergence);
261 
262  uint32_t segCwnd = m_cWnd / m_segmentSize;
263  uint32_t retSsThresh = cong->GetSsThresh (m_state, m_state->m_cWnd);
264  uint32_t retLastMaxCwnd = cong->m_lastMaxCwnd;
265 
266  DoubleValue beta;
267  UintegerValue lowWindow;
268  cong->GetAttribute ("Beta", beta);
269  cong->GetAttribute ("LowWnd", lowWindow);
270 
271  uint32_t lastMaxCwnd, ssThresh;
272 
273  if (segCwnd < m_lastMaxCwnd && m_fastConvergence.Get ())
274  {
275  lastMaxCwnd = beta.Get () * segCwnd;
276  NS_TEST_ASSERT_MSG_EQ (retLastMaxCwnd, lastMaxCwnd,
277  "Bic has not updated lastMaxCwnd during fast convergence");
278  }
279  else
280  {
281  lastMaxCwnd = segCwnd;
282  NS_TEST_ASSERT_MSG_EQ (retLastMaxCwnd, lastMaxCwnd,
283  "Bic has not reset lastMaxCwnd to current cwnd (in segments)");
284  }
285 
286 
287  if (segCwnd < lowWindow.Get ())
288  {
289  ssThresh = std::max (2 * m_segmentSize, m_cWnd / 2);
290  NS_TEST_ASSERT_MSG_EQ (retSsThresh, ssThresh,
291  "Bic has not updated ssThresh when cWnd less than lowWindow");
292  }
293  else
294  {
295  ssThresh = std::max (segCwnd * beta.Get (), 2.0) * m_segmentSize;
296  NS_TEST_ASSERT_MSG_EQ (retSsThresh, ssThresh,
297  "Bic has not updated ssThresh when cWnd greater than lowWindow");
298  }
299 }
300 
301 
309 {
310 public:
311  TcpBicTestSuite () : TestSuite ("tcp-bic-test", UNIT)
312  {
313  AddTestCase (new TcpBicIncrementTest (10 * 536, 536, 9 * 536, 11, 0,
314  "Bic increment test: under lowCwnd & enough ACKs received"),
315  TestCase::QUICK);
316  AddTestCase (new TcpBicIncrementTest (10 * 536, 536, 9 * 536, 8, 0,
317  "Bic increment test: under lowCwnd but not enough ACKs received"),
318  TestCase::QUICK);
319  AddTestCase (new TcpBicIncrementTest (18 * 1446, 1446, 15 * 1446, 5, 90,
320  "Bic increment test: linear increase when distance exceeds S_max"),
321  TestCase::QUICK);
322  AddTestCase (new TcpBicIncrementTest (18 * 1446, 1446, 15 * 1446, 24, 20,
323  "Bic increment test: binary search increase with smooth part"),
324  TestCase::QUICK);
325  AddTestCase (new TcpBicIncrementTest (19 * 1, 1, 17 * 1, 2, 83,
326  "Bic increment test: binary search increase"),
327  TestCase::QUICK);
328  AddTestCase (new TcpBicIncrementTest (15 * 536, 536, 9 * 536, 19, 13,
329  "Bic increment test: slow start AMD linear increase"),
330  TestCase::QUICK);
331  AddTestCase (new TcpBicIncrementTest (22 * 1000, 1000, 9 * 1000, 9, 16,
332  "Bic increment test: slow start but not enough ACKs received"),
333  TestCase::QUICK);
334  AddTestCase (new TcpBicIncrementTest (65 * 1000, 1000, 9 * 1000, 2, 16,
335  "Bic increment test: linear incrase but not enough ACKs received"),
336  TestCase::QUICK);
337 
338  AddTestCase (new TcpBicDecrementTest (5 * 1446, 1446, true, 10,
339  "Bic decrement test: fast convergence & cwnd less than lowWindow"),
340  TestCase::QUICK);
341  AddTestCase (new TcpBicDecrementTest (5 * 1446, 1446, false, 10,
342  "Bic decrement test: not in fast convergence & cwnd less than lowWindow"),
343  TestCase::QUICK);
344  AddTestCase (new TcpBicDecrementTest (15 * 1446, 1446, false, 10,
345  "Bic decrement test: not in fast convergence & cwnd greater than lowWindow"),
346  TestCase::QUICK);
347  }
348 };
349 
void ExecuteTest(void)
Execute the test.
AttributeValue implementation for Boolean.
Definition: boolean.h:36
virtual void DoRun(void)
Implementation to actually run this TestCase.
Definition: tcp-bic-test.cc:94
A suite of tests to run.
Definition: test.h:1343
uint32_t m_lastMaxCwnd
Last maximum cWnd.
Definition: tcp-bic.h:138
uint32_t Update(Ptr< TcpSocketState > tcb)
Update the TCP socket state.
uint32_t segmentSize
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:205
uint32_t m_segmentSize
Segment size.
TcpBicDecrementTest(uint32_t cWnd, uint32_t segmentSize, BooleanValue fastConvergence, uint32_t lastMaxCwnd, const std::string &name)
Constructor.
uint32_t m_cWnd
Congestion window.
encapsulates test code
Definition: test.h:1153
virtual void DoRun(void)
Implementation to actually run this TestCase.
uint32_t m_cWnd
Congestion window.
Definition: tcp-bic-test.cc:70
virtual uint32_t GetSsThresh(Ptr< const TcpSocketState > tcb, uint32_t bytesInFlight)
Get the slow start threshold after a loss event.
Definition: tcp-bic.cc:239
static TcpBicTestSuite g_tcpBicTest
Static variable for test initialization.
#define max(a, b)
Definition: 80211b.c:43
void AddTestCase(TestCase *testCase, TestDuration duration=QUICK)
Add an individual child TestCase to this test suite.
Definition: test.cc:299
TCP Bic TestSuite.
uint32_t m_ssThresh
Slow Start Threshold.
Definition: tcp-bic-test.cc:72
Testing the congestion avoidance increment on TcpBic.
Definition: tcp-bic-test.cc:36
Hold an unsigned integer type.
Definition: uinteger.h:44
#define NS_TEST_ASSERT_MSG_EQ(actual, limit, msg)
Test that an actual and expected (limit) value are equal and report and abort if not.
Definition: test.h:166
TcpBicIncrementTest(uint32_t cWnd, uint32_t segmentSize, uint32_t ssThresh, uint32_t segmentsAcked, uint32_t lastMaxCwnd, const std::string &name)
Constructor.
Definition: tcp-bic-test.cc:78
uint32_t m_segmentSize
Segment size.
Definition: tcp-bic-test.cc:71
TracedValue< uint32_t > m_ssThresh
Slow start threshold.
bool Get(void) const
Definition: boolean.cc:51
uint64_t Get(void) const
Definition: uinteger.cc:35
double Get(void) const
Definition: double.cc:35
uint32_t m_segmentSize
Segment size.
Every class exported by the ns3 library is enclosed in the ns3 namespace.
uint32_t m_lastMaxCwnd
Last max Cwnd.
Definition: tcp-bic-test.cc:74
Testing the congestion avoidance decrement on TcpBic.
TracedValue< uint32_t > m_cWnd
Congestion window.
void ExecuteTest(void)
Execute the test.
virtual void IncreaseWindow(Ptr< TcpSocketState > tcb, uint32_t segmentsAcked)
Congestion avoidance algorithm implementation.
Definition: tcp-bic.cc:96
T Get(void) const
Get the underlying value.
Definition: traced-value.h:229
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1289
uint32_t m_segmentsAcked
Number of segments acked.
Definition: tcp-bic-test.cc:73
Ptr< TcpSocketState > m_state
TCP socket state.
uint32_t m_lastMaxCwnd
Last max Cwnd.
This test suite implements a Unit Test.
Definition: test.h:1353
This class can be used to hold variables of floating point type such as &#39;double&#39; or &#39;float&#39;...
Definition: double.h:41
void SetAttribute(std::string name, const AttributeValue &value)
Set a single attribute, raising fatal errors if unsuccessful.
Definition: object-base.cc:185
BooleanValue m_fastConvergence
Fast convergence.
void GetAttribute(std::string name, AttributeValue &value) const
Get the value of an attribute, raising fatal errors if unsuccessful.
Definition: object-base.cc:223
Ptr< TcpSocketState > m_state
TCP socket state.
Definition: tcp-bic-test.cc:75