support different wifi bt chip auto compatible
[firefly-linux-kernel-4.4.55.git] / drivers / net / wireless / rockchip_wlan / mt5931_kk / drv_wlan / os / linux / gl_wext_priv.c
1 /*
2 ** $Id: //Department/DaVinci/BRANCHES/MT662X_593X_WIFI_DRIVER_V2_3/os/linux/gl_wext_priv.c#1 $
3 */
4
5 /*! \file gl_wext_priv.c
6     \brief This file includes private ioctl support.
7 */
8
9 /*******************************************************************************
10 * Copyright (c) 2007 MediaTek Inc.
11 *
12 * All rights reserved. Copying, compilation, modification, distribution
13 * or any other use whatsoever of this material is strictly prohibited
14 * except in accordance with a Software License Agreement with
15 * MediaTek Inc.
16 ********************************************************************************
17 */
18
19 /*******************************************************************************
20 * LEGAL DISCLAIMER
21 *
22 * BY OPENING THIS FILE, BUYER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND
23 * AGREES THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK
24 * SOFTWARE") RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE
25 * PROVIDED TO BUYER ON AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY
26 * DISCLAIMS ANY AND ALL WARRANTIES, EXPRESS OR IMPLIED, INCLUDING BUT NOT
27 * LIMITED TO THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
28 * PARTICULAR PURPOSE OR NONINFRINGEMENT. NEITHER DOES MEDIATEK PROVIDE
29 * ANY WARRANTY WHATSOEVER WITH RESPECT TO THE SOFTWARE OF ANY THIRD PARTY
30 * WHICH MAY BE USED BY, INCORPORATED IN, OR SUPPLIED WITH THE MEDIATEK
31 * SOFTWARE, AND BUYER AGREES TO LOOK ONLY TO SUCH THIRD PARTY FOR ANY
32 * WARRANTY CLAIM RELATING THERETO. MEDIATEK SHALL ALSO NOT BE RESPONSIBLE
33 * FOR ANY MEDIATEK SOFTWARE RELEASES MADE TO BUYER'S SPECIFICATION OR TO
34 * CONFORM TO A PARTICULAR STANDARD OR OPEN FORUM.
35 *
36 * BUYER'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK'S ENTIRE AND CUMULATIVE
37 * LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE RELEASED HEREUNDER WILL
38 * BE, AT MEDIATEK'S OPTION, TO REVISE OR REPLACE THE MEDIATEK SOFTWARE AT
39 * ISSUE, OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE CHARGE PAID BY
40 * BUYER TO MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE.
41 *
42 * THE TRANSACTION CONTEMPLATED HEREUNDER SHALL BE CONSTRUED IN ACCORDANCE
43 * WITH THE LAWS OF THE STATE OF CALIFORNIA, USA, EXCLUDING ITS CONFLICT
44 * OF LAWS PRINCIPLES.  ANY DISPUTES, CONTROVERSIES OR CLAIMS ARISING
45 * THEREOF AND RELATED THERETO SHALL BE SETTLED BY ARBITRATION IN SAN
46 * FRANCISCO, CA, UNDER THE RULES OF THE INTERNATIONAL CHAMBER OF COMMERCE
47 * (ICC).
48 ********************************************************************************
49 */
50
51 /*
52 ** $Log: gl_wext_priv.c $
53 **
54 ** 08 24 2012 cp.wu
55 ** [WCXRP00001269] [MT6620 Wi-Fi][Driver] cfg80211 porting merge back to DaVinci
56 ** .
57 **
58 ** 08 24 2012 cp.wu
59 ** [WCXRP00001269] [MT6620 Wi-Fi][Driver] cfg80211 porting merge back to DaVinci
60 ** cfg80211 support merge back from ALPS.JB to DaVinci - MT6620 Driver v2.3 branch.
61  *
62  * 07 17 2012 yuche.tsai
63  * NULL
64  * Let netdev bring up.
65  *
66  * 06 13 2012 yuche.tsai
67  * NULL
68  * Update maintrunk driver.
69  * Add support for driver compose assoc request frame.
70  *
71  * 03 20 2012 wh.su
72  * [WCXRP00001153] [MT6620 Wi-Fi][Driver] Adding the get_ch_list and set_tx_power proto type function[WCXRP00001202] [MT6628 Wi-Fi][FW] Adding the New PN init code
73  * use return to avoid the ioctl return not supported
74  *
75  * 03 02 2012 terry.wu
76  * NULL
77  * Snc CFG80211 modification for ICS migration from branch 2.2.
78  *
79  * 01 16 2012 wh.su
80  * [WCXRP00001170] [MT6620 Wi-Fi][Driver] Adding the related code for set/get band ioctl
81  * Adding the template code for set / get band IOCTL (with ICS supplicant_6)..
82  *
83  * 01 05 2012 wh.su
84  * [WCXRP00001153] [MT6620 Wi-Fi][Driver] Adding the get_ch_list and set_tx_power proto type function
85  * Adding the related ioctl / wlan oid function to set the Tx power cfg.
86  *
87  * 01 02 2012 wh.su
88  * [WCXRP00001153] [MT6620 Wi-Fi][Driver] Adding the get_ch_list and set_tx_power proto type function
89  * Adding the proto type function for set_int set_tx_power and get int get_ch_list.
90  *
91  * 11 10 2011 cp.wu
92  * [WCXRP00001098] [MT6620 Wi-Fi][Driver] Replace printk by DBG LOG macros in linux porting layer
93  * 1. eliminaite direct calls to printk in porting layer.
94  * 2. replaced by DBGLOG, which would be XLOG on ALPS platforms.
95  *
96  * 11 02 2011 chinghwa.yu
97  * [WCXRP00000063] Update BCM CoEx design and settings
98  * Fixed typo.
99  *
100  * 09 20 2011 chinglan.wang
101  * [WCXRP00000989] [WiFi Direct] [Driver] Add a new io control API to start the formation for the sigma test.
102  * .
103  *
104  * 07 28 2011 chinghwa.yu
105  * [WCXRP00000063] Update BCM CoEx design and settings
106  * Add BWCS cmd and event.
107  *
108  * 07 18 2011 chinghwa.yu
109  * [WCXRP00000063] Update BCM CoEx design and settings[WCXRP00000612] [MT6620 Wi-Fi] [FW] CSD update SWRDD algorithm
110  * Add CMD/Event for RDD and BWCS.
111  *
112  * 03 17 2011 chinglan.wang
113  * [WCXRP00000570] [MT6620 Wi-Fi][Driver] Add Wi-Fi Protected Setup v2.0 feature
114  * .
115  *
116  * 03 07 2011 terry.wu
117  * [WCXRP00000521] [MT6620 Wi-Fi][Driver] Remove non-standard debug message
118  * Toggle non-standard debug messages to comments.
119  *
120  * 01 27 2011 cm.chang
121  * [WCXRP00000402] [MT6620 Wi-Fi][Driver] Enable MCR read/write by iwpriv by default
122  * .
123  *
124  * 01 26 2011 wh.su
125  * [WCXRP00000396] [MT6620 Wi-Fi][Driver] Support Sw Ctrl ioctl at linux
126  * adding the SW cmd ioctl support, use set/get structure ioctl.
127  *
128  * 01 20 2011 eddie.chen
129  * [WCXRP00000374] [MT6620 Wi-Fi][DRV] SW debug control
130  * Adjust OID order.
131  *
132  * 01 20 2011 eddie.chen
133  * [WCXRP00000374] [MT6620 Wi-Fi][DRV] SW debug control
134  * Add Oid for sw control debug command
135  *
136  * 01 07 2011 cm.chang
137  * [WCXRP00000336] [MT6620 Wi-Fi][Driver] Add test mode commands in normal phone operation
138  * Add a new compiling option to control if MCR read/write is permitted
139  *
140  * 12 31 2010 cm.chang
141  * [WCXRP00000336] [MT6620 Wi-Fi][Driver] Add test mode commands in normal phone operation
142  * Add some iwpriv commands to support test mode operation
143  *
144  * 12 15 2010 george.huang
145  * [WCXRP00000152] [MT6620 Wi-Fi] AP mode power saving function
146  * Support set PS profile and set WMM-PS related iwpriv.
147  *
148  * 11 08 2010 wh.su
149  * [WCXRP00000171] [MT6620 Wi-Fi][Driver] Add message check code same behavior as mt5921
150  * add the message check code from mt5921.
151  *
152  * 10 18 2010 cp.wu
153  * [WCXRP00000056] [MT6620 Wi-Fi][Driver] NVRAM implementation with Version Check[WCXRP00000086] [MT6620 Wi-Fi][Driver] The mac address is all zero at android
154  * complete implementation of Android NVRAM access
155  *
156  * 09 24 2010 cp.wu
157  * [WCXRP00000056] [MT6620 Wi-Fi][Driver] NVRAM implementation with Version Check
158  * correct typo for NVRAM access.
159  *
160  * 09 23 2010 cp.wu
161  * [WCXRP00000056] [MT6620 Wi-Fi][Driver] NVRAM implementation with Version Check
162  * add skeleton for NVRAM integration
163  *
164  * 08 04 2010 cp.wu
165  * NULL
166  * revert changelist #15371, efuse read/write access will be done by RF test approach
167  *
168  * 08 04 2010 cp.wu
169  * NULL
170  * add OID definitions for EFUSE read/write access.
171  *
172  * 07 08 2010 cp.wu
173  *
174  * [WPD00003833] [MT6620 and MT5931] Driver migration - move to new repository.
175  *
176  * 06 06 2010 kevin.huang
177  * [WPD00003832][MT6620 5931] Create driver base
178  * [MT6620 5931] Create driver base
179  *
180  * 06 01 2010 cp.wu
181  * [WPD00001943]Create WiFi test driver framework on WinXP
182  * enable OID_CUSTOM_MTK_WIFI_TEST for RFTest & META tool
183  *
184  * 05 29 2010 jeffrey.chang
185  * [WPD00003826]Initial import for Linux port
186  * fix private ioctl for rftest
187  *
188  * 04 21 2010 jeffrey.chang
189  * [WPD00003826]Initial import for Linux port
190  * add for private ioctl support
191 **  \main\maintrunk.MT5921\32 2009-10-08 10:33:25 GMT mtk01090
192 **  Avoid accessing private data of net_device directly. Replace with netdev_priv(). Add more checking for input parameters and pointers.
193 **  \main\maintrunk.MT5921\31 2009-09-29 16:46:21 GMT mtk01090
194 **  Remove unused functions
195 **  \main\maintrunk.MT5921\30 2009-09-29 14:46:47 GMT mtk01090
196 **  Fix compile warning
197 **  \main\maintrunk.MT5921\29 2009-09-29 14:28:48 GMT mtk01090
198 **  Fix compile warning
199 **  \main\maintrunk.MT5921\28 2009-09-28 22:21:38 GMT mtk01090
200 **  Refine lines to supress compile warning
201 **  \main\maintrunk.MT5921\27 2009-09-28 20:19:14 GMT mtk01090
202 **  Add private ioctl to carry OID structures. Restructure public/private ioctl interfaces to Linux kernel.
203 **  \main\maintrunk.MT5921\26 2009-08-18 22:56:53 GMT mtk01090
204 **  Add Linux SDIO (with mmc core) support.
205 **  Add Linux 2.6.21, 2.6.25, 2.6.26.
206 **  Fix compile warning in Linux.
207 **  \main\maintrunk.MT5921\25 2009-05-07 22:26:15 GMT mtk01089
208 **  Add mandatory and private IO control for Linux BWCS
209 **  \main\maintrunk.MT5921\24 2009-04-29 10:07:05 GMT mtk01088
210 **  fixed the compiling error at linux
211 **  \main\maintrunk.MT5921\23 2009-04-24 09:09:45 GMT mtk01088
212 **  mark the code not used at linux supplicant v0.6.7
213 **  \main\maintrunk.MT5921\22 2008-11-24 21:03:51 GMT mtk01425
214 **  1. Add PTA_ENABLED flag
215 **  \main\maintrunk.MT5921\21 2008-08-29 14:55:59 GMT mtk01088
216 **  adjust the code for meet the coding style, and add assert check
217 **  \main\maintrunk.MT5921\20 2008-07-16 15:23:20 GMT mtk01104
218 **  Support GPIO2 mode
219 **  \main\maintrunk.MT5921\19 2008-07-15 17:43:11 GMT mtk01084
220 **  modify variable name
221 **  \main\maintrunk.MT5921\18 2008-07-14 14:37:58 GMT mtk01104
222 **  Add exception handle about length in function priv_set_struct()
223 **  \main\maintrunk.MT5921\17 2008-07-14 13:55:32 GMT mtk01104
224 **  Support PRIV_CMD_BT_COEXIST
225 **  \main\maintrunk.MT5921\16 2008-07-09 00:20:15 GMT mtk01461
226 **  Add priv oid to support WMM_PS_TEST
227 **  \main\maintrunk.MT5921\15 2008-06-02 11:15:22 GMT mtk01461
228 **  Update after wlanoidSetPowerMode changed
229 **  \main\maintrunk.MT5921\14 2008-05-30 19:31:07 GMT mtk01461
230 **  Add IOCTL for Power Mode
231 **  \main\maintrunk.MT5921\13 2008-05-30 18:57:15 GMT mtk01461
232 **  Not use wlanoidSetCSUMOffloadForLinux()
233 **  \main\maintrunk.MT5921\12 2008-05-30 15:13:18 GMT mtk01084
234 **  rename wlanoid
235 **  \main\maintrunk.MT5921\11 2008-05-29 14:16:31 GMT mtk01084
236 **  rename for wlanoidSetBeaconIntervalForLinux
237 **  \main\maintrunk.MT5921\10 2008-04-17 23:06:37 GMT mtk01461
238 **  Add iwpriv support for AdHocMode setting
239 **  \main\maintrunk.MT5921\9 2008-03-31 21:00:55 GMT mtk01461
240 **  Add priv IOCTL for VOIP setting
241 **  \main\maintrunk.MT5921\8 2008-03-31 13:49:43 GMT mtk01461
242 **  Add priv ioctl to turn on / off roaming
243 **  \main\maintrunk.MT5921\7 2008-03-26 15:35:14 GMT mtk01461
244 **  Add CSUM offload priv ioctl for Linux
245 **  \main\maintrunk.MT5921\6 2008-03-11 14:50:59 GMT mtk01461
246 **  Unify priv ioctl
247 **  \main\maintrunk.MT5921\5 2007-11-06 19:32:30 GMT mtk01088
248 **  add WPS code
249 **  \main\maintrunk.MT5921\4 2007-10-30 12:01:39 GMT MTK01425
250 **  1. Update wlanQueryInformation and wlanSetInformation
251 */
252
253 /*******************************************************************************
254 *                         C O M P I L E R   F L A G S
255 ********************************************************************************
256 */
257
258 /*******************************************************************************
259 *                    E X T E R N A L   R E F E R E N C E S
260 ********************************************************************************
261 */
262 #include "gl_os.h"
263 #include "gl_wext_priv.h"
264 #if CFG_SUPPORT_WAPI
265 #include "gl_sec.h"
266 #endif
267 #if CFG_ENABLE_WIFI_DIRECT
268 #include "gl_p2p_os.h"
269 #endif
270
271 /*******************************************************************************
272 *                              C O N S T A N T S
273 ********************************************************************************
274 */
275 #define NUM_SUPPORTED_OIDS      (sizeof(arWlanOidReqTable) / sizeof(WLAN_REQ_ENTRY))
276
277 /*******************************************************************************
278 *                  F U N C T I O N   D E C L A R A T I O N S
279 ********************************************************************************
280 */
281
282 static int
283 priv_get_ndis (
284     IN struct net_device *prNetDev,
285     IN NDIS_TRANSPORT_STRUCT* prNdisReq,
286     OUT PUINT_32 pu4OutputLen
287     );
288
289 static int
290 priv_set_ndis (
291     IN struct net_device *prNetDev,
292     IN NDIS_TRANSPORT_STRUCT* prNdisReq,
293     OUT PUINT_32 pu4OutputLen
294     );
295
296 #if 0 /* CFG_SUPPORT_WPS */
297 static int
298 priv_set_appie (
299     IN struct net_device *prNetDev,
300     IN struct iw_request_info *prIwReqInfo,
301     IN union iwreq_data *prIwReqData,
302     OUT char *pcExtra
303     );
304
305 static int
306 priv_set_filter (
307     IN struct net_device *prNetDev,
308     IN struct iw_request_info *prIwReqInfo,
309     IN union iwreq_data *prIwReqData,
310     OUT char *pcExtra
311     );
312 #endif /* CFG_SUPPORT_WPS */
313
314 static BOOLEAN
315 reqSearchSupportedOidEntry (
316     IN  UINT_32            rOid,
317     OUT P_WLAN_REQ_ENTRY    *ppWlanReqEntry
318     );
319
320 #if 0
321 static WLAN_STATUS
322 reqExtQueryConfiguration (
323     IN  P_GLUE_INFO_T   prGlueInfo,
324     OUT PVOID           pvQueryBuffer,
325     IN UINT_32          u4QueryBufferLen,
326     OUT PUINT_32        pu4QueryInfoLen
327     );
328
329 static WLAN_STATUS
330 reqExtSetConfiguration (
331     IN  P_GLUE_INFO_T prGlueInfo,
332     IN  PVOID         pvSetBuffer,
333     IN  UINT_32       u4SetBufferLen,
334     OUT PUINT_32      pu4SetInfoLen
335     );
336 #endif
337
338 static WLAN_STATUS
339 reqExtSetAcpiDevicePowerState (
340     IN  P_GLUE_INFO_T prGlueInfo,
341     IN  PVOID         pvSetBuffer,
342     IN  UINT_32       u4SetBufferLen,
343     OUT PUINT_32      pu4SetInfoLen
344     );
345
346 /*******************************************************************************
347 *                       P R I V A T E   D A T A
348 ********************************************************************************
349 */
350 static UINT_8 aucOidBuf[4096] = {0};
351
352 /* OID processing table */
353 /* Order is important here because the OIDs should be in order of
354    increasing value for binary searching. */
355 static WLAN_REQ_ENTRY arWlanOidReqTable[] = {
356     /*
357     {(NDIS_OID)rOid,
358         (PUINT_8)pucOidName,
359         fgQryBufLenChecking, fgSetBufLenChecking, fgIsHandleInGlueLayerOnly, u4InfoBufLen,
360         pfOidQueryHandler,
361         pfOidSetHandler}
362     */
363     /* General Operational Characteristics */
364
365     /* Ethernet Operational Characteristics */
366     {OID_802_3_CURRENT_ADDRESS,
367         DISP_STRING("OID_802_3_CURRENT_ADDRESS"),
368         TRUE, TRUE, ENUM_OID_DRIVER_CORE, 6,
369         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryCurrentAddr,
370         NULL},
371
372     /* OID_802_3_MULTICAST_LIST */
373     /* OID_802_3_MAXIMUM_LIST_SIZE */
374     /* Ethernet Statistics */
375
376     /* NDIS 802.11 Wireless LAN OIDs */
377     {OID_802_11_SUPPORTED_RATES,
378         DISP_STRING("OID_802_11_SUPPORTED_RATES"),
379         TRUE, FALSE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_RATES_EX),
380         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQuerySupportedRates,
381         NULL},
382     /*
383     {OID_802_11_CONFIGURATION,
384         DISP_STRING("OID_802_11_CONFIGURATION"),
385         TRUE, TRUE, ENUM_OID_GLUE_EXTENSION, sizeof(PARAM_802_11_CONFIG_T),
386         (PFN_OID_HANDLER_FUNC_REQ)reqExtQueryConfiguration,
387         (PFN_OID_HANDLER_FUNC_REQ)reqExtSetConfiguration},
388     */
389     {OID_PNP_SET_POWER,
390         DISP_STRING("OID_PNP_SET_POWER"),
391         TRUE, FALSE, ENUM_OID_GLUE_EXTENSION, sizeof(PARAM_DEVICE_POWER_STATE),
392         NULL,
393         (PFN_OID_HANDLER_FUNC_REQ)reqExtSetAcpiDevicePowerState},
394
395     /* Custom OIDs */
396     {OID_CUSTOM_OID_INTERFACE_VERSION,
397         DISP_STRING("OID_CUSTOM_OID_INTERFACE_VERSION"),
398         TRUE, FALSE, ENUM_OID_DRIVER_CORE, 4,
399         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryOidInterfaceVersion,
400         NULL},
401
402     /*
403 #if PTA_ENABLED
404     {OID_CUSTOM_BT_COEXIST_CTRL,
405         DISP_STRING("OID_CUSTOM_BT_COEXIST_CTRL"),
406         FALSE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_CUSTOM_BT_COEXIST_T),
407         NULL,
408         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetBtCoexistCtrl},
409 #endif
410     */
411
412     /*
413     {OID_CUSTOM_POWER_MANAGEMENT_PROFILE,
414         DISP_STRING("OID_CUSTOM_POWER_MANAGEMENT_PROFILE"),
415         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 0,
416         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryPwrMgmtProfParam,
417         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetPwrMgmtProfParam},
418     {OID_CUSTOM_PATTERN_CONFIG,
419         DISP_STRING("OID_CUSTOM_PATTERN_CONFIG"),
420         TRUE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_CUSTOM_PATTERN_SEARCH_CONFIG_STRUC_T),
421         NULL,
422         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetPatternConfig},
423     {OID_CUSTOM_BG_SSID_SEARCH_CONFIG,
424         DISP_STRING("OID_CUSTOM_BG_SSID_SEARCH_CONFIG"),
425         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 0,
426         NULL,
427         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetBgSsidParam},
428     {OID_CUSTOM_VOIP_SETUP,
429         DISP_STRING("OID_CUSTOM_VOIP_SETUP"),
430         TRUE, TRUE, ENUM_OID_DRIVER_CORE, 4,
431         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryVoipConnectionStatus,
432         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetVoipConnectionStatus},
433     {OID_CUSTOM_ADD_TS,
434         DISP_STRING("OID_CUSTOM_ADD_TS"),
435         TRUE, TRUE, ENUM_OID_DRIVER_CORE, 4,
436         NULL,
437         (PFN_OID_HANDLER_FUNC_REQ)wlanoidAddTS},
438     {OID_CUSTOM_DEL_TS,
439         DISP_STRING("OID_CUSTOM_DEL_TS"),
440         TRUE, TRUE, ENUM_OID_DRIVER_CORE, 4,
441         NULL,
442         (PFN_OID_HANDLER_FUNC_REQ)wlanoidDelTS},
443     */
444
445     /*
446 #if CFG_LP_PATTERN_SEARCH_SLT
447     {OID_CUSTOM_SLT,
448         DISP_STRING("OID_CUSTOM_SLT"),
449         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 0,
450         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQuerySltResult,
451         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetSltMode},
452 #endif
453
454     {OID_CUSTOM_ROAMING_EN,
455         DISP_STRING("OID_CUSTOM_ROAMING_EN"),
456         TRUE, TRUE, ENUM_OID_DRIVER_CORE, 4,
457         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryRoamingFunction,
458         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetRoamingFunction},
459     {OID_CUSTOM_WMM_PS_TEST,
460         DISP_STRING("OID_CUSTOM_WMM_PS_TEST"),
461         TRUE, TRUE, ENUM_OID_DRIVER_CORE, 4,
462         NULL,
463         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetWiFiWmmPsTest},
464     {OID_CUSTOM_COUNTRY_STRING,
465         DISP_STRING("OID_CUSTOM_COUNTRY_STRING"),
466         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 0,
467         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryCurrentCountry,
468         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetCurrentCountry},
469
470 #if CFG_SUPPORT_802_11D
471     {OID_CUSTOM_MULTI_DOMAIN_CAPABILITY,
472         DISP_STRING("OID_CUSTOM_MULTI_DOMAIN_CAPABILITY"),
473         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 0,
474         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryMultiDomainCap,
475         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetMultiDomainCap},
476 #endif
477
478     {OID_CUSTOM_GPIO2_MODE,
479         DISP_STRING("OID_CUSTOM_GPIO2_MODE"),
480         FALSE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(ENUM_PARAM_GPIO2_MODE_T),
481         NULL,
482         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetGPIO2Mode},
483     {OID_CUSTOM_CONTINUOUS_POLL,
484         DISP_STRING("OID_CUSTOM_CONTINUOUS_POLL"),
485         FALSE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_CONTINUOUS_POLL_T),
486         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryContinuousPollInterval,
487         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetContinuousPollProfile},
488     {OID_CUSTOM_DISABLE_BEACON_DETECTION,
489         DISP_STRING("OID_CUSTOM_DISABLE_BEACON_DETECTION"),
490         FALSE, TRUE, ENUM_OID_DRIVER_CORE, 4,
491         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryDisableBeaconDetectionFunc,
492         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetDisableBeaconDetectionFunc},
493     */
494
495     /* WPS */
496     /*
497     {OID_CUSTOM_DISABLE_PRIVACY_CHECK,
498         DISP_STRING("OID_CUSTOM_DISABLE_PRIVACY_CHECK"),
499         FALSE, TRUE, ENUM_OID_DRIVER_CORE, 4,
500         NULL,
501         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetDisablePriavcyCheck},
502     */
503
504     {OID_CUSTOM_MCR_RW,
505         DISP_STRING("OID_CUSTOM_MCR_RW"),
506         TRUE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_CUSTOM_MCR_RW_STRUC_T),
507         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryMcrRead,
508         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetMcrWrite},
509
510     {OID_CUSTOM_EEPROM_RW,
511         DISP_STRING("OID_CUSTOM_EEPROM_RW"),
512         TRUE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_CUSTOM_EEPROM_RW_STRUC_T),
513         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryEepromRead,
514         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetEepromWrite},
515
516     {OID_CUSTOM_SW_CTRL,
517         DISP_STRING("OID_CUSTOM_SW_CTRL"),
518         TRUE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_CUSTOM_SW_CTRL_STRUC_T),
519         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQuerySwCtrlRead,
520         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetSwCtrlWrite},
521
522     {OID_CUSTOM_MEM_DUMP,
523         DISP_STRING("OID_CUSTOM_MEM_DUMP"),
524         TRUE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_CUSTOM_MEM_DUMP_STRUC_T),
525         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryMemDump,
526         NULL},
527
528     {OID_CUSTOM_TEST_MODE,
529         DISP_STRING("OID_CUSTOM_TEST_MODE"),
530         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 0,
531         NULL,
532         (PFN_OID_HANDLER_FUNC_REQ)wlanoidRftestSetTestMode},
533
534     /*
535     {OID_CUSTOM_TEST_RX_STATUS,
536         DISP_STRING("OID_CUSTOM_TEST_RX_STATUS"),
537         FALSE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_CUSTOM_RFTEST_RX_STATUS_STRUC_T),
538         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryRfTestRxStatus,
539         NULL},
540     {OID_CUSTOM_TEST_TX_STATUS,
541         DISP_STRING("OID_CUSTOM_TEST_TX_STATUS"),
542         FALSE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_CUSTOM_RFTEST_TX_STATUS_STRUC_T),
543         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryRfTestTxStatus,
544         NULL},
545     */
546     {OID_CUSTOM_ABORT_TEST_MODE,
547         DISP_STRING("OID_CUSTOM_ABORT_TEST_MODE"),
548         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 0,
549         NULL,
550         (PFN_OID_HANDLER_FUNC_REQ)wlanoidRftestSetAbortTestMode},
551     {OID_CUSTOM_MTK_WIFI_TEST,
552         DISP_STRING("OID_CUSTOM_MTK_WIFI_TEST"),
553         TRUE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_MTK_WIFI_TEST_STRUC_T),
554         (PFN_OID_HANDLER_FUNC_REQ)wlanoidRftestQueryAutoTest,
555         (PFN_OID_HANDLER_FUNC_REQ)wlanoidRftestSetAutoTest},
556
557     /* OID_CUSTOM_EMULATION_VERSION_CONTROL */
558
559     /* BWCS */
560 #if CFG_SUPPORT_BCM && CFG_SUPPORT_BCM_BWCS
561     {OID_CUSTOM_BWCS_CMD,
562         DISP_STRING("OID_CUSTOM_BWCS_CMD"),
563         FALSE, FALSE, ENUM_OID_DRIVER_CORE, sizeof(PTA_IPC_T),
564         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryBT,
565         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetBT},
566 #endif
567
568 /*    {OID_CUSTOM_SINGLE_ANTENNA,
569         DISP_STRING("OID_CUSTOM_SINGLE_ANTENNA"),
570         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 4,
571         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryBtSingleAntenna,
572         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetBtSingleAntenna},
573     {OID_CUSTOM_SET_PTA,
574         DISP_STRING("OID_CUSTOM_SET_PTA"),
575         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 4,
576         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryPta,
577         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetPta},
578     */
579
580     { OID_CUSTOM_MTK_NVRAM_RW,
581         DISP_STRING("OID_CUSTOM_MTK_NVRAM_RW"),
582         TRUE, TRUE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_CUSTOM_NVRAM_RW_STRUCT_T),
583         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryNvramRead,
584         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetNvramWrite },
585
586     { OID_CUSTOM_CFG_SRC_TYPE,
587         DISP_STRING("OID_CUSTOM_CFG_SRC_TYPE"),
588         FALSE, FALSE, ENUM_OID_DRIVER_CORE, sizeof(ENUM_CFG_SRC_TYPE_T),
589         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryCfgSrcType,
590         NULL },
591
592     { OID_CUSTOM_EEPROM_TYPE,
593         DISP_STRING("OID_CUSTOM_EEPROM_TYPE"),
594         FALSE, FALSE, ENUM_OID_DRIVER_CORE, sizeof(ENUM_EEPROM_TYPE_T),
595         (PFN_OID_HANDLER_FUNC_REQ)wlanoidQueryEepromType,
596         NULL },
597
598 #if CFG_SUPPORT_WAPI
599     {OID_802_11_WAPI_MODE,
600         DISP_STRING("OID_802_11_WAPI_MODE"),
601         FALSE, TRUE, ENUM_OID_DRIVER_CORE, 4,
602         NULL,
603         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetWapiMode},
604     {OID_802_11_WAPI_ASSOC_INFO,
605         DISP_STRING("OID_802_11_WAPI_ASSOC_INFO"),
606         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 0,
607         NULL,
608         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetWapiAssocInfo},
609     {OID_802_11_SET_WAPI_KEY,
610         DISP_STRING("OID_802_11_SET_WAPI_KEY"),
611         FALSE, FALSE, ENUM_OID_DRIVER_CORE, sizeof(PARAM_WPI_KEY_T),
612         NULL,
613         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetWapiKey},
614 #endif
615
616 #if CFG_SUPPORT_WPS2
617     {OID_802_11_WSC_ASSOC_INFO,
618         DISP_STRING("OID_802_11_WSC_ASSOC_INFO"),
619         FALSE, FALSE, ENUM_OID_DRIVER_CORE, 0,
620         NULL,
621         (PFN_OID_HANDLER_FUNC_REQ)wlanoidSetWSCAssocInfo},
622 #endif
623 };
624
625 /*******************************************************************************
626 *                              F U N C T I O N S
627 ********************************************************************************
628 */
629
630 /*----------------------------------------------------------------------------*/
631 /*!
632 * \brief Dispatching function for private ioctl region (SIOCIWFIRSTPRIV ~
633 *   SIOCIWLASTPRIV).
634 *
635 * \param[in] prNetDev Net device requested.
636 * \param[in] prIfReq Pointer to ifreq structure.
637 * \param[in] i4Cmd Command ID between SIOCIWFIRSTPRIV and SIOCIWLASTPRIV.
638 *
639 * \retval 0 for success.
640 * \retval -EOPNOTSUPP If cmd is not supported.
641 * \retval -EFAULT For fail.
642 *
643 */
644 /*----------------------------------------------------------------------------*/
645 int
646 priv_support_ioctl (
647     IN struct net_device *prNetDev,
648     IN OUT struct ifreq *prIfReq,
649     IN int i4Cmd
650     )
651 {
652     /* prIfReq is verified in the caller function wlanDoIOCTL() */
653     struct iwreq *prIwReq = (struct iwreq *)prIfReq;
654     struct iw_request_info rIwReqInfo;
655
656     /* prDev is verified in the caller function wlanDoIOCTL() */
657
658     /* Prepare the call */
659     rIwReqInfo.cmd = (__u16)i4Cmd;
660     rIwReqInfo.flags = 0;
661
662     switch (i4Cmd) {
663     case IOCTL_SET_INT:
664         /* NOTE(Kevin): 1/3 INT Type <= IFNAMSIZ, so we don't need copy_from/to_user() */
665         return priv_set_int(prNetDev, &rIwReqInfo, &(prIwReq->u), (char *) &(prIwReq->u));
666
667     case IOCTL_GET_INT:
668         /* NOTE(Kevin): 1/3 INT Type <= IFNAMSIZ, so we don't need copy_from/to_user() */
669         return priv_get_int(prNetDev, &rIwReqInfo, &(prIwReq->u), (char *) &(prIwReq->u));
670
671     case IOCTL_SET_STRUCT:
672     case IOCTL_SET_STRUCT_FOR_EM:
673         return priv_set_struct(prNetDev, &rIwReqInfo, &prIwReq->u, (char *) &(prIwReq->u));
674
675     case IOCTL_GET_STRUCT:
676         return priv_get_struct(prNetDev, &rIwReqInfo, &prIwReq->u, (char *) &(prIwReq->u));
677
678     default:
679         return -EOPNOTSUPP;
680
681     } /* end of switch */
682
683 }/* priv_support_ioctl */
684
685
686 /*----------------------------------------------------------------------------*/
687 /*!
688 * \brief Private ioctl set int handler.
689 *
690 * \param[in] prNetDev Net device requested.
691 * \param[in] prIwReqInfo Pointer to iwreq structure.
692 * \param[in] prIwReqData The ioctl data structure, use the field of sub-command.
693 * \param[in] pcExtra The buffer with input value
694 *
695 * \retval 0 For success.
696 * \retval -EOPNOTSUPP If cmd is not supported.
697 * \retval -EINVAL If a value is out of range.
698 *
699 */
700 /*----------------------------------------------------------------------------*/
701 int
702 priv_set_int (
703     IN struct net_device *prNetDev,
704     IN struct iw_request_info *prIwReqInfo,
705     IN union iwreq_data *prIwReqData,
706     IN char *pcExtra
707     )
708 {
709     UINT_32                     u4SubCmd;
710     PUINT_32                    pu4IntBuf;
711     P_NDIS_TRANSPORT_STRUCT     prNdisReq;
712     P_GLUE_INFO_T               prGlueInfo;
713     UINT_32                     u4BufLen = 0;
714     int                         status = 0;
715     P_PTA_IPC_T         prPtaIpc;
716
717     ASSERT(prNetDev);
718     ASSERT(prIwReqInfo);
719     ASSERT(prIwReqData);
720     ASSERT(pcExtra);
721
722     if (FALSE == GLUE_CHK_PR3(prNetDev, prIwReqData, pcExtra)) {
723         return -EINVAL;
724     }
725     prGlueInfo = *((P_GLUE_INFO_T *) netdev_priv(prNetDev));
726
727     u4SubCmd = (UINT_32) prIwReqData->mode;
728     pu4IntBuf = (PUINT_32) pcExtra;
729
730     switch (u4SubCmd) {
731     case PRIV_CMD_TEST_MODE:
732         //printk("TestMode=%ld\n", pu4IntBuf[1]);
733         prNdisReq = (P_NDIS_TRANSPORT_STRUCT) &aucOidBuf[0];
734
735         if (pu4IntBuf[1] == PRIV_CMD_TEST_MAGIC_KEY) {
736             prNdisReq->ndisOidCmd = OID_CUSTOM_TEST_MODE;
737         }
738         else if (pu4IntBuf[1] == 0) {
739             prNdisReq->ndisOidCmd = OID_CUSTOM_ABORT_TEST_MODE;
740         }
741         else {
742             status = 0;
743             break;
744         }
745         prNdisReq->inNdisOidlength = 0;
746         prNdisReq->outNdisOidLength = 0;
747
748         /* Execute this OID */
749         status = priv_set_ndis(prNetDev, prNdisReq, &u4BufLen);
750         break;
751
752     case PRIV_CMD_TEST_CMD:
753         //printk("CMD=0x%08lx, data=0x%08lx\n", pu4IntBuf[1], pu4IntBuf[2]);
754         prNdisReq = (P_NDIS_TRANSPORT_STRUCT) &aucOidBuf[0];
755
756         kalMemCopy(&prNdisReq->ndisOidContent[0], &pu4IntBuf[1], 8);
757
758         prNdisReq->ndisOidCmd = OID_CUSTOM_MTK_WIFI_TEST;
759         prNdisReq->inNdisOidlength = 8;
760         prNdisReq->outNdisOidLength = 8;
761
762         /* Execute this OID */
763         status = priv_set_ndis(prNetDev, prNdisReq, &u4BufLen);
764         break;
765
766 #if CFG_SUPPORT_PRIV_MCR_RW
767     case PRIV_CMD_ACCESS_MCR:
768         //printk("addr=0x%08lx, data=0x%08lx\n", pu4IntBuf[1], pu4IntBuf[2]);
769         prNdisReq = (P_NDIS_TRANSPORT_STRUCT) &aucOidBuf[0];
770
771         if (!prGlueInfo->fgMcrAccessAllowed) {
772             if (pu4IntBuf[1] == PRIV_CMD_TEST_MAGIC_KEY &&
773                 pu4IntBuf[2] == PRIV_CMD_TEST_MAGIC_KEY) {
774                 prGlueInfo->fgMcrAccessAllowed = TRUE;
775             }
776             status = 0;
777             break;
778         }
779
780         kalMemCopy(&prNdisReq->ndisOidContent[0], &pu4IntBuf[1], 8);
781
782         prNdisReq->ndisOidCmd = OID_CUSTOM_MCR_RW;
783         prNdisReq->inNdisOidlength = 8;
784         prNdisReq->outNdisOidLength = 8;
785
786         /* Execute this OID */
787         status = priv_set_ndis(prNetDev, prNdisReq, &u4BufLen);
788         break;
789 #endif
790
791     case PRIV_CMD_SW_CTRL:
792         //printk("addr=0x%08lx, data=0x%08lx\n", pu4IntBuf[1], pu4IntBuf[2]);
793         prNdisReq = (P_NDIS_TRANSPORT_STRUCT) &aucOidBuf[0];
794
795         kalMemCopy(&prNdisReq->ndisOidContent[0], &pu4IntBuf[1], 8);
796
797         prNdisReq->ndisOidCmd = OID_CUSTOM_SW_CTRL;
798         prNdisReq->inNdisOidlength = 8;
799         prNdisReq->outNdisOidLength = 8;
800
801         /* Execute this OID */
802         status = priv_set_ndis(prNetDev, prNdisReq, &u4BufLen);
803         break;
804
805
806     #if 0
807     case PRIV_CMD_BEACON_PERIOD:
808         rStatus = wlanSetInformation(prGlueInfo->prAdapter,
809                            wlanoidSetBeaconInterval,
810                            (PVOID)&pu4IntBuf[1], /* pu4IntBuf[0] is used as input SubCmd */
811                            sizeof(UINT_32),
812                            &u4BufLen);
813         break;
814     #endif
815
816 #if CFG_TCP_IP_CHKSUM_OFFLOAD
817     case PRIV_CMD_CSUM_OFFLOAD:
818         {
819             UINT_32 u4CSUMFlags;
820
821
822             if (pu4IntBuf[1] == 1) {
823                 u4CSUMFlags = CSUM_OFFLOAD_EN_ALL;
824             }
825             else if (pu4IntBuf[1] == 0) {
826                 u4CSUMFlags = 0;
827             }
828             else {
829                 return -EINVAL;
830             }
831
832             if (kalIoctl(prGlueInfo,
833                         wlanoidSetCSUMOffload,
834                         (PVOID)&u4CSUMFlags,
835                         sizeof(UINT_32),
836                         FALSE,
837                         FALSE,
838                         TRUE,
839                         FALSE,
840                         &u4BufLen
841             ) == WLAN_STATUS_SUCCESS) {
842                 if (pu4IntBuf[1] == 1) {
843                     prNetDev->features |= NETIF_F_HW_CSUM;
844                 } else if (pu4IntBuf[1] == 0) {
845                     prNetDev->features &= ~NETIF_F_HW_CSUM;
846                 }
847             }
848         }
849         break;
850 #endif /* CFG_TCP_IP_CHKSUM_OFFLOAD */
851
852     case PRIV_CMD_POWER_MODE:
853             kalIoctl(prGlueInfo,
854                         wlanoidSet802dot11PowerSaveProfile,
855                         (PVOID)&pu4IntBuf[1], /* pu4IntBuf[0] is used as input SubCmd */
856                         sizeof(UINT_32),
857                         FALSE,
858                         FALSE,
859                         TRUE,
860                         FALSE,
861                         &u4BufLen);
862         break;
863
864     case PRIV_CMD_WMM_PS:
865         {
866             PARAM_CUSTOM_WMM_PS_TEST_STRUC_T rWmmPsTest;
867
868             rWmmPsTest.bmfgApsdEnAc = (UINT_8)pu4IntBuf[1];
869             rWmmPsTest.ucIsEnterPsAtOnce = (UINT_8)pu4IntBuf[2];
870             rWmmPsTest.ucIsDisableUcTrigger = (UINT_8)pu4IntBuf[3];
871             rWmmPsTest.reserved = 0;
872
873             kalIoctl(prGlueInfo,
874                         wlanoidSetWiFiWmmPsTest,
875                         (PVOID)&rWmmPsTest,
876                         sizeof(PARAM_CUSTOM_WMM_PS_TEST_STRUC_T),
877                         FALSE,
878                         FALSE,
879                         TRUE,
880                         FALSE,
881                         &u4BufLen);
882         }
883         break;
884
885     #if 0
886     case PRIV_CMD_ADHOC_MODE:
887         rStatus = wlanSetInformation(prGlueInfo->prAdapter,
888                            wlanoidSetAdHocMode,
889                            (PVOID)&pu4IntBuf[1], /* pu4IntBuf[0] is used as input SubCmd */
890                            sizeof(UINT_32),
891                            &u4BufLen);
892         break;
893     #endif
894
895     case PRIV_CUSTOM_BWCS_CMD:
896
897         DBGLOG(REQ, INFO, ("pu4IntBuf[1] = %x, size of PTA_IPC_T = %d.\n", pu4IntBuf[1], sizeof(PARAM_PTA_IPC_T)));
898
899         prPtaIpc = (P_PTA_IPC_T) aucOidBuf;
900         prPtaIpc->u.aucBTPParams[0] = (UINT_8) (pu4IntBuf[1] >> 24);
901         prPtaIpc->u.aucBTPParams[1] = (UINT_8) (pu4IntBuf[1] >> 16);
902         prPtaIpc->u.aucBTPParams[2] = (UINT_8) (pu4IntBuf[1] >> 8);
903         prPtaIpc->u.aucBTPParams[3] = (UINT_8) (pu4IntBuf[1]);
904
905         DBGLOG(REQ, INFO, ("BCM BWCS CMD : PRIV_CUSTOM_BWCS_CMD : aucBTPParams[0] = %02x, aucBTPParams[1] = %02x, aucBTPParams[2] = %02x, aucBTPParams[3] = %02x.\n",
906             prPtaIpc->u.aucBTPParams[0],
907             prPtaIpc->u.aucBTPParams[1],
908             prPtaIpc->u.aucBTPParams[2],
909             prPtaIpc->u.aucBTPParams[3]));
910
911 #if 0
912         status = wlanSetInformation(prGlueInfo->prAdapter,
913                             wlanoidSetBT,
914                             (PVOID)&aucOidBuf[0],
915                             u4CmdLen,
916                             &u4BufLen);
917 #endif
918
919         status = wlanoidSetBT(prGlueInfo->prAdapter,
920                             (PVOID)&aucOidBuf[0],
921                             sizeof(PARAM_PTA_IPC_T),
922                             &u4BufLen);
923
924         if (WLAN_STATUS_SUCCESS != status) {
925             status = -EFAULT;
926         }
927
928         break;
929
930     case PRIV_CMD_BAND_CONFIG:
931         {
932             DBGLOG(INIT, INFO, ("CMD set_band=%u\n", pu4IntBuf[1]));
933         }
934         break;
935
936 #if CFG_ENABLE_WIFI_DIRECT
937     case PRIV_CMD_P2P_MODE:
938         {
939             PARAM_CUSTOM_P2P_SET_STRUC_T rSetP2P;
940             WLAN_STATUS rWlanStatus = WLAN_STATUS_SUCCESS;
941
942             rSetP2P.u4Enable = pu4IntBuf[1];
943             rSetP2P.u4Mode = pu4IntBuf[2];
944
945             if(!rSetP2P.u4Enable) {
946                 p2pNetUnregister(prGlueInfo, TRUE);
947             }
948
949             rWlanStatus = kalIoctl(prGlueInfo,
950                                 wlanoidSetP2pMode,
951                                 (PVOID)&rSetP2P, /* pu4IntBuf[0] is used as input SubCmd */
952                                 sizeof(PARAM_CUSTOM_P2P_SET_STRUC_T),
953                                 FALSE,
954                                 FALSE,
955                                 TRUE,
956                                 FALSE,
957                                 &u4BufLen);
958
959             if(rSetP2P.u4Enable) {
960                 p2pNetRegister(prGlueInfo, TRUE);
961             }
962
963
964         }
965         break;
966 #endif
967
968     default:
969         return -EOPNOTSUPP;
970     }
971
972     return status;
973 }
974
975
976 /*----------------------------------------------------------------------------*/
977 /*!
978 * \brief Private ioctl get int handler.
979 *
980 * \param[in] pDev Net device requested.
981 * \param[out] pIwReq Pointer to iwreq structure.
982 * \param[in] prIwReqData The ioctl req structure, use the field of sub-command.
983 * \param[out] pcExtra The buffer with put the return value
984 *
985 * \retval 0 For success.
986 * \retval -EOPNOTSUPP If cmd is not supported.
987 * \retval -EFAULT For fail.
988 *
989 */
990 /*----------------------------------------------------------------------------*/
991 int
992 priv_get_int (
993     IN struct net_device *prNetDev,
994     IN struct iw_request_info *prIwReqInfo,
995     IN union iwreq_data *prIwReqData,
996     IN OUT char *pcExtra
997     )
998 {
999     UINT_32                     u4SubCmd;
1000     PUINT_32                    pu4IntBuf;
1001     P_GLUE_INFO_T               prGlueInfo;
1002     UINT_32                     u4BufLen = 0;
1003     int                         status = 0;
1004     P_NDIS_TRANSPORT_STRUCT     prNdisReq;
1005     INT_32                      ch[50];
1006
1007     ASSERT(prNetDev);
1008     ASSERT(prIwReqInfo);
1009     ASSERT(prIwReqData);
1010     ASSERT(pcExtra);
1011     if (FALSE == GLUE_CHK_PR3(prNetDev, prIwReqData, pcExtra)) {
1012         return -EINVAL;
1013     }
1014     prGlueInfo = *((P_GLUE_INFO_T *) netdev_priv(prNetDev));
1015
1016     u4SubCmd = (UINT_32) prIwReqData->mode;
1017     pu4IntBuf = (PUINT_32) pcExtra;
1018
1019     switch (u4SubCmd) {
1020     case PRIV_CMD_TEST_CMD:
1021         //printk("CMD=0x%08lx, data=0x%08lx\n", pu4IntBuf[1], pu4IntBuf[2]);
1022         prNdisReq = (P_NDIS_TRANSPORT_STRUCT) &aucOidBuf[0];
1023
1024         kalMemCopy(&prNdisReq->ndisOidContent[0], &pu4IntBuf[1], 8);
1025
1026         prNdisReq->ndisOidCmd = OID_CUSTOM_MTK_WIFI_TEST;
1027         prNdisReq->inNdisOidlength = 8;
1028         prNdisReq->outNdisOidLength = 8;
1029
1030         status = priv_get_ndis(prNetDev, prNdisReq, &u4BufLen);
1031         if (status == 0) {
1032             //printk("Result=%ld\n", *(PUINT_32)&prNdisReq->ndisOidContent[4]);
1033             prIwReqData->mode = *(PUINT_32)&prNdisReq->ndisOidContent[4];
1034             /*
1035             if (copy_to_user(prIwReqData->data.pointer,
1036                              &prNdisReq->ndisOidContent[4], 4)) {
1037                 printk(KERN_NOTICE "priv_get_int() copy_to_user oidBuf fail(3)\n");
1038                 return -EFAULT;
1039             }
1040             */
1041         }
1042         return status;
1043
1044 #if CFG_SUPPORT_PRIV_MCR_RW
1045     case PRIV_CMD_ACCESS_MCR:
1046         //printk("addr=0x%08lx\n", pu4IntBuf[1]);
1047         prNdisReq = (P_NDIS_TRANSPORT_STRUCT) &aucOidBuf[0];
1048
1049         if (!prGlueInfo->fgMcrAccessAllowed) {
1050             status = 0;
1051             return status;
1052         }
1053
1054         kalMemCopy(&prNdisReq->ndisOidContent[0], &pu4IntBuf[1], 8);
1055
1056         prNdisReq->ndisOidCmd = OID_CUSTOM_MCR_RW;
1057         prNdisReq->inNdisOidlength = 8;
1058         prNdisReq->outNdisOidLength = 8;
1059
1060         status = priv_get_ndis(prNetDev, prNdisReq, &u4BufLen);
1061         if (status == 0) {
1062             //printk("Result=%ld\n", *(PUINT_32)&prNdisReq->ndisOidContent[4]);
1063             prIwReqData->mode = *(PUINT_32)&prNdisReq->ndisOidContent[4];
1064         }
1065         return status;
1066 #endif
1067
1068     case PRIV_CMD_DUMP_MEM:
1069         prNdisReq = (P_NDIS_TRANSPORT_STRUCT) &aucOidBuf[0];
1070
1071 #if 1
1072         if (!prGlueInfo->fgMcrAccessAllowed) {
1073             status = 0;
1074             return status;
1075         }
1076 #endif
1077         kalMemCopy(&prNdisReq->ndisOidContent[0], &pu4IntBuf[1], 8);
1078
1079         prNdisReq->ndisOidCmd = OID_CUSTOM_MEM_DUMP;
1080         prNdisReq->inNdisOidlength = 8;
1081         prNdisReq->outNdisOidLength = 8;
1082
1083         status = priv_get_ndis(prNetDev, prNdisReq, &u4BufLen);
1084         if (status == 0) {
1085             prIwReqData->mode = *(PUINT_32)&prNdisReq->ndisOidContent[0];
1086         }
1087         return status;
1088
1089     case PRIV_CMD_SW_CTRL:
1090         //printk(" addr=0x%08lx\n", pu4IntBuf[1]);
1091
1092         prNdisReq = (P_NDIS_TRANSPORT_STRUCT) &aucOidBuf[0];
1093
1094         kalMemCopy(&prNdisReq->ndisOidContent[0], &pu4IntBuf[1], 8);
1095
1096         prNdisReq->ndisOidCmd = OID_CUSTOM_SW_CTRL;
1097         prNdisReq->inNdisOidlength = 8;
1098         prNdisReq->outNdisOidLength = 8;
1099
1100         status = priv_get_ndis(prNetDev, prNdisReq, &u4BufLen);
1101         if (status == 0) {
1102             //printk("Result=%ld\n", *(PUINT_32)&prNdisReq->ndisOidContent[4]);
1103             prIwReqData->mode = *(PUINT_32)&prNdisReq->ndisOidContent[4];
1104         }
1105         return status;
1106
1107     #if 0
1108     case PRIV_CMD_BEACON_PERIOD:
1109         status = wlanQueryInformation(prGlueInfo->prAdapter,
1110                              wlanoidQueryBeaconInterval,
1111                              (PVOID)pu4IntBuf,
1112                              sizeof(UINT_32),
1113                              &u4BufLen);
1114         return status;
1115
1116     case PRIV_CMD_POWER_MODE:
1117         status = wlanQueryInformation(prGlueInfo->prAdapter,
1118                              wlanoidQuery802dot11PowerSaveProfile,
1119                              (PVOID)pu4IntBuf,
1120                              sizeof(UINT_32),
1121                              &u4BufLen);
1122         return status;
1123
1124     case PRIV_CMD_ADHOC_MODE:
1125         status = wlanQueryInformation(prGlueInfo->prAdapter,
1126                              wlanoidQueryAdHocMode,
1127                              (PVOID)pu4IntBuf,
1128                              sizeof(UINT_32),
1129                              &u4BufLen);
1130         return status;
1131     #endif
1132
1133     case PRIV_CMD_BAND_CONFIG:
1134         DBGLOG(INIT, INFO, ("CMD get_band=\n"));
1135         prIwReqData->mode = 0;
1136         return status;
1137
1138     default:
1139         break;
1140     }
1141
1142     u4SubCmd = (UINT_32) prIwReqData->data.flags;
1143
1144     switch (u4SubCmd) {
1145     case PRIV_CMD_GET_CH_LIST:
1146         {
1147             UINT_16 i, j = 0;
1148             UINT_8 NumOfChannel = 50;
1149             UINT_8 ucMaxChannelNum = 50;
1150             RF_CHANNEL_INFO_T aucChannelList[50];
1151
1152             kalGetChannelList(prGlueInfo, BAND_NULL, ucMaxChannelNum, &NumOfChannel, aucChannelList);
1153             if (NumOfChannel > 50)
1154                 NumOfChannel = 50;
1155
1156             if (kalIsAPmode(prGlueInfo)) {
1157                 for (i = 0; i < NumOfChannel; i++) {
1158                     if ((aucChannelList[i].ucChannelNum <= 13) ||
1159                         (aucChannelList[i].ucChannelNum == 36 || aucChannelList[i].ucChannelNum == 40 ||
1160                         aucChannelList[i].ucChannelNum == 44 || aucChannelList[i].ucChannelNum == 48)) {
1161                         ch[j] = (INT_32)aucChannelList[i].ucChannelNum;
1162                         j++;
1163                     }
1164                 }
1165             }
1166             else {
1167                 for (j = 0; j < NumOfChannel; j++) {
1168                     ch[j] = (INT_32)aucChannelList[j].ucChannelNum;
1169                 }
1170             }
1171
1172             prIwReqData->data.length = j;
1173             if (copy_to_user(prIwReqData->data.pointer, ch, NumOfChannel*sizeof(INT_32))) {
1174                  return -EFAULT;
1175             }
1176             else
1177                  return status;
1178         }
1179 #if CFG_SUPPORT_BUILD_DATE_CODE
1180     case PRIV_CMD_GET_BUILD_DATE_CODE:
1181         {
1182             UINT_8  aucBuffer[16];
1183
1184             if(kalIoctl(prGlueInfo,
1185                         wlanoidQueryBuildDateCode,
1186                         (PVOID)aucBuffer,
1187                         sizeof(UINT_8) * 16,
1188                         TRUE,
1189                         TRUE,
1190                         TRUE,
1191                         FALSE,
1192                         &u4BufLen) == WLAN_STATUS_SUCCESS) {
1193                 prIwReqData->data.length = sizeof(UINT_8) * 16;
1194
1195                 if (copy_to_user(prIwReqData->data.pointer, aucBuffer, prIwReqData->data.length)) {
1196                      return -EFAULT;
1197                 }
1198                 else
1199                      return status;
1200             }
1201             else {
1202                 return -EFAULT;
1203             }
1204         }
1205 #endif
1206     default:
1207         return -EOPNOTSUPP;
1208     }
1209
1210     return status;
1211 } /* priv_get_int */
1212
1213
1214 /*----------------------------------------------------------------------------*/
1215 /*!
1216 * \brief Private ioctl set int array handler.
1217 *
1218 * \param[in] prNetDev Net device requested.
1219 * \param[in] prIwReqInfo Pointer to iwreq structure.
1220 * \param[in] prIwReqData The ioctl data structure, use the field of sub-command.
1221 * \param[in] pcExtra The buffer with input value
1222 *
1223 * \retval 0 For success.
1224 * \retval -EOPNOTSUPP If cmd is not supported.
1225 * \retval -EINVAL If a value is out of range.
1226 *
1227 */
1228 /*----------------------------------------------------------------------------*/
1229 int
1230 priv_set_ints (
1231     IN struct net_device *prNetDev,
1232     IN struct iw_request_info *prIwReqInfo,
1233     IN union iwreq_data *prIwReqData,
1234     IN char *pcExtra
1235     )
1236 {
1237     UINT_32                     u4SubCmd, u4BufLen;
1238     P_GLUE_INFO_T               prGlueInfo;
1239     int                         status = 0;
1240     WLAN_STATUS                 rStatus = WLAN_STATUS_SUCCESS;
1241     P_SET_TXPWR_CTRL_T          prTxpwr;
1242
1243     ASSERT(prNetDev);
1244     ASSERT(prIwReqInfo);
1245     ASSERT(prIwReqData);
1246     ASSERT(pcExtra);
1247
1248     if (FALSE == GLUE_CHK_PR3(prNetDev, prIwReqData, pcExtra)) {
1249         return -EINVAL;
1250     }
1251     prGlueInfo = *((P_GLUE_INFO_T *) netdev_priv(prNetDev));
1252
1253     u4SubCmd = (UINT_32) prIwReqData->data.flags;
1254
1255     switch (u4SubCmd) {
1256     case PRIV_CMD_SET_TX_POWER:
1257         {
1258         INT_32 *setting = prIwReqData->data.pointer;
1259         UINT_16 i;
1260
1261 #if 0
1262         printk("Tx power num = %d\n", prIwReqData->data.length);
1263
1264         printk("Tx power setting = %d %d %d %d\n",
1265                             setting[0], setting[1], setting[2], setting[3]);
1266 #endif
1267         prTxpwr = &prGlueInfo->rTxPwr;
1268         if (setting[0] == 0 && prIwReqData->data.length == 4 /* argc num */) {
1269             /* 0 (All networks), 1 (legacy STA), 2 (Hotspot AP), 3 (P2P), 4 (BT over Wi-Fi) */
1270             if (setting[1] == 1 || setting[1] == 0) {
1271                 if (setting[2] == 0 || setting[2] == 1)
1272                     prTxpwr->c2GLegacyStaPwrOffset = setting[3];
1273                 if (setting[2] == 0 || setting[2] == 2)
1274                     prTxpwr->c5GLegacyStaPwrOffset = setting[3];
1275             }
1276             if (setting[1] == 2 || setting[1] == 0) {
1277                 if (setting[2] == 0 || setting[2] == 1)
1278                     prTxpwr->c2GHotspotPwrOffset = setting[3];
1279                 if (setting[2] == 0 || setting[2] == 2)
1280                     prTxpwr->c5GHotspotPwrOffset = setting[3];
1281             }
1282             if (setting[1] == 3 || setting[1] == 0) {
1283                 if (setting[2] == 0 || setting[2] == 1)
1284                     prTxpwr->c2GP2pPwrOffset = setting[3];
1285                 if (setting[2] == 0 || setting[2] == 2)
1286                     prTxpwr->c5GP2pPwrOffset = setting[3];
1287             }
1288             if (setting[1] == 4 || setting[1] == 0) {
1289                 if (setting[2] == 0 || setting[2] == 1)
1290                     prTxpwr->c2GBowPwrOffset = setting[3];
1291                 if (setting[2] == 0 || setting[2] == 2)
1292                     prTxpwr->c5GBowPwrOffset = setting[3];
1293             }
1294         }
1295         else if (setting[0] == 1 && prIwReqData->data.length == 2) {
1296             prTxpwr->ucConcurrencePolicy = setting[1];
1297         }
1298         else if (setting[0] == 2 && prIwReqData->data.length == 3) {
1299             if (setting[1] == 0) {
1300                 for (i=0; i<14; i++)
1301                     prTxpwr->acTxPwrLimit2G[i] = setting[2];
1302             }
1303             else if (setting[1] <= 14)
1304                 prTxpwr->acTxPwrLimit2G[setting[1] - 1] = setting[2];
1305         }
1306         else if (setting[0] == 3 && prIwReqData->data.length == 3) {
1307             if (setting[1] == 0) {
1308                 for (i=0; i<4; i++)
1309                     prTxpwr->acTxPwrLimit5G[i] = setting[2];
1310             }
1311             else if (setting[1] <= 4)
1312                 prTxpwr->acTxPwrLimit5G[setting[1] - 1] = setting[2];
1313         }
1314         else if (setting[0] == 4 && prIwReqData->data.length == 2) {
1315             if (setting[1] == 0) {
1316                 wlanDefTxPowerCfg(prGlueInfo->prAdapter);
1317             }
1318             rStatus = kalIoctl(prGlueInfo,
1319                 wlanoidSetTxPower,
1320                 prTxpwr,
1321                 sizeof(SET_TXPWR_CTRL_T),
1322                 TRUE,
1323                 FALSE,
1324                 FALSE,
1325                 FALSE,
1326                 &u4BufLen);
1327         }
1328         else
1329             return -EFAULT;
1330         }
1331         return status;
1332     default:
1333         break;
1334     }
1335
1336     return status;
1337 }
1338
1339
1340 /*----------------------------------------------------------------------------*/
1341 /*!
1342 * \brief Private ioctl get int array handler.
1343 *
1344 * \param[in] pDev Net device requested.
1345 * \param[out] pIwReq Pointer to iwreq structure.
1346 * \param[in] prIwReqData The ioctl req structure, use the field of sub-command.
1347 * \param[out] pcExtra The buffer with put the return value
1348 *
1349 * \retval 0 For success.
1350 * \retval -EOPNOTSUPP If cmd is not supported.
1351 * \retval -EFAULT For fail.
1352 *
1353 */
1354 /*----------------------------------------------------------------------------*/
1355 int
1356 priv_get_ints (
1357     IN struct net_device *prNetDev,
1358     IN struct iw_request_info *prIwReqInfo,
1359     IN union iwreq_data *prIwReqData,
1360     IN OUT char *pcExtra
1361     )
1362 {
1363     UINT_32                     u4SubCmd;
1364     P_GLUE_INFO_T               prGlueInfo;
1365     int                         status = 0;
1366     INT_32                      ch[50];
1367
1368     ASSERT(prNetDev);
1369     ASSERT(prIwReqInfo);
1370     ASSERT(prIwReqData);
1371     ASSERT(pcExtra);
1372     if (FALSE == GLUE_CHK_PR3(prNetDev, prIwReqData, pcExtra)) {
1373         return -EINVAL;
1374     }
1375     prGlueInfo = *((P_GLUE_INFO_T *) netdev_priv(prNetDev));
1376
1377     u4SubCmd = (UINT_32) prIwReqData->data.flags;
1378
1379     switch (u4SubCmd) {
1380     case PRIV_CMD_GET_CH_LIST:
1381         {
1382             UINT_16 i;
1383             UINT_8 NumOfChannel = 50;
1384             UINT_8 ucMaxChannelNum = 50;
1385             RF_CHANNEL_INFO_T aucChannelList[50];
1386
1387             kalGetChannelList(prGlueInfo, BAND_NULL, ucMaxChannelNum, &NumOfChannel, aucChannelList);
1388             if (NumOfChannel > 50)
1389                 NumOfChannel = 50;
1390
1391             for (i = 0; i < NumOfChannel; i++) {
1392                 ch[i] = (INT_32)aucChannelList[i].ucChannelNum;
1393             }
1394
1395             prIwReqData->data.length = NumOfChannel;
1396             if (copy_to_user(prIwReqData->data.pointer, ch, NumOfChannel*sizeof(INT_32))) {
1397                  return -EFAULT;
1398             }
1399             else
1400                  return status;
1401         }
1402     default:
1403         break;
1404     }
1405
1406     return status;
1407 } /* priv_get_int */
1408
1409 /*----------------------------------------------------------------------------*/
1410 /*!
1411 * \brief Private ioctl set structure handler.
1412 *
1413 * \param[in] pDev Net device requested.
1414 * \param[in] prIwReqData Pointer to iwreq_data structure.
1415 *
1416 * \retval 0 For success.
1417 * \retval -EOPNOTSUPP If cmd is not supported.
1418 * \retval -EINVAL If a value is out of range.
1419 *
1420 */
1421 /*----------------------------------------------------------------------------*/
1422 int
1423 priv_set_struct (
1424     IN struct net_device *prNetDev,
1425     IN struct iw_request_info *prIwReqInfo,
1426     IN union iwreq_data *prIwReqData,
1427     IN char *pcExtra
1428     )
1429 {
1430     UINT_32 u4SubCmd = 0;
1431     int                 status = 0;
1432     //WLAN_STATUS rStatus = WLAN_STATUS_SUCCESS;
1433     UINT_32         u4CmdLen = 0;
1434     P_NDIS_TRANSPORT_STRUCT     prNdisReq;
1435     PUINT_32 pu4IntBuf = NULL;
1436
1437     P_GLUE_INFO_T   prGlueInfo = NULL;
1438     UINT_32         u4BufLen = 0;
1439
1440     ASSERT(prNetDev);
1441     //ASSERT(prIwReqInfo);
1442     ASSERT(prIwReqData);
1443     //ASSERT(pcExtra);
1444
1445         kalMemZero(&aucOidBuf[0], sizeof(aucOidBuf));
1446
1447     if (FALSE == GLUE_CHK_PR2(prNetDev, prIwReqData)) {
1448         return -EINVAL;
1449     }
1450     prGlueInfo = *((P_GLUE_INFO_T *) netdev_priv(prNetDev));
1451
1452     u4SubCmd = (UINT_32) prIwReqData->data.flags;
1453
1454 #if 0
1455     printk(KERN_INFO DRV_NAME"priv_set_struct(): prIwReqInfo->cmd(0x%X), u4SubCmd(%ld)\n",
1456         prIwReqInfo->cmd,
1457         u4SubCmd
1458         );
1459 #endif
1460
1461     switch (u4SubCmd) {
1462 #if 0 //PTA_ENABLED
1463     case PRIV_CMD_BT_COEXIST:
1464         u4CmdLen = prIwReqData->data.length * sizeof(UINT_32);
1465         ASSERT(sizeof(PARAM_CUSTOM_BT_COEXIST_T) >= u4CmdLen);
1466         if (sizeof(PARAM_CUSTOM_BT_COEXIST_T) < u4CmdLen) {
1467             return -EFAULT;
1468         }
1469
1470         if (copy_from_user(&aucOidBuf[0], prIwReqData->data.pointer, u4CmdLen)) {
1471             status = -EFAULT; //return -EFAULT;
1472             break;
1473         }
1474
1475         rStatus = wlanSetInformation(prGlueInfo->prAdapter,
1476                             wlanoidSetBtCoexistCtrl,
1477                             (PVOID)&aucOidBuf[0],
1478                             u4CmdLen,
1479                             &u4BufLen);
1480         if (WLAN_STATUS_SUCCESS != rStatus) {
1481             status = -EFAULT;
1482         }
1483         break;
1484 #endif
1485
1486     case PRIV_CUSTOM_BWCS_CMD:
1487         u4CmdLen = prIwReqData->data.length * sizeof(UINT_32);
1488         ASSERT(sizeof(PARAM_PTA_IPC_T) >= u4CmdLen);
1489         if (sizeof(PARAM_PTA_IPC_T) < u4CmdLen) {
1490             return -EFAULT;
1491         }
1492 #if CFG_SUPPORT_BCM && CFG_SUPPORT_BCM_BWCS && CFG_SUPPORT_BCM_BWCS_DEBUG
1493         DBGLOG(REQ, INFO, ("ucCmdLen = %d, size of PTA_IPC_T = %d, prIwReqData->data = 0x%x.\n", u4CmdLen, sizeof(PARAM_PTA_IPC_T), prIwReqData->data));
1494
1495         DBGLOG(REQ, INFO, ("priv_set_struct(): prIwReqInfo->cmd(0x%X), u4SubCmd(%ld)\n",
1496             prIwReqInfo->cmd,
1497             u4SubCmd
1498             ));
1499
1500         DBGLOG(REQ, INFO, ("*pcExtra = 0x%x\n", *pcExtra));
1501  #endif
1502
1503         if (copy_from_user(&aucOidBuf[0], prIwReqData->data.pointer, u4CmdLen)) {
1504             status = -EFAULT; //return -EFAULT;
1505             break;
1506         }
1507 #if CFG_SUPPORT_BCM && CFG_SUPPORT_BCM_BWCS && CFG_SUPPORT_BCM_BWCS_DEBUG
1508         DBGLOG(REQ, INFO, ("priv_set_struct(): BWCS CMD = %02x%02x%02x%02x\n",
1509             aucOidBuf[2], aucOidBuf[3], aucOidBuf[4], aucOidBuf[5]));
1510 #endif
1511
1512 #if 0
1513         status = wlanSetInformation(prGlueInfo->prAdapter,
1514                             wlanoidSetBT,
1515                             (PVOID)&aucOidBuf[0],
1516                             u4CmdLen,
1517                             &u4BufLen);
1518 #endif
1519
1520 #if 1
1521         status = wlanoidSetBT(prGlueInfo->prAdapter,
1522                             (PVOID)&aucOidBuf[0],
1523                             u4CmdLen,
1524                             &u4BufLen);
1525 #endif
1526
1527         if (WLAN_STATUS_SUCCESS != status) {
1528             status = -EFAULT;
1529         }
1530
1531         break;
1532
1533 #if CFG_SUPPORT_WPS2
1534     case PRIV_CMD_WSC_PROBE_REQ:
1535                 {
1536                         /* retrieve IE for Probe Request */
1537             if (prIwReqData->data.length > 0) {
1538                                 if (copy_from_user(prGlueInfo->aucWSCIE, prIwReqData->data.pointer,
1539                                         prIwReqData->data.length)) {
1540                     status = -EFAULT;
1541                                     break;
1542                 }
1543                                 prGlueInfo->u2WSCIELen = prIwReqData->data.length;
1544             }
1545                         else {
1546                             prGlueInfo->u2WSCIELen = 0;
1547                         }
1548         }
1549                 break;
1550 #endif
1551     case PRIV_CMD_OID:
1552         if (copy_from_user(&aucOidBuf[0],
1553                             prIwReqData->data.pointer,
1554                             prIwReqData->data.length)) {
1555             status = -EFAULT;
1556             break;
1557         }
1558         if (!kalMemCmp(&aucOidBuf[0], pcExtra, prIwReqData->data.length)) {
1559             DBGLOG(REQ, INFO, ("pcExtra buffer is valid\n"));
1560         }
1561         else
1562             DBGLOG(REQ, INFO, ("pcExtra 0x%p\n", pcExtra));
1563
1564         /* Execute this OID */
1565         status = priv_set_ndis(prNetDev, (P_NDIS_TRANSPORT_STRUCT)&aucOidBuf[0], &u4BufLen);
1566         /* Copy result to user space */
1567         ((P_NDIS_TRANSPORT_STRUCT)&aucOidBuf[0])->outNdisOidLength = u4BufLen;
1568
1569         if (copy_to_user(prIwReqData->data.pointer,
1570                         &aucOidBuf[0],
1571                         OFFSET_OF(NDIS_TRANSPORT_STRUCT, ndisOidContent))) {
1572             DBGLOG(REQ, INFO, ("copy_to_user oidBuf fail\n"));
1573             status = -EFAULT;
1574         }
1575
1576         break;
1577
1578     case PRIV_CMD_SW_CTRL:
1579         pu4IntBuf = (PUINT_32)prIwReqData->data.pointer;
1580         prNdisReq = (P_NDIS_TRANSPORT_STRUCT) &aucOidBuf[0];
1581
1582         //kalMemCopy(&prNdisReq->ndisOidContent[0], prIwReqData->data.pointer, 8);
1583         if (copy_from_user(&prNdisReq->ndisOidContent[0],
1584                            prIwReqData->data.pointer,
1585                            prIwReqData->data.length)) {
1586             status = -EFAULT;
1587             break;
1588         }
1589         prNdisReq->ndisOidCmd = OID_CUSTOM_SW_CTRL;
1590         prNdisReq->inNdisOidlength = 8;
1591         prNdisReq->outNdisOidLength = 8;
1592
1593         /* Execute this OID */
1594         status = priv_set_ndis(prNetDev, prNdisReq, &u4BufLen);
1595         break;
1596
1597     default:
1598         return -EOPNOTSUPP;
1599     }
1600
1601     return status;
1602 }
1603
1604 /*----------------------------------------------------------------------------*/
1605 /*!
1606 * \brief Private ioctl get struct handler.
1607 *
1608 * \param[in] pDev Net device requested.
1609 * \param[out] pIwReq Pointer to iwreq structure.
1610 * \param[in] cmd Private sub-command.
1611 *
1612 * \retval 0 For success.
1613 * \retval -EFAULT If copy from user space buffer fail.
1614 * \retval -EOPNOTSUPP Parameter "cmd" not recognized.
1615 *
1616 */
1617 /*----------------------------------------------------------------------------*/
1618 int
1619 priv_get_struct (
1620     IN struct net_device *prNetDev,
1621     IN struct iw_request_info *prIwReqInfo,
1622     IN union iwreq_data *prIwReqData,
1623     IN OUT char *pcExtra
1624     )
1625 {
1626     UINT_32 u4SubCmd = 0;
1627     P_NDIS_TRANSPORT_STRUCT prNdisReq= NULL;
1628
1629     P_GLUE_INFO_T   prGlueInfo = NULL;
1630     UINT_32         u4BufLen = 0;
1631     PUINT_32        pu4IntBuf = NULL;
1632     int             status = 0;
1633
1634     kalMemZero(&aucOidBuf[0], sizeof(aucOidBuf));
1635
1636     ASSERT(prNetDev);
1637     ASSERT(prIwReqData);
1638     if (!prNetDev || !prIwReqData) {
1639         DBGLOG(REQ, INFO, ("priv_get_struct(): invalid param(0x%p, 0x%p)\n",
1640             prNetDev, prIwReqData));
1641         return -EINVAL;
1642     }
1643
1644     u4SubCmd = (UINT_32) prIwReqData->data.flags;
1645     prGlueInfo = *((P_GLUE_INFO_T *) netdev_priv(prNetDev));
1646     ASSERT(prGlueInfo);
1647     if (!prGlueInfo) {
1648         DBGLOG(REQ, INFO, ("priv_get_struct(): invalid prGlueInfo(0x%p, 0x%p)\n",
1649             prNetDev, *((P_GLUE_INFO_T *) netdev_priv(prNetDev))));
1650         return -EINVAL;
1651     }
1652
1653 #if 0
1654     printk(KERN_INFO DRV_NAME"priv_get_struct(): prIwReqInfo->cmd(0x%X), u4SubCmd(%ld)\n",
1655         prIwReqInfo->cmd,
1656         u4SubCmd
1657         );
1658 #endif
1659     memset(aucOidBuf, 0, sizeof(aucOidBuf));
1660
1661     switch (u4SubCmd) {
1662     case PRIV_CMD_OID:
1663         if (copy_from_user(&aucOidBuf[0],
1664                 prIwReqData->data.pointer,
1665                 sizeof(NDIS_TRANSPORT_STRUCT))) {
1666             DBGLOG(REQ, INFO, ("priv_get_struct() copy_from_user oidBuf fail\n"));
1667             return -EFAULT;
1668         }
1669
1670         prNdisReq = (P_NDIS_TRANSPORT_STRUCT)&aucOidBuf[0];
1671 #if 0
1672         printk(KERN_NOTICE "\n priv_get_struct cmd 0x%02x len:%d OID:0x%08x OID Len:%d\n",
1673             cmd,
1674             pIwReq->u.data.length,
1675             ndisReq->ndisOidCmd,
1676             ndisReq->inNdisOidlength);
1677 #endif
1678         if (priv_get_ndis(prNetDev, prNdisReq, &u4BufLen) == 0) {
1679             prNdisReq->outNdisOidLength = u4BufLen;
1680             if (copy_to_user(prIwReqData->data.pointer,
1681                     &aucOidBuf[0],
1682                     u4BufLen + sizeof(NDIS_TRANSPORT_STRUCT) - sizeof(prNdisReq->ndisOidContent))) {
1683                 DBGLOG(REQ, INFO, ("priv_get_struct() copy_to_user oidBuf fail(1)\n"));
1684                 return -EFAULT;
1685             }
1686             return 0;
1687         }
1688         else {
1689             prNdisReq->outNdisOidLength = u4BufLen;
1690             if (copy_to_user(prIwReqData->data.pointer,
1691                     &aucOidBuf[0],
1692                     OFFSET_OF(NDIS_TRANSPORT_STRUCT, ndisOidContent))) {
1693                 DBGLOG(REQ, INFO, ("priv_get_struct() copy_to_user oidBuf fail(2)\n"));
1694             }
1695             return -EFAULT;
1696         }
1697         break;
1698
1699     case PRIV_CMD_SW_CTRL:
1700         pu4IntBuf = (PUINT_32)prIwReqData->data.pointer;
1701         prNdisReq = (P_NDIS_TRANSPORT_STRUCT) &aucOidBuf[0];
1702
1703         if (copy_from_user(&prNdisReq->ndisOidContent[0],
1704                 prIwReqData->data.pointer,
1705                 prIwReqData->data.length)) {
1706             DBGLOG(REQ, INFO, ("priv_get_struct() copy_from_user oidBuf fail\n"));
1707             return -EFAULT;
1708         }
1709
1710         prNdisReq->ndisOidCmd = OID_CUSTOM_SW_CTRL;
1711         prNdisReq->inNdisOidlength = 8;
1712         prNdisReq->outNdisOidLength = 8;
1713
1714         status = priv_get_ndis(prNetDev, prNdisReq, &u4BufLen);
1715         if (status == 0) {
1716             prNdisReq->outNdisOidLength = u4BufLen;
1717             //printk("len=%d Result=%08lx\n", u4BufLen, *(PUINT_32)&prNdisReq->ndisOidContent[4]);
1718
1719             if (copy_to_user(prIwReqData->data.pointer,
1720                     &prNdisReq->ndisOidContent[4],
1721                     4 /* OFFSET_OF(NDIS_TRANSPORT_STRUCT, ndisOidContent)*/)) {
1722                 DBGLOG(REQ, INFO, ("priv_get_struct() copy_to_user oidBuf fail(2)\n"));
1723             }
1724         }
1725         return 0;
1726         break;
1727     default:
1728         DBGLOG(REQ, WARN, ("get struct cmd:0x%lx\n", u4SubCmd));
1729         return -EOPNOTSUPP;
1730     }
1731 } /* priv_get_struct */
1732
1733 /*----------------------------------------------------------------------------*/
1734 /*!
1735 * \brief The routine handles a set operation for a single OID.
1736 *
1737 * \param[in] pDev Net device requested.
1738 * \param[in] ndisReq Ndis request OID information copy from user.
1739 * \param[out] outputLen_p If the call is successful, returns the number of
1740 *                         bytes written into the query buffer. If the
1741 *                         call failed due to invalid length of the query
1742 *                         buffer, returns the amount of storage needed..
1743 *
1744 * \retval 0 On success.
1745 * \retval -EOPNOTSUPP If cmd is not supported.
1746 *
1747 */
1748 /*----------------------------------------------------------------------------*/
1749 static int
1750 priv_set_ndis (
1751     IN struct net_device *prNetDev,
1752     IN NDIS_TRANSPORT_STRUCT* prNdisReq,
1753     OUT PUINT_32 pu4OutputLen
1754     )
1755 {
1756     P_WLAN_REQ_ENTRY prWlanReqEntry = NULL;
1757     WLAN_STATUS status = WLAN_STATUS_SUCCESS;
1758     P_GLUE_INFO_T prGlueInfo = NULL;
1759     UINT_32             u4SetInfoLen = 0;
1760
1761     ASSERT(prNetDev);
1762     ASSERT(prNdisReq);
1763     ASSERT(pu4OutputLen);
1764
1765     if (!prNetDev || !prNdisReq || !pu4OutputLen) {
1766         DBGLOG(REQ, INFO, ("priv_set_ndis(): invalid param(0x%p, 0x%p, 0x%p)\n",
1767             prNetDev, prNdisReq, pu4OutputLen));
1768         return -EINVAL;
1769     }
1770
1771     prGlueInfo = *((P_GLUE_INFO_T *) netdev_priv(prNetDev));
1772     ASSERT(prGlueInfo);
1773     if (!prGlueInfo) {
1774         DBGLOG(REQ, INFO, ("priv_set_ndis(): invalid prGlueInfo(0x%p, 0x%p)\n",
1775             prNetDev, *((P_GLUE_INFO_T *) netdev_priv(prNetDev))));
1776         return -EINVAL;
1777     }
1778
1779 #if 0
1780     printk(KERN_INFO DRV_NAME"priv_set_ndis(): prNdisReq->ndisOidCmd(0x%lX)\n",
1781         prNdisReq->ndisOidCmd
1782         );
1783 #endif
1784
1785     if (FALSE == reqSearchSupportedOidEntry(prNdisReq->ndisOidCmd,
1786                                             &prWlanReqEntry)) {
1787         //WARNLOG(("Set OID: 0x%08lx (unknown)\n", prNdisReq->ndisOidCmd));
1788         return -EOPNOTSUPP;
1789     }
1790
1791     if (NULL == prWlanReqEntry->pfOidSetHandler) {
1792         //WARNLOG(("Set %s: Null set handler\n", prWlanReqEntry->pucOidName));
1793         return -EOPNOTSUPP;
1794     }
1795
1796 #if 0
1797     printk(KERN_INFO DRV_NAME"priv_set_ndis(): %s\n",
1798         prWlanReqEntry->pucOidName
1799         );
1800 #endif
1801
1802     if (prWlanReqEntry->fgSetBufLenChecking) {
1803         if (prNdisReq->inNdisOidlength != prWlanReqEntry->u4InfoBufLen) {
1804             DBGLOG(REQ, WARN, ("Set %s: Invalid length (current=%ld, needed=%ld)\n",
1805                 prWlanReqEntry->pucOidName,
1806                 prNdisReq->inNdisOidlength,
1807                 prWlanReqEntry->u4InfoBufLen));
1808
1809             *pu4OutputLen = prWlanReqEntry->u4InfoBufLen;
1810             return -EINVAL;
1811         }
1812     }
1813
1814     if (prWlanReqEntry->eOidMethod == ENUM_OID_GLUE_ONLY) {
1815         /* GLUE sw info only */
1816         status = prWlanReqEntry->pfOidSetHandler(prGlueInfo,
1817                                                     prNdisReq->ndisOidContent,
1818                                                     prNdisReq->inNdisOidlength,
1819                                                     &u4SetInfoLen);
1820     }
1821     else if (prWlanReqEntry->eOidMethod == ENUM_OID_GLUE_EXTENSION) {
1822         /* multiple sw operations */
1823         status = prWlanReqEntry->pfOidSetHandler(prGlueInfo,
1824                                                     prNdisReq->ndisOidContent,
1825                                                     prNdisReq->inNdisOidlength,
1826                                                     &u4SetInfoLen);
1827     }
1828     else if (prWlanReqEntry->eOidMethod == ENUM_OID_DRIVER_CORE) {
1829         /* driver core*/
1830
1831         status = kalIoctl(prGlueInfo,
1832             (PFN_OID_HANDLER_FUNC)prWlanReqEntry->pfOidSetHandler,
1833             prNdisReq->ndisOidContent,
1834             prNdisReq->inNdisOidlength,
1835             FALSE,
1836             FALSE,
1837             TRUE,
1838             FALSE,
1839             &u4SetInfoLen);
1840     }
1841     else {
1842         DBGLOG(REQ, INFO, ("priv_set_ndis(): unsupported OID method:0x%x\n",
1843                     prWlanReqEntry->eOidMethod));
1844         return -EOPNOTSUPP;
1845     }
1846
1847     *pu4OutputLen = u4SetInfoLen;
1848
1849     switch (status) {
1850     case WLAN_STATUS_SUCCESS:
1851         break;
1852
1853     case WLAN_STATUS_INVALID_LENGTH:
1854         //WARNLOG(("Set %s: Invalid length (current=%ld, needed=%ld)\n",
1855            // prWlanReqEntry->pucOidName,
1856             //prNdisReq->inNdisOidlength,
1857             //u4SetInfoLen));
1858         break;
1859     }
1860
1861     if (WLAN_STATUS_SUCCESS != status) {
1862         return -EFAULT;
1863     }
1864
1865     return 0;
1866 } /* priv_set_ndis */
1867
1868 /*----------------------------------------------------------------------------*/
1869 /*!
1870 * \brief The routine handles a query operation for a single OID. Basically we
1871 *   return information about the current state of the OID in question.
1872 *
1873 * \param[in] pDev Net device requested.
1874 * \param[in] ndisReq Ndis request OID information copy from user.
1875 * \param[out] outputLen_p If the call is successful, returns the number of
1876 *                        bytes written into the query buffer. If the
1877 *                        call failed due to invalid length of the query
1878 *                        buffer, returns the amount of storage needed..
1879 *
1880 * \retval 0 On success.
1881 * \retval -EOPNOTSUPP If cmd is not supported.
1882 * \retval -EINVAL invalid input parameters
1883 *
1884 */
1885 /*----------------------------------------------------------------------------*/
1886 static int
1887 priv_get_ndis (
1888     IN struct net_device *prNetDev,
1889     IN NDIS_TRANSPORT_STRUCT* prNdisReq,
1890     OUT PUINT_32 pu4OutputLen
1891     )
1892 {
1893     P_WLAN_REQ_ENTRY prWlanReqEntry = NULL;
1894     UINT_32 u4BufLen = 0;
1895     WLAN_STATUS status = WLAN_STATUS_SUCCESS;
1896     P_GLUE_INFO_T prGlueInfo = NULL;
1897
1898     ASSERT(prNetDev);
1899     ASSERT(prNdisReq);
1900     ASSERT(pu4OutputLen);
1901
1902     if (!prNetDev || !prNdisReq || !pu4OutputLen) {
1903         DBGLOG(REQ, INFO, ("priv_get_ndis(): invalid param(0x%p, 0x%p, 0x%p)\n",
1904             prNetDev, prNdisReq, pu4OutputLen));
1905         return -EINVAL;
1906     }
1907
1908     prGlueInfo = *((P_GLUE_INFO_T *) netdev_priv(prNetDev));
1909     ASSERT(prGlueInfo);
1910     if (!prGlueInfo) {
1911         DBGLOG(REQ, INFO, ("priv_get_ndis(): invalid prGlueInfo(0x%p, 0x%p)\n",
1912             prNetDev, *((P_GLUE_INFO_T *) netdev_priv(prNetDev))));
1913         return -EINVAL;
1914     }
1915
1916 #if 0
1917     printk(KERN_INFO DRV_NAME"priv_get_ndis(): prNdisReq->ndisOidCmd(0x%lX)\n",
1918         prNdisReq->ndisOidCmd
1919         );
1920 #endif
1921
1922     if (FALSE == reqSearchSupportedOidEntry(prNdisReq->ndisOidCmd,
1923                                             &prWlanReqEntry)) {
1924         //WARNLOG(("Query OID: 0x%08lx (unknown)\n", prNdisReq->ndisOidCmd));
1925         return -EOPNOTSUPP;
1926     }
1927
1928
1929     if (NULL == prWlanReqEntry->pfOidQueryHandler) {
1930         //WARNLOG(("Query %s: Null query handler\n", prWlanReqEntry->pucOidName));
1931         return -EOPNOTSUPP;
1932     }
1933
1934 #if 0
1935     printk(KERN_INFO DRV_NAME"priv_get_ndis(): %s\n",
1936         prWlanReqEntry->pucOidName
1937         );
1938 #endif
1939
1940     if (prWlanReqEntry->fgQryBufLenChecking) {
1941         if (prNdisReq->inNdisOidlength < prWlanReqEntry->u4InfoBufLen) {
1942             /* Not enough room in InformationBuffer. Punt */
1943             //WARNLOG(("Query %s: Buffer too short (current=%ld, needed=%ld)\n",
1944                 //prWlanReqEntry->pucOidName,
1945                 //prNdisReq->inNdisOidlength,
1946                 //prWlanReqEntry->u4InfoBufLen));
1947
1948             *pu4OutputLen = prWlanReqEntry->u4InfoBufLen;
1949
1950             status = WLAN_STATUS_INVALID_LENGTH;
1951             return -EINVAL;
1952         }
1953     }
1954
1955
1956     if (prWlanReqEntry->eOidMethod == ENUM_OID_GLUE_ONLY) {
1957         /* GLUE sw info only */
1958         status = prWlanReqEntry->pfOidQueryHandler(prGlueInfo,
1959                                                     prNdisReq->ndisOidContent,
1960                                                     prNdisReq->inNdisOidlength,
1961                                                     &u4BufLen);
1962     }
1963     else if (prWlanReqEntry->eOidMethod == ENUM_OID_GLUE_EXTENSION) {
1964         /* multiple sw operations */
1965         status = prWlanReqEntry->pfOidQueryHandler(prGlueInfo,
1966                                                     prNdisReq->ndisOidContent,
1967                                                     prNdisReq->inNdisOidlength,
1968                                                     &u4BufLen);
1969     }
1970     else if (prWlanReqEntry->eOidMethod == ENUM_OID_DRIVER_CORE) {
1971         /* driver core*/
1972
1973         status = kalIoctl(prGlueInfo,
1974             (PFN_OID_HANDLER_FUNC)prWlanReqEntry->pfOidQueryHandler,
1975             prNdisReq->ndisOidContent,
1976             prNdisReq->inNdisOidlength,
1977             TRUE,
1978             TRUE,
1979             TRUE,
1980             FALSE,
1981             &u4BufLen);
1982     }
1983     else {
1984         DBGLOG(REQ, INFO, ("priv_set_ndis(): unsupported OID method:0x%x\n",
1985                     prWlanReqEntry->eOidMethod));
1986         return -EOPNOTSUPP;
1987     }
1988
1989     *pu4OutputLen = u4BufLen;
1990
1991     switch (status) {
1992     case WLAN_STATUS_SUCCESS:
1993         break;
1994
1995     case WLAN_STATUS_INVALID_LENGTH:
1996         //WARNLOG(("Set %s: Invalid length (current=%ld, needed=%ld)\n",
1997            // prWlanReqEntry->pucOidName,
1998             //prNdisReq->inNdisOidlength,
1999             //u4BufLen));
2000         break;
2001     }
2002
2003     if (WLAN_STATUS_SUCCESS != status) {
2004         return -EOPNOTSUPP;
2005     }
2006
2007     return 0;
2008 } /* priv_get_ndis */
2009
2010 /*----------------------------------------------------------------------------*/
2011 /*!
2012 * \brief This routine is called to search desired OID.
2013 *
2014 * \param rOid[in]               Desired NDIS_OID
2015 * \param ppWlanReqEntry[out]    Found registered OID entry
2016 *
2017 * \retval TRUE: Matched OID is found
2018 * \retval FALSE: No matched OID is found
2019 */
2020 /*----------------------------------------------------------------------------*/
2021 static BOOLEAN
2022 reqSearchSupportedOidEntry (
2023     IN  UINT_32            rOid,
2024     OUT P_WLAN_REQ_ENTRY    *ppWlanReqEntry
2025     )
2026 {
2027     INT_32 i, j, k;
2028
2029     i = 0;
2030     j = NUM_SUPPORTED_OIDS - 1;
2031
2032     while (i <= j) {
2033         k = (i + j) / 2;
2034
2035         if (rOid == arWlanOidReqTable[k].rOid) {
2036             *ppWlanReqEntry = &arWlanOidReqTable[k];
2037             return TRUE;
2038         } else if (rOid < arWlanOidReqTable[k].rOid) {
2039             j = k - 1;
2040         } else {
2041             i = k + 1;
2042         }
2043     }
2044
2045     return FALSE;
2046 }   /* reqSearchSupportedOidEntry */
2047
2048 #if 0
2049 /*----------------------------------------------------------------------------*/
2050 /*!
2051 * \brief This routine is called to query the radio configuration used in IBSS
2052 *        mode and RF test mode.
2053 *
2054 * \param[in] prGlueInfo         Pointer to the GLUE_INFO_T structure.
2055 * \param[out] pvQueryBuffer     Pointer to the buffer that holds the result of the query.
2056 * \param[in] u4QueryBufferLen   The length of the query buffer.
2057 * \param[out] pu4QueryInfoLen   If the call is successful, returns the number of
2058 *                               bytes written into the query buffer. If the call
2059 *                               failed due to invalid length of the query buffer,
2060 *                               returns the amount of storage needed.
2061 *
2062 * \retval WLAN_STATUS_SUCCESS
2063 * \retval WLAN_STATUS_INVALID_LENGTH
2064 */
2065 /*----------------------------------------------------------------------------*/
2066 static WLAN_STATUS
2067 reqExtQueryConfiguration (
2068     IN  P_GLUE_INFO_T   prGlueInfo,
2069     OUT PVOID           pvQueryBuffer,
2070     IN UINT_32          u4QueryBufferLen,
2071     OUT PUINT_32        pu4QueryInfoLen
2072     )
2073 {
2074     P_PARAM_802_11_CONFIG_T prQueryConfig = (P_PARAM_802_11_CONFIG_T)pvQueryBuffer;
2075     WLAN_STATUS rStatus = WLAN_STATUS_SUCCESS;
2076     UINT_32 u4QueryInfoLen = 0;
2077
2078     DEBUGFUNC("wlanoidQueryConfiguration");
2079
2080
2081     ASSERT(prGlueInfo);
2082     ASSERT(pu4QueryInfoLen);
2083
2084     *pu4QueryInfoLen = sizeof(PARAM_802_11_CONFIG_T);
2085     if (u4QueryBufferLen < sizeof(PARAM_802_11_CONFIG_T)) {
2086         return WLAN_STATUS_INVALID_LENGTH;
2087     }
2088
2089     ASSERT(pvQueryBuffer);
2090
2091     kalMemZero(prQueryConfig, sizeof(PARAM_802_11_CONFIG_T));
2092
2093     /* Update the current radio configuration. */
2094     prQueryConfig->u4Length = sizeof(PARAM_802_11_CONFIG_T);
2095
2096 #if defined(_HIF_SDIO)
2097     rStatus = sdio_io_ctrl(prGlueInfo,
2098                             wlanoidSetBeaconInterval,
2099                             &prQueryConfig->u4BeaconPeriod,
2100                             sizeof(UINT_32),
2101                             TRUE,
2102                             TRUE,
2103                             &u4QueryInfoLen);
2104 #else
2105     rStatus = wlanQueryInformation(prGlueInfo->prAdapter,
2106                                    wlanoidQueryBeaconInterval,
2107                                    &prQueryConfig->u4BeaconPeriod,
2108                                    sizeof(UINT_32),
2109                                    &u4QueryInfoLen);
2110 #endif
2111     if (rStatus != WLAN_STATUS_SUCCESS) {
2112         return rStatus;
2113     }
2114
2115 #if defined(_HIF_SDIO)
2116     rStatus = sdio_io_ctrl(prGlueInfo,
2117                             wlanoidQueryAtimWindow,
2118                             &prQueryConfig->u4ATIMWindow,
2119                             sizeof(UINT_32),
2120                             TRUE,
2121                             TRUE,
2122                             &u4QueryInfoLen);
2123 #else
2124     rStatus = wlanQueryInformation(prGlueInfo->prAdapter,
2125                                    wlanoidQueryAtimWindow,
2126                                    &prQueryConfig->u4ATIMWindow,
2127                                    sizeof(UINT_32),
2128                                    &u4QueryInfoLen);
2129 #endif
2130     if (rStatus != WLAN_STATUS_SUCCESS) {
2131         return rStatus;
2132     }
2133
2134 #if defined(_HIF_SDIO)
2135     rStatus = sdio_io_ctrl(prGlueInfo,
2136                             wlanoidQueryFrequency,
2137                             &prQueryConfig->u4DSConfig,
2138                             sizeof(UINT_32),
2139                             TRUE,
2140                             TRUE,
2141                             &u4QueryInfoLen);
2142 #else
2143     rStatus = wlanQueryInformation(prGlueInfo->prAdapter,
2144                                    wlanoidQueryFrequency,
2145                                    &prQueryConfig->u4DSConfig,
2146                                    sizeof(UINT_32),
2147                                    &u4QueryInfoLen);
2148 #endif
2149     if (rStatus != WLAN_STATUS_SUCCESS) {
2150         return rStatus;
2151     }
2152
2153     prQueryConfig->rFHConfig.u4Length = sizeof(PARAM_802_11_CONFIG_FH_T);
2154
2155     return rStatus;
2156
2157 } /* end of reqExtQueryConfiguration() */
2158
2159
2160 /*----------------------------------------------------------------------------*/
2161 /*!
2162 * \brief This routine is called to set the radio configuration used in IBSS
2163 *        mode.
2164 *
2165 * \param[in] prGlueInfo     Pointer to the GLUE_INFO_T structure.
2166 * \param[in] pvSetBuffer    A pointer to the buffer that holds the data to be set.
2167 * \param[in] u4SetBufferLen The length of the set buffer.
2168 * \param[out] pu4SetInfoLen If the call is successful, returns the number of
2169 *                           bytes read from the set buffer. If the call failed
2170 *                           due to invalid length of the set buffer, returns
2171 *                           the amount of storage needed.
2172 *
2173 * \retval WLAN_STATUS_SUCCESS
2174 * \retval WLAN_STATUS_INVALID_LENGTH
2175 * \retval WLAN_STATUS_NOT_ACCEPTED
2176 */
2177 /*----------------------------------------------------------------------------*/
2178 static WLAN_STATUS
2179 reqExtSetConfiguration (
2180     IN  P_GLUE_INFO_T prGlueInfo,
2181     IN  PVOID         pvSetBuffer,
2182     IN  UINT_32       u4SetBufferLen,
2183     OUT PUINT_32      pu4SetInfoLen
2184     )
2185 {
2186     WLAN_STATUS  rStatus = WLAN_STATUS_SUCCESS;
2187     P_PARAM_802_11_CONFIG_T prNewConfig = (P_PARAM_802_11_CONFIG_T)pvSetBuffer;
2188     UINT_32 u4SetInfoLen = 0;
2189
2190     DEBUGFUNC("wlanoidSetConfiguration");
2191
2192
2193     ASSERT(prGlueInfo);
2194     ASSERT(pu4SetInfoLen);
2195
2196     *pu4SetInfoLen = sizeof(PARAM_802_11_CONFIG_T);
2197
2198     if (u4SetBufferLen < *pu4SetInfoLen) {
2199         return WLAN_STATUS_INVALID_LENGTH;
2200     }
2201
2202     /* OID_802_11_CONFIGURATION. If associated, NOT_ACCEPTED shall be returned. */
2203     if (prGlueInfo->eParamMediaStateIndicated == PARAM_MEDIA_STATE_CONNECTED) {
2204         return WLAN_STATUS_NOT_ACCEPTED;
2205     }
2206
2207     ASSERT(pvSetBuffer);
2208
2209 #if defined(_HIF_SDIO)
2210     rStatus = sdio_io_ctrl(prGlueInfo,
2211                             wlanoidSetBeaconInterval,
2212                             &prNewConfig->u4BeaconPeriod,
2213                             sizeof(UINT_32),
2214                             FALSE,
2215                             TRUE,
2216                             &u4SetInfoLen);
2217 #else
2218     rStatus = wlanSetInformation(prGlueInfo->prAdapter,
2219                                  wlanoidSetBeaconInterval,
2220                                  &prNewConfig->u4BeaconPeriod,
2221                                  sizeof(UINT_32),
2222                                  &u4SetInfoLen);
2223 #endif
2224     if (rStatus != WLAN_STATUS_SUCCESS) {
2225         return rStatus;
2226     }
2227
2228 #if defined(_HIF_SDIO)
2229     rStatus = sdio_io_ctrl(prGlueInfo,
2230                             wlanoidSetAtimWindow,
2231                              &prNewConfig->u4ATIMWindow,
2232                             sizeof(UINT_32),
2233                             FALSE,
2234                             TRUE,
2235                             &u4SetInfoLen);
2236 #else
2237     rStatus = wlanSetInformation(prGlueInfo->prAdapter,
2238                                  wlanoidSetAtimWindow,
2239                                  &prNewConfig->u4ATIMWindow,
2240                                  sizeof(UINT_32),
2241                                  &u4SetInfoLen);
2242 #endif
2243     if (rStatus != WLAN_STATUS_SUCCESS) {
2244         return rStatus;
2245     }
2246
2247 #if defined(_HIF_SDIO)
2248     rStatus = sdio_io_ctrl(prGlueInfo,
2249                             wlanoidSetFrequency,
2250                             &prNewConfig->u4DSConfig,
2251                             sizeof(UINT_32),
2252                             FALSE,
2253                             TRUE,
2254                             &u4SetInfoLen);
2255 #else
2256     rStatus = wlanSetInformation(prGlueInfo->prAdapter,
2257                                  wlanoidSetFrequency,
2258                                  &prNewConfig->u4DSConfig,
2259                                  sizeof(UINT_32),
2260                                  &u4SetInfoLen);
2261 #endif
2262
2263     if (rStatus != WLAN_STATUS_SUCCESS) {
2264         return rStatus;
2265     }
2266
2267     return rStatus;
2268
2269 } /* end of reqExtSetConfiguration() */
2270
2271 #endif
2272 /*----------------------------------------------------------------------------*/
2273 /*!
2274 * \brief This routine is called to set beacon detection function enable/disable state
2275 *        This is mainly designed for usage under BT inquiry state (disable function).
2276 *
2277 * \param[in] pvAdapter Pointer to the Adapter structure
2278 * \param[in] pvSetBuffer A pointer to the buffer that holds the data to be set
2279 * \param[in] u4SetBufferLen The length of the set buffer
2280 * \param[out] pu4SetInfoLen If the call is successful, returns the number of
2281 *   bytes read from the set buffer. If the call failed due to invalid length of
2282 *   the set buffer, returns the amount of storage needed.
2283 *
2284 * \retval WLAN_STATUS_SUCCESS
2285 * \retval WLAN_STATUS_INVALID_DATA If new setting value is wrong.
2286 * \retval WLAN_STATUS_INVALID_LENGTH
2287 *
2288 */
2289 /*----------------------------------------------------------------------------*/
2290 static WLAN_STATUS
2291 reqExtSetAcpiDevicePowerState (
2292     IN  P_GLUE_INFO_T prGlueInfo,
2293     IN  PVOID         pvSetBuffer,
2294     IN  UINT_32       u4SetBufferLen,
2295     OUT PUINT_32      pu4SetInfoLen
2296     )
2297 {
2298     WLAN_STATUS  rStatus = WLAN_STATUS_SUCCESS;
2299
2300     ASSERT(prGlueInfo);
2301     ASSERT(pvSetBuffer);
2302     ASSERT(pu4SetInfoLen);
2303
2304     /* WIFI is enabled, when ACPI is D0 (ParamDeviceStateD0 = 1). And vice versa */
2305
2306     //rStatus = wlanSetInformation(prGlueInfo->prAdapter,
2307     //                   wlanoidSetAcpiDevicePowerState,
2308     //                   pvSetBuffer,
2309     //                   u4SetBufferLen,
2310     //                   pu4SetInfoLen);
2311     return rStatus;
2312 }
2313