A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
wifi-mac-queue-scheduler-impl.h
Go to the documentation of this file.
1/*
2 * Copyright (c) 2022 Universita' degli Studi di Napoli Federico II
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License version 2 as
6 * published by the Free Software Foundation;
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program; if not, write to the Free Software
15 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
16 *
17 * Author: Stefano Avallone <stavallo@unina.it>
18 */
19
20#ifndef WIFI_MAC_QUEUE_SCHEDULER_IMPL_H
21#define WIFI_MAC_QUEUE_SCHEDULER_IMPL_H
22
24#include "wifi-mac-queue.h"
25#include "wifi-mac.h"
26
27#include <algorithm>
28#include <functional>
29#include <list>
30#include <map>
31#include <numeric>
32#include <unordered_map>
33#include <vector>
34
36
37namespace ns3
38{
39
40class WifiMpdu;
41class WifiMacQueue;
42
50template <class Priority, class Compare = std::less<Priority>>
52{
53 public:
55 friend class ::WifiMacQueueDropOldestTest;
56
61 static TypeId GetTypeId();
62
67
69 void SetWifiMac(Ptr<WifiMac> mac) final;
71 std::optional<WifiContainerQueueId> GetNext(AcIndex ac, std::optional<uint8_t> linkId) final;
76 std::optional<WifiContainerQueueId> GetNext(AcIndex ac,
77 std::optional<uint8_t> linkId,
78 const WifiContainerQueueId& prevQueueId) final;
80 std::list<uint8_t> GetLinkIds(AcIndex ac, Ptr<const WifiMpdu> mpdu) final;
83 AcIndex ac,
84 const std::list<WifiContainerQueueType>& types,
85 const Mac48Address& rxAddress,
86 const Mac48Address& txAddress,
87 const std::set<uint8_t>& tids,
88 const std::set<uint8_t>& linkIds) final;
91 AcIndex ac,
92 const std::list<WifiContainerQueueType>& types,
93 const Mac48Address& rxAddress,
94 const Mac48Address& txAddress,
95 const std::set<uint8_t>& tids,
96 const std::set<uint8_t>& linkIds) final;
98 std::optional<Mask> GetQueueLinkMask(AcIndex ac,
99 const WifiContainerQueueId& queueId,
100 uint8_t linkId) final;
104 void NotifyEnqueue(AcIndex ac, Ptr<WifiMpdu> mpdu) final;
106 void NotifyDequeue(AcIndex ac, const std::list<Ptr<WifiMpdu>>& mpdus) final;
108 void NotifyRemove(AcIndex ac, const std::list<Ptr<WifiMpdu>>& mpdus) final;
109
110 protected:
112 void DoDispose() override;
113
121 void SetPriority(AcIndex ac, const WifiContainerQueueId& queueId, const Priority& priority);
122
123 struct QueueInfo;
124
131 using QueueInfoMap = std::unordered_map<WifiContainerQueueId, QueueInfo>;
132
134 using QueueInfoPair = std::pair<const WifiContainerQueueId, QueueInfo>;
135
145 using SortedQueues = std::multimap<Priority, std::reference_wrapper<QueueInfoPair>, Compare>;
146
151 {
152 std::optional<typename SortedQueues::iterator>
155 std::map<uint8_t, Mask> linkIds;
159 };
160
165 {
169 };
170
180
188
189 private:
201 typename QueueInfoMap::iterator InitQueueInfo(AcIndex ac, Ptr<const WifiMpdu> mpdu);
202
214 std::optional<WifiContainerQueueId> DoGetNext(AcIndex ac,
215 std::optional<uint8_t> linkId,
216 typename SortedQueues::iterator sortedQueuesIt);
217
234 virtual void DoNotifyEnqueue(AcIndex ac, Ptr<WifiMpdu> mpdu) = 0;
243 virtual void DoNotifyDequeue(AcIndex ac, const std::list<Ptr<WifiMpdu>>& mpdus) = 0;
252 virtual void DoNotifyRemove(AcIndex ac, const std::list<Ptr<WifiMpdu>>& mpdus) = 0;
253
268 void DoBlockQueues(bool block,
270 AcIndex ac,
271 const std::list<WifiContainerQueueType>& types,
272 const Mac48Address& rxAddress,
273 const Mac48Address& txAddress,
274 const std::set<uint8_t>& tids,
275 const std::set<uint8_t>& linkIds);
276
277 std::vector<PerAcInfo> m_perAcInfo{AC_UNDEF};
279};
280
285template <class Priority, class Compare>
287 : NS_LOG_TEMPLATE_DEFINE("WifiMacQueueScheduler")
288{
289}
290
291template <class Priority, class Compare>
292TypeId
294{
295 static TypeId tid = TypeId("ns3::WifiMacQueueSchedulerImpl")
297 .SetGroupName("Wifi");
298 return tid;
299}
300
301template <class Priority, class Compare>
302void
304{
305 m_perAcInfo.clear();
307}
308
309template <class Priority, class Compare>
310void
312{
313 for (auto ac : {AC_BE, AC_BK, AC_VI, AC_VO, AC_BE_NQOS, AC_BEACON})
314 {
315 if (auto queue = mac->GetTxopQueue(ac); queue != nullptr)
316 {
317 m_perAcInfo.at(ac).wifiMacQueue = queue;
318 queue->SetScheduler(this);
319 }
320 }
322}
323
324template <class Priority, class Compare>
327{
328 NS_ASSERT(static_cast<uint8_t>(ac) < AC_UNDEF);
329 return m_perAcInfo.at(ac).wifiMacQueue;
330}
331
332template <class Priority, class Compare>
335{
336 NS_ASSERT(static_cast<uint8_t>(ac) < AC_UNDEF);
337 return m_perAcInfo.at(ac).sortedQueues;
338}
339
340template <class Priority, class Compare>
343{
344 NS_LOG_FUNCTION(this << ac << *mpdu);
345
346 auto queueId = WifiMacQueueContainer::GetQueueId(mpdu);
347 // insert queueId in the queue info map if not present yet
348 auto [queueInfoIt, ret] = m_perAcInfo[ac].queueInfoMap.insert({queueId, QueueInfo()});
349
350 // Initialize/update the set of link IDs depending on the container queue type
351 if (GetMac() && GetMac()->GetNLinks() > 1 &&
352 mpdu->GetHeader().GetAddr2() == GetMac()->GetAddress())
353 {
354 // this is an MLD and the TA field of the frame contains the MLD address,
355 // which means that the frame can be sent on multiple links
356 const auto rxAddr = mpdu->GetHeader().GetAddr1();
357
358 // this assert checks that the RA field also contain an MLD address, unless
359 // it contains the broadcast address
360 NS_ASSERT_MSG(rxAddr.IsGroup() || GetMac()->GetMldAddress(rxAddr) == rxAddr,
361 "Address 1 (" << rxAddr << ") is not an MLD address");
362
363 // this assert checks that association (ML setup) has been established
364 // between sender and receiver (unless the receiver is the broadcast address)
365 NS_ASSERT_MSG(GetMac()->CanForwardPacketsTo(rxAddr), "Cannot forward frame to " << rxAddr);
366 // we have to include all the links in case of broadcast frame (we are an AP)
367 // and the links that have been setup with the receiver in case of unicast frame
368 for (const auto linkId : GetMac()->GetLinkIds())
369 {
370 if (rxAddr.IsGroup() ||
371 GetMac()->GetWifiRemoteStationManager(linkId)->GetAffiliatedStaAddress(rxAddr))
372 {
373 // the mask is not modified if linkId is already in the map
374 queueInfoIt->second.linkIds.emplace(linkId, Mask{});
375 }
376 else
377 {
378 // this link is no (longer) setup
379 queueInfoIt->second.linkIds.erase(linkId);
380 }
381 }
382 }
383 else
384 {
385 // the TA field of the frame contains a link address, which means that the
386 // frame can only be sent on the corresponding link
387 auto linkId = GetMac() ? GetMac()->GetLinkIdByAddress(mpdu->GetHeader().GetAddr2())
388 : SINGLE_LINK_OP_ID; // make unit test happy
389 NS_ASSERT(linkId.has_value());
390 auto& linkIdsMap = queueInfoIt->second.linkIds;
391 NS_ASSERT_MSG(linkIdsMap.size() <= 1,
392 "At most one link can be associated with this container queue");
393 // set the link map to contain one entry corresponding to the computed link ID;
394 // unless the link map already contained such an entry (in which case the mask
395 // is preserved)
396 if (linkIdsMap.empty() || linkIdsMap.cbegin()->first != *linkId)
397 {
398 linkIdsMap = {{*linkId, Mask{}}};
399 }
400 }
401
402 return queueInfoIt;
403}
404
405template <class Priority, class Compare>
406void
408 const WifiContainerQueueId& queueId,
409 const Priority& priority)
410{
411 NS_LOG_FUNCTION(this << +ac);
412 NS_ASSERT(static_cast<uint8_t>(ac) < AC_UNDEF);
413
414 NS_ABORT_MSG_IF(GetWifiMacQueue(ac)->GetNBytes(queueId) == 0,
415 "Cannot set the priority of an empty queue");
416
417 auto queueInfoIt = m_perAcInfo[ac].queueInfoMap.find(queueId);
418 NS_ASSERT_MSG(queueInfoIt != m_perAcInfo[ac].queueInfoMap.end(),
419 "No queue info for the given container queue");
420 typename SortedQueues::iterator sortedQueuesIt;
421
422 if (queueInfoIt->second.priorityIt.has_value())
423 {
424 // an element for queueId is present in the set of sorted queues. If the priority
425 // has not changed, do nothing. Otherwise, unlink the node containing such element,
426 // change the priority and insert it back
427 if (queueInfoIt->second.priorityIt.value()->first == priority)
428 {
429 return;
430 }
431
432 auto handle = m_perAcInfo[ac].sortedQueues.extract(queueInfoIt->second.priorityIt.value());
433 handle.key() = priority;
434 sortedQueuesIt = m_perAcInfo[ac].sortedQueues.insert(std::move(handle));
435 }
436 else
437 {
438 // an element for queueId is not present in the set of sorted queues
439 sortedQueuesIt = m_perAcInfo[ac].sortedQueues.insert({priority, std::ref(*queueInfoIt)});
440 }
441 // update the stored iterator
442 queueInfoIt->second.priorityIt = sortedQueuesIt;
443}
444
445template <class Priority, class Compare>
446std::list<uint8_t>
448{
449 auto queueInfoIt = InitQueueInfo(ac, mpdu);
450 std::list<uint8_t> linkIds;
451
452 // include only links that are not blocked in the returned list
453 for (const auto& [linkId, mask] : queueInfoIt->second.linkIds)
454 {
455 if (mask.none())
456 {
457 linkIds.emplace_back(linkId);
458 }
459 }
460
461 return linkIds;
462}
463
464template <class Priority, class Compare>
465void
467 bool block,
469 AcIndex ac,
470 const std::list<WifiContainerQueueType>& types,
471 const Mac48Address& rxAddress,
472 const Mac48Address& txAddress,
473 const std::set<uint8_t>& tids,
474 const std::set<uint8_t>& linkIds)
475{
476 NS_LOG_FUNCTION(this << block << reason << ac << rxAddress << txAddress);
477 std::list<WifiMacHeader> headers;
478
479 for (const auto queueType : types)
480 {
481 switch (queueType)
482 {
483 case WIFI_CTL_QUEUE:
484 headers.emplace_back(WIFI_MAC_CTL_BACKREQ);
485 break;
486 case WIFI_MGT_QUEUE:
487 headers.emplace_back(WIFI_MAC_MGT_ACTION);
488 break;
490 NS_ASSERT_MSG(!tids.empty(),
491 "TID must be specified for queues containing QoS data frames");
492 for (const auto tid : tids)
493 {
494 headers.emplace_back(WIFI_MAC_QOSDATA);
495 headers.back().SetQosTid(tid);
496 }
497 break;
498 case WIFI_DATA_QUEUE:
499 headers.emplace_back(WIFI_MAC_DATA);
500 break;
501 }
502 }
503 for (auto& hdr : headers)
504 {
505 hdr.SetAddr1(rxAddress);
506 hdr.SetAddr2(txAddress);
507
508 auto queueInfoIt = InitQueueInfo(ac, Create<WifiMpdu>(Create<Packet>(), hdr));
509 for (auto& [linkId, mask] : queueInfoIt->second.linkIds)
510 {
511 if (linkIds.empty() || linkIds.count(linkId) > 0)
512 {
513 mask.set(static_cast<std::size_t>(reason), block);
514 }
515 }
516 }
517}
518
519template <class Priority, class Compare>
520void
523 AcIndex ac,
524 const std::list<WifiContainerQueueType>& types,
525 const Mac48Address& rxAddress,
526 const Mac48Address& txAddress,
527 const std::set<uint8_t>& tids,
528 const std::set<uint8_t>& linkIds)
529{
530 DoBlockQueues(true, reason, ac, types, rxAddress, txAddress, tids, linkIds);
531}
532
533template <class Priority, class Compare>
534void
537 AcIndex ac,
538 const std::list<WifiContainerQueueType>& types,
539 const Mac48Address& rxAddress,
540 const Mac48Address& txAddress,
541 const std::set<uint8_t>& tids,
542 const std::set<uint8_t>& linkIds)
543{
544 DoBlockQueues(false, reason, ac, types, rxAddress, txAddress, tids, linkIds);
545}
546
547template <class Priority, class Compare>
548std::optional<WifiMacQueueScheduler::Mask>
550 const WifiContainerQueueId& queueId,
551 uint8_t linkId)
552{
553 NS_LOG_FUNCTION(this << +ac << +linkId);
554
555 const auto queueInfoIt = m_perAcInfo[ac].queueInfoMap.find(queueId);
556
557 if (queueInfoIt == m_perAcInfo[ac].queueInfoMap.cend())
558 {
559 // the given container queue does not exist
560 return std::nullopt;
561 }
562
563 const auto& linkIds = queueInfoIt->second.linkIds;
564 if (const auto linkIt = linkIds.find(linkId); linkIt != linkIds.cend())
565 {
566 return linkIt->second;
567 }
568
569 return std::nullopt;
570}
571
572template <class Priority, class Compare>
573std::optional<WifiContainerQueueId>
575{
576 NS_LOG_FUNCTION(this << +ac << linkId.has_value());
577 return DoGetNext(ac, linkId, m_perAcInfo[ac].sortedQueues.begin());
578}
579
580template <class Priority, class Compare>
581std::optional<WifiContainerQueueId>
583 std::optional<uint8_t> linkId,
584 const WifiContainerQueueId& prevQueueId)
585{
586 NS_LOG_FUNCTION(this << +ac << linkId.has_value());
587
588 auto queueInfoIt = m_perAcInfo[ac].queueInfoMap.find(prevQueueId);
589 NS_ABORT_IF(queueInfoIt == m_perAcInfo[ac].queueInfoMap.end() ||
590 !queueInfoIt->second.priorityIt.has_value());
591
592 auto sortedQueuesIt = queueInfoIt->second.priorityIt.value();
593 NS_ABORT_IF(sortedQueuesIt == m_perAcInfo[ac].sortedQueues.end());
594
595 return DoGetNext(ac, linkId, ++sortedQueuesIt);
596}
597
598template <class Priority, class Compare>
599std::optional<WifiContainerQueueId>
601 AcIndex ac,
602 std::optional<uint8_t> linkId,
603 typename SortedQueues::iterator sortedQueuesIt)
604{
605 NS_LOG_FUNCTION(this << +ac << linkId.has_value());
606 NS_ASSERT(static_cast<uint8_t>(ac) < AC_UNDEF);
607
608 while (sortedQueuesIt != m_perAcInfo[ac].sortedQueues.end())
609 {
610 const auto& queueInfoPair = sortedQueuesIt->second.get();
611 const auto& linkIds = queueInfoPair.second.linkIds;
612 typename std::decay_t<decltype(linkIds)>::const_iterator linkIt;
613
614 if (!linkId.has_value() ||
615 ((linkIt = linkIds.find(*linkId)) != linkIds.cend() && linkIt->second.none()))
616 {
617 // Packets in this queue can be sent over the link we got channel access on.
618 // Now remove packets with expired lifetime from this queue.
619 // In case the queue becomes empty, the queue is removed from the sorted
620 // list and sortedQueuesIt is invalidated; thus, store an iterator to the
621 // previous queue in the sorted list (if any) to resume the search afterwards.
622 std::optional<typename SortedQueues::iterator> prevQueueIt;
623 if (sortedQueuesIt != m_perAcInfo[ac].sortedQueues.begin())
624 {
625 prevQueueIt = std::prev(sortedQueuesIt);
626 }
627
628 GetWifiMacQueue(ac)->ExtractExpiredMpdus(queueInfoPair.first);
629
630 if (GetWifiMacQueue(ac)->GetNBytes(queueInfoPair.first) == 0)
631 {
632 sortedQueuesIt = (prevQueueIt.has_value() ? std::next(prevQueueIt.value())
633 : m_perAcInfo[ac].sortedQueues.begin());
634 continue;
635 }
636 break;
637 }
638
639 sortedQueuesIt++;
640 }
641
642 std::optional<WifiContainerQueueId> queueId;
643
644 if (sortedQueuesIt != m_perAcInfo[ac].sortedQueues.end())
645 {
646 queueId = sortedQueuesIt->second.get().first;
647 }
648 return queueId;
649}
650
651template <class Priority, class Compare>
654{
655 NS_LOG_FUNCTION(this << +ac << *mpdu);
656 return HasToDropBeforeEnqueuePriv(ac, mpdu);
657}
658
659template <class Priority, class Compare>
660void
662{
663 NS_LOG_FUNCTION(this << +ac << *mpdu);
664 NS_ASSERT(static_cast<uint8_t>(ac) < AC_UNDEF);
665
666 // add information for the queue storing the MPDU to the queue info map, if not present yet
667 auto queueInfoIt = InitQueueInfo(ac, mpdu);
668
669 DoNotifyEnqueue(ac, mpdu);
670
671 if (!queueInfoIt->second.priorityIt.has_value())
672 {
674 "No info for the queue the MPDU was stored into (forgot to call SetPriority()?)");
675 }
676}
677
678template <class Priority, class Compare>
679void
681 const std::list<Ptr<WifiMpdu>>& mpdus)
682{
683 NS_LOG_FUNCTION(this << +ac);
684 NS_ASSERT(static_cast<uint8_t>(ac) < AC_UNDEF);
685
686 DoNotifyDequeue(ac, mpdus);
687
688 std::list<WifiContainerQueueId> queueIds;
689
690 for (const auto& mpdu : mpdus)
691 {
692 queueIds.push_back(WifiMacQueueContainer::GetQueueId(mpdu));
693 }
694
695 for (const auto& queueId : queueIds)
696 {
697 if (GetWifiMacQueue(ac)->GetNBytes(queueId) == 0)
698 {
699 // The queue has now become empty and needs to be removed from the sorted
700 // list kept by the scheduler
701 auto queueInfoIt = m_perAcInfo[ac].queueInfoMap.find(queueId);
702 NS_ASSERT(queueInfoIt != m_perAcInfo[ac].queueInfoMap.end());
703 if (queueInfoIt->second.priorityIt.has_value())
704 {
705 m_perAcInfo[ac].sortedQueues.erase(queueInfoIt->second.priorityIt.value());
706 queueInfoIt->second.priorityIt.reset();
707 }
708 }
709 }
710}
711
712template <class Priority, class Compare>
713void
715 const std::list<Ptr<WifiMpdu>>& mpdus)
716{
717 NS_LOG_FUNCTION(this << +ac);
718 NS_ASSERT(static_cast<uint8_t>(ac) < AC_UNDEF);
719
720 DoNotifyRemove(ac, mpdus);
721
722 std::list<WifiContainerQueueId> queueIds;
723
724 for (const auto& mpdu : mpdus)
725 {
726 queueIds.push_back(WifiMacQueueContainer::GetQueueId(mpdu));
727 }
728
729 for (const auto& queueId : queueIds)
730 {
731 if (GetWifiMacQueue(ac)->GetNBytes(queueId) == 0)
732 {
733 // The queue has now become empty and needs to be removed from the sorted
734 // list kept by the scheduler
735 auto queueInfoIt = m_perAcInfo[ac].queueInfoMap.find(queueId);
736 NS_ASSERT(queueInfoIt != m_perAcInfo[ac].queueInfoMap.end());
737 if (queueInfoIt->second.priorityIt.has_value())
738 {
739 m_perAcInfo[ac].sortedQueues.erase(queueInfoIt->second.priorityIt.value());
740 queueInfoIt->second.priorityIt.reset();
741 }
742 }
743 }
744}
745
746} // namespace ns3
747
748#endif /* WIFI_MAC_QUEUE_SCHEDULER_IMPL_H */
Test DROP_OLDEST setting.
an EUI-48 address
Definition: mac48-address.h:46
Smart pointer class similar to boost::intrusive_ptr.
Definition: ptr.h:77
a unique identifier for an interface.
Definition: type-id.h:59
TypeId SetParent(TypeId tid)
Set the parent TypeId.
Definition: type-id.cc:932
static WifiContainerQueueId GetQueueId(Ptr< const WifiMpdu > mpdu)
Return the QueueId identifying the container queue in which the given MPDU is (or is to be) enqueued.
WifiMacQueueScheduler is an abstract base class defining the public interface for a wifi MAC queue sc...
virtual void SetWifiMac(Ptr< WifiMac > mac)
Set the wifi MAC.
std::bitset< static_cast< std::size_t >(WifiQueueBlockedReason::REASONS_COUNT)> Mask
Bitset identifying the reasons to block individual links for a container queue.
void DoDispose() override
Destructor implementation.
WifiMacQueueSchedulerImpl is a template class enabling the definition of different types of priority ...
void DoBlockQueues(bool block, WifiQueueBlockedReason reason, AcIndex ac, const std::list< WifiContainerQueueType > &types, const Mac48Address &rxAddress, const Mac48Address &txAddress, const std::set< uint8_t > &tids, const std::set< uint8_t > &linkIds)
Block or unblock the given set of links for the container queues of the given types and Access Catego...
void UnblockQueues(WifiQueueBlockedReason reason, AcIndex ac, const std::list< WifiContainerQueueType > &types, const Mac48Address &rxAddress, const Mac48Address &txAddress, const std::set< uint8_t > &tids, const std::set< uint8_t > &linkIds) final
Unblock the given set of links for the container queues of the given types and Access Category that h...
std::pair< const WifiContainerQueueId, QueueInfo > QueueInfoPair
typedef for a QueueInfoMap element
std::optional< Mask > GetQueueLinkMask(AcIndex ac, const WifiContainerQueueId &queueId, uint8_t linkId) final
Get the mask associated with the given container queue indicating whether the given link is blocked a...
void SetWifiMac(Ptr< WifiMac > mac) final
Set the wifi MAC.
void DoDispose() override
Destructor implementation.
void NotifyDequeue(AcIndex ac, const std::list< Ptr< WifiMpdu > > &mpdus) final
Notify the scheduler that the given list of MPDUs have been dequeued by the given Access Category.
std::unordered_map< WifiContainerQueueId, QueueInfo > QueueInfoMap
Map identifiers (QueueIds) to information associated with container queues.
void NotifyEnqueue(AcIndex ac, Ptr< WifiMpdu > mpdu) final
Notify the scheduler that the given MPDU has been enqueued by the given Access Category.
virtual void DoNotifyDequeue(AcIndex ac, const std::list< Ptr< WifiMpdu > > &mpdus)=0
Notify the scheduler that the given list of MPDUs have been dequeued by the given Access Category.
void BlockQueues(WifiQueueBlockedReason reason, AcIndex ac, const std::list< WifiContainerQueueType > &types, const Mac48Address &rxAddress, const Mac48Address &txAddress, const std::set< uint8_t > &tids, const std::set< uint8_t > &linkIds) final
Block the given set of links for the container queues of the given types and Access Category that hol...
virtual void DoNotifyEnqueue(AcIndex ac, Ptr< WifiMpdu > mpdu)=0
Notify the scheduler that the given MPDU has been enqueued by the given Access Category.
Ptr< WifiMacQueue > GetWifiMacQueue(AcIndex ac) const
Get the wifi MAC queue associated with the given Access Category.
std::list< uint8_t > GetLinkIds(AcIndex ac, Ptr< const WifiMpdu > mpdu) final
Get the list of the IDs of the links the given MPDU (belonging to the given Access Category) can be s...
static TypeId GetTypeId()
Get the type ID.
std::vector< PerAcInfo > m_perAcInfo
vector of per-AC information
std::optional< WifiContainerQueueId > GetNext(AcIndex ac, std::optional< uint8_t > linkId) final
Get the next queue to serve, which is guaranteed to contain at least an MPDU whose lifetime has not e...
const SortedQueues & GetSortedQueues(AcIndex ac) const
Get a const reference to the sorted list of container queues for the given Access Category.
Ptr< WifiMpdu > HasToDropBeforeEnqueue(AcIndex ac, Ptr< WifiMpdu > mpdu) final
Check whether an MPDU has to be dropped before enqueuing the given MPDU.
void NotifyRemove(AcIndex ac, const std::list< Ptr< WifiMpdu > > &mpdus) final
Notify the scheduler that the given list of MPDUs have been removed by the given Access Category.
virtual Ptr< WifiMpdu > HasToDropBeforeEnqueuePriv(AcIndex ac, Ptr< WifiMpdu > mpdu)=0
Check whether an MPDU has to be dropped before enqueuing the given MPDU.
QueueInfoMap::iterator InitQueueInfo(AcIndex ac, Ptr< const WifiMpdu > mpdu)
If no information for the container queue used to store the given MPDU of the given Access Category i...
std::optional< WifiContainerQueueId > GetNext(AcIndex ac, std::optional< uint8_t > linkId, const WifiContainerQueueId &prevQueueId) final
Get the next queue to serve after the given one.
std::multimap< Priority, std::reference_wrapper< QueueInfoPair >, Compare > SortedQueues
List of container queues sorted in decreasing order of priority.
std::optional< WifiContainerQueueId > DoGetNext(AcIndex ac, std::optional< uint8_t > linkId, typename SortedQueues::iterator sortedQueuesIt)
Get the next queue to serve.
virtual void DoNotifyRemove(AcIndex ac, const std::list< Ptr< WifiMpdu > > &mpdus)=0
Notify the scheduler that the given list of MPDUs have been removed by the given Access Category.
void SetPriority(AcIndex ac, const WifiContainerQueueId &queueId, const Priority &priority)
Set the priority for the given container queue belonging to the given Access Category.
#define NS_ASSERT(condition)
At runtime, in debugging builds, if this condition is not true, the program prints the source file,...
Definition: assert.h:66
#define NS_ASSERT_MSG(condition, message)
At runtime, in debugging builds, if this condition is not true, the program prints the message to out...
Definition: assert.h:86
#define NS_ABORT_MSG(msg)
Unconditional abnormal program termination with a message.
Definition: abort.h:49
#define NS_ABORT_MSG_IF(cond, msg)
Abnormal program termination if a condition is true, with a message.
Definition: abort.h:108
#define NS_ABORT_IF(cond)
Abnormal program termination if a condition is true.
Definition: abort.h:76
#define NS_LOG_TEMPLATE_DEFINE(name)
Initialize a reference to a Log component.
Definition: log.h:236
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by ",...
WifiQueueBlockedReason
Enumeration of the reasons to block container queues.
AcIndex
This enumeration defines the Access Categories as an enumeration with values corresponding to the AC ...
Definition: qos-utils.h:73
@ AC_BE_NQOS
Non-QoS.
Definition: qos-utils.h:83
@ AC_BE
Best Effort.
Definition: qos-utils.h:75
@ AC_VO
Voice.
Definition: qos-utils.h:81
@ AC_VI
Video.
Definition: qos-utils.h:79
@ AC_BK
Background.
Definition: qos-utils.h:77
@ AC_UNDEF
Total number of ACs.
Definition: qos-utils.h:87
@ AC_BEACON
Beacon queue.
Definition: qos-utils.h:85
Every class exported by the ns3 library is enclosed in the ns3 namespace.
std::tuple< WifiContainerQueueType, WifiReceiverAddressType, Mac48Address, std::optional< uint8_t > > WifiContainerQueueId
Tuple (queue type, receiver address type, Address, TID) identifying a container queue.
static constexpr uint8_t SINGLE_LINK_OP_ID
Link ID for single link operations (helps tracking places where correct link ID is to be used to supp...
Definition: wifi-utils.h:192
@ WIFI_MAC_CTL_BACKREQ
@ WIFI_MAC_MGT_ACTION
@ WIFI_MAC_DATA
@ WIFI_MAC_QOSDATA
Information specific to a wifi MAC queue.
SortedQueues sortedQueues
sorted list of container queues
Ptr< WifiMacQueue > wifiMacQueue
pointer to the WifiMacQueue object
QueueInfoMap queueInfoMap
information associated with container queues
Information associated with a container queue.
std::map< uint8_t, Mask > linkIds
Maps ID of each link on which packets contained in this queue can be sent to a bitset indicating whet...
std::optional< typename SortedQueues::iterator > priorityIt
iterator pointing to the entry for this queue in the sorted list