1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3 * Copyright (c) 2009, 2010 MIRKO BANCHI
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 * Author: Mirko Banchi <mk.banchi@gmail.com>
19 */
20
21 #include "ns3/test.h"
22 #include "ns3/string.h"
23 #include "ns3/qos-utils.h"
24 #include "ns3/ctrl-headers.h"
25 #include "ns3/packet.h"
26 #include "ns3/wifi-net-device.h"
27 #include "ns3/ap-wifi-mac.h"
28 #include "ns3/wifi-mac-header.h"
29 #include "ns3/mobility-helper.h"
30 #include "ns3/yans-wifi-helper.h"
31 #include "ns3/packet-socket-server.h"
32 #include "ns3/packet-socket-client.h"
33 #include "ns3/packet-socket-helper.h"
34 #include "ns3/config.h"
35 #include "ns3/pointer.h"
36 #include "ns3/recipient-block-ack-agreement.h"
37 #include "ns3/mac-rx-middle.h"
38 #include <list>
39
40 using namespace ns3;
41
42 /**
43 * \ingroup wifi-test
44 * \ingroup tests
45 *
46 * \brief Packet Buffering Case A
47 *
48 * This simple test verifies the correctness of buffering for packets received
49 * under block ack. In order to completely understand this example is important to cite
50 * section 9.10.3 in IEEE802.11 standard:
51 *
52 * "[...] The sequence number space is considered divided into two parts, one of which
53 * is “old” and one of which is “new” by means of a boundary created by adding half the
54 * sequence number range to the current start of receive window (modulo 2^12)."
55 */
56 //-------------------------------------------------------------------------------------
57
58 /* ----- = old packets
59 * +++++ = new packets
60 *
61 * CASE A: startSeq < endSeq
62 * - - +
63 * initial buffer state: 0 16 56000
64 *
65 *
66 * 0 4095
67 * |------|++++++++++++++++|-----|
68 * ^ ^
69 * | startSeq | endSeq = 4000
70 *
71 * first received packet's sequence control = 64016 (seqNum = 4001, fragNum = 0) -
72 * second received packet's sequence control = 63984 (seqNum = 3999, fragNum = 0) +
73 * 4001 is older seq number so this packet should be inserted at the buffer's begin.
74 * 3999 is previous element of older of new packets: it should be inserted at the end of buffer.
75 *
76 * expected buffer state: 64016 0 16 56000 63984
77 *
78 */
79 class PacketBufferingCaseA : public TestCase
80 {
81 public:
82 PacketBufferingCaseA ();
83 virtual ~PacketBufferingCaseA ();
84 private:
85 void DoRun (void) override;
86 std::list<uint16_t> m_expectedBuffer; ///< expected test buffer
87 };
88
PacketBufferingCaseA()89 PacketBufferingCaseA::PacketBufferingCaseA ()
90 : TestCase ("Check correct order of buffering when startSequence < endSeq")
91 {
92 m_expectedBuffer.push_back (64016);
93 m_expectedBuffer.push_back (0);
94 m_expectedBuffer.push_back (16);
95 m_expectedBuffer.push_back (56000);
96 m_expectedBuffer.push_back (63984);
97 }
98
~PacketBufferingCaseA()99 PacketBufferingCaseA::~PacketBufferingCaseA ()
100 {
101 }
102
103 void
DoRun(void)104 PacketBufferingCaseA::DoRun (void)
105 {
106 std::list<uint16_t> m_buffer;
107 std::list<uint16_t>::iterator i,j;
108 m_buffer.push_back (0);
109 m_buffer.push_back (16);
110 m_buffer.push_back (56000);
111
112 uint16_t endSeq = 4000;
113
114 uint16_t receivedSeq = 4001 * 16;
115 uint32_t mappedSeq = QosUtilsMapSeqControlToUniqueInteger (receivedSeq, endSeq);
116 /* cycle to right position for this packet */
117 for (i = m_buffer.begin (); i != m_buffer.end (); i++)
118 {
119 if (QosUtilsMapSeqControlToUniqueInteger ((*i), endSeq) >= mappedSeq)
120 {
121 //position found
122 break;
123 }
124 }
125 m_buffer.insert (i, receivedSeq);
126
127 receivedSeq = 3999 * 16;
128 mappedSeq = QosUtilsMapSeqControlToUniqueInteger (receivedSeq, endSeq);
129 /* cycle to right position for this packet */
130 for (i = m_buffer.begin (); i != m_buffer.end (); i++)
131 {
132 if (QosUtilsMapSeqControlToUniqueInteger ((*i), endSeq) >= mappedSeq)
133 {
134 //position found
135 break;
136 }
137 }
138 m_buffer.insert (i, receivedSeq);
139
140 for (i = m_buffer.begin (), j = m_expectedBuffer.begin (); i != m_buffer.end (); i++, j++)
141 {
142 NS_TEST_EXPECT_MSG_EQ (*i, *j, "error in buffer order");
143 }
144 }
145
146
147 /**
148 * \ingroup wifi-test
149 * \ingroup tests
150 *
151 * \brief Packet Buffering Case B
152 *
153 * ----- = old packets
154 * +++++ = new packets
155 *
156 * CASE B: startSeq > endSeq
157 * - + +
158 * initial buffer state: 256 64000 16
159 *
160 *
161 * 0 4095
162 * |++++++|----------------|++++++|
163 * ^ ^
164 * | endSeq = 10 | startSeq
165 *
166 * first received packet's sequence control = 240 (seqNum = 15, fragNum = 0) -
167 * second received packet's sequence control = 241 (seqNum = 15, fragNum = 1) -
168 * third received packet's sequence control = 64800 (seqNum = 4050, fragNum = 0) +
169 * 240 is an old packet should be inserted at the buffer's begin.
170 * 241 is an old packet: second segment of the above packet.
171 * 4050 is a new packet: it should be inserted between 64000 and 16.
172 *
173 * expected buffer state: 240 241 256 64000 64800 16
174 *
175 */
176 class PacketBufferingCaseB : public TestCase
177 {
178 public:
179 PacketBufferingCaseB ();
180 virtual ~PacketBufferingCaseB ();
181 private:
182 void DoRun (void) override;
183 std::list<uint16_t> m_expectedBuffer; ///< expected test buffer
184 };
185
PacketBufferingCaseB()186 PacketBufferingCaseB::PacketBufferingCaseB ()
187 : TestCase ("Check correct order of buffering when startSequence > endSeq")
188 {
189 m_expectedBuffer.push_back (240);
190 m_expectedBuffer.push_back (241);
191 m_expectedBuffer.push_back (256);
192 m_expectedBuffer.push_back (64000);
193 m_expectedBuffer.push_back (64800);
194 m_expectedBuffer.push_back (16);
195 }
196
~PacketBufferingCaseB()197 PacketBufferingCaseB::~PacketBufferingCaseB ()
198 {
199 }
200
201 void
DoRun(void)202 PacketBufferingCaseB::DoRun (void)
203 {
204 std::list<uint16_t> m_buffer;
205 std::list<uint16_t>::iterator i,j;
206 m_buffer.push_back (256);
207 m_buffer.push_back (64000);
208 m_buffer.push_back (16);
209
210 uint16_t endSeq = 10;
211
212 uint16_t receivedSeq = 15 * 16;
213 uint32_t mappedSeq = QosUtilsMapSeqControlToUniqueInteger (receivedSeq, endSeq);
214 /* cycle to right position for this packet */
215 for (i = m_buffer.begin (); i != m_buffer.end (); i++)
216 {
217 if (QosUtilsMapSeqControlToUniqueInteger ((*i), endSeq) >= mappedSeq)
218 {
219 //position found
220 break;
221 }
222 }
223 m_buffer.insert (i, receivedSeq);
224
225 receivedSeq = 15 * 16 + 1;
226 mappedSeq = QosUtilsMapSeqControlToUniqueInteger (receivedSeq, endSeq);
227 /* cycle to right position for this packet */
228 for (i = m_buffer.begin (); i != m_buffer.end (); i++)
229 {
230 if (QosUtilsMapSeqControlToUniqueInteger ((*i), endSeq) >= mappedSeq)
231 {
232 //position found
233 break;
234 }
235 }
236 m_buffer.insert (i, receivedSeq);
237
238 receivedSeq = 4050 * 16;
239 mappedSeq = QosUtilsMapSeqControlToUniqueInteger (receivedSeq, endSeq);
240 /* cycle to right position for this packet */
241 for (i = m_buffer.begin (); i != m_buffer.end (); i++)
242 {
243 if (QosUtilsMapSeqControlToUniqueInteger ((*i), endSeq) >= mappedSeq)
244 {
245 //position found
246 break;
247 }
248 }
249 m_buffer.insert (i, receivedSeq);
250
251 for (i = m_buffer.begin (), j = m_expectedBuffer.begin (); i != m_buffer.end (); i++, j++)
252 {
253 NS_TEST_EXPECT_MSG_EQ (*i, *j, "error in buffer order");
254 }
255 }
256
257 /**
258 * \ingroup wifi-test
259 * \ingroup tests
260 *
261 * \brief Test for the originator block ack window
262 */
263 class OriginatorBlockAckWindowTest : public TestCase
264 {
265 public:
266 OriginatorBlockAckWindowTest ();
267 private:
268 void DoRun (void) override;
269 };
270
OriginatorBlockAckWindowTest()271 OriginatorBlockAckWindowTest::OriginatorBlockAckWindowTest ()
272 : TestCase ("Check the correctness of the originator block ack window")
273 {
274 }
275
276 void
DoRun(void)277 OriginatorBlockAckWindowTest::DoRun (void)
278 {
279 uint16_t winSize = 16;
280 uint16_t startingSeq = 4090;
281
282 OriginatorBlockAckAgreement agreement (Mac48Address ("00:00:00:00:00:01"), 0);
283 agreement.SetBufferSize (winSize);
284 agreement.SetStartingSequence (startingSeq);
285 agreement.InitTxWindow ();
286
287 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.GetWinSize (), winSize, "Incorrect window size");
288 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.GetWinStart (), startingSeq, "Incorrect winStart");
289 // check that all the elements in the window are cleared
290 for (uint16_t i = 0; i < winSize; i++)
291 {
292 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Not all flags are cleared after initialization");
293 }
294
295 // Notify the acknowledgment of 5 packets
296 WifiMacHeader hdr;
297 hdr.SetType (WIFI_MAC_QOSDATA);
298 Ptr<WifiMacQueueItem> mpdu = Create<WifiMacQueueItem> (Create<Packet> (), hdr);
299 uint16_t seqNumber = startingSeq;
300 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
301 agreement.NotifyAckedMpdu (mpdu);
302
303 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
304 agreement.NotifyAckedMpdu (mpdu);
305
306 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
307 agreement.NotifyAckedMpdu (mpdu);
308
309 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
310 agreement.NotifyAckedMpdu (mpdu);
311
312 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
313 agreement.NotifyAckedMpdu (mpdu);
314
315 // the current window must look like this:
316 //
317 // |0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|
318 // ^
319 // |
320 // HEAD
321
322 startingSeq = (seqNumber + 1) % SEQNO_SPACE_SIZE;
323 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq, "Incorrect starting sequence after 5 acknowledgments");
324 for (uint16_t i = 0; i < winSize; i++)
325 {
326 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Not all flags are cleared after 5 acknowledgments");
327 }
328
329 // the next MPDU is not acknowledged, hence the window is blocked while the
330 // subsequent 4 MPDUs are acknowledged
331 ++seqNumber %= SEQNO_SPACE_SIZE;
332 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
333 agreement.NotifyAckedMpdu (mpdu);
334
335 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
336 agreement.NotifyAckedMpdu (mpdu);
337
338 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
339 agreement.NotifyAckedMpdu (mpdu);
340
341 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
342 agreement.NotifyAckedMpdu (mpdu);
343
344 // the current window must look like this:
345 //
346 // |0|0|0|0|0|0|1|1|1|1|0|0|0|0|0|0|
347 // ^
348 // |
349 // HEAD
350
351 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq, "Incorrect starting sequence after 1 unacknowledged MPDU");
352 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (0), false, "Incorrect flag after 1 unacknowledged MPDU");
353 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (1), true, "Incorrect flag after 1 unacknowledged MPDU");
354 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (2), true, "Incorrect flag after 1 unacknowledged MPDU");
355 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (3), true, "Incorrect flag after 1 unacknowledged MPDU");
356 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (4), true, "Incorrect flag after 1 unacknowledged MPDU");
357 for (uint16_t i = 5; i < winSize; i++)
358 {
359 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after 1 unacknowledged MPDU");
360 }
361
362 // the missing MPDU is now acknowledged; the window moves forward and the starting
363 // sequence number is the one of the first unacknowledged MPDU
364 mpdu->GetHeader ().SetSequenceNumber (startingSeq);
365 agreement.NotifyAckedMpdu (mpdu);
366
367 // the current window must look like this:
368 //
369 // |0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|
370 // ^
371 // |
372 // HEAD
373
374 startingSeq = (seqNumber + 1) % SEQNO_SPACE_SIZE;
375 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq, "Incorrect starting sequence after acknowledgment of missing MPDU");
376 for (uint16_t i = 0; i < winSize; i++)
377 {
378 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Not all flags are cleared after acknowledgment of missing MPDU");
379 }
380
381 // Now, create a hole of 3 MPDUs before 4 acknowledged MPDUs, another hole of 2 MPDUs before 3 acknowledged MPDUs
382 seqNumber = (seqNumber + 4) % SEQNO_SPACE_SIZE;
383 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
384 agreement.NotifyAckedMpdu (mpdu);
385
386 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
387 agreement.NotifyAckedMpdu (mpdu);
388
389 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
390 agreement.NotifyAckedMpdu (mpdu);
391
392 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
393 agreement.NotifyAckedMpdu (mpdu);
394
395 seqNumber = (seqNumber + 3) % SEQNO_SPACE_SIZE;
396 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
397 agreement.NotifyAckedMpdu (mpdu);
398
399 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
400 agreement.NotifyAckedMpdu (mpdu);
401
402 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
403 agreement.NotifyAckedMpdu (mpdu);
404
405 // the current window must look like this:
406 //
407 // |1|0|0|1|1|1|0|0|0|0|0|0|0|1|1|1|
408 // ^
409 // |
410 // HEAD
411
412 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq, "Incorrect starting sequence after 3 unacknowledged MPDUs");
413 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (0), false, "Incorrect flag after 3 unacknowledged MPDUs");
414 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (1), false, "Incorrect flag after 3 unacknowledged MPDUs");
415 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (2), false, "Incorrect flag after 3 unacknowledged MPDUs");
416 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (3), true, "Incorrect flag after 3 unacknowledged MPDUs");
417 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (4), true, "Incorrect flag after 3 unacknowledged MPDUs");
418 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (5), true, "Incorrect flag after 3 unacknowledged MPDUs");
419 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (6), true, "Incorrect flag after 3 unacknowledged MPDUs");
420 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (7), false, "Incorrect flag after 3 unacknowledged MPDUs");
421 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (8), false, "Incorrect flag after 3 unacknowledged MPDUs");
422 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (9), true, "Incorrect flag after 3 unacknowledged MPDUs");
423 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (10), true, "Incorrect flag after 3 unacknowledged MPDUs");
424 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (11), true, "Incorrect flag after 3 unacknowledged MPDUs");
425 for (uint16_t i = 12; i < winSize; i++)
426 {
427 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after 3 unacknowledged MPDUs");
428 }
429
430 // the transmission of an MPDU beyond the current window (by 2 positions) is
431 // notified, hence the window moves forward 2 positions
432 seqNumber = (agreement.m_txWindow.GetWinEnd () + 2) % SEQNO_SPACE_SIZE;
433 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
434 agreement.NotifyTransmittedMpdu (mpdu);
435
436 // the current window must look like this:
437 //
438 // |1|0|0|1|1|1|0|0|0|0|0|0|0|1|1|1|
439 // ^
440 // |
441 // HEAD
442
443 startingSeq = (startingSeq + 2) % SEQNO_SPACE_SIZE;
444 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq,
445 "Incorrect starting sequence after transmitting an MPDU beyond the current window");
446 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (0), false, "Incorrect flag after transmitting an MPDU beyond the current window");
447 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (1), true, "Incorrect flag after transmitting an MPDU beyond the current window");
448 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (2), true, "Incorrect flag after transmitting an MPDU beyond the current window");
449 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (3), true, "Incorrect flag after transmitting an MPDU beyond the current window");
450 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (4), true, "Incorrect flag after transmitting an MPDU beyond the current window");
451 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (5), false, "Incorrect flag after transmitting an MPDU beyond the current window");
452 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (6), false, "Incorrect flag after transmitting an MPDU beyond the current window");
453 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (7), true, "Incorrect flag after transmitting an MPDU beyond the current window");
454 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (8), true, "Incorrect flag after transmitting an MPDU beyond the current window");
455 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (9), true, "Incorrect flag after transmitting an MPDU beyond the current window");
456 for (uint16_t i = 10; i < winSize; i++)
457 {
458 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after transmitting an MPDU beyond the current window");
459 }
460
461 // another MPDU is transmitted beyond the current window. Now, the window advances
462 // until the first unacknowledged MPDU
463 seqNumber = (agreement.m_txWindow.GetWinEnd () + 1) % SEQNO_SPACE_SIZE;
464 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
465 agreement.NotifyTransmittedMpdu (mpdu);
466
467 // the current window must look like this:
468 //
469 // |0|0|0|1|1|1|0|0|0|0|0|0|0|0|0|0|
470 // ^
471 // |
472 // HEAD
473
474 startingSeq = (startingSeq + 5) % SEQNO_SPACE_SIZE;
475 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq,
476 "Incorrect starting sequence after transmitting another MPDU beyond the current window");
477 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (0), false, "Incorrect flag after transmitting another MPDU beyond the current window");
478 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (1), false, "Incorrect flag after transmitting another MPDU beyond the current window");
479 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (2), true, "Incorrect flag after transmitting another MPDU beyond the current window");
480 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (3), true, "Incorrect flag after transmitting another MPDU beyond the current window");
481 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (4), true, "Incorrect flag after transmitting another MPDU beyond the current window");
482 for (uint16_t i = 5; i < winSize; i++)
483 {
484 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after transmitting another MPDU beyond the current window");
485 }
486
487 // the MPDU next to winStart is discarded, hence the window advances to make it an old packet.
488 // Since the subsequent MPDUs have been acknowledged, the window advances further.
489 seqNumber = (startingSeq + 1) % SEQNO_SPACE_SIZE;
490 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
491 agreement.NotifyDiscardedMpdu (mpdu);
492
493 // the current window must look like this:
494 //
495 // |0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|
496 // ^
497 // |
498 // HEAD
499
500 startingSeq = (startingSeq + 5) % SEQNO_SPACE_SIZE;
501 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq,
502 "Incorrect starting sequence after discarding an MPDU");
503 for (uint16_t i = 0; i < winSize; i++)
504 {
505 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after discarding an MPDU");
506 }
507
508 // Finally, check that the window correctly advances when the MPDU with the starting sequence number
509 // is acknowledged after being the only unacknowledged MPDU
510 for (uint16_t i = 1; i < winSize; i++)
511 {
512 mpdu->GetHeader ().SetSequenceNumber ((startingSeq + i) % SEQNO_SPACE_SIZE);
513 agreement.NotifyAckedMpdu (mpdu);
514 }
515
516 // the current window must look like this:
517 //
518 // |1|1|1|1|1|1|0|1|1|1|1|1|1|1|1|1|
519 // ^
520 // |
521 // HEAD
522
523 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq,
524 "Incorrect starting sequence after acknowledging all but the first MPDU");
525 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (0), false, "Incorrect flag after acknowledging all but the first MPDU");
526 for (uint16_t i = 1; i < winSize; i++)
527 {
528 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), true, "Incorrect flag after acknowledging all but the first MPDU");
529 }
530
531 // acknowledge the first MPDU
532 mpdu->GetHeader ().SetSequenceNumber (startingSeq % SEQNO_SPACE_SIZE);
533 agreement.NotifyAckedMpdu (mpdu);
534
535 // the current window must look like this:
536 //
537 // |0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|
538 // ^
539 // |
540 // HEAD
541
542 startingSeq = (startingSeq + winSize) % SEQNO_SPACE_SIZE;
543 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq,
544 "Incorrect starting sequence after acknowledging the first MPDU");
545 for (uint16_t i = 0; i < winSize; i++)
546 {
547 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after acknowledging the first MPDU");
548 }
549 }
550
551
552 /**
553 * \ingroup wifi-test
554 * \ingroup tests
555 *
556 * \brief Test for block ack header
557 */
558 class CtrlBAckResponseHeaderTest : public TestCase
559 {
560 public:
561 CtrlBAckResponseHeaderTest ();
562 private:
563 void DoRun (void) override;
564 CtrlBAckResponseHeader m_blockAckHdr; ///< block ack header
565 };
566
CtrlBAckResponseHeaderTest()567 CtrlBAckResponseHeaderTest::CtrlBAckResponseHeaderTest ()
568 : TestCase ("Check the correctness of block ack compressed bitmap")
569 {
570 }
571
572 void
DoRun(void)573 CtrlBAckResponseHeaderTest::DoRun (void)
574 {
575 m_blockAckHdr.SetType (BlockAckType::COMPRESSED);
576
577 //Case 1: startSeq < endSeq
578 // 179 242
579 m_blockAckHdr.SetStartingSequence (179);
580 for (uint16_t i = 179; i < 220; i++)
581 {
582 m_blockAckHdr.SetReceivedPacket (i);
583 }
584 for (uint16_t i = 225; i <= 242; i++)
585 {
586 m_blockAckHdr.SetReceivedPacket (i);
587 }
588 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[0], 0xff, "error in compressed bitmap");
589 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[1], 0xff, "error in compressed bitmap");
590 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[2], 0xff, "error in compressed bitmap");
591 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[3], 0xff, "error in compressed bitmap");
592 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[4], 0xff, "error in compressed bitmap");
593 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[5], 0xc1, "error in compressed bitmap");
594 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[6], 0xff, "error in compressed bitmap");
595 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[7], 0xff, "error in compressed bitmap");
596 m_blockAckHdr.SetReceivedPacket (1500);
597 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[0], 0xff, "error in compressed bitmap");
598 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[1], 0xff, "error in compressed bitmap");
599 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[2], 0xff, "error in compressed bitmap");
600 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[3], 0xff, "error in compressed bitmap");
601 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[4], 0xff, "error in compressed bitmap");
602 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[5], 0xc1, "error in compressed bitmap");
603 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[6], 0xff, "error in compressed bitmap");
604 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[7], 0xff, "error in compressed bitmap");
605 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (220), false, "error in compressed bitmap");
606 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (225), true, "error in compressed bitmap");
607 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (1500), false, "error in compressed bitmap");
608
609 m_blockAckHdr.ResetBitmap ();
610
611 //Case 2: startSeq > endSeq
612 // 4090 58
613 m_blockAckHdr.SetStartingSequence (4090);
614 for (uint16_t i = 4090; i != 10; i = (i + 1) % 4096)
615 {
616 m_blockAckHdr.SetReceivedPacket (i);
617 }
618 for (uint16_t i = 22; i < 25; i++)
619 {
620 m_blockAckHdr.SetReceivedPacket (i);
621 }
622 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[0], 0xff, "error in compressed bitmap");
623 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[1], 0xff, "error in compressed bitmap");
624 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[2], 0x00, "error in compressed bitmap");
625 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[3], 0x70, "error in compressed bitmap");
626 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[4], 0x00, "error in compressed bitmap");
627 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[5], 0x00, "error in compressed bitmap");
628 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[6], 0x00, "error in compressed bitmap");
629 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[7], 0x00, "error in compressed bitmap");
630 m_blockAckHdr.SetReceivedPacket (80);
631 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[0], 0xff, "error in compressed bitmap");
632 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[1], 0xff, "error in compressed bitmap");
633 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[2], 0x00, "error in compressed bitmap");
634 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[3], 0x70, "error in compressed bitmap");
635 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[4], 0x00, "error in compressed bitmap");
636 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[5], 0x00, "error in compressed bitmap");
637 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[6], 0x00, "error in compressed bitmap");
638 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[7], 0x00, "error in compressed bitmap");
639 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (4090), true, "error in compressed bitmap");
640 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (4095), true, "error in compressed bitmap");
641 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (10), false, "error in compressed bitmap");
642 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (35), false, "error in compressed bitmap");
643 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (80), false, "error in compressed bitmap");
644 }
645
646
647 /**
648 * \ingroup wifi-test
649 * \ingroup tests
650 *
651 * \brief Test for recipient reordering buffer operations
652 */
653 class BlockAckRecipientBufferTest : public TestCase
654 {
655 public:
656 /**
657 * \brief Constructor
658 * \param ssn the Starting Sequence Number used to initialize WinStartB
659 */
660 BlockAckRecipientBufferTest (uint16_t ssn);
661 virtual ~BlockAckRecipientBufferTest ();
662
663 void DoRun (void) override;
664
665 /**
666 * Keep track of MPDUs that are forwarded up.
667 *
668 * \param mpdu an MPDU that is forwarded up
669 */
670 void ForwardUp (Ptr<WifiMacQueueItem> mpdu);
671
672 private:
673 uint16_t m_ssn; //!< the Starting Sequence Number used to initialize WinStartB
674 std::list<Ptr<WifiMacQueueItem>> m_fwup; //!< list of MPDUs that have been forwarded up
675 };
676
BlockAckRecipientBufferTest(uint16_t ssn)677 BlockAckRecipientBufferTest::BlockAckRecipientBufferTest (uint16_t ssn)
678 : TestCase ("Test case for Block Ack recipient reordering buffer operations"),
679 m_ssn (ssn)
680 {
681 }
682
~BlockAckRecipientBufferTest()683 BlockAckRecipientBufferTest::~BlockAckRecipientBufferTest ()
684 {
685 }
686
687 void
ForwardUp(Ptr<WifiMacQueueItem> mpdu)688 BlockAckRecipientBufferTest::ForwardUp (Ptr<WifiMacQueueItem> mpdu)
689 {
690 m_fwup.push_back (mpdu);
691 }
692
693 void
DoRun(void)694 BlockAckRecipientBufferTest::DoRun (void)
695 {
696 Ptr<MacRxMiddle> rxMiddle = Create<MacRxMiddle> ();
697 rxMiddle->SetForwardCallback (MakeCallback (&BlockAckRecipientBufferTest::ForwardUp, this));
698
699 RecipientBlockAckAgreement agreement (Mac48Address::Allocate () /* originator */,
700 true /* amsduSupported */, 0 /* tid */, 10 /* bufferSize */,
701 0 /* timeout */, m_ssn, true /* htSupported */);
702 agreement.SetMacRxMiddle (rxMiddle);
703
704 WifiMacHeader hdr;
705 hdr.SetType (WIFI_MAC_QOSDATA);
706 hdr.SetAddr1 (Mac48Address::Allocate ());
707 hdr.SetQosTid (0);
708
709 // Notify the reception of an MPDU with SN = SSN.
710 hdr.SetSequenceNumber (m_ssn);
711 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
712
713 // This MPDU is forwarded up and WinStartB is set to SSN + 1.
714 NS_TEST_ASSERT_MSG_EQ (m_fwup.size (), 1, "MPDU with SN=SSN must have been forwarded up");
715 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (), m_ssn,
716 "The MPDU forwarded up is not the expected one");
717
718 m_fwup.clear ();
719
720 // Notify the reception of MPDUs with SN = SSN + {4, 2, 5, 3, 10, 7}
721 // Recipient buffer: | |X|X|X|X| |X| | |X|
722 // ^
723 // |
724 // SSN + 1
725 hdr.SetSequenceNumber ((m_ssn + 4) % SEQNO_SPACE_SIZE);
726 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
727 hdr.SetSequenceNumber ((m_ssn + 2) % SEQNO_SPACE_SIZE);
728 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
729 hdr.SetSequenceNumber ((m_ssn + 5) % SEQNO_SPACE_SIZE);
730 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
731 hdr.SetSequenceNumber ((m_ssn + 3) % SEQNO_SPACE_SIZE);
732 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
733 hdr.SetSequenceNumber ((m_ssn + 10) % SEQNO_SPACE_SIZE);
734 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
735 hdr.SetSequenceNumber ((m_ssn + 7) % SEQNO_SPACE_SIZE);
736 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
737
738 // No MPDU is forwarded up because the one with SN = SSN + 1 is missing
739 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
740
741 // Notify the reception of an "old" MPDU (SN = SSN)
742 hdr.SetSequenceNumber (m_ssn);
743 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
744
745 // No MPDU is forwarded up
746 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
747
748 // Notify the reception of a duplicate MPDU (SN = SSN + 2)
749 hdr.SetSequenceNumber ((m_ssn + 2) % SEQNO_SPACE_SIZE);
750 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(10), hdr));
751
752 // No MPDU is forwarded up
753 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
754
755 // Notify the reception of an MPDU with SN = SSN + 1
756 // Recipient buffer: |X|X|X|X|X| |X| | |X|
757 // ^
758 // |
759 // SSN + 1
760 hdr.SetSequenceNumber ((m_ssn + 1) % SEQNO_SPACE_SIZE);
761 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
762
763 // All the MPDUs with SN = SSN + {1, 2, 3, 4, 5} must have been forwarded up in order
764 NS_TEST_ASSERT_MSG_EQ (m_fwup.size (), 5, "5 MPDUs must have been forwarded up");
765
766 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
767 (m_ssn + 1) % SEQNO_SPACE_SIZE,
768 "The MPDU forwarded up is not the expected one");
769 m_fwup.pop_front ();
770
771 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
772 (m_ssn + 2) % SEQNO_SPACE_SIZE,
773 "The MPDU forwarded up is not the expected one");
774 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetPacketSize (), 0,
775 "The MPDU forwarded up is not the expected one");
776 m_fwup.pop_front ();
777
778 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
779 (m_ssn + 3) % SEQNO_SPACE_SIZE,
780 "The MPDU forwarded up is not the expected one");
781 m_fwup.pop_front ();
782
783 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
784 (m_ssn + 4) % SEQNO_SPACE_SIZE,
785 "The MPDU forwarded up is not the expected one");
786 m_fwup.pop_front ();
787
788 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
789 (m_ssn + 5) % SEQNO_SPACE_SIZE,
790 "The MPDU forwarded up is not the expected one");
791 m_fwup.pop_front ();
792
793 // Recipient buffer: | |X| | |X| | | | | |
794 // ^ ^
795 // | |
796 // SSN + 6 SSN + 15
797 // Notify the reception of an MPDU beyond the current window (SN = SSN + 17)
798 hdr.SetSequenceNumber ((m_ssn + 17) % SEQNO_SPACE_SIZE);
799 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
800
801 // WinStartB is set to SSN + 8 (so that WinEndB = SSN + 17). The MPDU with
802 // SN = SSN + 7 is forwarded up, irrespective of the missed reception of the
803 // MPDU with SN = SSN + 6
804 NS_TEST_ASSERT_MSG_EQ (m_fwup.size (), 1, "One MPDU must have been forwarded up");
805
806 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
807 (m_ssn + 7) % SEQNO_SPACE_SIZE,
808 "The MPDU forwarded up is not the expected one");
809 m_fwup.pop_front ();
810
811 // Recipient buffer: | | |X| | | | | | |X|
812 // ^ ^
813 // | |
814 // SSN + 8 SSN + 17
815 // Notify the reception of a BlockAckReq with SSN = SSN + 7
816 agreement.NotifyReceivedBar ((m_ssn + 7) % SEQNO_SPACE_SIZE);
817
818 // No MPDU is forwarded up
819 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
820
821 // Notify the reception of a BlockAckReq with SSN = SSN + 8
822 agreement.NotifyReceivedBar ((m_ssn + 8) % SEQNO_SPACE_SIZE);
823
824 // No MPDU is forwarded up
825 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
826
827 // Notify the reception of MPDUs with SN = SSN + {9, 11}
828 // Recipient buffer: | |X|X|X| | | | | |X|
829 // ^ ^
830 // | |
831 // SSN + 8 SSN + 17
832 hdr.SetSequenceNumber ((m_ssn + 9) % SEQNO_SPACE_SIZE);
833 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
834 hdr.SetSequenceNumber ((m_ssn + 11) % SEQNO_SPACE_SIZE);
835 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
836
837 // No MPDU is forwarded up because the one with SN = SSN + 8 is missing
838 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
839
840 // Notify the reception of a BlockAckReq with SSN = SSN + 10
841 agreement.NotifyReceivedBar ((m_ssn + 10) % SEQNO_SPACE_SIZE);
842
843 // Forward up buffered MPDUs with SN < SSN + 10 (the MPDU with SN = SSN + 9)
844 // and then buffered MPDUs with SN >= SSN + 10 until a hole is found (MPDUs
845 // with SN = SSN + 10 and SN = SSN + 11)
846 NS_TEST_ASSERT_MSG_EQ (m_fwup.size (), 3, "3 MPDUs must have been forwarded up");
847
848 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
849 (m_ssn + 9) % SEQNO_SPACE_SIZE,
850 "The MPDU forwarded up is not the expected one");
851 m_fwup.pop_front ();
852
853 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
854 (m_ssn + 10) % SEQNO_SPACE_SIZE,
855 "The MPDU forwarded up is not the expected one");
856 m_fwup.pop_front ();
857
858 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
859 (m_ssn + 11) % SEQNO_SPACE_SIZE,
860 "The MPDU forwarded up is not the expected one");
861 m_fwup.pop_front ();
862
863 Simulator::Run ();
864 Simulator::Destroy ();
865 }
866
867
868 /**
869 * \ingroup wifi-test
870 * \ingroup tests
871 *
872 * \brief Test for Multi-STA block ack header
873 */
874 class MultiStaCtrlBAckResponseHeaderTest : public TestCase
875 {
876 public:
877 MultiStaCtrlBAckResponseHeaderTest ();
878 private:
879 virtual void DoRun (void);
880 };
881
MultiStaCtrlBAckResponseHeaderTest()882 MultiStaCtrlBAckResponseHeaderTest::MultiStaCtrlBAckResponseHeaderTest ()
883 : TestCase ("Check the correctness of Multi-STA block ack")
884 {
885 }
886
887 void
DoRun(void)888 MultiStaCtrlBAckResponseHeaderTest::DoRun (void)
889 {
890 // Create a Multi-STA Block Ack with 6 Per AID TID Info subfields
891 BlockAckType baType (BlockAckType::MULTI_STA, {0, 4, 8, 16, 32, 8});
892
893 CtrlBAckResponseHeader blockAck;
894 blockAck.SetType (baType);
895
896 /* 1st Per AID TID Info subfield */
897 uint16_t aid1 = 100;
898 bool ackType1 = true;
899 uint8_t tid1 = 1;
900
901 blockAck.SetAid11 (aid1, 0);
902 blockAck.SetAckType (ackType1, 0);
903 blockAck.SetTidInfo (tid1, 0);
904
905 /* 2nd Per AID TID Info subfield */
906 uint16_t aid2 = 200;
907 bool ackType2 = false;
908 uint8_t tid2 = 2;
909 uint16_t startSeq2 = 1000;
910
911 blockAck.SetAid11 (aid2, 1);
912 blockAck.SetAckType (ackType2, 1);
913 blockAck.SetTidInfo (tid2, 1);
914 blockAck.SetStartingSequence (startSeq2, 1);
915 // 1st byte of the bitmap: 01010101
916 for (uint16_t i = startSeq2; i < startSeq2 + 8; i+=2)
917 {
918 blockAck.SetReceivedPacket (i, 1);
919 }
920 // 2nd byte of the bitmap: 10101010
921 for (uint16_t i = startSeq2 + 9; i < startSeq2 + 16; i+=2)
922 {
923 blockAck.SetReceivedPacket (i, 1);
924 }
925 // 3rd byte of the bitmap: 00000000
926 // 4th byte of the bitmap: 11111111
927 for (uint16_t i = startSeq2 + 24; i < startSeq2 + 32; i++)
928 {
929 blockAck.SetReceivedPacket (i, 1);
930 }
931
932 /* 3rd Per AID TID Info subfield */
933 uint16_t aid3 = 300;
934 bool ackType3 = false;
935 uint8_t tid3 = 3;
936 uint16_t startSeq3 = 2000;
937
938 blockAck.SetAid11 (aid3, 2);
939 blockAck.SetAckType (ackType3, 2);
940 blockAck.SetTidInfo (tid3, 2);
941 blockAck.SetStartingSequence (startSeq3, 2);
942 // 1st byte of the bitmap: 01010101
943 for (uint16_t i = startSeq3; i < startSeq3 + 8; i+=2)
944 {
945 blockAck.SetReceivedPacket (i, 2);
946 }
947 // 2nd byte of the bitmap: 10101010
948 for (uint16_t i = startSeq3 + 9; i < startSeq3 + 16; i+=2)
949 {
950 blockAck.SetReceivedPacket (i, 2);
951 }
952 // 3rd byte of the bitmap: 00000000
953 // 4th byte of the bitmap: 11111111
954 for (uint16_t i = startSeq3 + 24; i < startSeq3 + 32; i++)
955 {
956 blockAck.SetReceivedPacket (i, 2);
957 }
958 // 5th byte of the bitmap: 00001111
959 for (uint16_t i = startSeq3 + 32; i < startSeq3 + 36; i++)
960 {
961 blockAck.SetReceivedPacket (i, 2);
962 }
963 // 6th byte of the bitmap: 11110000
964 for (uint16_t i = startSeq3 + 44; i < startSeq3 + 48; i++)
965 {
966 blockAck.SetReceivedPacket (i, 2);
967 }
968 // 7th byte of the bitmap: 00000000
969 // 8th byte of the bitmap: 11111111
970 for (uint16_t i = startSeq3 + 56; i < startSeq3 + 64; i++)
971 {
972 blockAck.SetReceivedPacket (i, 2);
973 }
974
975 /* 4th Per AID TID Info subfield */
976 uint16_t aid4 = 400;
977 bool ackType4 = false;
978 uint8_t tid4 = 4;
979 uint16_t startSeq4 = 3000;
980
981 blockAck.SetAid11 (aid4, 3);
982 blockAck.SetAckType (ackType4, 3);
983 blockAck.SetTidInfo (tid4, 3);
984 blockAck.SetStartingSequence (startSeq4, 3);
985 // 1st byte of the bitmap: 01010101
986 for (uint16_t i = startSeq4; i < startSeq4 + 8; i+=2)
987 {
988 blockAck.SetReceivedPacket (i, 3);
989 }
990 // 2nd byte of the bitmap: 10101010
991 for (uint16_t i = startSeq4 + 9; i < startSeq4 + 16; i+=2)
992 {
993 blockAck.SetReceivedPacket (i, 3);
994 }
995 // 3rd byte of the bitmap: 00000000
996 // 4th byte of the bitmap: 11111111
997 for (uint16_t i = startSeq4 + 24; i < startSeq4 + 32; i++)
998 {
999 blockAck.SetReceivedPacket (i, 3);
1000 }
1001 // 5th byte of the bitmap: 00001111
1002 for (uint16_t i = startSeq4 + 32; i < startSeq4 + 36; i++)
1003 {
1004 blockAck.SetReceivedPacket (i, 3);
1005 }
1006 // 6th byte of the bitmap: 11110000
1007 for (uint16_t i = startSeq4 + 44; i < startSeq4 + 48; i++)
1008 {
1009 blockAck.SetReceivedPacket (i, 3);
1010 }
1011 // 7th byte of the bitmap: 00000000
1012 // 8th byte of the bitmap: 11111111
1013 for (uint16_t i = startSeq4 + 56; i < startSeq4 + 64; i++)
1014 {
1015 blockAck.SetReceivedPacket (i, 3);
1016 }
1017 // 9th byte of the bitmap: 00000000
1018 // 10th byte of the bitmap: 11111111
1019 for (uint16_t i = startSeq4 + 72; i < startSeq4 + 80; i++)
1020 {
1021 blockAck.SetReceivedPacket (i, 3);
1022 }
1023 // 11th byte of the bitmap: 00000000
1024 // 12th byte of the bitmap: 11111111
1025 for (uint16_t i = startSeq4 + 88; i < startSeq4 + 96; i++)
1026 {
1027 blockAck.SetReceivedPacket (i, 3);
1028 }
1029 // 13th byte of the bitmap: 00000000
1030 // 14th byte of the bitmap: 11111111
1031 for (uint16_t i = startSeq4 + 104; i < startSeq4 + 112; i++)
1032 {
1033 blockAck.SetReceivedPacket (i, 3);
1034 }
1035 // 15th byte of the bitmap: 00000000
1036 // 16th byte of the bitmap: 11111111
1037 for (uint16_t i = startSeq4 + 120; i < startSeq4 + 128; i++)
1038 {
1039 blockAck.SetReceivedPacket (i, 3);
1040 }
1041
1042 /* 5th Per AID TID Info subfield */
1043 uint16_t aid5 = 500;
1044 bool ackType5 = false;
1045 uint8_t tid5 = 5;
1046 uint16_t startSeq5 = 4000;
1047
1048 blockAck.SetAid11 (aid5, 4);
1049 blockAck.SetAckType (ackType5, 4);
1050 blockAck.SetTidInfo (tid5, 4);
1051 blockAck.SetStartingSequence (startSeq5, 4);
1052 // 1st byte of the bitmap: 01010101
1053 for (uint16_t i = startSeq5; i < startSeq5 + 8; i+=2)
1054 {
1055 blockAck.SetReceivedPacket (i, 4);
1056 }
1057 // 2nd byte of the bitmap: 10101010
1058 for (uint16_t i = startSeq5 + 9; i < startSeq5 + 16; i+=2)
1059 {
1060 blockAck.SetReceivedPacket (i, 4);
1061 }
1062 // 3rd byte of the bitmap: 00000000
1063 // 4th byte of the bitmap: 11111111
1064 for (uint16_t i = startSeq5 + 24; i < startSeq5 + 32; i++)
1065 {
1066 blockAck.SetReceivedPacket (i, 4);
1067 }
1068 // 5th byte of the bitmap: 00001111
1069 for (uint16_t i = startSeq5 + 32; i < startSeq5 + 36; i++)
1070 {
1071 blockAck.SetReceivedPacket (i, 4);
1072 }
1073 // 6th byte of the bitmap: 11110000
1074 for (uint16_t i = startSeq5 + 44; i < startSeq5 + 48; i++)
1075 {
1076 blockAck.SetReceivedPacket (i, 4);
1077 }
1078 // 7th byte of the bitmap: 00000000
1079 // 8th byte of the bitmap: 11111111
1080 for (uint16_t i = startSeq5 + 56; i < startSeq5 + 64; i++)
1081 {
1082 blockAck.SetReceivedPacket (i, 4);
1083 }
1084 // 9th byte of the bitmap: 00000000
1085 // 10th byte of the bitmap: 11111111
1086 for (uint16_t i = startSeq5 + 72; i < startSeq5 + 80; i++)
1087 {
1088 blockAck.SetReceivedPacket (i, 4);
1089 }
1090 // 11th byte of the bitmap: 00000000
1091 // 12th byte of the bitmap: 11111111
1092 for (uint16_t i = startSeq5 + 88; i < startSeq5 + 96; i++)
1093 {
1094 blockAck.SetReceivedPacket (i, 4);
1095 }
1096 // 13th byte of the bitmap: 00000000
1097 // 14th byte of the bitmap: 11111111
1098 for (uint16_t i = (startSeq5 + 104) % 4096; i < (startSeq5 + 112) % 4096; i++)
1099 {
1100 blockAck.SetReceivedPacket (i, 4);
1101 }
1102 // 15th byte of the bitmap: 00000000
1103 // 16th byte of the bitmap: 11111111
1104 for (uint16_t i = (startSeq5 + 120) % 4096; i < (startSeq5 + 128) % 4096; i++)
1105 {
1106 blockAck.SetReceivedPacket (i, 4);
1107 }
1108 // 17th byte of the bitmap: 00000000
1109 // 18th byte of the bitmap: 11111111
1110 for (uint16_t i = (startSeq5 + 136) % 4096; i < (startSeq5 + 144) % 4096; i++)
1111 {
1112 blockAck.SetReceivedPacket (i, 4);
1113 }
1114 // 19th byte of the bitmap: 00000000
1115 // 20th byte of the bitmap: 11111111
1116 for (uint16_t i = (startSeq5 + 152) % 4096; i < (startSeq5 + 160) % 4096; i++)
1117 {
1118 blockAck.SetReceivedPacket (i, 4);
1119 }
1120 // 21th byte of the bitmap: 00000000
1121 // 22th byte of the bitmap: 11111111
1122 for (uint16_t i = (startSeq5 + 168) % 4096; i < (startSeq5 + 176) % 4096; i++)
1123 {
1124 blockAck.SetReceivedPacket (i, 4);
1125 }
1126 // 23th byte of the bitmap: 00000000
1127 // 24th byte of the bitmap: 11111111
1128 for (uint16_t i = (startSeq5 + 184) % 4096; i < (startSeq5 + 192) % 4096; i++)
1129 {
1130 blockAck.SetReceivedPacket (i, 4);
1131 }
1132 // 25th byte of the bitmap: 00000000
1133 // 26th byte of the bitmap: 11111111
1134 for (uint16_t i = (startSeq5 + 200) % 4096; i < (startSeq5 + 208) % 4096; i++)
1135 {
1136 blockAck.SetReceivedPacket (i, 4);
1137 }
1138 // 27th byte of the bitmap: 00000000
1139 // 28th byte of the bitmap: 11111111
1140 for (uint16_t i = (startSeq5 + 216) % 4096; i < (startSeq5 + 224) % 4096; i++)
1141 {
1142 blockAck.SetReceivedPacket (i, 4);
1143 }
1144 // 29th byte of the bitmap: 00000000
1145 // 30th byte of the bitmap: 11111111
1146 for (uint16_t i = (startSeq5 + 232) % 4096; i < (startSeq5 + 240) % 4096; i++)
1147 {
1148 blockAck.SetReceivedPacket (i, 4);
1149 }
1150 // 31th byte of the bitmap: 00000000
1151 // 32th byte of the bitmap: 11111111
1152 for (uint16_t i = (startSeq5 + 248) % 4096; i < (startSeq5 + 256) % 4096; i++)
1153 {
1154 blockAck.SetReceivedPacket (i, 4);
1155 }
1156
1157 /* 6th Per AID TID Info subfield */
1158 uint16_t aid6 = 2045;
1159 bool ackType6 = true;
1160 uint8_t tid6 = 6;
1161 Mac48Address address6 = Mac48Address ("00:00:00:00:00:01");
1162
1163 blockAck.SetAid11 (aid6, 5);
1164 blockAck.SetAckType (ackType6, 5);
1165 blockAck.SetTidInfo (tid6, 5);
1166 blockAck.SetUnassociatedStaAddress (address6, 5);
1167
1168 // Serialize the header
1169 Ptr<Packet> packet = Create<Packet> ();
1170 packet->AddHeader (blockAck);
1171
1172 // Deserialize the header
1173 CtrlBAckResponseHeader blockAckCopy;
1174 packet->RemoveHeader (blockAckCopy);
1175
1176 // Check that the header has been correctly deserialized
1177 BlockAckType baTypeCopy = blockAckCopy.GetType ();
1178
1179 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_variant, BlockAckType::MULTI_STA, "Different block ack variant");
1180 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen.size (), 6, "Different number of bitmaps");
1181 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[0], 0, "Different length of the first bitmap");
1182 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[1], 4, "Different length of the second bitmap");
1183 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[2], 8, "Different length of the third bitmap");
1184 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[3], 16, "Different length of the fourth bitmap");
1185 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[4], 32, "Different length of the fifth bitmap");
1186 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[5], 8, "Different length for the sixth bitmap");
1187
1188 /* Check 1st Per AID TID Info subfield */
1189 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (0), aid1, "Different AID for the first Per AID TID Info subfield");
1190 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (0), ackType1, "Different Ack Type for the first Per AID TID Info subfield");
1191 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (0), tid1, "Different TID for the first Per AID TID Info subfield");
1192
1193 /* Check 2nd Per AID TID Info subfield */
1194 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (1), aid2, "Different AID for the second Per AID TID Info subfield");
1195 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (1), ackType2, "Different Ack Type for the second Per AID TID Info subfield");
1196 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (1), tid2, "Different TID for the second Per AID TID Info subfield");
1197 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetStartingSequence (1), startSeq2, "Different starting sequence number for the second Per AID TID Info subfield");
1198
1199 auto& bitmap2 = blockAckCopy.GetBitmap (1);
1200 NS_TEST_EXPECT_MSG_EQ (bitmap2.size (), 4, "Different bitmap length for the second Per AID TID Info subfield");
1201 NS_TEST_EXPECT_MSG_EQ (bitmap2[0], 0x55, "Error in the 1st byte of the bitmap for the second Per AID TID Info subfield");
1202 NS_TEST_EXPECT_MSG_EQ (bitmap2[1], 0xaa, "Error in the 2nd byte of the bitmap for the second Per AID TID Info subfield");
1203 NS_TEST_EXPECT_MSG_EQ (bitmap2[2], 0x00, "Error in the 3rd byte of the bitmap for the second Per AID TID Info subfield");
1204 NS_TEST_EXPECT_MSG_EQ (bitmap2[3], 0xff, "Error in the 4th byte of the bitmap for the second Per AID TID Info subfield");
1205
1206 /* Check 3rd Per AID TID Info subfield */
1207 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (2), aid3, "Different AID for the third Per AID TID Info subfield");
1208 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (2), ackType3, "Different Ack Type for the third Per AID TID Info subfield");
1209 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (2), tid3, "Different TID for the third Per AID TID Info subfield");
1210 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetStartingSequence (2), startSeq3, "Different starting sequence number for the third Per AID TID Info subfield");
1211
1212 auto& bitmap3 = blockAckCopy.GetBitmap (2);
1213 NS_TEST_EXPECT_MSG_EQ (bitmap3.size (), 8, "Different bitmap length for the third Per AID TID Info subfield");
1214 NS_TEST_EXPECT_MSG_EQ (bitmap3[0], 0x55, "Error in the 1st byte of the bitmap for the third Per AID TID Info subfield");
1215 NS_TEST_EXPECT_MSG_EQ (bitmap3[1], 0xaa, "Error in the 2nd byte of the bitmap for the third Per AID TID Info subfield");
1216 NS_TEST_EXPECT_MSG_EQ (bitmap3[2], 0x00, "Error in the 3rd byte of the bitmap for the third Per AID TID Info subfield");
1217 NS_TEST_EXPECT_MSG_EQ (bitmap3[3], 0xff, "Error in the 4th byte of the bitmap for the third Per AID TID Info subfield");
1218 NS_TEST_EXPECT_MSG_EQ (bitmap3[4], 0x0f, "Error in the 5th byte of the bitmap for the third Per AID TID Info subfield");
1219 NS_TEST_EXPECT_MSG_EQ (bitmap3[5], 0xf0, "Error in the 6th byte of the bitmap for the third Per AID TID Info subfield");
1220 NS_TEST_EXPECT_MSG_EQ (bitmap3[6], 0x00, "Error in the 7th byte of the bitmap for the third Per AID TID Info subfield");
1221 NS_TEST_EXPECT_MSG_EQ (bitmap3[7], 0xff, "Error in the 8th byte of the bitmap for the third Per AID TID Info subfield");
1222
1223 /* Check 4th Per AID TID Info subfield */
1224 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (3), aid4, "Different AID for the fourth Per AID TID Info subfield");
1225 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (3), ackType4, "Different Ack Type for the fourth Per AID TID Info subfield");
1226 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (3), tid4, "Different TID for the fourth Per AID TID Info subfield");
1227 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetStartingSequence (3), startSeq4, "Different starting sequence number for the fourth Per AID TID Info subfield");
1228
1229 auto& bitmap4 = blockAckCopy.GetBitmap (3);
1230 NS_TEST_EXPECT_MSG_EQ (bitmap4.size (), 16, "Different bitmap length for the fourth Per AID TID Info subfield");
1231 NS_TEST_EXPECT_MSG_EQ (bitmap4[0], 0x55, "Error in the 1st byte of the bitmap for the fourth Per AID TID Info subfield");
1232 NS_TEST_EXPECT_MSG_EQ (bitmap4[1], 0xaa, "Error in the 2nd byte of the bitmap for the fourth Per AID TID Info subfield");
1233 NS_TEST_EXPECT_MSG_EQ (bitmap4[2], 0x00, "Error in the 3rd byte of the bitmap for the fourth Per AID TID Info subfield");
1234 NS_TEST_EXPECT_MSG_EQ (bitmap4[3], 0xff, "Error in the 4th byte of the bitmap for the fourth Per AID TID Info subfield");
1235 NS_TEST_EXPECT_MSG_EQ (bitmap4[4], 0x0f, "Error in the 5th byte of the bitmap for the fourth Per AID TID Info subfield");
1236 NS_TEST_EXPECT_MSG_EQ (bitmap4[5], 0xf0, "Error in the 6th byte of the bitmap for the fourth Per AID TID Info subfield");
1237 NS_TEST_EXPECT_MSG_EQ (bitmap4[6], 0x00, "Error in the 7th byte of the bitmap for the fourth Per AID TID Info subfield");
1238 NS_TEST_EXPECT_MSG_EQ (bitmap4[7], 0xff, "Error in the 8th byte of the bitmap for the fourth Per AID TID Info subfield");
1239 NS_TEST_EXPECT_MSG_EQ (bitmap4[8], 0x00, "Error in the 9th byte of the bitmap for the fourth Per AID TID Info subfield");
1240 NS_TEST_EXPECT_MSG_EQ (bitmap4[9], 0xff, "Error in the 10th byte of the bitmap for the fourth Per AID TID Info subfield");
1241 NS_TEST_EXPECT_MSG_EQ (bitmap4[10], 0x00, "Error in the 11th byte of the bitmap for the fourth Per AID TID Info subfield");
1242 NS_TEST_EXPECT_MSG_EQ (bitmap4[11], 0xff, "Error in the 12th byte of the bitmap for the fourth Per AID TID Info subfield");
1243 NS_TEST_EXPECT_MSG_EQ (bitmap4[12], 0x00, "Error in the 13th byte of the bitmap for the fourth Per AID TID Info subfield");
1244 NS_TEST_EXPECT_MSG_EQ (bitmap4[13], 0xff, "Error in the 14th byte of the bitmap for the fourth Per AID TID Info subfield");
1245 NS_TEST_EXPECT_MSG_EQ (bitmap4[14], 0x00, "Error in the 15th byte of the bitmap for the fourth Per AID TID Info subfield");
1246 NS_TEST_EXPECT_MSG_EQ (bitmap4[15], 0xff, "Error in the 16th byte of the bitmap for the fourth Per AID TID Info subfield");
1247
1248 /* Check 5th Per AID TID Info subfield */
1249 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (4), aid5, "Different AID for the fifth Per AID TID Info subfield");
1250 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (4), ackType5, "Different Ack Type for the fifth Per AID TID Info subfield");
1251 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (4), tid5, "Different TID for the fifth Per AID TID Info subfield");
1252 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetStartingSequence (4), startSeq5, "Different starting sequence number for the fifth Per AID TID Info subfield");
1253
1254 auto& bitmap5 = blockAckCopy.GetBitmap (4);
1255 NS_TEST_EXPECT_MSG_EQ (bitmap5.size (), 32, "Different bitmap length for the fifth Per AID TID Info subfield");
1256 NS_TEST_EXPECT_MSG_EQ (bitmap5[0], 0x55, "Error in the 1st byte of the bitmap for the fifth Per AID TID Info subfield");
1257 NS_TEST_EXPECT_MSG_EQ (bitmap5[1], 0xaa, "Error in the 2nd byte of the bitmap for the fifth Per AID TID Info subfield");
1258 NS_TEST_EXPECT_MSG_EQ (bitmap5[2], 0x00, "Error in the 3rd byte of the bitmap for the fifth Per AID TID Info subfield");
1259 NS_TEST_EXPECT_MSG_EQ (bitmap5[3], 0xff, "Error in the 4th byte of the bitmap for the fifth Per AID TID Info subfield");
1260 NS_TEST_EXPECT_MSG_EQ (bitmap5[4], 0x0f, "Error in the 5th byte of the bitmap for the fifth Per AID TID Info subfield");
1261 NS_TEST_EXPECT_MSG_EQ (bitmap5[5], 0xf0, "Error in the 6th byte of the bitmap for the fifth Per AID TID Info subfield");
1262 NS_TEST_EXPECT_MSG_EQ (bitmap5[6], 0x00, "Error in the 7th byte of the bitmap for the fifth Per AID TID Info subfield");
1263 NS_TEST_EXPECT_MSG_EQ (bitmap5[7], 0xff, "Error in the 8th byte of the bitmap for the fifth Per AID TID Info subfield");
1264 NS_TEST_EXPECT_MSG_EQ (bitmap5[8], 0x00, "Error in the 9th byte of the bitmap for the fifth Per AID TID Info subfield");
1265 NS_TEST_EXPECT_MSG_EQ (bitmap5[9], 0xff, "Error in the 10th byte of the bitmap for the fifth Per AID TID Info subfield");
1266 NS_TEST_EXPECT_MSG_EQ (bitmap5[10], 0x00, "Error in the 11th byte of the bitmap for the fifth Per AID TID Info subfield");
1267 NS_TEST_EXPECT_MSG_EQ (bitmap5[11], 0xff, "Error in the 12th byte of the bitmap for the fifth Per AID TID Info subfield");
1268 NS_TEST_EXPECT_MSG_EQ (bitmap5[12], 0x00, "Error in the 13th byte of the bitmap for the fifth Per AID TID Info subfield");
1269 NS_TEST_EXPECT_MSG_EQ (bitmap5[13], 0xff, "Error in the 14th byte of the bitmap for the fifth Per AID TID Info subfield");
1270 NS_TEST_EXPECT_MSG_EQ (bitmap5[14], 0x00, "Error in the 15th byte of the bitmap for the fifth Per AID TID Info subfield");
1271 NS_TEST_EXPECT_MSG_EQ (bitmap5[15], 0xff, "Error in the 16th byte of the bitmap for the fifth Per AID TID Info subfield");
1272 NS_TEST_EXPECT_MSG_EQ (bitmap5[16], 0x00, "Error in the 17th byte of the bitmap for the fifth Per AID TID Info subfield");
1273 NS_TEST_EXPECT_MSG_EQ (bitmap5[17], 0xff, "Error in the 18th byte of the bitmap for the fifth Per AID TID Info subfield");
1274 NS_TEST_EXPECT_MSG_EQ (bitmap5[18], 0x00, "Error in the 19th byte of the bitmap for the fifth Per AID TID Info subfield");
1275 NS_TEST_EXPECT_MSG_EQ (bitmap5[19], 0xff, "Error in the 20th byte of the bitmap for the fifth Per AID TID Info subfield");
1276 NS_TEST_EXPECT_MSG_EQ (bitmap5[20], 0x00, "Error in the 21th byte of the bitmap for the fifth Per AID TID Info subfield");
1277 NS_TEST_EXPECT_MSG_EQ (bitmap5[21], 0xff, "Error in the 22th byte of the bitmap for the fifth Per AID TID Info subfield");
1278 NS_TEST_EXPECT_MSG_EQ (bitmap5[22], 0x00, "Error in the 23th byte of the bitmap for the fifth Per AID TID Info subfield");
1279 NS_TEST_EXPECT_MSG_EQ (bitmap5[23], 0xff, "Error in the 24th byte of the bitmap for the fifth Per AID TID Info subfield");
1280 NS_TEST_EXPECT_MSG_EQ (bitmap5[24], 0x00, "Error in the 25th byte of the bitmap for the fifth Per AID TID Info subfield");
1281 NS_TEST_EXPECT_MSG_EQ (bitmap5[25], 0xff, "Error in the 26th byte of the bitmap for the fifth Per AID TID Info subfield");
1282 NS_TEST_EXPECT_MSG_EQ (bitmap5[26], 0x00, "Error in the 27th byte of the bitmap for the fifth Per AID TID Info subfield");
1283 NS_TEST_EXPECT_MSG_EQ (bitmap5[27], 0xff, "Error in the 28th byte of the bitmap for the fifth Per AID TID Info subfield");
1284 NS_TEST_EXPECT_MSG_EQ (bitmap5[28], 0x00, "Error in the 29th byte of the bitmap for the fifth Per AID TID Info subfield");
1285 NS_TEST_EXPECT_MSG_EQ (bitmap5[29], 0xff, "Error in the 30th byte of the bitmap for the fifth Per AID TID Info subfield");
1286 NS_TEST_EXPECT_MSG_EQ (bitmap5[30], 0x00, "Error in the 31th byte of the bitmap for the fifth Per AID TID Info subfield");
1287 NS_TEST_EXPECT_MSG_EQ (bitmap5[31], 0xff, "Error in the 32th byte of the bitmap for the fifth Per AID TID Info subfield");
1288
1289 /* Check 6th Per AID TID Info subfield */
1290 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (5), aid6, "Different AID for the sixth Per AID TID Info subfield");
1291 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (5), ackType6, "Different Ack Type for the sixth Per AID TID Info subfield");
1292 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (5), tid6, "Different TID for the sixth Per AID TID Info subfield");
1293 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetUnassociatedStaAddress (5), address6, "Different starting sequence number for the sixth Per AID TID Info subfield");
1294 }
1295
1296
1297 /**
1298 * \ingroup wifi-test
1299 * \ingroup tests
1300 *
1301 * \brief Test for Block Ack Policy with aggregation disabled
1302 *
1303 * This test aims to check the Block Ack policy when A-MPDU aggregation is disabled.
1304 * In this case, a QoS station can transmit multiple QoS data frames before requesting
1305 * a Block Ack through a Block Ack Request frame. If the AC is granted a non-null TXOP
1306 * limit, MPDUs can be separated by a SIFS.
1307 *
1308 * In this test, an HT STA sends 14 packets to an HT AP. The ack policy selector is
1309 * configured so that a Block Ack is requested once 8 (= 0.125 * 64) MPDUs are sent
1310 * in addition to the MPDU having the starting sequence number. The block ack threshold
1311 * is set to 2, hence a block ack agreement is established when there are at least two
1312 * packets in the EDCA queue.
1313 *
1314 * When the TXOP limit is null:
1315 * - the first packet is sent with Normal Ack policy because the BA agreement has not
1316 * been established yet (there are no queued packets when the first one arrives);
1317 * - packets from the 2nd to the 10th are sent with Block Ack policy (and hence
1318 * are not immediately acknowledged);
1319 * - after the 10th packet, a Block Ack Request is sent, followed by a Block Ack;
1320 * - the remaining 4 packets are sent with Block Ack policy (and hence
1321 * are not immediately acknowledged);
1322 * - the last packet is followed by a Block Ack Request because there are no more
1323 * packets in the EDCA queue and hence a response is needed independently of
1324 * the number of outstanding MPDUs.
1325 *
1326 * When the TXOP is not null (and long enough to include the transmission of all packets):
1327 * - the first packet is sent with Normal Ack policy because the BA agreement has not
1328 * been established yet (there are no queued packets when the first one arrives);
1329 * - the second packet is sent with Normal Ack Policy because the first packet sent in
1330 * a TXOP shall request an immediate response and no previous MPDUs have to be
1331 * acknowledged;
1332 * - packets from the 3rd to the 11th are sent with Block Ack policy (and hence
1333 * are not immediately acknowledged);
1334 * - after the 11th packet, a Block Ack Request is sent, followed by a Block Ack;
1335 * - the remaining 3 packets are sent with Block Ack policy (and hence
1336 * are not immediately acknowledged);
1337 * - the last packet is followed by a Block Ack Request because there are no more
1338 * packets in the EDCA queue and hence a response is needed independently of
1339 * the number of outstanding MPDUs.
1340 */
1341 class BlockAckAggregationDisabledTest : public TestCase
1342 {
1343 /**
1344 * Keeps the maximum duration among all TXOPs
1345 */
1346 struct TxopDurationTracer
1347 {
1348 /**
1349 * Callback for the TxopTrace trace
1350 * \param startTime TXOP start time
1351 * \param duration TXOP duration
1352 */
1353 void Trace (Time startTime, Time duration);
1354 Time m_max {Seconds (0)}; ///< max TXOP duration
1355 };
1356
1357 public:
1358 /**
1359 * \brief Constructor
1360 * \param txop true for non-null TXOP limit
1361 */
1362 BlockAckAggregationDisabledTest (bool txop);
1363 virtual ~BlockAckAggregationDisabledTest ();
1364
1365 void DoRun (void) override;
1366
1367
1368 private:
1369 bool m_txop; ///< true for non-null TXOP limit
1370 uint32_t m_received; ///< received packets
1371 uint16_t m_txTotal; ///< transmitted data packets
1372 uint16_t m_txSinceBar; ///< packets transmitted since the agreement was established
1373 ///< or the last block ack was received
1374 uint16_t m_nBar; ///< transmitted BlockAckReq frames
1375 uint16_t m_nBa; ///< received BlockAck frames
1376
1377 /**
1378 * Function to trace packets received by the server application
1379 * \param context the context
1380 * \param p the packet
1381 * \param adr the address
1382 */
1383 void L7Receive (std::string context, Ptr<const Packet> p, const Address &adr);
1384 /**
1385 * Callback invoked when PHY transmits a packet
1386 * \param context the context
1387 * \param p the packet
1388 * \param power the tx power
1389 */
1390 void Transmit (std::string context, Ptr<const Packet> p, double power);
1391 /**
1392 * Callback invoked when PHY receives a packet
1393 * \param context the context
1394 * \param p the packet
1395 * \param rxPowersW the received power per channel band in watts
1396 */
1397 void Receive (std::string context, Ptr<const Packet> p, RxPowerWattPerChannelBand rxPowersW);
1398 };
1399
1400 void
Trace(Time startTime,Time duration)1401 BlockAckAggregationDisabledTest::TxopDurationTracer::Trace (Time startTime, Time duration)
1402 {
1403 if (duration > m_max)
1404 {
1405 m_max = duration;
1406 }
1407 }
1408
BlockAckAggregationDisabledTest(bool txop)1409 BlockAckAggregationDisabledTest::BlockAckAggregationDisabledTest (bool txop)
1410 : TestCase ("Test case for Block Ack Policy with aggregation disabled"),
1411 m_txop (txop),
1412 m_received (0),
1413 m_txTotal (0),
1414 m_txSinceBar (0),
1415 m_nBar (0),
1416 m_nBa (0)
1417 {
1418 }
1419
~BlockAckAggregationDisabledTest()1420 BlockAckAggregationDisabledTest::~BlockAckAggregationDisabledTest ()
1421 {
1422 }
1423
1424 void
L7Receive(std::string context,Ptr<const Packet> p,const Address & adr)1425 BlockAckAggregationDisabledTest::L7Receive (std::string context, Ptr<const Packet> p, const Address &adr)
1426 {
1427 if (p->GetSize () == 1400)
1428 {
1429 m_received++;
1430 }
1431 }
1432
1433 void
Transmit(std::string context,Ptr<const Packet> p,double power)1434 BlockAckAggregationDisabledTest::Transmit (std::string context, Ptr<const Packet> p, double power)
1435 {
1436 WifiMacHeader hdr;
1437 p->PeekHeader (hdr);
1438
1439 if (m_nBar < 2 && (m_txSinceBar == 9 || m_txTotal == 14))
1440 {
1441 NS_TEST_ASSERT_MSG_EQ (hdr.IsBlockAckReq (), true, "Didn't get a BlockAckReq when expected");
1442 }
1443 else
1444 {
1445 NS_TEST_ASSERT_MSG_EQ (hdr.IsBlockAckReq (), false, "Got a BlockAckReq when not expected");
1446 }
1447
1448 if (hdr.IsQosData ())
1449 {
1450 m_txTotal++;
1451 if (hdr.IsQosBlockAck ())
1452 {
1453 m_txSinceBar++;
1454 }
1455
1456 if (!m_txop)
1457 {
1458 NS_TEST_EXPECT_MSG_EQ ((m_txTotal == 1 || hdr.IsQosBlockAck ()), true, "Unexpected QoS ack policy");
1459 }
1460 else
1461 {
1462 NS_TEST_EXPECT_MSG_EQ ((m_txTotal <= 2 || hdr.IsQosBlockAck ()), true, "Unexpected QoS ack policy");
1463 }
1464 }
1465 else if (hdr.IsBlockAckReq ())
1466 {
1467 m_txSinceBar = 0;
1468 m_nBar++;
1469 }
1470 }
1471
1472 void
Receive(std::string context,Ptr<const Packet> p,RxPowerWattPerChannelBand rxPowersW)1473 BlockAckAggregationDisabledTest::Receive (std::string context, Ptr<const Packet> p, RxPowerWattPerChannelBand rxPowersW)
1474 {
1475 WifiMacHeader hdr;
1476 p->PeekHeader (hdr);
1477
1478 if (hdr.IsBlockAck ())
1479 {
1480 m_nBa++;
1481 }
1482 }
1483
1484 void
DoRun(void)1485 BlockAckAggregationDisabledTest::DoRun (void)
1486 {
1487 NodeContainer wifiStaNode;
1488 wifiStaNode.Create (1);
1489
1490 NodeContainer wifiApNode;
1491 wifiApNode.Create (1);
1492
1493 YansWifiChannelHelper channel = YansWifiChannelHelper::Default ();
1494 YansWifiPhyHelper phy;
1495 phy.SetChannel (channel.Create ());
1496
1497 WifiHelper wifi;
1498 wifi.SetStandard (WIFI_STANDARD_80211n_5GHZ);
1499 Config::SetDefault ("ns3::WifiDefaultAckManager::BaThreshold", DoubleValue (0.125));
1500 wifi.SetRemoteStationManager ("ns3::IdealWifiManager");
1501
1502 WifiMacHelper mac;
1503 Ssid ssid = Ssid ("ns-3-ssid");
1504 mac.SetType ("ns3::StaWifiMac",
1505 "BE_MaxAmsduSize", UintegerValue (0),
1506 "BE_MaxAmpduSize", UintegerValue (0),
1507 "Ssid", SsidValue (ssid),
1508 /* setting blockack threshold for sta's BE queue */
1509 "BE_BlockAckThreshold", UintegerValue (2),
1510 "ActiveProbing", BooleanValue (false));
1511
1512 NetDeviceContainer staDevices;
1513 staDevices = wifi.Install (phy, mac, wifiStaNode);
1514
1515 mac.SetType ("ns3::ApWifiMac",
1516 "BE_MaxAmsduSize", UintegerValue (0),
1517 "BE_MaxAmpduSize", UintegerValue (0),
1518 "Ssid", SsidValue (ssid),
1519 "BeaconGeneration", BooleanValue (true));
1520
1521 NetDeviceContainer apDevices;
1522 apDevices = wifi.Install (phy, mac, wifiApNode);
1523
1524 MobilityHelper mobility;
1525 Ptr<ListPositionAllocator> positionAlloc = CreateObject<ListPositionAllocator> ();
1526
1527 positionAlloc->Add (Vector (0.0, 0.0, 0.0));
1528 positionAlloc->Add (Vector (1.0, 0.0, 0.0));
1529 mobility.SetPositionAllocator (positionAlloc);
1530
1531 mobility.SetMobilityModel ("ns3::ConstantPositionMobilityModel");
1532 mobility.Install (wifiApNode);
1533 mobility.Install (wifiStaNode);
1534
1535 Ptr<WifiNetDevice> ap_device = DynamicCast<WifiNetDevice> (apDevices.Get (0));
1536 Ptr<WifiNetDevice> sta_device = DynamicCast<WifiNetDevice> (staDevices.Get (0));
1537
1538 // Disable A-MPDU aggregation
1539 sta_device->GetMac ()->SetAttribute ("BE_MaxAmpduSize", UintegerValue (0));
1540 TxopDurationTracer txopTracer;
1541
1542 if (m_txop)
1543 {
1544 PointerValue ptr;
1545 sta_device->GetMac ()->GetAttribute ("BE_Txop", ptr);
1546 ptr.Get<QosTxop> ()->TraceConnectWithoutContext ("TxopTrace", MakeCallback (&TxopDurationTracer::Trace, &txopTracer));
1547
1548 // set the TXOP limit on BE AC
1549 Ptr<RegularWifiMac> ap_mac = DynamicCast<RegularWifiMac> (ap_device->GetMac ());
1550 NS_ASSERT (ap_mac);
1551 ap_mac->GetAttribute ("BE_Txop", ptr);
1552 ptr.Get<QosTxop> ()->SetTxopLimit (MicroSeconds (4800));
1553 }
1554
1555 PacketSocketAddress socket;
1556 socket.SetSingleDevice (sta_device->GetIfIndex ());
1557 socket.SetPhysicalAddress (ap_device->GetAddress ());
1558 socket.SetProtocol (1);
1559
1560 // give packet socket powers to nodes.
1561 PacketSocketHelper packetSocket;
1562 packetSocket.Install (wifiStaNode);
1563 packetSocket.Install (wifiApNode);
1564
1565 // the first client application generates a single packet, which is sent
1566 // with the normal ack policy because there are no other packets queued
1567 Ptr<PacketSocketClient> client1 = CreateObject<PacketSocketClient> ();
1568 client1->SetAttribute ("PacketSize", UintegerValue (1400));
1569 client1->SetAttribute ("MaxPackets", UintegerValue (1));
1570 client1->SetAttribute ("Interval", TimeValue (MicroSeconds (0)));
1571 client1->SetRemote (socket);
1572 wifiStaNode.Get (0)->AddApplication (client1);
1573 client1->SetStartTime (Seconds (1));
1574 client1->SetStopTime (Seconds (3.0));
1575
1576 // the second client application generates 13 packets. Even if when the first
1577 // packet is queued the queue is empty, the first packet is not transmitted
1578 // immediately, but the EDCAF waits for the next slot boundary. At that time,
1579 // other packets have been queued, hence a BA agreement is established first.
1580 Ptr<PacketSocketClient> client2 = CreateObject<PacketSocketClient> ();
1581 client2->SetAttribute ("PacketSize", UintegerValue (1400));
1582 client2->SetAttribute ("MaxPackets", UintegerValue (13));
1583 client2->SetAttribute ("Interval", TimeValue (MicroSeconds (0)));
1584 client2->SetRemote (socket);
1585 wifiStaNode.Get (0)->AddApplication (client2);
1586 client2->SetStartTime (Seconds (1.5));
1587 client2->SetStopTime (Seconds (3.0));
1588
1589 Ptr<PacketSocketServer> server = CreateObject<PacketSocketServer> ();
1590 server->SetLocal (socket);
1591 wifiApNode.Get (0)->AddApplication (server);
1592 server->SetStartTime (Seconds (0.0));
1593 server->SetStopTime (Seconds (4.0));
1594
1595 Config::Connect ("/NodeList/*/ApplicationList/0/$ns3::PacketSocketServer/Rx", MakeCallback (&BlockAckAggregationDisabledTest::L7Receive, this));
1596 Config::Connect ("/NodeList/0/DeviceList/0/Phy/PhyTxBegin", MakeCallback (&BlockAckAggregationDisabledTest::Transmit, this));
1597 Config::Connect ("/NodeList/0/DeviceList/0/Phy/PhyRxBegin", MakeCallback (&BlockAckAggregationDisabledTest::Receive, this));
1598
1599 Simulator::Stop (Seconds (5));
1600 Simulator::Run ();
1601
1602 Simulator::Destroy ();
1603
1604 // The client applications generate 14 packets, so we expect that the wifi PHY
1605 // layer transmits 14 MPDUs, the server application receives 14 packets, and
1606 // two BARs are transmitted.
1607 NS_TEST_EXPECT_MSG_EQ (m_txTotal, 14, "Unexpected number of transmitted packets");
1608 NS_TEST_EXPECT_MSG_EQ (m_received, 14, "Unexpected number of received packets");
1609 NS_TEST_EXPECT_MSG_EQ (m_nBar, 2, "Unexpected number of Block Ack Requests");
1610 NS_TEST_EXPECT_MSG_EQ (m_nBa, 2, "Unexpected number of Block Ack Responses");
1611 if (m_txop)
1612 {
1613 NS_TEST_EXPECT_MSG_LT (txopTracer.m_max, MicroSeconds (4800), "TXOP duration exceeded!");
1614 NS_TEST_EXPECT_MSG_GT (txopTracer.m_max, MicroSeconds (3008), "The maximum TXOP duration is too short!");
1615 }
1616 }
1617
1618 /**
1619 * \ingroup wifi-test
1620 * \ingroup tests
1621 *
1622 * \brief Block Ack Test Suite
1623 */
1624 class BlockAckTestSuite : public TestSuite
1625 {
1626 public:
1627 BlockAckTestSuite ();
1628 };
1629
BlockAckTestSuite()1630 BlockAckTestSuite::BlockAckTestSuite ()
1631 : TestSuite ("wifi-block-ack", UNIT)
1632 {
1633 AddTestCase (new PacketBufferingCaseA, TestCase::QUICK);
1634 AddTestCase (new PacketBufferingCaseB, TestCase::QUICK);
1635 AddTestCase (new OriginatorBlockAckWindowTest, TestCase::QUICK);
1636 AddTestCase (new CtrlBAckResponseHeaderTest, TestCase::QUICK);
1637 AddTestCase (new BlockAckRecipientBufferTest (0), TestCase::QUICK);
1638 AddTestCase (new BlockAckRecipientBufferTest (4090), TestCase::QUICK);
1639 AddTestCase (new MultiStaCtrlBAckResponseHeaderTest, TestCase::QUICK);
1640 AddTestCase (new BlockAckAggregationDisabledTest (false), TestCase::QUICK);
1641 AddTestCase (new BlockAckAggregationDisabledTest (true), TestCase::QUICK);
1642 }
1643
1644 static BlockAckTestSuite g_blockAckTestSuite; ///< the test suite
1645