1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2020 Orange Labs
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: Rediet <getachew.redieteab@orange.com>
19  *         Muhammad Iqbal Rochman <muhiqbalcr@uchicago.edu>
20  *         Sébastien Deronne <sebastien.deronne@gmail.com> (HeSigHeader)
21  */
22 
23 #ifndef HE_PPDU_H
24 #define HE_PPDU_H
25 
26 #include "ns3/ofdm-ppdu.h"
27 
28 /**
29  * \file
30  * \ingroup wifi
31  * Declaration of ns3::HePpdu class.
32  */
33 
34 namespace ns3 {
35 
36 class WifiPsdu;
37 
38 /**
39  * \brief HE PPDU (11ax)
40  * \ingroup wifi
41  *
42  * HePpdu stores a preamble, PHY headers and a map of PSDUs of a PPDU with HE header
43  */
44 class HePpdu : public OfdmPpdu
45 {
46 public:
47 
48   /**
49    * HE-SIG PHY header (HE-SIG-A1/A2/B)
50    */
51   class HeSigHeader : public Header
52   {
53   public:
54     HeSigHeader ();
55     virtual ~HeSigHeader ();
56 
57     /**
58      * \brief Get the type ID.
59      * \return the object TypeId
60      */
61     static TypeId GetTypeId (void);
62 
63     TypeId GetInstanceTypeId (void) const override;
64     void Print (std::ostream &os) const override;
65     uint32_t GetSerializedSize (void) const override;
66     void Serialize (Buffer::Iterator start) const override;
67     uint32_t Deserialize (Buffer::Iterator start) override;
68 
69     /**
70      * Set the Multi-User (MU) flag.
71      *
72      * \param mu the MU flag
73      */
74     void SetMuFlag (bool mu);
75 
76     /**
77      * Fill the MCS field of HE-SIG-A1.
78      *
79      * \param mcs the MCS field of HE-SIG-A1
80      */
81     void SetMcs (uint8_t mcs);
82     /**
83      * Return the MCS field of HE-SIG-A1.
84      *
85      * \return the MCS field of HE-SIG-A1
86      */
87     uint8_t GetMcs (void) const;
88     /**
89      * Fill the BSS Color field of HE-SIG-A1.
90      *
91      * \param bssColor the BSS Color value
92      */
93     void SetBssColor (uint8_t bssColor);
94     /**
95      * Return the BSS Color field in the HE-SIG-A1.
96      *
97      * \return the BSS Color field in the HE-SIG-A1
98      */
99     uint8_t GetBssColor (void) const;
100     /**
101      * Fill the channel width field of HE-SIG-A1 (in MHz).
102      *
103      * \param channelWidth the channel width (in MHz)
104      */
105     void SetChannelWidth (uint16_t channelWidth);
106     /**
107      * Return the channel width (in MHz).
108      *
109      * \return the channel width (in MHz)
110      */
111     uint16_t GetChannelWidth (void) const;
112     /**
113      * Fill the GI + LTF size field of HE-SIG-A1.
114      *
115      * \param gi the guard interval (in nanoseconds)
116      * \param ltf the sequence of HE-LTF
117      */
118     void SetGuardIntervalAndLtfSize (uint16_t gi, uint8_t ltf);
119     /**
120      * Return the guard interval (in nanoseconds).
121      *
122      * \return the guard interval (in nanoseconds)
123      */
124     uint16_t GetGuardInterval (void) const;
125     /**
126      * Fill the number of streams field of HE-SIG-A1.
127      *
128      * \param nStreams the number of streams
129      */
130     void SetNStreams (uint8_t nStreams);
131     /**
132      * Return the number of streams.
133      *
134      * \return the number of streams
135      */
136     uint8_t GetNStreams (void) const;
137 
138   private:
139     //HE-SIG-A1 fields
140     uint8_t m_format;       ///< Format bit
141     uint8_t m_bssColor;     ///< BSS color field
142     uint8_t m_ul_dl;        ///< UL/DL bit
143     uint8_t m_mcs;          ///< MCS field
144     uint8_t m_spatialReuse; ///< Spatial Reuse field
145     uint8_t m_bandwidth;    ///< Bandwidth field
146     uint8_t m_gi_ltf_size;  ///< GI+LTF Size field
147     uint8_t m_nsts;         ///< NSTS
148 
149     /// This is used to decide whether MU SIG-B should be added or not
150     bool m_mu;
151   }; //class HeSigHeader
152 
153   /**
154    * The transmit power spectral density flag, namely used
155    * to correctly build PSD for HE TB PPDU non-OFDMA and
156    * OFDMA portions.
157    */
158   enum TxPsdFlag
159   {
160     PSD_NON_HE_TB = 0,           //!< non-HE TB PPDU transmissions
161     PSD_HE_TB_NON_OFDMA_PORTION, //!< preamble of HE TB PPDU, which should only be sent on minimum subset of 20 MHz channels containing RU
162     PSD_HE_TB_OFDMA_PORTION      //!< OFDMA portion of HE TB PPDU, which should only be sent on RU
163   };
164 
165   /**
166    * Create an SU HE PPDU, storing a PSDU.
167    *
168    * \param psdu the PHY payload (PSDU)
169    * \param txVector the TXVECTOR that was used for this PPDU
170    * \param ppduDuration the transmission duration of this PPDU
171    * \param band the WifiPhyBand used for the transmission of this PPDU
172    * \param uid the unique ID of this PPDU
173    */
174   HePpdu (Ptr<const WifiPsdu> psdu, const WifiTxVector& txVector, Time ppduDuration,
175           WifiPhyBand band, uint64_t uid);
176   /**
177    * Create an MU HE PPDU, storing a map of PSDUs.
178    *
179    * This PPDU can either be UL or DL.
180    *
181    * \param psdus the PHY payloads (PSDUs)
182    * \param txVector the TXVECTOR that was used for this PPDU
183    * \param ppduDuration the transmission duration of this PPDU
184    * \param band the WifiPhyBand used for the transmission of this PPDU
185    * \param uid the unique ID of this PPDU or of the triggering PPDU if this is an HE TB PPDU
186    * \param flag the flag indicating the type of Tx PSD to build
187    */
188   HePpdu (const WifiConstPsduMap & psdus, const WifiTxVector& txVector, Time ppduDuration,
189           WifiPhyBand band, uint64_t uid, TxPsdFlag flag);
190   /**
191    * Destructor for HePpdu.
192    */
193   virtual ~HePpdu ();
194 
195   Time GetTxDuration (void) const override;
196   Ptr<WifiPpdu> Copy (void) const override;
197   WifiPpduType GetType (void) const override;
198   uint16_t GetStaId (void) const override;
199   uint16_t GetTransmissionChannelWidth (void) const override;
200   bool CanBeReceived (uint16_t txCenterFreq, uint16_t p20MinFreq,
201                       uint16_t p20MaxFreq) const override;
202 
203   /**
204    * Get the payload of the PPDU.
205    *
206    * \param bssColor the BSS color of the PHY calling this function.
207    * \param staId the STA-ID of the PHY calling this function.
208    * \return the PSDU
209    */
210   Ptr<const WifiPsdu> GetPsdu (uint8_t bssColor, uint16_t staId = SU_STA_ID) const;
211 
212   /**
213    * \return the transmit PSD flag set for this PPDU
214    *
215    * \see TxPsdFlag
216    */
217   TxPsdFlag GetTxPsdFlag (void) const;
218 
219   /**
220    * \param flag the transmit PSD flag set for this PPDU
221    *
222    * \see TxPsdFlag
223    */
224   void SetTxPsdFlag (TxPsdFlag flag);
225 
226 protected:
227   std::string PrintPayload (void) const override;
228 
229   /**
230    * Return true if the PPDU is a MU PPDU
231    * \return true if the PPDU is a MU PPDU
232    */
233   bool IsMu (void) const;
234   /**
235    * Return true if the PPDU is a DL MU PPDU
236    * \return true if the PPDU is a DL MU PPDU
237    */
238   bool IsDlMu (void) const;
239   /**
240    * Return true if the PPDU is an UL MU PPDU
241    * \return true if the PPDU is an UL MU PPDU
242    */
243   bool IsUlMu (void) const;
244 
245   WifiTxVector::HeMuUserInfoMap m_muUserInfos; //!< the HE MU specific per-user information (to be removed once HE-SIG-B headers are implemented)
246 
247 private:
248   WifiTxVector DoGetTxVector (void) const override;
249 
250   /**
251    * Fill in the HE PHY headers.
252    *
253    * \param txVector the TXVECTOR that was used for this PPDU
254    * \param ppduDuration the transmission duration of this PPDU
255    */
256   void SetPhyHeaders (const WifiTxVector& txVector, Time ppduDuration);
257 
258   HeSigHeader m_heSig;   //!< the HE-SIG PHY header
259   TxPsdFlag m_txPsdFlag; //!< the transmit power spectral density flag
260 }; //class HePpdu
261 
262 /**
263 * \brief Stream insertion operator.
264 *
265 * \param os the stream
266 * \param flag the transmit power spectral density flag
267 * \returns a reference to the stream
268 */
269 std::ostream& operator<< (std::ostream& os, const HePpdu::TxPsdFlag &flag);
270 
271 } //namespace ns3
272 
273 #endif /* HE_PPDU_H */
274