1 /*
2 * StaCap.c
3 *
4 * Copyright(c) 1998 - 2009 Texas Instruments. All rights reserved.
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 *
11 * * Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * * Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in
15 * the documentation and/or other materials provided with the
16 * distribution.
17 * * Neither the name Texas Instruments nor the names of its
18 * contributors may be used to endorse or promote products derived
19 * from this software without specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
24 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
25 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
26 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
27 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
28 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
29 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
30 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
31 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 */
33
34
35 /** \file StaCap.c
36 * \brief STA capabilities module that responsible to publish STA capabilities to all others modules.
37 *
38 * \see StaCap.c
39 */
40
41 #define __FILE_ID__ FILE_ID_86
42 #include "osApi.h"
43 #include "report.h"
44 #include "StaCap.h"
45 #include "TWDriver.h"
46 #include "802_11Defs.h"
47 #include "qosMngr_API.h"
48 #include "Device1273.h"
49 #include "smeApi.h"
50
51 /**
52 * \fn staCap_Create
53 * \brief Create the staCap module.
54 *
55 * Allocate and clear the staCap module object.
56 *
57 * \param hOs - Handle to Os Abstraction Layer
58 * \return Handle of the allocated object
59 * \sa staCap_Destroy
60 */
StaCap_Create(TI_HANDLE hOs)61 TI_HANDLE StaCap_Create (TI_HANDLE hOs)
62 {
63 TI_HANDLE hStaCap;
64
65 /* allocate module object */
66 hStaCap = os_memoryAlloc (hOs, sizeof(TStaCap));
67
68 if (!hStaCap)
69 {
70 WLAN_OS_REPORT (("StaCap_Create(): Allocation failed!!\n"));
71 return NULL;
72 }
73
74 os_memoryZero (hOs, hStaCap, (sizeof(TStaCap)));
75
76 return (hStaCap);
77 }
78
79
80 /**
81 * \fn StaCap_Destroy
82 * \brief Destroy the module.
83 *
84 * Free the module's queues and object.
85 *
86 * \param hStaCap - The module object
87 * \return TI_OK on success or TI_NOK on failure
88 * \sa StaCap_Create
89 */
StaCap_Destroy(TI_HANDLE hStaCap)90 TI_STATUS StaCap_Destroy (TI_HANDLE hStaCap)
91 {
92 TStaCap *pStaCap = (TStaCap *)hStaCap;
93
94 /* free module object */
95 os_memoryFree (pStaCap->hOs, pStaCap, sizeof(TStaCap));
96
97 return TI_OK;
98 }
99
100
101 /**
102 * \fn StaCap_Init
103 * \brief Init required handles
104 *
105 * Init required handles and module variables.
106 *
107 * \note
108 * \param pStadHandles - The driver modules handles
109 * \return TI_OK on success or TI_NOK on failure
110 * \sa
111 */
StaCap_Init(TStadHandlesList * pStadHandles)112 TI_STATUS StaCap_Init (TStadHandlesList *pStadHandles)
113 {
114 TStaCap *pStaCap = (TStaCap *)pStadHandles->hStaCap;
115
116 pStaCap->hOs = pStadHandles->hOs;
117 pStaCap->hReport = pStadHandles->hReport;
118 pStaCap->hTWD = pStadHandles->hTWD;
119 pStaCap->hQosMngr = pStadHandles->hQosMngr;
120 pStaCap->hSme = pStadHandles->hSme;
121
122 return TI_OK;
123 }
124
125
126 /**
127 * \fn StaCap_IsHtEnable
128 * \brief verify if HT enable\disable at the STA according to 11n_Enable init flag and Chip type
129 *
130 * \note
131 * \param hStaCap - The module object
132 * \param b11nEnable - pointer to enable\disable flag
133 * \return NONE
134 * \sa
135 */
StaCap_IsHtEnable(TI_HANDLE hStaCap,TI_BOOL * b11nEnable)136 void StaCap_IsHtEnable (TI_HANDLE hStaCap, TI_BOOL *b11nEnable)
137 {
138 TStaCap *pStaCap = (TStaCap *)hStaCap;
139 TTwdHtCapabilities *pTwdHtCapabilities;
140 paramInfo_t tParam;
141
142 tParam.paramType = SME_DESIRED_BSS_TYPE_PARAM;
143 sme_GetParam (pStaCap->hSme, &tParam);
144
145 /* If Infra-BSS, get actual HT capabilities from TWD */
146 if (tParam.content.smeDesiredBSSType == BSS_INFRASTRUCTURE)
147 {
148 TWD_GetTwdHtCapabilities (pStaCap->hTWD, &pTwdHtCapabilities);
149 *b11nEnable = pTwdHtCapabilities->b11nEnable;
150 }
151 /* If IBSS, HT shouldn't be used */
152 else
153 {
154 *b11nEnable = TI_FALSE;
155 }
156 }
157
158
159 /**
160 * \fn StaCap_GetHtCapabilitiesIe
161 * \brief Get the desired STA HT capabilities IE. get the physical HT capabilities from TWD
162 * and build HT capabilities IE.
163 *
164 * \note
165 * \param hStaCap - The module object
166 * \param pRequest - pointer to request buffer\n
167 * \param len - size of returned IE\n
168 * \return TI_OK on success or TI_NOK on failure
169 * \sa
170 */
StaCap_GetHtCapabilitiesIe(TI_HANDLE hStaCap,TI_UINT8 * pRequest,TI_UINT32 * pLen)171 TI_STATUS StaCap_GetHtCapabilitiesIe (TI_HANDLE hStaCap, TI_UINT8 *pRequest, TI_UINT32 *pLen)
172 {
173 TStaCap *pStaCap = (TStaCap *)hStaCap;
174 TTwdHtCapabilities *pTwdHtCapabilities;
175 TI_UINT8 *pDataBuf = pRequest;
176 TStaCapHtCapabilities tHtCapabilities;
177 TI_BOOL bWmeEnable;
178
179 /* verify that WME flag enable */
180 qosMngr_GetWmeEnableFlag (pStaCap->hQosMngr, &bWmeEnable);
181 if (bWmeEnable == TI_FALSE)
182 {
183 TRACE0(pStaCap->hReport, REPORT_SEVERITY_INFORMATION, "StaCap_GetHtCapabilitiesIe: 802.11n disable due to WME init flag.\n");
184 *pLen = 0;
185 return TI_OK;
186 }
187
188 TWD_GetTwdHtCapabilities (pStaCap->hTWD, &pTwdHtCapabilities);
189 /* verify that 802.11n flag enable */
190 if (pTwdHtCapabilities->b11nEnable == TI_FALSE)
191 {
192 TRACE0(pStaCap->hReport, REPORT_SEVERITY_INFORMATION, "StaCap_GetHtCapabilitiesIe: 802.11n disable due to 11n_Enable init flag.\n");
193 *pLen = 0;
194 return TI_OK;
195 }
196
197 /*
198 * set TWD values to HT capabilities structure
199 *
200 * Note: all numbers after "<<" represent the position of the values in the filed according
201 * to 11n SPEC.
202 */
203 tHtCapabilities.uHtCapabilitiesInfo = ((pTwdHtCapabilities->uChannelWidth << 1) |
204 (pTwdHtCapabilities->uRxSTBC << 8) |
205 (pTwdHtCapabilities->uMaxAMSDU << 11)|
206 (DSSS_CCK_MODE << 12));
207
208 tHtCapabilities.uHtCapabilitiesInfo |= ((((pTwdHtCapabilities->uHTCapabilitiesBitMask & CAP_BIT_MASK_LDPC_CODING) ? 1 : 0) << 0) |
209 (((pTwdHtCapabilities->uHTCapabilitiesBitMask & CAP_BIT_MASK_GREENFIELD_FRAME_FORMAT) ? 1 : 0) << 4) |
210 (((pTwdHtCapabilities->uHTCapabilitiesBitMask & CAP_BIT_MASK_SHORT_GI_FOR_20MHZ_PACKETS) ? 1 : 0) << 5) |
211 (((pTwdHtCapabilities->uHTCapabilitiesBitMask & CAP_BIT_MASK_SHORT_GI_FOR_40MHZ_PACKETS) ? 1 : 0) << 6) |
212 (((pTwdHtCapabilities->uHTCapabilitiesBitMask & CAP_BIT_MASK_SUPPORT_FOR_STBC_IN_TRANSMISSION) ? 1 : 0) << 7) |
213 (((pTwdHtCapabilities->uHTCapabilitiesBitMask & CAP_BIT_MASK_DELAYED_BLOCK_ACK) ? 1 : 0) << 10) |
214 (((pTwdHtCapabilities->uHTCapabilitiesBitMask & CAP_BIT_MASK_DSSS_CCK_IN_40_MHZ) ? 1 : 0) << 12) |
215 (((pTwdHtCapabilities->uHTCapabilitiesBitMask & CAP_BIT_MASK_LSIG_TXOP_PROTECTION) ? 1 : 0) << 15));
216
217 tHtCapabilities.uAMpduParam = ((pTwdHtCapabilities->uMaxAMPDU << 0) |
218 (pTwdHtCapabilities->uAMPDUSpacing << 2));
219
220 /* copy RX supported MCS rates */
221 os_memoryCopy (pStaCap->hOs, tHtCapabilities.tSuppMcsSet.aRxMscBitmask, pTwdHtCapabilities->aRxMCS, RX_TX_MCS_BITMASK_SIZE);
222
223 tHtCapabilities.tSuppMcsSet.uHighestSupportedDataRate = pTwdHtCapabilities->uRxMaxDataRate;
224
225 /* check if supported MCS rates identical to TX and RX */
226 if( 0 == os_memoryCompare(pStaCap->hOs, pTwdHtCapabilities->aRxMCS, pTwdHtCapabilities->aTxMCS, RX_TX_MCS_BITMASK_SIZE))
227 {
228 tHtCapabilities.tSuppMcsSet.uTxRxSetting = ((TX_MCS_SET_YES << 0) | /* set supported TX MCS rate */
229 (TX_RX_NOT_EQUAL_NO << 1)); /* set TX&RX MCS rate are equal */
230 }
231 /* in case supported MCS rates TX different from the RX */
232 else
233 {
234 TI_UINT32 i;
235
236 /* check if there are TX MCS rates supported */
237 for (i = 0; i <= (RX_TX_MCS_BITMASK_SIZE - 1); ++i)
238 {
239 if (pTwdHtCapabilities->aTxMCS[i] != 0)
240 {
241 break;
242 }
243 }
244
245 /* TX MCS supported */
246 if(i <= (RX_TX_MCS_BITMASK_SIZE -1))
247 {
248 tHtCapabilities.tSuppMcsSet.uTxRxSetting = ((TX_MCS_SET_YES << 0) | /* set supported TX MCS rates */
249 (TX_RX_NOT_EQUAL_YES << 1)); /* set TX&RX MCS rates different */
250 }
251 /* TX MCS not supported */
252 else
253 {
254 tHtCapabilities.tSuppMcsSet.uTxRxSetting = (TX_MCS_SET_NO << 0); /* set no supported TX MCS rates */
255 }
256 }
257
258 tHtCapabilities.uExteCapabilities = (((pTwdHtCapabilities->uHTCapabilitiesBitMask & CAP_BIT_MASK_PCO) ? 1 : 0) << 0);
259
260 if (tHtCapabilities.uExteCapabilities != 0)
261 {
262 tHtCapabilities.uExteCapabilities |= (pTwdHtCapabilities->uPCOTransTime << 1);
263 }
264
265 tHtCapabilities.uExteCapabilities |= ((pTwdHtCapabilities->uMCSFeedback << 8) |
266 (HTC_SUPPORT_NO << 10));
267
268 tHtCapabilities.uTxBfCapabilities = ((IMPLICIT_TXBF_REC_CAPABLE << 0) |
269 (TRANSMIT_STAGGERED_SOUNDING_CAPABLE << 2));
270
271 tHtCapabilities.uAselCapabilities = 0x0;
272
273
274 /* build IE */
275 *pDataBuf = HT_CAPABILITIES_IE_ID;
276 *(pDataBuf + 1) = DOT11_HT_CAPABILITIES_ELE_LEN;
277 COPY_WLAN_WORD(pDataBuf + 2, &(tHtCapabilities.uHtCapabilitiesInfo));
278 *(pDataBuf + 4) = tHtCapabilities.uAMpduParam;
279 os_memoryCopy (pStaCap->hOs, pDataBuf + 5, tHtCapabilities.tSuppMcsSet.aRxMscBitmask, RX_TX_MCS_BITMASK_SIZE);
280 COPY_WLAN_WORD(pDataBuf + 15, &(tHtCapabilities.tSuppMcsSet.uHighestSupportedDataRate));
281 *(pDataBuf + 17) = tHtCapabilities.tSuppMcsSet.uTxRxSetting;
282 /* clear the reserved bytes */
283 os_memoryZero (pStaCap->hOs, (pDataBuf + 18), 3);
284 COPY_WLAN_WORD(pDataBuf + 21, &(tHtCapabilities.uExteCapabilities));
285 COPY_WLAN_LONG(pDataBuf + 23, &(tHtCapabilities.uTxBfCapabilities));
286 *(pDataBuf + 27) = tHtCapabilities.uAselCapabilities;
287
288 *pLen = DOT11_HT_CAPABILITIES_ELE_LEN + sizeof(dot11_eleHdr_t);
289
290 return TI_OK;
291 }
292
293