A Discrete-Event Network Simulator
API
block-ack-test-suite.cc
Go to the documentation of this file.
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/double.h"
23#include "ns3/boolean.h"
24#include "ns3/string.h"
25#include "ns3/qos-utils.h"
26#include "ns3/ctrl-headers.h"
27#include "ns3/packet.h"
28#include "ns3/wifi-net-device.h"
29#include "ns3/ap-wifi-mac.h"
30#include "ns3/wifi-mac-header.h"
31#include "ns3/mobility-helper.h"
32#include "ns3/yans-wifi-helper.h"
33#include "ns3/packet-socket-server.h"
34#include "ns3/packet-socket-client.h"
35#include "ns3/packet-socket-helper.h"
36#include "ns3/config.h"
37#include "ns3/pointer.h"
38#include "ns3/recipient-block-ack-agreement.h"
39#include "ns3/mac-rx-middle.h"
40#include "ns3/qos-txop.h"
41#include "ns3/originator-block-ack-agreement.h"
42#include "ns3/wifi-mac-queue-item.h"
43#include <list>
44
45using namespace ns3;
46
61//-------------------------------------------------------------------------------------
62
63/* ----- = old packets
64 * +++++ = new packets
65 *
66 * CASE A: startSeq < endSeq
67 * - - +
68 * initial buffer state: 0 16 56000
69 *
70 *
71 * 0 4095
72 * |------|++++++++++++++++|-----|
73 * ^ ^
74 * | startSeq | endSeq = 4000
75 *
76 * first received packet's sequence control = 64016 (seqNum = 4001, fragNum = 0) -
77 * second received packet's sequence control = 63984 (seqNum = 3999, fragNum = 0) +
78 * 4001 is older seq number so this packet should be inserted at the buffer's begin.
79 * 3999 is previous element of older of new packets: it should be inserted at the end of buffer.
80 *
81 * expected buffer state: 64016 0 16 56000 63984
82 *
83 */
85{
86public:
88 virtual ~PacketBufferingCaseA ();
89private:
90 void DoRun (void) override;
91 std::list<uint16_t> m_expectedBuffer;
92};
93
95 : TestCase ("Check correct order of buffering when startSequence < endSeq")
96{
97 m_expectedBuffer.push_back (64016);
98 m_expectedBuffer.push_back (0);
99 m_expectedBuffer.push_back (16);
100 m_expectedBuffer.push_back (56000);
101 m_expectedBuffer.push_back (63984);
102}
103
105{
106}
107
108void
110{
111 std::list<uint16_t> m_buffer;
112 std::list<uint16_t>::iterator i,j;
113 m_buffer.push_back (0);
114 m_buffer.push_back (16);
115 m_buffer.push_back (56000);
116
117 uint16_t endSeq = 4000;
118
119 uint16_t receivedSeq = 4001 * 16;
120 uint32_t mappedSeq = QosUtilsMapSeqControlToUniqueInteger (receivedSeq, endSeq);
121 /* cycle to right position for this packet */
122 for (i = m_buffer.begin (); i != m_buffer.end (); i++)
123 {
124 if (QosUtilsMapSeqControlToUniqueInteger ((*i), endSeq) >= mappedSeq)
125 {
126 //position found
127 break;
128 }
129 }
130 m_buffer.insert (i, receivedSeq);
131
132 receivedSeq = 3999 * 16;
133 mappedSeq = QosUtilsMapSeqControlToUniqueInteger (receivedSeq, endSeq);
134 /* cycle to right position for this packet */
135 for (i = m_buffer.begin (); i != m_buffer.end (); i++)
136 {
137 if (QosUtilsMapSeqControlToUniqueInteger ((*i), endSeq) >= mappedSeq)
138 {
139 //position found
140 break;
141 }
142 }
143 m_buffer.insert (i, receivedSeq);
144
145 for (i = m_buffer.begin (), j = m_expectedBuffer.begin (); i != m_buffer.end (); i++, j++)
146 {
147 NS_TEST_EXPECT_MSG_EQ (*i, *j, "error in buffer order");
148 }
149}
150
151
182{
183public:
185 virtual ~PacketBufferingCaseB ();
186private:
187 void DoRun (void) override;
188 std::list<uint16_t> m_expectedBuffer;
189};
190
192 : TestCase ("Check correct order of buffering when startSequence > endSeq")
193{
194 m_expectedBuffer.push_back (240);
195 m_expectedBuffer.push_back (241);
196 m_expectedBuffer.push_back (256);
197 m_expectedBuffer.push_back (64000);
198 m_expectedBuffer.push_back (64800);
199 m_expectedBuffer.push_back (16);
200}
201
203{
204}
205
206void
208{
209 std::list<uint16_t> m_buffer;
210 std::list<uint16_t>::iterator i,j;
211 m_buffer.push_back (256);
212 m_buffer.push_back (64000);
213 m_buffer.push_back (16);
214
215 uint16_t endSeq = 10;
216
217 uint16_t receivedSeq = 15 * 16;
218 uint32_t mappedSeq = QosUtilsMapSeqControlToUniqueInteger (receivedSeq, endSeq);
219 /* cycle to right position for this packet */
220 for (i = m_buffer.begin (); i != m_buffer.end (); i++)
221 {
222 if (QosUtilsMapSeqControlToUniqueInteger ((*i), endSeq) >= mappedSeq)
223 {
224 //position found
225 break;
226 }
227 }
228 m_buffer.insert (i, receivedSeq);
229
230 receivedSeq = 15 * 16 + 1;
231 mappedSeq = QosUtilsMapSeqControlToUniqueInteger (receivedSeq, endSeq);
232 /* cycle to right position for this packet */
233 for (i = m_buffer.begin (); i != m_buffer.end (); i++)
234 {
235 if (QosUtilsMapSeqControlToUniqueInteger ((*i), endSeq) >= mappedSeq)
236 {
237 //position found
238 break;
239 }
240 }
241 m_buffer.insert (i, receivedSeq);
242
243 receivedSeq = 4050 * 16;
244 mappedSeq = QosUtilsMapSeqControlToUniqueInteger (receivedSeq, endSeq);
245 /* cycle to right position for this packet */
246 for (i = m_buffer.begin (); i != m_buffer.end (); i++)
247 {
248 if (QosUtilsMapSeqControlToUniqueInteger ((*i), endSeq) >= mappedSeq)
249 {
250 //position found
251 break;
252 }
253 }
254 m_buffer.insert (i, receivedSeq);
255
256 for (i = m_buffer.begin (), j = m_expectedBuffer.begin (); i != m_buffer.end (); i++, j++)
257 {
258 NS_TEST_EXPECT_MSG_EQ (*i, *j, "error in buffer order");
259 }
260}
261
269{
270public:
272private:
273 void DoRun (void) override;
274};
275
277 : TestCase ("Check the correctness of the originator block ack window")
278{
279}
280
281void
283{
284 uint16_t winSize = 16;
285 uint16_t startingSeq = 4090;
286
287 OriginatorBlockAckAgreement agreement (Mac48Address ("00:00:00:00:00:01"), 0);
288 agreement.SetBufferSize (winSize);
289 agreement.SetStartingSequence (startingSeq);
290 agreement.InitTxWindow ();
291
292 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.GetWinSize (), winSize, "Incorrect window size");
293 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.GetWinStart (), startingSeq, "Incorrect winStart");
294 // check that all the elements in the window are cleared
295 for (uint16_t i = 0; i < winSize; i++)
296 {
297 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Not all flags are cleared after initialization");
298 }
299
300 // Notify the acknowledgment of 5 packets
301 WifiMacHeader hdr;
303 Ptr<WifiMacQueueItem> mpdu = Create<WifiMacQueueItem> (Create<Packet> (), hdr);
304 uint16_t seqNumber = startingSeq;
305 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
306 agreement.NotifyAckedMpdu (mpdu);
307
308 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
309 agreement.NotifyAckedMpdu (mpdu);
310
311 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
312 agreement.NotifyAckedMpdu (mpdu);
313
314 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
315 agreement.NotifyAckedMpdu (mpdu);
316
317 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
318 agreement.NotifyAckedMpdu (mpdu);
319
320 // the current window must look like this:
321 //
322 // |0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|
323 // ^
324 // |
325 // HEAD
326
327 startingSeq = (seqNumber + 1) % SEQNO_SPACE_SIZE;
328 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq, "Incorrect starting sequence after 5 acknowledgments");
329 for (uint16_t i = 0; i < winSize; i++)
330 {
331 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Not all flags are cleared after 5 acknowledgments");
332 }
333
334 // the next MPDU is not acknowledged, hence the window is blocked while the
335 // subsequent 4 MPDUs are acknowledged
336 ++seqNumber %= SEQNO_SPACE_SIZE;
337 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
338 agreement.NotifyAckedMpdu (mpdu);
339
340 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
341 agreement.NotifyAckedMpdu (mpdu);
342
343 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
344 agreement.NotifyAckedMpdu (mpdu);
345
346 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
347 agreement.NotifyAckedMpdu (mpdu);
348
349 // the current window must look like this:
350 //
351 // |0|0|0|0|0|0|1|1|1|1|0|0|0|0|0|0|
352 // ^
353 // |
354 // HEAD
355
356 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq, "Incorrect starting sequence after 1 unacknowledged MPDU");
357 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (0), false, "Incorrect flag after 1 unacknowledged MPDU");
358 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (1), true, "Incorrect flag after 1 unacknowledged MPDU");
359 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (2), true, "Incorrect flag after 1 unacknowledged MPDU");
360 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (3), true, "Incorrect flag after 1 unacknowledged MPDU");
361 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (4), true, "Incorrect flag after 1 unacknowledged MPDU");
362 for (uint16_t i = 5; i < winSize; i++)
363 {
364 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after 1 unacknowledged MPDU");
365 }
366
367 // the missing MPDU is now acknowledged; the window moves forward and the starting
368 // sequence number is the one of the first unacknowledged MPDU
369 mpdu->GetHeader ().SetSequenceNumber (startingSeq);
370 agreement.NotifyAckedMpdu (mpdu);
371
372 // the current window must look like this:
373 //
374 // |0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|
375 // ^
376 // |
377 // HEAD
378
379 startingSeq = (seqNumber + 1) % SEQNO_SPACE_SIZE;
380 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq, "Incorrect starting sequence after acknowledgment of missing MPDU");
381 for (uint16_t i = 0; i < winSize; i++)
382 {
383 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Not all flags are cleared after acknowledgment of missing MPDU");
384 }
385
386 // Now, create a hole of 3 MPDUs before 4 acknowledged MPDUs, another hole of 2 MPDUs before 3 acknowledged MPDUs
387 seqNumber = (seqNumber + 4) % SEQNO_SPACE_SIZE;
388 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
389 agreement.NotifyAckedMpdu (mpdu);
390
391 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
392 agreement.NotifyAckedMpdu (mpdu);
393
394 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
395 agreement.NotifyAckedMpdu (mpdu);
396
397 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
398 agreement.NotifyAckedMpdu (mpdu);
399
400 seqNumber = (seqNumber + 3) % SEQNO_SPACE_SIZE;
401 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
402 agreement.NotifyAckedMpdu (mpdu);
403
404 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
405 agreement.NotifyAckedMpdu (mpdu);
406
407 mpdu->GetHeader ().SetSequenceNumber (++seqNumber %= SEQNO_SPACE_SIZE);
408 agreement.NotifyAckedMpdu (mpdu);
409
410 // the current window must look like this:
411 //
412 // |1|0|0|1|1|1|0|0|0|0|0|0|0|1|1|1|
413 // ^
414 // |
415 // HEAD
416
417 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq, "Incorrect starting sequence after 3 unacknowledged MPDUs");
418 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (0), false, "Incorrect flag after 3 unacknowledged MPDUs");
419 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (1), false, "Incorrect flag after 3 unacknowledged MPDUs");
420 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (2), false, "Incorrect flag after 3 unacknowledged MPDUs");
421 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (3), true, "Incorrect flag after 3 unacknowledged MPDUs");
422 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (4), true, "Incorrect flag after 3 unacknowledged MPDUs");
423 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (5), true, "Incorrect flag after 3 unacknowledged MPDUs");
424 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (6), true, "Incorrect flag after 3 unacknowledged MPDUs");
425 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (7), false, "Incorrect flag after 3 unacknowledged MPDUs");
426 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (8), false, "Incorrect flag after 3 unacknowledged MPDUs");
427 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (9), true, "Incorrect flag after 3 unacknowledged MPDUs");
428 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (10), true, "Incorrect flag after 3 unacknowledged MPDUs");
429 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (11), true, "Incorrect flag after 3 unacknowledged MPDUs");
430 for (uint16_t i = 12; i < winSize; i++)
431 {
432 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after 3 unacknowledged MPDUs");
433 }
434
435 // the transmission of an MPDU beyond the current window (by 2 positions) is
436 // notified, hence the window moves forward 2 positions
437 seqNumber = (agreement.m_txWindow.GetWinEnd () + 2) % SEQNO_SPACE_SIZE;
438 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
439 agreement.NotifyTransmittedMpdu (mpdu);
440
441 // the current window must look like this:
442 //
443 // |1|0|0|1|1|1|0|0|0|0|0|0|0|1|1|1|
444 // ^
445 // |
446 // HEAD
447
448 startingSeq = (startingSeq + 2) % SEQNO_SPACE_SIZE;
449 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq,
450 "Incorrect starting sequence after transmitting an MPDU beyond the current window");
451 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (0), false, "Incorrect flag after transmitting an MPDU beyond the current window");
452 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (1), true, "Incorrect flag after transmitting an MPDU beyond the current window");
453 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (2), true, "Incorrect flag after transmitting an MPDU beyond the current window");
454 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (3), true, "Incorrect flag after transmitting an MPDU beyond the current window");
455 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (4), true, "Incorrect flag after transmitting an MPDU beyond the current window");
456 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (5), false, "Incorrect flag after transmitting an MPDU beyond the current window");
457 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (6), false, "Incorrect flag after transmitting an MPDU beyond the current window");
458 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (7), true, "Incorrect flag after transmitting an MPDU beyond the current window");
459 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (8), true, "Incorrect flag after transmitting an MPDU beyond the current window");
460 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (9), true, "Incorrect flag after transmitting an MPDU beyond the current window");
461 for (uint16_t i = 10; i < winSize; i++)
462 {
463 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after transmitting an MPDU beyond the current window");
464 }
465
466 // another MPDU is transmitted beyond the current window. Now, the window advances
467 // until the first unacknowledged MPDU
468 seqNumber = (agreement.m_txWindow.GetWinEnd () + 1) % SEQNO_SPACE_SIZE;
469 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
470 agreement.NotifyTransmittedMpdu (mpdu);
471
472 // the current window must look like this:
473 //
474 // |0|0|0|1|1|1|0|0|0|0|0|0|0|0|0|0|
475 // ^
476 // |
477 // HEAD
478
479 startingSeq = (startingSeq + 5) % SEQNO_SPACE_SIZE;
480 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq,
481 "Incorrect starting sequence after transmitting another MPDU beyond the current window");
482 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (0), false, "Incorrect flag after transmitting another MPDU beyond the current window");
483 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (1), false, "Incorrect flag after transmitting another MPDU beyond the current window");
484 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (2), true, "Incorrect flag after transmitting another MPDU beyond the current window");
485 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (3), true, "Incorrect flag after transmitting another MPDU beyond the current window");
486 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (4), true, "Incorrect flag after transmitting another MPDU beyond the current window");
487 for (uint16_t i = 5; i < winSize; i++)
488 {
489 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after transmitting another MPDU beyond the current window");
490 }
491
492 // the MPDU next to winStart is discarded, hence the window advances to make it an old packet.
493 // Since the subsequent MPDUs have been acknowledged, the window advances further.
494 seqNumber = (startingSeq + 1) % SEQNO_SPACE_SIZE;
495 mpdu->GetHeader ().SetSequenceNumber (seqNumber);
496 agreement.NotifyDiscardedMpdu (mpdu);
497
498 // the current window must look like this:
499 //
500 // |0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|
501 // ^
502 // |
503 // HEAD
504
505 startingSeq = (startingSeq + 5) % SEQNO_SPACE_SIZE;
506 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq,
507 "Incorrect starting sequence after discarding an MPDU");
508 for (uint16_t i = 0; i < winSize; i++)
509 {
510 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after discarding an MPDU");
511 }
512
513 // Finally, check that the window correctly advances when the MPDU with the starting sequence number
514 // is acknowledged after being the only unacknowledged MPDU
515 for (uint16_t i = 1; i < winSize; i++)
516 {
517 mpdu->GetHeader ().SetSequenceNumber ((startingSeq + i) % SEQNO_SPACE_SIZE);
518 agreement.NotifyAckedMpdu (mpdu);
519 }
520
521 // the current window must look like this:
522 //
523 // |1|1|1|1|1|1|0|1|1|1|1|1|1|1|1|1|
524 // ^
525 // |
526 // HEAD
527
528 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq,
529 "Incorrect starting sequence after acknowledging all but the first MPDU");
530 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (0), false, "Incorrect flag after acknowledging all but the first MPDU");
531 for (uint16_t i = 1; i < winSize; i++)
532 {
533 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), true, "Incorrect flag after acknowledging all but the first MPDU");
534 }
535
536 // acknowledge the first MPDU
537 mpdu->GetHeader ().SetSequenceNumber (startingSeq % SEQNO_SPACE_SIZE);
538 agreement.NotifyAckedMpdu (mpdu);
539
540 // the current window must look like this:
541 //
542 // |0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|0|
543 // ^
544 // |
545 // HEAD
546
547 startingSeq = (startingSeq + winSize) % SEQNO_SPACE_SIZE;
548 NS_TEST_EXPECT_MSG_EQ (agreement.GetStartingSequence (), startingSeq,
549 "Incorrect starting sequence after acknowledging the first MPDU");
550 for (uint16_t i = 0; i < winSize; i++)
551 {
552 NS_TEST_EXPECT_MSG_EQ (agreement.m_txWindow.At (i), false, "Incorrect flag after acknowledging the first MPDU");
553 }
554}
555
556
564{
565public:
567private:
568 void DoRun (void) override;
570};
571
573 : TestCase ("Check the correctness of block ack compressed bitmap")
574{
575}
576
577void
579{
580 m_blockAckHdr.SetType (BlockAckType::COMPRESSED);
581
582 //Case 1: startSeq < endSeq
583 // 179 242
585 for (uint16_t i = 179; i < 220; i++)
586 {
588 }
589 for (uint16_t i = 225; i <= 242; i++)
590 {
592 }
593 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[0], 0xff, "error in compressed bitmap");
594 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[1], 0xff, "error in compressed bitmap");
595 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[2], 0xff, "error in compressed bitmap");
596 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[3], 0xff, "error in compressed bitmap");
597 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[4], 0xff, "error in compressed bitmap");
598 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[5], 0xc1, "error in compressed bitmap");
599 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[6], 0xff, "error in compressed bitmap");
600 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[7], 0xff, "error in compressed bitmap");
602 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[0], 0xff, "error in compressed bitmap");
603 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[1], 0xff, "error in compressed bitmap");
604 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[2], 0xff, "error in compressed bitmap");
605 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[3], 0xff, "error in compressed bitmap");
606 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[4], 0xff, "error in compressed bitmap");
607 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[5], 0xc1, "error in compressed bitmap");
608 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[6], 0xff, "error in compressed bitmap");
609 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[7], 0xff, "error in compressed bitmap");
610 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (220), false, "error in compressed bitmap");
611 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (225), true, "error in compressed bitmap");
612 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (1500), false, "error in compressed bitmap");
613
615
616 //Case 2: startSeq > endSeq
617 // 4090 58
619 for (uint16_t i = 4090; i != 10; i = (i + 1) % 4096)
620 {
622 }
623 for (uint16_t i = 22; i < 25; i++)
624 {
626 }
627 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[0], 0xff, "error in compressed bitmap");
628 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[1], 0xff, "error in compressed bitmap");
629 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[2], 0x00, "error in compressed bitmap");
630 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[3], 0x70, "error in compressed bitmap");
631 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[4], 0x00, "error in compressed bitmap");
632 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[5], 0x00, "error in compressed bitmap");
633 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[6], 0x00, "error in compressed bitmap");
634 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[7], 0x00, "error in compressed bitmap");
636 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[0], 0xff, "error in compressed bitmap");
637 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[1], 0xff, "error in compressed bitmap");
638 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[2], 0x00, "error in compressed bitmap");
639 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[3], 0x70, "error in compressed bitmap");
640 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[4], 0x00, "error in compressed bitmap");
641 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[5], 0x00, "error in compressed bitmap");
642 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[6], 0x00, "error in compressed bitmap");
643 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.GetBitmap ()[7], 0x00, "error in compressed bitmap");
644 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (4090), true, "error in compressed bitmap");
645 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (4095), true, "error in compressed bitmap");
646 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (10), false, "error in compressed bitmap");
647 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (35), false, "error in compressed bitmap");
648 NS_TEST_EXPECT_MSG_EQ (m_blockAckHdr.IsPacketReceived (80), false, "error in compressed bitmap");
649}
650
651
659{
660public:
665 BlockAckRecipientBufferTest (uint16_t ssn);
667
668 void DoRun (void) override;
669
676
677private:
678 uint16_t m_ssn;
679 std::list<Ptr<WifiMacQueueItem>> m_fwup;
680};
681
683 : TestCase ("Test case for Block Ack recipient reordering buffer operations"),
684 m_ssn (ssn)
685{
686}
687
689{
690}
691
692void
694{
695 m_fwup.push_back (mpdu);
696}
697
698void
700{
701 Ptr<MacRxMiddle> rxMiddle = Create<MacRxMiddle> ();
702 rxMiddle->SetForwardCallback (MakeCallback (&BlockAckRecipientBufferTest::ForwardUp, this));
703
704 RecipientBlockAckAgreement agreement (Mac48Address::Allocate () /* originator */,
705 true /* amsduSupported */, 0 /* tid */, 10 /* bufferSize */,
706 0 /* timeout */, m_ssn, true /* htSupported */);
707 agreement.SetMacRxMiddle (rxMiddle);
708
709 WifiMacHeader hdr;
711 hdr.SetAddr1 (Mac48Address::Allocate ());
712 hdr.SetQosTid (0);
713
714 // Notify the reception of an MPDU with SN = SSN.
716 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
717
718 // This MPDU is forwarded up and WinStartB is set to SSN + 1.
719 NS_TEST_ASSERT_MSG_EQ (m_fwup.size (), 1, "MPDU with SN=SSN must have been forwarded up");
720 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (), m_ssn,
721 "The MPDU forwarded up is not the expected one");
722
723 m_fwup.clear ();
724
725 // Notify the reception of MPDUs with SN = SSN + {4, 2, 5, 3, 10, 7}
726 // Recipient buffer: | |X|X|X|X| |X| | |X|
727 // ^
728 // |
729 // SSN + 1
731 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
733 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
735 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
737 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
739 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
741 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
742
743 // No MPDU is forwarded up because the one with SN = SSN + 1 is missing
744 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
745
746 // Notify the reception of an "old" MPDU (SN = SSN)
748 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
749
750 // No MPDU is forwarded up
751 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
752
753 // Notify the reception of a duplicate MPDU (SN = SSN + 2)
755 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(10), hdr));
756
757 // No MPDU is forwarded up
758 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
759
760 // Notify the reception of an MPDU with SN = SSN + 1
761 // Recipient buffer: |X|X|X|X|X| |X| | |X|
762 // ^
763 // |
764 // SSN + 1
766 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
767
768 // All the MPDUs with SN = SSN + {1, 2, 3, 4, 5} must have been forwarded up in order
769 NS_TEST_ASSERT_MSG_EQ (m_fwup.size (), 5, "5 MPDUs must have been forwarded up");
770
771 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
772 (m_ssn + 1) % SEQNO_SPACE_SIZE,
773 "The MPDU forwarded up is not the expected one");
774 m_fwup.pop_front ();
775
776 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
777 (m_ssn + 2) % SEQNO_SPACE_SIZE,
778 "The MPDU forwarded up is not the expected one");
779 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetPacketSize (), 0,
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 + 3) % 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 + 4) % SEQNO_SPACE_SIZE,
790 "The MPDU forwarded up is not the expected one");
791 m_fwup.pop_front ();
792
793 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
794 (m_ssn + 5) % SEQNO_SPACE_SIZE,
795 "The MPDU forwarded up is not the expected one");
796 m_fwup.pop_front ();
797
798 // Recipient buffer: | |X| | |X| | | | | |
799 // ^ ^
800 // | |
801 // SSN + 6 SSN + 15
802 // Notify the reception of an MPDU beyond the current window (SN = SSN + 17)
804 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
805
806 // WinStartB is set to SSN + 8 (so that WinEndB = SSN + 17). The MPDU with
807 // SN = SSN + 7 is forwarded up, irrespective of the missed reception of the
808 // MPDU with SN = SSN + 6
809 NS_TEST_ASSERT_MSG_EQ (m_fwup.size (), 1, "One MPDU must have been forwarded up");
810
811 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
812 (m_ssn + 7) % SEQNO_SPACE_SIZE,
813 "The MPDU forwarded up is not the expected one");
814 m_fwup.pop_front ();
815
816 // Recipient buffer: | | |X| | | | | | |X|
817 // ^ ^
818 // | |
819 // SSN + 8 SSN + 17
820 // Notify the reception of a BlockAckReq with SSN = SSN + 7
821 agreement.NotifyReceivedBar ((m_ssn + 7) % SEQNO_SPACE_SIZE);
822
823 // No MPDU is forwarded up
824 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
825
826 // Notify the reception of a BlockAckReq with SSN = SSN + 8
827 agreement.NotifyReceivedBar ((m_ssn + 8) % SEQNO_SPACE_SIZE);
828
829 // No MPDU is forwarded up
830 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
831
832 // Notify the reception of MPDUs with SN = SSN + {9, 11}
833 // Recipient buffer: | |X|X|X| | | | | |X|
834 // ^ ^
835 // | |
836 // SSN + 8 SSN + 17
838 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
840 agreement.NotifyReceivedMpdu (Create<WifiMacQueueItem> (Create<Packet>(), hdr));
841
842 // No MPDU is forwarded up because the one with SN = SSN + 8 is missing
843 NS_TEST_ASSERT_MSG_EQ (m_fwup.empty (), true, "No MPDU must have been forwarded up");
844
845 // Notify the reception of a BlockAckReq with SSN = SSN + 10
846 agreement.NotifyReceivedBar ((m_ssn + 10) % SEQNO_SPACE_SIZE);
847
848 // Forward up buffered MPDUs with SN < SSN + 10 (the MPDU with SN = SSN + 9)
849 // and then buffered MPDUs with SN >= SSN + 10 until a hole is found (MPDUs
850 // with SN = SSN + 10 and SN = SSN + 11)
851 NS_TEST_ASSERT_MSG_EQ (m_fwup.size (), 3, "3 MPDUs must have been forwarded up");
852
853 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
854 (m_ssn + 9) % 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 + 10) % SEQNO_SPACE_SIZE,
860 "The MPDU forwarded up is not the expected one");
861 m_fwup.pop_front ();
862
863 NS_TEST_ASSERT_MSG_EQ (m_fwup.front ()->GetHeader ().GetSequenceNumber (),
864 (m_ssn + 11) % SEQNO_SPACE_SIZE,
865 "The MPDU forwarded up is not the expected one");
866 m_fwup.pop_front ();
867
868 Simulator::Run ();
869 Simulator::Destroy ();
870}
871
872
880{
881public:
883private:
884 virtual void DoRun (void);
885};
886
888 : TestCase ("Check the correctness of Multi-STA block ack")
889{
890}
891
892void
894{
895 // Create a Multi-STA Block Ack with 6 Per AID TID Info subfields
896 BlockAckType baType (BlockAckType::MULTI_STA, {0, 4, 8, 16, 32, 8});
897
898 CtrlBAckResponseHeader blockAck;
899 blockAck.SetType (baType);
900
901 /* 1st Per AID TID Info subfield */
902 uint16_t aid1 = 100;
903 bool ackType1 = true;
904 uint8_t tid1 = 1;
905
906 blockAck.SetAid11 (aid1, 0);
907 blockAck.SetAckType (ackType1, 0);
908 blockAck.SetTidInfo (tid1, 0);
909
910 /* 2nd Per AID TID Info subfield */
911 uint16_t aid2 = 200;
912 bool ackType2 = false;
913 uint8_t tid2 = 2;
914 uint16_t startSeq2 = 1000;
915
916 blockAck.SetAid11 (aid2, 1);
917 blockAck.SetAckType (ackType2, 1);
918 blockAck.SetTidInfo (tid2, 1);
919 blockAck.SetStartingSequence (startSeq2, 1);
920 // 1st byte of the bitmap: 01010101
921 for (uint16_t i = startSeq2; i < startSeq2 + 8; i+=2)
922 {
923 blockAck.SetReceivedPacket (i, 1);
924 }
925 // 2nd byte of the bitmap: 10101010
926 for (uint16_t i = startSeq2 + 9; i < startSeq2 + 16; i+=2)
927 {
928 blockAck.SetReceivedPacket (i, 1);
929 }
930 // 3rd byte of the bitmap: 00000000
931 // 4th byte of the bitmap: 11111111
932 for (uint16_t i = startSeq2 + 24; i < startSeq2 + 32; i++)
933 {
934 blockAck.SetReceivedPacket (i, 1);
935 }
936
937 /* 3rd Per AID TID Info subfield */
938 uint16_t aid3 = 300;
939 bool ackType3 = false;
940 uint8_t tid3 = 3;
941 uint16_t startSeq3 = 2000;
942
943 blockAck.SetAid11 (aid3, 2);
944 blockAck.SetAckType (ackType3, 2);
945 blockAck.SetTidInfo (tid3, 2);
946 blockAck.SetStartingSequence (startSeq3, 2);
947 // 1st byte of the bitmap: 01010101
948 for (uint16_t i = startSeq3; i < startSeq3 + 8; i+=2)
949 {
950 blockAck.SetReceivedPacket (i, 2);
951 }
952 // 2nd byte of the bitmap: 10101010
953 for (uint16_t i = startSeq3 + 9; i < startSeq3 + 16; i+=2)
954 {
955 blockAck.SetReceivedPacket (i, 2);
956 }
957 // 3rd byte of the bitmap: 00000000
958 // 4th byte of the bitmap: 11111111
959 for (uint16_t i = startSeq3 + 24; i < startSeq3 + 32; i++)
960 {
961 blockAck.SetReceivedPacket (i, 2);
962 }
963 // 5th byte of the bitmap: 00001111
964 for (uint16_t i = startSeq3 + 32; i < startSeq3 + 36; i++)
965 {
966 blockAck.SetReceivedPacket (i, 2);
967 }
968 // 6th byte of the bitmap: 11110000
969 for (uint16_t i = startSeq3 + 44; i < startSeq3 + 48; i++)
970 {
971 blockAck.SetReceivedPacket (i, 2);
972 }
973 // 7th byte of the bitmap: 00000000
974 // 8th byte of the bitmap: 11111111
975 for (uint16_t i = startSeq3 + 56; i < startSeq3 + 64; i++)
976 {
977 blockAck.SetReceivedPacket (i, 2);
978 }
979
980 /* 4th Per AID TID Info subfield */
981 uint16_t aid4 = 400;
982 bool ackType4 = false;
983 uint8_t tid4 = 4;
984 uint16_t startSeq4 = 3000;
985
986 blockAck.SetAid11 (aid4, 3);
987 blockAck.SetAckType (ackType4, 3);
988 blockAck.SetTidInfo (tid4, 3);
989 blockAck.SetStartingSequence (startSeq4, 3);
990 // 1st byte of the bitmap: 01010101
991 for (uint16_t i = startSeq4; i < startSeq4 + 8; i+=2)
992 {
993 blockAck.SetReceivedPacket (i, 3);
994 }
995 // 2nd byte of the bitmap: 10101010
996 for (uint16_t i = startSeq4 + 9; i < startSeq4 + 16; i+=2)
997 {
998 blockAck.SetReceivedPacket (i, 3);
999 }
1000 // 3rd byte of the bitmap: 00000000
1001 // 4th byte of the bitmap: 11111111
1002 for (uint16_t i = startSeq4 + 24; i < startSeq4 + 32; i++)
1003 {
1004 blockAck.SetReceivedPacket (i, 3);
1005 }
1006 // 5th byte of the bitmap: 00001111
1007 for (uint16_t i = startSeq4 + 32; i < startSeq4 + 36; i++)
1008 {
1009 blockAck.SetReceivedPacket (i, 3);
1010 }
1011 // 6th byte of the bitmap: 11110000
1012 for (uint16_t i = startSeq4 + 44; i < startSeq4 + 48; i++)
1013 {
1014 blockAck.SetReceivedPacket (i, 3);
1015 }
1016 // 7th byte of the bitmap: 00000000
1017 // 8th byte of the bitmap: 11111111
1018 for (uint16_t i = startSeq4 + 56; i < startSeq4 + 64; i++)
1019 {
1020 blockAck.SetReceivedPacket (i, 3);
1021 }
1022 // 9th byte of the bitmap: 00000000
1023 // 10th byte of the bitmap: 11111111
1024 for (uint16_t i = startSeq4 + 72; i < startSeq4 + 80; i++)
1025 {
1026 blockAck.SetReceivedPacket (i, 3);
1027 }
1028 // 11th byte of the bitmap: 00000000
1029 // 12th byte of the bitmap: 11111111
1030 for (uint16_t i = startSeq4 + 88; i < startSeq4 + 96; i++)
1031 {
1032 blockAck.SetReceivedPacket (i, 3);
1033 }
1034 // 13th byte of the bitmap: 00000000
1035 // 14th byte of the bitmap: 11111111
1036 for (uint16_t i = startSeq4 + 104; i < startSeq4 + 112; i++)
1037 {
1038 blockAck.SetReceivedPacket (i, 3);
1039 }
1040 // 15th byte of the bitmap: 00000000
1041 // 16th byte of the bitmap: 11111111
1042 for (uint16_t i = startSeq4 + 120; i < startSeq4 + 128; i++)
1043 {
1044 blockAck.SetReceivedPacket (i, 3);
1045 }
1046
1047 /* 5th Per AID TID Info subfield */
1048 uint16_t aid5 = 500;
1049 bool ackType5 = false;
1050 uint8_t tid5 = 5;
1051 uint16_t startSeq5 = 4000;
1052
1053 blockAck.SetAid11 (aid5, 4);
1054 blockAck.SetAckType (ackType5, 4);
1055 blockAck.SetTidInfo (tid5, 4);
1056 blockAck.SetStartingSequence (startSeq5, 4);
1057 // 1st byte of the bitmap: 01010101
1058 for (uint16_t i = startSeq5; i < startSeq5 + 8; i+=2)
1059 {
1060 blockAck.SetReceivedPacket (i, 4);
1061 }
1062 // 2nd byte of the bitmap: 10101010
1063 for (uint16_t i = startSeq5 + 9; i < startSeq5 + 16; i+=2)
1064 {
1065 blockAck.SetReceivedPacket (i, 4);
1066 }
1067 // 3rd byte of the bitmap: 00000000
1068 // 4th byte of the bitmap: 11111111
1069 for (uint16_t i = startSeq5 + 24; i < startSeq5 + 32; i++)
1070 {
1071 blockAck.SetReceivedPacket (i, 4);
1072 }
1073 // 5th byte of the bitmap: 00001111
1074 for (uint16_t i = startSeq5 + 32; i < startSeq5 + 36; i++)
1075 {
1076 blockAck.SetReceivedPacket (i, 4);
1077 }
1078 // 6th byte of the bitmap: 11110000
1079 for (uint16_t i = startSeq5 + 44; i < startSeq5 + 48; i++)
1080 {
1081 blockAck.SetReceivedPacket (i, 4);
1082 }
1083 // 7th byte of the bitmap: 00000000
1084 // 8th byte of the bitmap: 11111111
1085 for (uint16_t i = startSeq5 + 56; i < startSeq5 + 64; i++)
1086 {
1087 blockAck.SetReceivedPacket (i, 4);
1088 }
1089 // 9th byte of the bitmap: 00000000
1090 // 10th byte of the bitmap: 11111111
1091 for (uint16_t i = startSeq5 + 72; i < startSeq5 + 80; i++)
1092 {
1093 blockAck.SetReceivedPacket (i, 4);
1094 }
1095 // 11th byte of the bitmap: 00000000
1096 // 12th byte of the bitmap: 11111111
1097 for (uint16_t i = startSeq5 + 88; i < startSeq5 + 96; i++)
1098 {
1099 blockAck.SetReceivedPacket (i, 4);
1100 }
1101 // 13th byte of the bitmap: 00000000
1102 // 14th byte of the bitmap: 11111111
1103 for (uint16_t i = (startSeq5 + 104) % 4096; i < (startSeq5 + 112) % 4096; i++)
1104 {
1105 blockAck.SetReceivedPacket (i, 4);
1106 }
1107 // 15th byte of the bitmap: 00000000
1108 // 16th byte of the bitmap: 11111111
1109 for (uint16_t i = (startSeq5 + 120) % 4096; i < (startSeq5 + 128) % 4096; i++)
1110 {
1111 blockAck.SetReceivedPacket (i, 4);
1112 }
1113 // 17th byte of the bitmap: 00000000
1114 // 18th byte of the bitmap: 11111111
1115 for (uint16_t i = (startSeq5 + 136) % 4096; i < (startSeq5 + 144) % 4096; i++)
1116 {
1117 blockAck.SetReceivedPacket (i, 4);
1118 }
1119 // 19th byte of the bitmap: 00000000
1120 // 20th byte of the bitmap: 11111111
1121 for (uint16_t i = (startSeq5 + 152) % 4096; i < (startSeq5 + 160) % 4096; i++)
1122 {
1123 blockAck.SetReceivedPacket (i, 4);
1124 }
1125 // 21th byte of the bitmap: 00000000
1126 // 22th byte of the bitmap: 11111111
1127 for (uint16_t i = (startSeq5 + 168) % 4096; i < (startSeq5 + 176) % 4096; i++)
1128 {
1129 blockAck.SetReceivedPacket (i, 4);
1130 }
1131 // 23th byte of the bitmap: 00000000
1132 // 24th byte of the bitmap: 11111111
1133 for (uint16_t i = (startSeq5 + 184) % 4096; i < (startSeq5 + 192) % 4096; i++)
1134 {
1135 blockAck.SetReceivedPacket (i, 4);
1136 }
1137 // 25th byte of the bitmap: 00000000
1138 // 26th byte of the bitmap: 11111111
1139 for (uint16_t i = (startSeq5 + 200) % 4096; i < (startSeq5 + 208) % 4096; i++)
1140 {
1141 blockAck.SetReceivedPacket (i, 4);
1142 }
1143 // 27th byte of the bitmap: 00000000
1144 // 28th byte of the bitmap: 11111111
1145 for (uint16_t i = (startSeq5 + 216) % 4096; i < (startSeq5 + 224) % 4096; i++)
1146 {
1147 blockAck.SetReceivedPacket (i, 4);
1148 }
1149 // 29th byte of the bitmap: 00000000
1150 // 30th byte of the bitmap: 11111111
1151 for (uint16_t i = (startSeq5 + 232) % 4096; i < (startSeq5 + 240) % 4096; i++)
1152 {
1153 blockAck.SetReceivedPacket (i, 4);
1154 }
1155 // 31th byte of the bitmap: 00000000
1156 // 32th byte of the bitmap: 11111111
1157 for (uint16_t i = (startSeq5 + 248) % 4096; i < (startSeq5 + 256) % 4096; i++)
1158 {
1159 blockAck.SetReceivedPacket (i, 4);
1160 }
1161
1162 /* 6th Per AID TID Info subfield */
1163 uint16_t aid6 = 2045;
1164 bool ackType6 = true;
1165 uint8_t tid6 = 6;
1166 Mac48Address address6 = Mac48Address ("00:00:00:00:00:01");
1167
1168 blockAck.SetAid11 (aid6, 5);
1169 blockAck.SetAckType (ackType6, 5);
1170 blockAck.SetTidInfo (tid6, 5);
1171 blockAck.SetUnassociatedStaAddress (address6, 5);
1172
1173 // Serialize the header
1174 Ptr<Packet> packet = Create<Packet> ();
1175 packet->AddHeader (blockAck);
1176
1177 // Deserialize the header
1178 CtrlBAckResponseHeader blockAckCopy;
1179 packet->RemoveHeader (blockAckCopy);
1180
1181 // Check that the header has been correctly deserialized
1182 BlockAckType baTypeCopy = blockAckCopy.GetType ();
1183
1184 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_variant, BlockAckType::MULTI_STA, "Different block ack variant");
1185 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen.size (), 6, "Different number of bitmaps");
1186 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[0], 0, "Different length of the first bitmap");
1187 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[1], 4, "Different length of the second bitmap");
1188 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[2], 8, "Different length of the third bitmap");
1189 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[3], 16, "Different length of the fourth bitmap");
1190 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[4], 32, "Different length of the fifth bitmap");
1191 NS_TEST_EXPECT_MSG_EQ (baTypeCopy.m_bitmapLen[5], 8, "Different length for the sixth bitmap");
1192
1193 /* Check 1st Per AID TID Info subfield */
1194 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (0), aid1, "Different AID for the first Per AID TID Info subfield");
1195 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (0), ackType1, "Different Ack Type for the first Per AID TID Info subfield");
1196 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (0), tid1, "Different TID for the first Per AID TID Info subfield");
1197
1198 /* Check 2nd Per AID TID Info subfield */
1199 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (1), aid2, "Different AID for the second Per AID TID Info subfield");
1200 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (1), ackType2, "Different Ack Type for the second Per AID TID Info subfield");
1201 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (1), tid2, "Different TID for the second Per AID TID Info subfield");
1202 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetStartingSequence (1), startSeq2, "Different starting sequence number for the second Per AID TID Info subfield");
1203
1204 auto& bitmap2 = blockAckCopy.GetBitmap (1);
1205 NS_TEST_EXPECT_MSG_EQ (bitmap2.size (), 4, "Different bitmap length for the second Per AID TID Info subfield");
1206 NS_TEST_EXPECT_MSG_EQ (bitmap2[0], 0x55, "Error in the 1st byte of the bitmap for the second Per AID TID Info subfield");
1207 NS_TEST_EXPECT_MSG_EQ (bitmap2[1], 0xaa, "Error in the 2nd byte of the bitmap for the second Per AID TID Info subfield");
1208 NS_TEST_EXPECT_MSG_EQ (bitmap2[2], 0x00, "Error in the 3rd byte of the bitmap for the second Per AID TID Info subfield");
1209 NS_TEST_EXPECT_MSG_EQ (bitmap2[3], 0xff, "Error in the 4th byte of the bitmap for the second Per AID TID Info subfield");
1210
1211 /* Check 3rd Per AID TID Info subfield */
1212 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (2), aid3, "Different AID for the third Per AID TID Info subfield");
1213 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (2), ackType3, "Different Ack Type for the third Per AID TID Info subfield");
1214 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (2), tid3, "Different TID for the third Per AID TID Info subfield");
1215 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetStartingSequence (2), startSeq3, "Different starting sequence number for the third Per AID TID Info subfield");
1216
1217 auto& bitmap3 = blockAckCopy.GetBitmap (2);
1218 NS_TEST_EXPECT_MSG_EQ (bitmap3.size (), 8, "Different bitmap length for the third Per AID TID Info subfield");
1219 NS_TEST_EXPECT_MSG_EQ (bitmap3[0], 0x55, "Error in the 1st byte of the bitmap for the third Per AID TID Info subfield");
1220 NS_TEST_EXPECT_MSG_EQ (bitmap3[1], 0xaa, "Error in the 2nd byte of the bitmap for the third Per AID TID Info subfield");
1221 NS_TEST_EXPECT_MSG_EQ (bitmap3[2], 0x00, "Error in the 3rd byte of the bitmap for the third Per AID TID Info subfield");
1222 NS_TEST_EXPECT_MSG_EQ (bitmap3[3], 0xff, "Error in the 4th byte of the bitmap for the third Per AID TID Info subfield");
1223 NS_TEST_EXPECT_MSG_EQ (bitmap3[4], 0x0f, "Error in the 5th byte of the bitmap for the third Per AID TID Info subfield");
1224 NS_TEST_EXPECT_MSG_EQ (bitmap3[5], 0xf0, "Error in the 6th byte of the bitmap for the third Per AID TID Info subfield");
1225 NS_TEST_EXPECT_MSG_EQ (bitmap3[6], 0x00, "Error in the 7th byte of the bitmap for the third Per AID TID Info subfield");
1226 NS_TEST_EXPECT_MSG_EQ (bitmap3[7], 0xff, "Error in the 8th byte of the bitmap for the third Per AID TID Info subfield");
1227
1228 /* Check 4th Per AID TID Info subfield */
1229 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (3), aid4, "Different AID for the fourth Per AID TID Info subfield");
1230 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (3), ackType4, "Different Ack Type for the fourth Per AID TID Info subfield");
1231 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (3), tid4, "Different TID for the fourth Per AID TID Info subfield");
1232 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetStartingSequence (3), startSeq4, "Different starting sequence number for the fourth Per AID TID Info subfield");
1233
1234 auto& bitmap4 = blockAckCopy.GetBitmap (3);
1235 NS_TEST_EXPECT_MSG_EQ (bitmap4.size (), 16, "Different bitmap length for the fourth Per AID TID Info subfield");
1236 NS_TEST_EXPECT_MSG_EQ (bitmap4[0], 0x55, "Error in the 1st byte of the bitmap for the fourth Per AID TID Info subfield");
1237 NS_TEST_EXPECT_MSG_EQ (bitmap4[1], 0xaa, "Error in the 2nd byte of the bitmap for the fourth Per AID TID Info subfield");
1238 NS_TEST_EXPECT_MSG_EQ (bitmap4[2], 0x00, "Error in the 3rd byte of the bitmap for the fourth Per AID TID Info subfield");
1239 NS_TEST_EXPECT_MSG_EQ (bitmap4[3], 0xff, "Error in the 4th byte of the bitmap for the fourth Per AID TID Info subfield");
1240 NS_TEST_EXPECT_MSG_EQ (bitmap4[4], 0x0f, "Error in the 5th byte of the bitmap for the fourth Per AID TID Info subfield");
1241 NS_TEST_EXPECT_MSG_EQ (bitmap4[5], 0xf0, "Error in the 6th byte of the bitmap for the fourth Per AID TID Info subfield");
1242 NS_TEST_EXPECT_MSG_EQ (bitmap4[6], 0x00, "Error in the 7th byte of the bitmap for the fourth Per AID TID Info subfield");
1243 NS_TEST_EXPECT_MSG_EQ (bitmap4[7], 0xff, "Error in the 8th byte of the bitmap for the fourth Per AID TID Info subfield");
1244 NS_TEST_EXPECT_MSG_EQ (bitmap4[8], 0x00, "Error in the 9th byte of the bitmap for the fourth Per AID TID Info subfield");
1245 NS_TEST_EXPECT_MSG_EQ (bitmap4[9], 0xff, "Error in the 10th byte of the bitmap for the fourth Per AID TID Info subfield");
1246 NS_TEST_EXPECT_MSG_EQ (bitmap4[10], 0x00, "Error in the 11th byte of the bitmap for the fourth Per AID TID Info subfield");
1247 NS_TEST_EXPECT_MSG_EQ (bitmap4[11], 0xff, "Error in the 12th byte of the bitmap for the fourth Per AID TID Info subfield");
1248 NS_TEST_EXPECT_MSG_EQ (bitmap4[12], 0x00, "Error in the 13th byte of the bitmap for the fourth Per AID TID Info subfield");
1249 NS_TEST_EXPECT_MSG_EQ (bitmap4[13], 0xff, "Error in the 14th byte of the bitmap for the fourth Per AID TID Info subfield");
1250 NS_TEST_EXPECT_MSG_EQ (bitmap4[14], 0x00, "Error in the 15th byte of the bitmap for the fourth Per AID TID Info subfield");
1251 NS_TEST_EXPECT_MSG_EQ (bitmap4[15], 0xff, "Error in the 16th byte of the bitmap for the fourth Per AID TID Info subfield");
1252
1253 /* Check 5th Per AID TID Info subfield */
1254 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (4), aid5, "Different AID for the fifth Per AID TID Info subfield");
1255 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (4), ackType5, "Different Ack Type for the fifth Per AID TID Info subfield");
1256 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (4), tid5, "Different TID for the fifth Per AID TID Info subfield");
1257 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetStartingSequence (4), startSeq5, "Different starting sequence number for the fifth Per AID TID Info subfield");
1258
1259 auto& bitmap5 = blockAckCopy.GetBitmap (4);
1260 NS_TEST_EXPECT_MSG_EQ (bitmap5.size (), 32, "Different bitmap length for the fifth Per AID TID Info subfield");
1261 NS_TEST_EXPECT_MSG_EQ (bitmap5[0], 0x55, "Error in the 1st byte of the bitmap for the fifth Per AID TID Info subfield");
1262 NS_TEST_EXPECT_MSG_EQ (bitmap5[1], 0xaa, "Error in the 2nd byte of the bitmap for the fifth Per AID TID Info subfield");
1263 NS_TEST_EXPECT_MSG_EQ (bitmap5[2], 0x00, "Error in the 3rd byte of the bitmap for the fifth Per AID TID Info subfield");
1264 NS_TEST_EXPECT_MSG_EQ (bitmap5[3], 0xff, "Error in the 4th byte of the bitmap for the fifth Per AID TID Info subfield");
1265 NS_TEST_EXPECT_MSG_EQ (bitmap5[4], 0x0f, "Error in the 5th byte of the bitmap for the fifth Per AID TID Info subfield");
1266 NS_TEST_EXPECT_MSG_EQ (bitmap5[5], 0xf0, "Error in the 6th byte of the bitmap for the fifth Per AID TID Info subfield");
1267 NS_TEST_EXPECT_MSG_EQ (bitmap5[6], 0x00, "Error in the 7th byte of the bitmap for the fifth Per AID TID Info subfield");
1268 NS_TEST_EXPECT_MSG_EQ (bitmap5[7], 0xff, "Error in the 8th byte of the bitmap for the fifth Per AID TID Info subfield");
1269 NS_TEST_EXPECT_MSG_EQ (bitmap5[8], 0x00, "Error in the 9th byte of the bitmap for the fifth Per AID TID Info subfield");
1270 NS_TEST_EXPECT_MSG_EQ (bitmap5[9], 0xff, "Error in the 10th byte of the bitmap for the fifth Per AID TID Info subfield");
1271 NS_TEST_EXPECT_MSG_EQ (bitmap5[10], 0x00, "Error in the 11th byte of the bitmap for the fifth Per AID TID Info subfield");
1272 NS_TEST_EXPECT_MSG_EQ (bitmap5[11], 0xff, "Error in the 12th byte of the bitmap for the fifth Per AID TID Info subfield");
1273 NS_TEST_EXPECT_MSG_EQ (bitmap5[12], 0x00, "Error in the 13th byte of the bitmap for the fifth Per AID TID Info subfield");
1274 NS_TEST_EXPECT_MSG_EQ (bitmap5[13], 0xff, "Error in the 14th byte of the bitmap for the fifth Per AID TID Info subfield");
1275 NS_TEST_EXPECT_MSG_EQ (bitmap5[14], 0x00, "Error in the 15th byte of the bitmap for the fifth Per AID TID Info subfield");
1276 NS_TEST_EXPECT_MSG_EQ (bitmap5[15], 0xff, "Error in the 16th byte of the bitmap for the fifth Per AID TID Info subfield");
1277 NS_TEST_EXPECT_MSG_EQ (bitmap5[16], 0x00, "Error in the 17th byte of the bitmap for the fifth Per AID TID Info subfield");
1278 NS_TEST_EXPECT_MSG_EQ (bitmap5[17], 0xff, "Error in the 18th byte of the bitmap for the fifth Per AID TID Info subfield");
1279 NS_TEST_EXPECT_MSG_EQ (bitmap5[18], 0x00, "Error in the 19th byte of the bitmap for the fifth Per AID TID Info subfield");
1280 NS_TEST_EXPECT_MSG_EQ (bitmap5[19], 0xff, "Error in the 20th byte of the bitmap for the fifth Per AID TID Info subfield");
1281 NS_TEST_EXPECT_MSG_EQ (bitmap5[20], 0x00, "Error in the 21th byte of the bitmap for the fifth Per AID TID Info subfield");
1282 NS_TEST_EXPECT_MSG_EQ (bitmap5[21], 0xff, "Error in the 22th byte of the bitmap for the fifth Per AID TID Info subfield");
1283 NS_TEST_EXPECT_MSG_EQ (bitmap5[22], 0x00, "Error in the 23th byte of the bitmap for the fifth Per AID TID Info subfield");
1284 NS_TEST_EXPECT_MSG_EQ (bitmap5[23], 0xff, "Error in the 24th byte of the bitmap for the fifth Per AID TID Info subfield");
1285 NS_TEST_EXPECT_MSG_EQ (bitmap5[24], 0x00, "Error in the 25th byte of the bitmap for the fifth Per AID TID Info subfield");
1286 NS_TEST_EXPECT_MSG_EQ (bitmap5[25], 0xff, "Error in the 26th byte of the bitmap for the fifth Per AID TID Info subfield");
1287 NS_TEST_EXPECT_MSG_EQ (bitmap5[26], 0x00, "Error in the 27th byte of the bitmap for the fifth Per AID TID Info subfield");
1288 NS_TEST_EXPECT_MSG_EQ (bitmap5[27], 0xff, "Error in the 28th byte of the bitmap for the fifth Per AID TID Info subfield");
1289 NS_TEST_EXPECT_MSG_EQ (bitmap5[28], 0x00, "Error in the 29th byte of the bitmap for the fifth Per AID TID Info subfield");
1290 NS_TEST_EXPECT_MSG_EQ (bitmap5[29], 0xff, "Error in the 30th byte of the bitmap for the fifth Per AID TID Info subfield");
1291 NS_TEST_EXPECT_MSG_EQ (bitmap5[30], 0x00, "Error in the 31th byte of the bitmap for the fifth Per AID TID Info subfield");
1292 NS_TEST_EXPECT_MSG_EQ (bitmap5[31], 0xff, "Error in the 32th byte of the bitmap for the fifth Per AID TID Info subfield");
1293
1294 /* Check 6th Per AID TID Info subfield */
1295 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAid11 (5), aid6, "Different AID for the sixth Per AID TID Info subfield");
1296 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetAckType (5), ackType6, "Different Ack Type for the sixth Per AID TID Info subfield");
1297 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetTidInfo (5), tid6, "Different TID for the sixth Per AID TID Info subfield");
1298 NS_TEST_EXPECT_MSG_EQ (blockAckCopy.GetUnassociatedStaAddress (5), address6, "Different starting sequence number for the sixth Per AID TID Info subfield");
1299}
1300
1301
1347{
1352 {
1358 void Trace (Time startTime, Time duration);
1360 };
1361
1362public:
1369
1370 void DoRun (void) override;
1371
1372
1373private:
1374 bool m_txop;
1376 uint16_t m_txTotal;
1377 uint16_t m_txSinceBar;
1379 uint16_t m_nBar;
1380 uint16_t m_nBa;
1381
1388 void L7Receive (std::string context, Ptr<const Packet> p, const Address &adr);
1395 void Transmit (std::string context, Ptr<const Packet> p, double power);
1402 void Receive (std::string context, Ptr<const Packet> p, RxPowerWattPerChannelBand rxPowersW);
1403};
1404
1405void
1407{
1408 if (duration > m_max)
1409 {
1410 m_max = duration;
1411 }
1412}
1413
1415 : TestCase ("Test case for Block Ack Policy with aggregation disabled"),
1416 m_txop (txop),
1417 m_received (0),
1418 m_txTotal (0),
1419 m_txSinceBar (0),
1420 m_nBar (0),
1421 m_nBa (0)
1422{
1423}
1424
1426{
1427}
1428
1429void
1431{
1432 if (p->GetSize () == 1400)
1433 {
1434 m_received++;
1435 }
1436}
1437
1438void
1440{
1441 WifiMacHeader hdr;
1442 p->PeekHeader (hdr);
1443
1444 if (m_nBar < 2 && (m_txSinceBar == 9 || m_txTotal == 14))
1445 {
1446 NS_TEST_ASSERT_MSG_EQ (hdr.IsBlockAckReq (), true, "Didn't get a BlockAckReq when expected");
1447 }
1448 else
1449 {
1450 NS_TEST_ASSERT_MSG_EQ (hdr.IsBlockAckReq (), false, "Got a BlockAckReq when not expected");
1451 }
1452
1453 if (hdr.IsQosData ())
1454 {
1455 m_txTotal++;
1456 if (hdr.IsQosBlockAck ())
1457 {
1458 m_txSinceBar++;
1459 }
1460
1461 if (!m_txop)
1462 {
1463 NS_TEST_EXPECT_MSG_EQ ((m_txTotal == 1 || hdr.IsQosBlockAck ()), true, "Unexpected QoS ack policy");
1464 }
1465 else
1466 {
1467 NS_TEST_EXPECT_MSG_EQ ((m_txTotal <= 2 || hdr.IsQosBlockAck ()), true, "Unexpected QoS ack policy");
1468 }
1469 }
1470 else if (hdr.IsBlockAckReq ())
1471 {
1472 m_txSinceBar = 0;
1473 m_nBar++;
1474 }
1475}
1476
1477void
1479{
1480 WifiMacHeader hdr;
1481 p->PeekHeader (hdr);
1482
1483 if (hdr.IsBlockAck ())
1484 {
1485 m_nBa++;
1486 }
1487}
1488
1489void
1491{
1492 NodeContainer wifiStaNode;
1493 wifiStaNode.Create (1);
1494
1496 wifiApNode.Create (1);
1497
1498 YansWifiChannelHelper channel = YansWifiChannelHelper::Default ();
1500 phy.SetChannel (channel.Create ());
1501
1503 wifi.SetStandard (WIFI_STANDARD_80211n);
1504 Config::SetDefault ("ns3::WifiDefaultAckManager::BaThreshold", DoubleValue (0.125));
1505 wifi.SetRemoteStationManager ("ns3::IdealWifiManager");
1506
1508 Ssid ssid = Ssid ("ns-3-ssid");
1509 mac.SetType ("ns3::StaWifiMac",
1510 "BE_MaxAmsduSize", UintegerValue (0),
1511 "BE_MaxAmpduSize", UintegerValue (0),
1512 "Ssid", SsidValue (ssid),
1513 /* setting blockack threshold for sta's BE queue */
1514 "BE_BlockAckThreshold", UintegerValue (2),
1515 "ActiveProbing", BooleanValue (false));
1516
1518 staDevices = wifi.Install (phy, mac, wifiStaNode);
1519
1520 mac.SetType ("ns3::ApWifiMac",
1521 "BE_MaxAmsduSize", UintegerValue (0),
1522 "BE_MaxAmpduSize", UintegerValue (0),
1523 "Ssid", SsidValue (ssid),
1524 "BeaconGeneration", BooleanValue (true));
1525
1527 apDevices = wifi.Install (phy, mac, wifiApNode);
1528
1530 Ptr<ListPositionAllocator> positionAlloc = CreateObject<ListPositionAllocator> ();
1531
1532 positionAlloc->Add (Vector (0.0, 0.0, 0.0));
1533 positionAlloc->Add (Vector (1.0, 0.0, 0.0));
1534 mobility.SetPositionAllocator (positionAlloc);
1535
1536 mobility.SetMobilityModel ("ns3::ConstantPositionMobilityModel");
1537 mobility.Install (wifiApNode);
1538 mobility.Install (wifiStaNode);
1539
1540 Ptr<WifiNetDevice> ap_device = DynamicCast<WifiNetDevice> (apDevices.Get (0));
1541 Ptr<WifiNetDevice> sta_device = DynamicCast<WifiNetDevice> (staDevices.Get (0));
1542
1543 // Disable A-MPDU aggregation
1544 sta_device->GetMac ()->SetAttribute ("BE_MaxAmpduSize", UintegerValue (0));
1545 TxopDurationTracer txopTracer;
1546
1547 if (m_txop)
1548 {
1549 PointerValue ptr;
1550 sta_device->GetMac ()->GetAttribute ("BE_Txop", ptr);
1551 ptr.Get<QosTxop> ()->TraceConnectWithoutContext ("TxopTrace", MakeCallback (&TxopDurationTracer::Trace, &txopTracer));
1552
1553 // set the TXOP limit on BE AC
1554 ap_device->GetMac ()->GetAttribute ("BE_Txop", ptr);
1555 ptr.Get<QosTxop> ()->SetTxopLimit (MicroSeconds (4800));
1556 }
1557
1558 PacketSocketAddress socket;
1559 socket.SetSingleDevice (sta_device->GetIfIndex ());
1560 socket.SetPhysicalAddress (ap_device->GetAddress ());
1561 socket.SetProtocol (1);
1562
1563 // give packet socket powers to nodes.
1564 PacketSocketHelper packetSocket;
1565 packetSocket.Install (wifiStaNode);
1566 packetSocket.Install (wifiApNode);
1567
1568 // the first client application generates a single packet, which is sent
1569 // with the normal ack policy because there are no other packets queued
1570 Ptr<PacketSocketClient> client1 = CreateObject<PacketSocketClient> ();
1571 client1->SetAttribute ("PacketSize", UintegerValue (1400));
1572 client1->SetAttribute ("MaxPackets", UintegerValue (1));
1573 client1->SetAttribute ("Interval", TimeValue (MicroSeconds (0)));
1574 client1->SetRemote (socket);
1575 wifiStaNode.Get (0)->AddApplication (client1);
1576 client1->SetStartTime (Seconds (1));
1577 client1->SetStopTime (Seconds (3.0));
1578
1579 // the second client application generates 13 packets. Even if when the first
1580 // packet is queued the queue is empty, the first packet is not transmitted
1581 // immediately, but the EDCAF waits for the next slot boundary. At that time,
1582 // other packets have been queued, hence a BA agreement is established first.
1583 Ptr<PacketSocketClient> client2 = CreateObject<PacketSocketClient> ();
1584 client2->SetAttribute ("PacketSize", UintegerValue (1400));
1585 client2->SetAttribute ("MaxPackets", UintegerValue (13));
1586 client2->SetAttribute ("Interval", TimeValue (MicroSeconds (0)));
1587 client2->SetRemote (socket);
1588 wifiStaNode.Get (0)->AddApplication (client2);
1589 client2->SetStartTime (Seconds (1.5));
1590 client2->SetStopTime (Seconds (3.0));
1591
1592 Ptr<PacketSocketServer> server = CreateObject<PacketSocketServer> ();
1593 server->SetLocal (socket);
1594 wifiApNode.Get (0)->AddApplication (server);
1595 server->SetStartTime (Seconds (0.0));
1596 server->SetStopTime (Seconds (4.0));
1597
1598 Config::Connect ("/NodeList/*/ApplicationList/0/$ns3::PacketSocketServer/Rx", MakeCallback (&BlockAckAggregationDisabledTest::L7Receive, this));
1599 Config::Connect ("/NodeList/0/DeviceList/0/Phy/PhyTxBegin", MakeCallback (&BlockAckAggregationDisabledTest::Transmit, this));
1600 Config::Connect ("/NodeList/0/DeviceList/0/Phy/PhyRxBegin", MakeCallback (&BlockAckAggregationDisabledTest::Receive, this));
1601
1602 Simulator::Stop (Seconds (5));
1603 Simulator::Run ();
1604
1605 Simulator::Destroy ();
1606
1607 // The client applications generate 14 packets, so we expect that the wifi PHY
1608 // layer transmits 14 MPDUs, the server application receives 14 packets, and
1609 // two BARs are transmitted.
1610 NS_TEST_EXPECT_MSG_EQ (m_txTotal, 14, "Unexpected number of transmitted packets");
1611 NS_TEST_EXPECT_MSG_EQ (m_received, 14, "Unexpected number of received packets");
1612 NS_TEST_EXPECT_MSG_EQ (m_nBar, 2, "Unexpected number of Block Ack Requests");
1613 NS_TEST_EXPECT_MSG_EQ (m_nBa, 2, "Unexpected number of Block Ack Responses");
1614 if (m_txop)
1615 {
1616 NS_TEST_EXPECT_MSG_LT (txopTracer.m_max, MicroSeconds (4800), "TXOP duration exceeded!");
1617 NS_TEST_EXPECT_MSG_GT (txopTracer.m_max, MicroSeconds (3008), "The maximum TXOP duration is too short!");
1618 }
1619}
1620
1628{
1629public:
1631};
1632
1634 : TestSuite ("wifi-block-ack", UNIT)
1635{
1636 AddTestCase (new PacketBufferingCaseA, TestCase::QUICK);
1637 AddTestCase (new PacketBufferingCaseB, TestCase::QUICK);
1638 AddTestCase (new OriginatorBlockAckWindowTest, TestCase::QUICK);
1639 AddTestCase (new CtrlBAckResponseHeaderTest, TestCase::QUICK);
1640 AddTestCase (new BlockAckRecipientBufferTest (0), TestCase::QUICK);
1641 AddTestCase (new BlockAckRecipientBufferTest (4090), TestCase::QUICK);
1642 AddTestCase (new MultiStaCtrlBAckResponseHeaderTest, TestCase::QUICK);
1643 AddTestCase (new BlockAckAggregationDisabledTest (false), TestCase::QUICK);
1644 AddTestCase (new BlockAckAggregationDisabledTest (true), TestCase::QUICK);
1645}
1646
static BlockAckTestSuite g_blockAckTestSuite
the test suite
Test for Block Ack Policy with aggregation disabled.
uint16_t m_nBa
received BlockAck frames
void DoRun(void) override
Implementation to actually run this TestCase.
uint16_t m_txTotal
transmitted data packets
void L7Receive(std::string context, Ptr< const Packet > p, const Address &adr)
Function to trace packets received by the server application.
BlockAckAggregationDisabledTest(bool txop)
Constructor.
uint16_t m_nBar
transmitted BlockAckReq frames
void Receive(std::string context, Ptr< const Packet > p, RxPowerWattPerChannelBand rxPowersW)
Callback invoked when PHY receives a packet.
void Transmit(std::string context, Ptr< const Packet > p, double power)
Callback invoked when PHY transmits a packet.
uint16_t m_txSinceBar
packets transmitted since the agreement was established or the last block ack was received
bool m_txop
true for non-null TXOP limit
Test for recipient reordering buffer operations.
void DoRun(void) override
Implementation to actually run this TestCase.
uint16_t m_ssn
the Starting Sequence Number used to initialize WinStartB
void ForwardUp(Ptr< WifiMacQueueItem > mpdu)
Keep track of MPDUs that are forwarded up.
BlockAckRecipientBufferTest(uint16_t ssn)
Constructor.
std::list< Ptr< WifiMacQueueItem > > m_fwup
list of MPDUs that have been forwarded up
Block Ack Test Suite.
Test for block ack header.
CtrlBAckResponseHeader m_blockAckHdr
block ack header
void DoRun(void) override
Implementation to actually run this TestCase.
Test for Multi-STA block ack header.
virtual void DoRun(void)
Implementation to actually run this TestCase.
Test for the originator block ack window.
void DoRun(void) override
Implementation to actually run this TestCase.
Packet Buffering Case A.
void DoRun(void) override
Implementation to actually run this TestCase.
std::list< uint16_t > m_expectedBuffer
expected test buffer
Packet Buffering Case B.
std::list< uint16_t > m_expectedBuffer
expected test buffer
void DoRun(void) override
Implementation to actually run this TestCase.
a polymophic address class
Definition: address.h:91
void SetStartingSequence(uint16_t seq)
Set starting sequence number.
void SetBufferSize(uint16_t bufferSize)
Set buffer size.
std::size_t GetWinSize(void) const
Get the window size.
uint16_t GetWinStart(void) const
Get the current winStart value.
std::vector< bool >::reference At(std::size_t distance)
Get a reference to the element in the window having the given distance from the current winStart.
uint16_t GetWinEnd(void) const
Get the current winEnd value.
AttributeValue implementation for Boolean.
Definition: boolean.h:37
Headers for BlockAck response.
Definition: ctrl-headers.h:202
void SetStartingSequence(uint16_t seq, std::size_t index=0)
For Block Ack variants other than Multi-STA Block Ack, set the starting sequence number to the given ...
bool IsPacketReceived(uint16_t seq, std::size_t index=0) const
Check if the packet with the given sequence number was acknowledged in this BlockAck response.
uint16_t GetStartingSequence(std::size_t index=0) const
For Block Ack variants other than Multi-STA Block Ack, get the starting sequence number.
Mac48Address GetUnassociatedStaAddress(std::size_t index) const
For Multi-STA Block Acks, get the RA subfield of the Per AID TID Info subfield (with AID11 subfield e...
uint8_t GetTidInfo(std::size_t index=0) const
For Block Ack variants other than Multi-STA Block Ack, get the TID_INFO subfield of the BA Control fi...
const std::vector< uint8_t > & GetBitmap(std::size_t index=0) const
Return a const reference to the bitmap from the BlockAck response header.
void ResetBitmap(std::size_t index=0)
Reset the bitmap to 0.
void SetType(BlockAckType type)
Set the block ack type.
BlockAckType GetType(void) const
Return the block ack type ID.
void SetReceivedPacket(uint16_t seq, std::size_t index=0)
Record in the bitmap that the packet with the given sequence number was received.
bool GetAckType(std::size_t index) const
For Multi-STA Block Acks, get the Ack Type subfield of the Per AID TID Info subfield identified by th...
uint16_t GetAid11(std::size_t index) const
For Multi-STA Block Acks, get the AID11 subfield of the Per AID TID Info subfield identified by the g...
This class can be used to hold variables of floating point type such as 'double' or 'float'.
Definition: double.h:41
an EUI-48 address
Definition: mac48-address.h:44
Helper class used to assign positions and mobility models to nodes.
holds a vector of ns3::NetDevice pointers
keep track of a set of node pointers.
void Create(uint32_t n)
Create n nodes and append pointers to them to the end of this NodeContainer.
Ptr< Node > Get(uint32_t i) const
Get the Ptr<Node> stored in this container at a given index.
uint32_t AddApplication(Ptr< Application > application)
Associate an Application to this Node.
Definition: node.cc:159
Maintains the state and information about transmitted MPDUs with Ack Policy set to Block Ack for an o...
void InitTxWindow(void)
Initialize the originator's transmit window by setting its size and starting sequence number equal to...
void NotifyAckedMpdu(Ptr< const WifiMacQueueItem > mpdu)
Record that the given MPDU has been acknowledged and advance the transmit window if possible.
void NotifyTransmittedMpdu(Ptr< const WifiMacQueueItem > mpdu)
Advance the transmit window so as to include the transmitted MPDU, if the latter is not an old packet...
BlockAckWindow m_txWindow
originator's transmit window
uint16_t GetStartingSequence(void) const override
Return the starting sequence number of the transmit window, if a transmit window has been initialized...
void NotifyDiscardedMpdu(Ptr< const WifiMacQueueItem > mpdu)
Advance the transmit window beyond the MPDU that has been reported to be discarded.
uint32_t RemoveHeader(Header &header)
Deserialize and remove the header from the internal buffer.
Definition: packet.cc:280
void AddHeader(const Header &header)
Add header to this packet.
Definition: packet.cc:256
uint32_t PeekHeader(Header &header) const
Deserialize but does not remove the header from the internal buffer.
Definition: packet.cc:290
uint32_t GetSize(void) const
Returns the the size in bytes of the packet (including the zero-filled initial payload).
Definition: packet.h:856
an address for a packet socket
void SetProtocol(uint16_t protocol)
Set the protocol.
void SetPhysicalAddress(const Address address)
Set the destination address.
void SetSingleDevice(uint32_t device)
Set the address to match only a specified NetDevice.
Give ns3::PacketSocket powers to ns3::Node.
void Install(Ptr< Node > node) const
Aggregate an instance of a ns3::PacketSocketFactory onto the provided node.
Hold objects of type Ptr<T>.
Definition: pointer.h:37
Ptr< T > Get(void) const
Definition: pointer.h:201
Smart pointer class similar to boost::intrusive_ptr.
Definition: ptr.h:74
Handle packet fragmentation and retransmissions for QoS data frames as well as MSDU aggregation (A-MS...
Definition: qos-txop.h:72
Maintains the scoreboard and the receive reordering buffer used by a recipient of a Block Ack agreeme...
void NotifyReceivedBar(uint16_t startingSequenceNumber)
Update both the scoreboard and the receive reordering buffer upon reception of a Block Ack Request.
void NotifyReceivedMpdu(Ptr< WifiMacQueueItem > mpdu)
Update both the scoreboard and the receive reordering buffer upon reception of the given MPDU.
void SetMacRxMiddle(const Ptr< MacRxMiddle > rxMiddle)
Set the MAC RX Middle to use.
The IEEE 802.11 SSID Information Element.
Definition: ssid.h:36
AttributeValue implementation for Ssid.
encapsulates test code
Definition: test.h:994
void AddTestCase(TestCase *testCase, TestDuration duration=QUICK)
Add an individual child TestCase to this test suite.
Definition: test.cc:299
A suite of tests to run.
Definition: test.h:1188
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:103
AttributeValue implementation for Time.
Definition: nstime.h:1308
Hold an unsigned integer type.
Definition: uinteger.h:44
helps to create WifiNetDevice objects
Definition: wifi-helper.h:323
Implements the IEEE 802.11 MAC header.
bool IsBlockAck(void) const
Return true if the header is a BlockAck header.
bool IsQosData(void) const
Return true if the Type is DATA and Subtype is one of the possible values for QoS Data.
void SetSequenceNumber(uint16_t seq)
Set the sequence number of the header.
void SetAddr1(Mac48Address address)
Fill the Address 1 field with the given address.
void SetType(WifiMacType type, bool resetToDsFromDs=true)
Set Type/Subtype values with the correct values depending on the given type.
void SetQosTid(uint8_t tid)
Set the TID for the QoS header.
bool IsBlockAckReq(void) const
Return true if the header is a BlockAckRequest header.
bool IsQosBlockAck(void) const
Return if the QoS Ack policy is Block Ack.
create MAC layers for a ns3::WifiNetDevice.
Ptr< WifiMac > GetMac(void) const
Address GetAddress(void) const override
uint32_t GetIfIndex(void) const override
manage and create wifi channel objects for the YANS model.
Make it easy to create and manage PHY objects for the YANS model.
void SetDefault(std::string name, const AttributeValue &value)
Definition: config.cc:849
void Connect(std::string path, const CallbackBase &cb)
Definition: config.cc:920
#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:141
#define NS_TEST_EXPECT_MSG_LT(actual, limit, msg)
Test that an actual value is less than a limit and report if not.
Definition: test.h:748
#define NS_TEST_EXPECT_MSG_GT(actual, limit, msg)
Test that an actual value is greater than a limit and report if not.
Definition: test.h:899
#define NS_TEST_EXPECT_MSG_EQ(actual, limit, msg)
Test that an actual and expected (limit) value are equal and report if not.
Definition: test.h:240
Time MicroSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1260
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1244
uint32_t QosUtilsMapSeqControlToUniqueInteger(uint16_t seqControl, uint16_t endSequence)
Next function is useful to correctly sort buffered packets under block ack.
Definition: qos-utils.cc:167
@ WIFI_STANDARD_80211n
Every class exported by the ns3 library is enclosed in the ns3 namespace.
std::map< WifiSpectrumBand, double > RxPowerWattPerChannelBand
A map of the received power (Watts) for each band.
Definition: phy-entity.h:75
@ WIFI_MAC_QOSDATA
const uint16_t SEQNO_SPACE_SIZE
Size of the space of sequence numbers.
Definition: wifi-utils.h:131
Callback< R, Ts... > MakeCallback(R(T::*memPtr)(Ts...), OBJ objPtr)
Build Callbacks for class method members which take varying numbers of arguments and potentially retu...
Definition: callback.h:1648
staDevices
Definition: third.py:102
ssid
Definition: third.py:97
channel
Definition: third.py:92
mac
Definition: third.py:96
wifi
Definition: third.py:99
apDevices
Definition: third.py:105
wifiApNode
Definition: third.py:90
mobility
Definition: third.py:107
phy
Definition: third.py:93
Keeps the maximum duration among all TXOPs.
void Trace(Time startTime, Time duration)
Callback for the TxopTrace trace.
The different BlockAck variants.
enum Variant m_variant
Block Ack variant.
std::vector< uint8_t > m_bitmapLen
Length (bytes) of included bitmaps.