net: wireless: rockchip_wlan: add rtl8723bs support
[firefly-linux-kernel-4.4.55.git] / drivers / net / wireless / rockchip_wlan / rtl8723bs / os_dep / linux / ioctl_mp.c
1 /******************************************************************************
2  *
3  * Copyright(c) 2007 - 2012 Realtek Corporation. All rights reserved.
4  *
5  * This program is free software; you can redistribute it and/or modify it
6  * under the terms of version 2 of the GNU General Public License as
7  * published by the Free Software Foundation.
8  *
9  * This program is distributed in the hope that it will be useful, but WITHOUT
10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11  * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12  * more details.
13  *
14  * You should have received a copy of the GNU General Public License along with
15  * this program; if not, write to the Free Software Foundation, Inc.,
16  * 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA
17  *
18  *
19  ******************************************************************************/
20 #if defined(CONFIG_MP_INCLUDED)
21
22 #include <drv_types.h>
23 #include <rtw_mp.h>
24 #include <rtw_mp_ioctl.h>
25 #include "../../hal/phydm/phydm_precomp.h"
26
27
28 #if defined(CONFIG_RTL8723B)
29 #include <rtw_bt_mp.h>
30 #endif
31
32 /*
33  * Input Format: %s,%d,%d
34  *      %s is width, could be
35  *              "b" for 1 byte
36  *              "w" for WORD (2 bytes)
37  *              "dw" for DWORD (4 bytes)
38  *      1st %d is address(offset)
39  *      2st %d is data to write
40  */
41 int rtw_mp_write_reg(struct net_device *dev,
42                                          struct iw_request_info *info,
43                                          struct iw_point *wrqu, char *extra)
44 {
45         char *pch, *pnext, *ptmp;
46         char *width_str;
47         char width, buf[5];
48         u32 addr, data;
49         int ret;
50         PADAPTER padapter = rtw_netdev_priv(dev);
51         char input[wrqu->length];
52
53         if (copy_from_user(input, wrqu->pointer, wrqu->length))
54                 return -EFAULT;
55
56         _rtw_memset(extra, 0, wrqu->length);
57
58         pch = input;
59
60         pnext = strpbrk(pch, " ,.-");
61         if (pnext == NULL)
62                 return -EINVAL;
63         *pnext = 0;
64         width_str = pch;
65
66         pch = pnext + 1;
67         pnext = strpbrk(pch, " ,.-");
68         if (pnext == NULL)
69                 return -EINVAL;
70         *pnext = 0;
71         /*addr = simple_strtoul(pch, &ptmp, 16);
72         _rtw_memset(buf, '\0', sizeof(buf));
73         _rtw_memcpy(buf, pch, pnext-pch);
74         ret = kstrtoul(buf, 16, &addr);*/
75         ret = sscanf(pch, "%x", &addr);
76         if (addr > 0x3FFF)
77                 return -EINVAL;
78
79         pch = pnext + 1;
80         pnext = strpbrk(pch, " ,.-");
81         if ((pch - input) >= wrqu->length)
82                 return -EINVAL;
83         /*data = simple_strtoul(pch, &ptmp, 16);*/
84         ret = sscanf(pch, "%x", &data);
85         DBG_871X("data=%x,addr=%x\n", (u32)data, (u32)addr);
86         ret = 0;
87         width = width_str[0];
88         switch (width) {
89         case 'b':
90                 /* 1 byte*/
91                 if (data > 0xFF) {
92                         ret = -EINVAL;
93                         break;
94                 }
95                 rtw_write8(padapter, addr, data);
96                 break;
97         case 'w':
98                 /* 2 bytes*/
99                 if (data > 0xFFFF) {
100                         ret = -EINVAL;
101                         break;
102                 }
103                 rtw_write16(padapter, addr, data);
104                 break;
105         case 'd':
106                 /* 4 bytes*/
107                 rtw_write32(padapter, addr, data);
108                 break;
109         default:
110                 ret = -EINVAL;
111                 break;
112         }
113
114         return ret;
115 }
116
117
118 /*
119  * Input Format: %s,%d
120  *      %s is width, could be
121  *              "b" for 1 byte
122  *              "w" for WORD (2 bytes)
123  *              "dw" for DWORD (4 bytes)
124  *      %d is address(offset)
125  *
126  * Return:
127  *      %d for data readed
128  */
129 int rtw_mp_read_reg(struct net_device *dev,
130                                         struct iw_request_info *info,
131                                         struct iw_point *wrqu, char *extra)
132 {
133         char input[wrqu->length];
134         char *pch, *pnext, *ptmp;
135         char *width_str;
136         char width;
137         char data[20], tmp[20], buf[3];
138         u32 addr = 0, strtout = 0;
139         u32 i = 0, j = 0, ret = 0, data32 = 0;
140         PADAPTER padapter = rtw_netdev_priv(dev);
141
142
143         if (wrqu->length > 128)
144                 return -EFAULT;
145
146         if (copy_from_user(input, wrqu->pointer, wrqu->length))
147                 return -EFAULT;
148
149         _rtw_memset(extra, 0, wrqu->length);
150         _rtw_memset(data, '\0', sizeof(data));
151         _rtw_memset(tmp, '\0', sizeof(tmp));
152         pch = input;
153         pnext = strpbrk(pch, " ,.-");
154         if (pnext == NULL)
155                 return -EINVAL;
156         *pnext = 0;
157         width_str = pch;
158
159         pch = pnext + 1;
160
161         ret = sscanf(pch, "%x", &addr);
162         if (addr > 0x3FFF)
163                 return -EINVAL;
164
165         ret = 0;
166         width = width_str[0];
167
168         switch (width) {
169         case 'b':
170                         data32 = rtw_read8(padapter, addr);
171                         DBG_871X("%x\n", data32);
172                         sprintf(extra, "%d", data32);
173                         wrqu->length = strlen(extra);
174                         break;
175         case 'w':
176                         /* 2 bytes*/
177                         sprintf(data, "%04x\n", rtw_read16(padapter, addr));
178
179                         for (i = 0 ; i <= strlen(data) ; i++) {
180                                 if (i % 2 == 0) {
181                                         tmp[j] = ' ';
182                                         j++;
183                                 }
184                                 if (data[i] != '\0')
185                                         tmp[j] = data[i];
186
187                                 j++;
188                         }
189                         pch = tmp;
190                         DBG_871X("pch=%s", pch);
191
192                         while (*pch != '\0') {
193                                 pnext = strpbrk(pch, " ");
194                                 if (!pnext || ((pnext - tmp) > 4))
195                                         break;
196                                         
197                                 pnext++;
198                                 if (*pnext != '\0') {
199                                         /*strtout = simple_strtoul(pnext , &ptmp, 16);*/
200                                         ret = sscanf(pnext, "%x", &strtout);
201                                         sprintf(extra, "%s %d" , extra , strtout);
202                                 } else
203                                         break;
204                                 pch = pnext;
205                         }
206                         wrqu->length = strlen(extra);
207                         break;
208         case 'd':
209                         /* 4 bytes */
210                         sprintf(data, "%08x", rtw_read32(padapter, addr));
211                         /*add read data format blank*/
212                         for (i = 0 ; i <= strlen(data) ; i++) {
213                                 if (i % 2 == 0) {
214                                         tmp[j] = ' ';
215                                         j++;
216                                 }
217                                 if (data[i] != '\0')
218                                         tmp[j] = data[i];
219
220                                 j++;
221                         }
222                         pch = tmp;
223                         DBG_871X("pch=%s", pch);
224
225                         while (*pch != '\0') {
226                                 pnext = strpbrk(pch, " ");
227                                 if (!pnext)
228                                         break;
229
230                                 pnext++;
231                                 if (*pnext != '\0') {
232                                         ret = sscanf(pnext, "%x", &strtout);
233                                         sprintf(extra, "%s %d" , extra , strtout);
234                                 } else
235                                         break;
236                                 pch = pnext;
237                         }
238                         wrqu->length = strlen(extra);
239                         break;
240
241         default:
242                         wrqu->length = 0;
243                         ret = -EINVAL;
244                         break;
245                 }
246
247         return ret;
248 }
249
250
251 /*
252  * Input Format: %d,%x,%x
253  *      %d is RF path, should be smaller than MAX_RF_PATH_NUMS
254  *      1st %x is address(offset)
255  *      2st %x is data to write
256  */
257 int rtw_mp_write_rf(struct net_device *dev,
258                                         struct iw_request_info *info,
259                                         struct iw_point *wrqu, char *extra)
260 {
261
262         u32 path, addr, data;
263         int ret;
264         PADAPTER padapter = rtw_netdev_priv(dev);
265         char input[wrqu->length];
266
267
268         _rtw_memset(input, 0, wrqu->length);
269         if (copy_from_user(input, wrqu->pointer, wrqu->length))
270                 return -EFAULT;
271
272
273         ret = sscanf(input, "%d,%x,%x", &path, &addr, &data);
274         if (ret < 3)
275                 return -EINVAL;
276
277         if (path >= GET_HAL_RFPATH_NUM(padapter))
278                 return -EINVAL;
279         if (addr > 0xFF)
280                 return -EINVAL;
281         if (data > 0xFFFFF)
282                 return -EINVAL;
283
284         _rtw_memset(extra, 0, wrqu->length);
285
286         write_rfreg(padapter, path, addr, data);
287
288         sprintf(extra, "write_rf completed\n");
289         wrqu->length = strlen(extra);
290
291         return 0;
292 }
293
294
295 /*
296  * Input Format: %d,%x
297  *      %d is RF path, should be smaller than MAX_RF_PATH_NUMS
298  *      %x is address(offset)
299  *
300  * Return:
301  *      %d for data readed
302  */
303 int rtw_mp_read_rf(struct net_device *dev,
304                                    struct iw_request_info *info,
305                                    struct iw_point *wrqu, char *extra)
306 {
307         char input[wrqu->length];
308         char *pch, *pnext, *ptmp;
309         char data[20], tmp[20], buf[3];
310         u32 path, addr, strtou;
311         u32 ret, i = 0 , j = 0;
312         PADAPTER padapter = rtw_netdev_priv(dev);
313         
314         if (wrqu->length > 128)
315                 return -EFAULT;
316         _rtw_memset(input, 0, wrqu->length);
317         if (copy_from_user(input, wrqu->pointer, wrqu->length))
318                 return -EFAULT;
319
320         ret = sscanf(input, "%d,%x", &path, &addr);
321         if (ret < 2)
322                 return -EINVAL;
323
324         if (path >= GET_HAL_RFPATH_NUM(padapter))
325                 return -EINVAL;
326         if (addr > 0xFF)
327                 return -EINVAL;
328
329         _rtw_memset(extra, 0, wrqu->length);
330
331         sprintf(data, "%08x", read_rfreg(padapter, path, addr));
332         /*add read data format blank*/
333         for (i = 0 ; i <= strlen(data) ; i++) {
334                 if (i % 2 == 0) {
335                         tmp[j] = ' ';
336                         j++;
337                 }
338                 tmp[j] = data[i];
339                 j++;
340         }
341         pch = tmp;
342         DBG_871X("pch=%s", pch);
343
344         while (*pch != '\0') {
345                 pnext = strpbrk(pch, " ");
346                 if (!pnext)
347                         break;
348                 pnext++;
349                 if (*pnext != '\0') {
350                         /*strtou =simple_strtoul(pnext , &ptmp, 16);*/
351                         ret = sscanf(pnext, "%x", &strtou);
352                         sprintf(extra, "%s %d" , extra , strtou);
353                 } else
354                         break;
355                 pch = pnext;
356         }
357         wrqu->length = strlen(extra);
358
359         return 0;
360 }
361
362
363 int rtw_mp_start(struct net_device *dev,
364                                  struct iw_request_info *info,
365                                  struct iw_point *wrqu, char *extra)
366 {
367         u8 val8;
368         PADAPTER padapter = rtw_netdev_priv(dev);
369         HAL_DATA_TYPE   *pHalData = GET_HAL_DATA(padapter);
370         struct hal_ops *pHalFunc = &padapter->HalFunc;
371
372         rtw_pm_set_ips(padapter, IPS_NONE);
373         LeaveAllPowerSaveMode(padapter);
374
375         if (padapter->registrypriv.mp_mode == 0) {
376                 rtw_hal_deinit(padapter);
377                 padapter->registrypriv.mp_mode = 1;
378                 #ifdef CONFIG_RF_GAIN_OFFSET
379                 if (!IS_HARDWARE_TYPE_8814A(padapter))
380                         padapter->registrypriv.RegRfKFreeEnable = 1;
381                 rtw_hal_read_chip_info(padapter);
382                 #endif /*CONFIG_RF_GAIN_OFFSET*/
383                 rtw_hal_init(padapter);
384         }
385
386         if (padapter->registrypriv.mp_mode == 0)
387                 return -EPERM;
388
389         if (padapter->mppriv.mode == MP_OFF) {
390                 if (mp_start_test(padapter) == _FAIL)
391                         return -EPERM;
392                 padapter->mppriv.mode = MP_ON;
393                 MPT_PwrCtlDM(padapter, 0);
394         }
395         padapter->mppriv.bmac_filter = _FALSE;
396 #ifdef CONFIG_RTL8723B
397 #ifdef CONFIG_USB_HCI
398         rtw_write32(padapter, 0x765, 0x0000);
399         rtw_write32(padapter, 0x948, 0x0280);
400 #else
401         rtw_write32(padapter, 0x765, 0x0000);
402         rtw_write32(padapter, 0x948, 0x0000);
403 #endif
404 #ifdef CONFIG_FOR_RTL8723BS_VQ0
405         rtw_write32(padapter, 0x765, 0x0000);
406         rtw_write32(padapter, 0x948, 0x0280);
407 #endif
408         rtw_write8(padapter, 0x66, 0x27); /*Open BT uart Log*/
409         rtw_write8(padapter, 0xc50, 0x20); /*for RX init Gain*/
410 #endif
411         ODM_Write_DIG(&pHalData->odmpriv, 0x20);
412
413         return 0;
414 }
415
416
417
418 int rtw_mp_stop(struct net_device *dev,
419                                 struct iw_request_info *info,
420                                 struct iw_point *wrqu, char *extra)
421 {
422         PADAPTER padapter = rtw_netdev_priv(dev);
423         struct hal_ops *pHalFunc = &padapter->HalFunc;
424
425         if (padapter->registrypriv.mp_mode == 1) {
426
427                 MPT_DeInitAdapter(padapter);
428                 pHalFunc->hal_deinit(padapter);
429                 padapter->registrypriv.mp_mode = 0;
430                 pHalFunc->hal_init(padapter);
431         }
432
433         if (padapter->mppriv.mode != MP_OFF) {
434                 mp_stop_test(padapter);
435                 padapter->mppriv.mode = MP_OFF;
436         }
437
438         return 0;
439 }
440
441
442 int rtw_mp_rate(struct net_device *dev,
443                                 struct iw_request_info *info,
444                                 struct iw_point *wrqu, char *extra)
445 {
446         u32 rate = MPT_RATE_1M;
447         u8              input[wrqu->length];
448         PADAPTER padapter = rtw_netdev_priv(dev);
449         PMPT_CONTEXT            pMptCtx = &(padapter->mppriv.MptCtx);
450
451         if (copy_from_user(input, wrqu->pointer, wrqu->length))
452                 return -EFAULT;
453
454         rate = rtw_mpRateParseFunc(padapter, input);
455         padapter->mppriv.rateidx = rate;
456
457         if (rate == 0 && strcmp(input, "1M") != 0) {
458                 rate = rtw_atoi(input);
459                 padapter->mppriv.rateidx = MRateToHwRate(rate);
460                 /*if (rate <= 0x7f)
461                         rate = wifirate2_ratetbl_inx((u8)rate);
462                 else if (rate < 0xC8)
463                         rate = (rate - 0x79 + MPT_RATE_MCS0);
464                 HT  rate 0x80(MCS0)  ~ 0x8F(MCS15) ~ 0x9F(MCS31) 128~159
465                 VHT1SS~2SS rate 0xA0 (VHT1SS_MCS0 44) ~ 0xB3 (VHT2SS_MCS9 #63) 160~179
466                 VHT rate 0xB4 (VHT3SS_MCS0 64) ~ 0xC7 (VHT2SS_MCS9 #83) 180~199
467                 else
468                 VHT rate 0x90(VHT1SS_MCS0) ~ 0x99(VHT1SS_MCS9) 144~153
469                 rate =(rate - MPT_RATE_VHT1SS_MCS0);
470                 */
471         }
472         _rtw_memset(extra, 0, wrqu->length);
473
474         sprintf(extra, "Set data rate to %s index %d" , input, padapter->mppriv.rateidx);
475         DBG_871X("%s: %s rate index=%d\n", __func__, input, padapter->mppriv.rateidx);
476
477         if (padapter->mppriv.rateidx >= DESC_RATEVHTSS4MCS9)
478                 return -EINVAL;
479
480         pMptCtx->MptRateIndex = HwRateToMPTRate(padapter->mppriv.rateidx);
481         SetDataRate(padapter);
482
483         wrqu->length = strlen(extra);
484         return 0;
485 }
486
487
488 int rtw_mp_channel(struct net_device *dev,
489                                    struct iw_request_info *info,
490                                    struct iw_point *wrqu, char *extra)
491 {
492
493         PADAPTER padapter = rtw_netdev_priv(dev);
494         HAL_DATA_TYPE   *pHalData       = GET_HAL_DATA(padapter);
495         u8              input[wrqu->length];
496         u32     channel = 1;
497         int cur_ch_offset;
498
499         if (copy_from_user(input, wrqu->pointer, wrqu->length))
500                 return -EFAULT;
501
502         channel = rtw_atoi(input);
503         /*DBG_871X("%s: channel=%d\n", __func__, channel);*/
504         _rtw_memset(extra, 0, wrqu->length);
505         sprintf(extra, "Change channel %d to channel %d", padapter->mppriv.channel , channel);
506         padapter->mppriv.channel = channel;
507         SetChannel(padapter);
508         pHalData->CurrentChannel = channel;
509
510         wrqu->length = strlen(extra);
511         return 0;
512 }
513
514
515 int rtw_mp_bandwidth(struct net_device *dev,
516                                          struct iw_request_info *info,
517                                          struct iw_point *wrqu, char *extra)
518 {
519         u32 bandwidth = 0, sg = 0;
520         int cur_ch_offset;
521         PADAPTER padapter = rtw_netdev_priv(dev);
522         HAL_DATA_TYPE   *pHalData       = GET_HAL_DATA(padapter);
523
524         if (sscanf(extra, "40M=%d,shortGI=%d", &bandwidth, &sg) > 0)
525                 DBG_871X("%s: bw=%d sg=%d\n", __func__, bandwidth , sg);
526
527         if (bandwidth == 1)
528                 bandwidth = CHANNEL_WIDTH_40;
529         else if (bandwidth == 2)
530                 bandwidth = CHANNEL_WIDTH_80;
531
532         padapter->mppriv.bandwidth = (u8)bandwidth;
533         padapter->mppriv.preamble = sg;
534
535         SetBandwidth(padapter);
536         pHalData->CurrentChannelBW = bandwidth;
537         /*cur_ch_offset =  rtw_get_offset_by_ch(padapter->mppriv.channel);*/
538         /*set_channel_bwmode(padapter, padapter->mppriv.channel, cur_ch_offset, bandwidth);*/
539
540         return 0;
541 }
542
543
544 int rtw_mp_txpower_index(struct net_device *dev,
545                                                  struct iw_request_info *info,
546                                                  struct iw_point *wrqu, char *extra)
547 {
548         PADAPTER padapter = rtw_netdev_priv(dev);
549         char input[wrqu->length];
550         u32 rfpath;
551         u32 txpower_inx;
552
553         if (wrqu->length > 128)
554                 return -EFAULT;
555
556         if (copy_from_user(input, wrqu->pointer, wrqu->length))
557                 return -EFAULT;
558
559         rfpath = rtw_atoi(input);
560         txpower_inx = mpt_ProQueryCalTxPower(padapter, rfpath);
561         sprintf(extra, " %d", txpower_inx);
562         wrqu->length = strlen(extra);
563
564         return 0;
565 }
566
567
568 int rtw_mp_txpower(struct net_device *dev,
569                                    struct iw_request_info *info,
570                                    struct iw_point *wrqu, char *extra)
571 {
572         u32 idx_a = 0, idx_b = 0, idx_c = 0, idx_d = 0, status = 0;
573         int MsetPower = 1;
574         u8              input[wrqu->length];
575
576         PADAPTER padapter = rtw_netdev_priv(dev);
577         PMPT_CONTEXT            pMptCtx = &(padapter->mppriv.MptCtx);
578
579         if (copy_from_user(input, wrqu->pointer, wrqu->length))
580                 return -EFAULT;
581
582         MsetPower = strncmp(input, "off", 3);
583         if (MsetPower == 0) {
584                 padapter->mppriv.bSetTxPower = 0;
585                 sprintf(extra, "MP Set power off");
586         } else {
587                 if (sscanf(input, "patha=%d,pathb=%d,pathc=%d,pathd=%d", &idx_a, &idx_b, &idx_c, &idx_d) < 3)
588                         DBG_871X("Invalid format on line %s ,patha=%d,pathb=%d,pathc=%d,pathd=%d\n", input , idx_a , idx_b , idx_c , idx_d);
589
590                 sprintf(extra, "Set power level path_A:%d path_B:%d path_C:%d path_D:%d", idx_a , idx_b , idx_c , idx_d);
591                 padapter->mppriv.txpoweridx = (u8)idx_a;
592
593                 pMptCtx->TxPwrLevel[ODM_RF_PATH_A] = (u8)idx_a;
594                 pMptCtx->TxPwrLevel[ODM_RF_PATH_B] = (u8)idx_b;
595                 pMptCtx->TxPwrLevel[ODM_RF_PATH_C] = (u8)idx_c;
596                 pMptCtx->TxPwrLevel[ODM_RF_PATH_D]  = (u8)idx_d;
597                 padapter->mppriv.bSetTxPower = 1;
598
599                 SetTxPower(padapter);
600         }
601
602         wrqu->length = strlen(extra);
603         return 0;
604 }
605
606
607 int rtw_mp_ant_tx(struct net_device *dev,
608                                   struct iw_request_info *info,
609                                   struct iw_point *wrqu, char *extra)
610 {
611         u8 i;
612         u8              input[wrqu->length];
613         u16 antenna = 0;
614         PADAPTER padapter = rtw_netdev_priv(dev);
615         HAL_DATA_TYPE   *pHalData = GET_HAL_DATA(padapter);
616
617         if (copy_from_user(input, wrqu->pointer, wrqu->length))
618                 return -EFAULT;
619
620         sprintf(extra, "switch Tx antenna to %s", input);
621
622         for (i = 0; i < strlen(input); i++) {
623                 switch (input[i]) {
624                 case 'a':
625                         antenna |= ANTENNA_A;
626                         break;
627                 case 'b':
628                         antenna |= ANTENNA_B;
629                         break;
630                 case 'c':
631                         antenna |= ANTENNA_C;
632                         break;
633                 case 'd':
634                         antenna |= ANTENNA_D;
635                         break;
636                 }
637         }
638         /*antenna |= BIT(extra[i]-'a');*/
639         DBG_871X("%s: antenna=0x%x\n", __func__, antenna);
640         padapter->mppriv.antenna_tx = antenna;
641         padapter->mppriv.antenna_rx = antenna;
642         /*DBG_871X("%s:mppriv.antenna_rx=%d\n", __func__, padapter->mppriv.antenna_tx);*/
643         pHalData->AntennaTxPath = antenna;
644
645         SetAntenna(padapter);
646
647         wrqu->length = strlen(extra);
648         return 0;
649 }
650
651
652 int rtw_mp_ant_rx(struct net_device *dev,
653                                   struct iw_request_info *info,
654                                   struct iw_point *wrqu, char *extra)
655 {
656         u8 i;
657         u16 antenna = 0;
658         u8              input[wrqu->length];
659         PADAPTER padapter = rtw_netdev_priv(dev);
660         HAL_DATA_TYPE   *pHalData = GET_HAL_DATA(padapter);
661
662         if (copy_from_user(input, wrqu->pointer, wrqu->length))
663                 return -EFAULT;
664         /*DBG_871X("%s: input=%s\n", __func__, input);*/
665         _rtw_memset(extra, 0, wrqu->length);
666
667         sprintf(extra, "switch Rx antenna to %s", input);
668
669         for (i = 0; i < strlen(input); i++) {
670                 switch (input[i]) {
671                 case 'a':
672                         antenna |= ANTENNA_A;
673                         break;
674                 case 'b':
675                         antenna |= ANTENNA_B;
676                         break;
677                 case 'c':
678                         antenna |= ANTENNA_C;
679                         break;
680                 case 'd':
681                         antenna |= ANTENNA_D;
682                         break;
683                 }
684         }
685
686         DBG_871X("%s: antenna=0x%x\n", __func__, antenna);
687         padapter->mppriv.antenna_tx = antenna;
688         padapter->mppriv.antenna_rx = antenna;
689         pHalData->AntennaRxPath = antenna;
690         /*DBG_871X("%s:mppriv.antenna_rx=%d\n", __func__, padapter->mppriv.antenna_rx);*/
691         SetAntenna(padapter);
692         wrqu->length = strlen(extra);
693
694         return 0;
695 }
696
697
698 int rtw_set_ctx_destAddr(struct net_device *dev,
699                                                  struct iw_request_info *info,
700                                                  struct iw_point *wrqu, char *extra)
701 {
702         int jj, kk = 0;
703
704         struct pkt_attrib *pattrib;
705         struct mp_priv *pmp_priv;
706         PADAPTER padapter = rtw_netdev_priv(dev);
707         
708         pmp_priv = &padapter->mppriv;
709         pattrib = &pmp_priv->tx.attrib;
710
711         if (strlen(extra) < 5)
712                 return _FAIL;
713
714         DBG_871X("%s: in=%s\n", __func__, extra);
715         for (jj = 0, kk = 0; jj < ETH_ALEN; jj++, kk += 3)
716                 pattrib->dst[jj] = key_2char2num(extra[kk], extra[kk + 1]);
717
718         DBG_871X("pattrib->dst:%x %x %x %x %x %x\n", pattrib->dst[0], pattrib->dst[1], pattrib->dst[2], pattrib->dst[3], pattrib->dst[4], pattrib->dst[5]);
719         return 0;
720 }
721
722
723
724 int rtw_mp_ctx(struct net_device *dev,
725                            struct iw_request_info *info,
726                            struct iw_point *wrqu, char *extra)
727 {
728         u32 pkTx = 1;
729         int countPkTx = 1, cotuTx = 1, CarrSprTx = 1, scTx = 1, sgleTx = 1, stop = 1;
730         u32 bStartTest = 1;
731         u32 count = 0, pktinterval = 0, pktlen = 0;
732         u8 status;
733         struct mp_priv *pmp_priv;
734         struct pkt_attrib *pattrib;
735         PADAPTER padapter = rtw_netdev_priv(dev);
736         HAL_DATA_TYPE   *pHalData = GET_HAL_DATA(padapter);
737
738         pmp_priv = &padapter->mppriv;
739         pattrib = &pmp_priv->tx.attrib;
740
741         if (copy_from_user(extra, wrqu->pointer, wrqu->length))
742                 return -EFAULT;
743
744         DBG_871X("%s: in=%s\n", __func__, extra);
745 #ifdef CONFIG_CONCURRENT_MODE
746         if (padapter->adapter_type == SECONDARY_ADAPTER) {
747                 sprintf(extra, "Error: MP mode can't support Virtual Adapter, Please to use main Adapter.\n");
748                 wrqu->length = strlen(extra);
749                 return 0;
750         }
751 #endif
752         countPkTx = strncmp(extra, "count=", 5); /* strncmp TRUE is 0*/
753         cotuTx = strncmp(extra, "background", 20);
754         CarrSprTx = strncmp(extra, "background,cs", 20);
755         scTx = strncmp(extra, "background,sc", 20);
756         sgleTx = strncmp(extra, "background,stone", 20);
757         pkTx = strncmp(extra, "background,pkt", 20);
758         stop = strncmp(extra, "stop", 4);
759         if (sscanf(extra, "count=%d,pkt", &count) > 0)
760                 DBG_871X("count= %d\n", count);
761         if (sscanf(extra, "pktinterval=%d", &pktinterval) > 0)
762                 DBG_871X("pktinterval= %d\n", pktinterval);
763
764         if (sscanf(extra, "pktlen=%d", &pktlen) > 0)
765                 DBG_871X("pktlen= %d\n", pktlen);
766
767         if (_rtw_memcmp(extra, "destmac=", 8)) {
768                 wrqu->length -= 8;
769                 rtw_set_ctx_destAddr(dev, info, wrqu, &extra[8]);
770                 sprintf(extra, "Set dest mac OK !\n");
771                 return 0;
772         }
773
774         /*DBG_871X("%s: count=%d countPkTx=%d cotuTx=%d CarrSprTx=%d scTx=%d sgleTx=%d pkTx=%d stop=%d\n", __func__, count, countPkTx, cotuTx, CarrSprTx, pkTx, sgleTx, scTx, stop);*/
775         _rtw_memset(extra, '\0', strlen(extra));
776
777         if (pktinterval != 0) {
778                 sprintf(extra, "Pkt Interval = %d", pktinterval);
779                 padapter->mppriv.pktInterval = pktinterval;
780                 wrqu->length = strlen(extra);
781                 return 0;
782         }
783         if (pktlen != 0) {
784                 sprintf(extra, "Pkt len = %d", pktlen);
785                 pattrib->pktlen = pktlen;
786                 wrqu->length = strlen(extra);
787                 return 0;
788         }
789         if (stop == 0) {
790                 bStartTest = 0; /* To set Stop*/
791                 pmp_priv->tx.stop = 1;
792                 sprintf(extra, "Stop continuous Tx");
793                 ODM_Write_DIG(&pHalData->odmpriv, 0x20);
794         } else {
795                 bStartTest = 1;
796                 ODM_Write_DIG(&pHalData->odmpriv, 0x7f);
797                 if (pmp_priv->mode != MP_ON) {
798                         if (pmp_priv->tx.stop != 1) {
799                                 DBG_871X("%s: MP_MODE != ON %d\n", __func__, pmp_priv->mode);
800                                 return  -EFAULT;
801                         }
802                 }
803         }
804
805         pmp_priv->tx.count = count;
806
807         if (pkTx == 0 || countPkTx == 0)
808                 pmp_priv->mode = MP_PACKET_TX;
809         if (sgleTx == 0)
810                 pmp_priv->mode = MP_SINGLE_TONE_TX;
811         if (cotuTx == 0)
812                 pmp_priv->mode = MP_CONTINUOUS_TX;
813         if (CarrSprTx == 0)
814                 pmp_priv->mode = MP_CARRIER_SUPPRISSION_TX;
815         if (scTx == 0)
816                 pmp_priv->mode = MP_SINGLE_CARRIER_TX;
817
818         status = rtw_mp_pretx_proc(padapter, bStartTest, extra);
819
820         wrqu->length = strlen(extra);
821         return status;
822 }
823
824
825
826 int rtw_mp_disable_bt_coexist(struct net_device *dev,
827                                                           struct iw_request_info *info,
828                                                           union iwreq_data *wrqu, char *extra)
829 {
830         PADAPTER padapter = (PADAPTER)rtw_netdev_priv(dev);
831         HAL_DATA_TYPE   *pHalData = GET_HAL_DATA(padapter);
832         struct hal_ops *pHalFunc = &padapter->HalFunc;
833
834         u8 input[wrqu->data.length];
835         u32 bt_coexist;
836
837         if (copy_from_user(input, wrqu->data.pointer, wrqu->data.length))
838                 return -EFAULT;
839
840         bt_coexist = rtw_atoi(input);
841
842         if (bt_coexist == 0) {
843                 RT_TRACE(_module_mp_, _drv_info_,
844                                  ("Set OID_RT_SET_DISABLE_BT_COEXIST: disable BT_COEXIST\n"));
845                 DBG_871X("Set OID_RT_SET_DISABLE_BT_COEXIST: disable BT_COEXIST\n");
846 #ifdef CONFIG_BT_COEXIST
847                 rtw_btcoex_HaltNotify(padapter);
848                 rtw_btcoex_SetManualControl(padapter, _TRUE);
849                 /* Force to switch Antenna to WiFi*/
850                 rtw_write16(padapter, 0x870, 0x300);
851                 rtw_write16(padapter, 0x860, 0x110);
852 #endif 
853                 /* CONFIG_BT_COEXIST */
854         } else {
855                 RT_TRACE(_module_mp_, _drv_info_,
856                                  ("Set OID_RT_SET_DISABLE_BT_COEXIST: enable BT_COEXIST\n"));
857 #ifdef CONFIG_BT_COEXIST
858                 rtw_btcoex_SetManualControl(padapter, _FALSE);
859 #endif
860         }
861
862         return 0;
863 }
864
865
866 int rtw_mp_arx(struct net_device *dev,
867                            struct iw_request_info *info,
868                            struct iw_point *wrqu, char *extra)
869 {
870         int bStartRx = 0, bStopRx = 0, bQueryPhy = 0, bQueryMac = 0, bSetBssid = 0;
871         int bmac_filter = 0, bfilter_init = 0, bmon = 0, bSmpCfg = 0;
872         u8              input[wrqu->length];
873         char *pch, *ptmp, *token, *tmp[2] = {0x00, 0x00};
874         u32 i = 0, ii = 0, jj = 0, kk = 0, cnts = 0, ret;
875         PADAPTER padapter = rtw_netdev_priv(dev);
876         struct mp_priv *pmppriv = &padapter->mppriv;
877         struct dbg_rx_counter rx_counter;
878
879         if (copy_from_user(input, wrqu->pointer, wrqu->length))
880                 return -EFAULT;
881
882         DBG_871X("%s: %s\n", __func__, input);
883 #ifdef CONFIG_CONCURRENT_MODE
884         if (padapter->adapter_type == SECONDARY_ADAPTER) {
885                 sprintf(extra, "Error: MP mode can't support Virtual Adapter, Please to use main Adapter.\n");
886                 wrqu->length = strlen(extra);
887                 return 0;
888         }
889 #endif
890         bStartRx = (strncmp(input, "start", 5) == 0) ? 1 : 0; /* strncmp TRUE is 0*/
891         bStopRx = (strncmp(input, "stop", 5) == 0) ? 1 : 0; /* strncmp TRUE is 0*/
892         bQueryPhy = (strncmp(input, "phy", 3) == 0) ? 1 : 0; /* strncmp TRUE is 0*/
893         bQueryMac = (strncmp(input, "mac", 3) == 0) ? 1 : 0; /* strncmp TRUE is 0*/
894         bSetBssid = (strncmp(input, "setbssid=", 8) == 0) ? 1 : 0; /* strncmp TRUE is 0*/
895         /*bfilter_init = (strncmp(input, "filter_init",11)==0)?1:0;*/
896         bmac_filter = (strncmp(input, "accept_mac", 10) == 0) ? 1 : 0;
897         bmon = (strncmp(input, "mon=", 4) == 0) ? 1 : 0;
898         bSmpCfg = (strncmp(input , "smpcfg=" , 7) == 0) ? 1 : 0;
899
900         if (bSetBssid == 1) {
901                 pch = input;
902                 while ((token = strsep(&pch, "=")) != NULL) {
903                         if (i > 1)
904                                 break;
905                         tmp[i] = token;
906                         i++;
907                 }
908                 if ((tmp[0] != NULL) && (tmp[1] != NULL)) {
909                         cnts = strlen(tmp[1]) / 2;
910                         if (cnts < 1)
911                                 return -EFAULT;
912                         DBG_871X("%s: cnts=%d\n", __func__, cnts);
913                         DBG_871X("%s: data=%s\n", __func__, tmp[1]);
914                         for (jj = 0, kk = 0; jj < cnts ; jj++, kk += 2) {
915                                 pmppriv->network_macaddr[jj] = key_2char2num(tmp[1][kk], tmp[1][kk + 1]);
916                                 DBG_871X("network_macaddr[%d]=%x\n", jj, pmppriv->network_macaddr[jj]);
917                         } 
918                 } else
919                         return -EFAULT;
920                         
921                 pmppriv->bSetRxBssid = _TRUE;
922         }
923
924         if (bmac_filter) {
925                 pmppriv->bmac_filter = bmac_filter;
926                 pch = input;
927                 while ((token = strsep(&pch, "=")) != NULL) {
928                         if (i > 1)
929                                 break;
930                         tmp[i] = token;
931                         i++;
932                 }
933                 if ((tmp[0] != NULL) && (tmp[1] != NULL)) {
934                         cnts = strlen(tmp[1]) / 2;
935                         if (cnts < 1)
936                                 return -EFAULT;
937                         DBG_871X("%s: cnts=%d\n", __func__, cnts);
938                         DBG_871X("%s: data=%s\n", __func__, tmp[1]);
939                         for (jj = 0, kk = 0; jj < cnts ; jj++, kk += 2) {
940                                 pmppriv->mac_filter[jj] = key_2char2num(tmp[1][kk], tmp[1][kk + 1]);
941                                 DBG_871X("%s mac_filter[%d]=%x\n", __func__, jj, pmppriv->mac_filter[jj]);
942                         } 
943                 } else 
944                         return -EFAULT;
945
946         }
947
948         if (bStartRx) {
949                 sprintf(extra, "start");
950                 SetPacketRx(padapter, bStartRx, _FALSE);
951         } else if (bStopRx) {
952                 SetPacketRx(padapter, bStartRx, _FALSE);
953                 pmppriv->bmac_filter = _FALSE;
954                 sprintf(extra, "Received packet OK:%d CRC error:%d ,Filter out:%d", padapter->mppriv.rx_pktcount, padapter->mppriv.rx_crcerrpktcount, padapter->mppriv.rx_pktcount_filter_out);
955         } else if (bQueryPhy) {
956                 _rtw_memset(&rx_counter, 0, sizeof(struct dbg_rx_counter));
957                 rtw_dump_phy_rx_counters(padapter, &rx_counter);
958
959                 DBG_871X("%s: OFDM_FA =%d\n", __func__, rx_counter.rx_ofdm_fa);
960                 DBG_871X("%s: CCK_FA =%d\n", __func__, rx_counter.rx_cck_fa);
961                 sprintf(extra, "Phy Received packet OK:%d CRC error:%d FA Counter: %d", rx_counter.rx_pkt_ok, rx_counter.rx_pkt_crc_error, rx_counter.rx_cck_fa + rx_counter.rx_ofdm_fa);
962
963
964         } else if (bQueryMac) {
965                 _rtw_memset(&rx_counter, 0, sizeof(struct dbg_rx_counter));
966                 rtw_dump_mac_rx_counters(padapter, &rx_counter);
967                 sprintf(extra, "Mac Received packet OK: %d , CRC error: %d , Drop Packets: %d\n",
968                                 rx_counter.rx_pkt_ok, rx_counter.rx_pkt_crc_error, rx_counter.rx_pkt_drop);
969
970         }
971
972         if (bmon == 1) {
973                 ret = sscanf(input, "mon=%d", &bmon);
974
975                 if (bmon == 1) {
976                         pmppriv->rx_bindicatePkt = _TRUE;
977                         sprintf(extra, "Indicating Receive Packet to network start\n");
978                 } else {
979                         pmppriv->rx_bindicatePkt = _FALSE;
980                         sprintf(extra, "Indicating Receive Packet to network Stop\n");
981                 }
982         }
983         if (bSmpCfg == 1) {
984                 ret = sscanf(input, "smpcfg=%d", &bSmpCfg);
985
986                 if (bSmpCfg == 1) {
987                         pmppriv->bRTWSmbCfg = _TRUE;
988                         sprintf(extra , "Indicate By Simple Config Format\n");
989                         SetPacketRx(padapter, _TRUE, _TRUE);
990                 } else {
991                         pmppriv->bRTWSmbCfg = _FALSE;
992                         sprintf(extra , "Indicate By Normal Format\n");
993                         SetPacketRx(padapter, _TRUE, _FALSE);
994                 }
995         }
996
997         wrqu->length = strlen(extra) + 1;
998
999         return 0;
1000 }
1001
1002
1003 int rtw_mp_trx_query(struct net_device *dev,
1004                                          struct iw_request_info *info,
1005                                          struct iw_point *wrqu, char *extra)
1006 {
1007         u32 txok, txfail, rxok, rxfail, rxfilterout;
1008         PADAPTER padapter = rtw_netdev_priv(dev);
1009
1010         txok = padapter->mppriv.tx.sended;
1011         txfail = 0;
1012         rxok = padapter->mppriv.rx_pktcount;
1013         rxfail = padapter->mppriv.rx_crcerrpktcount;
1014         rxfilterout = padapter->mppriv.rx_pktcount_filter_out;
1015
1016         _rtw_memset(extra, '\0', 128);
1017
1018         sprintf(extra, "Tx OK:%d, Tx Fail:%d, Rx OK:%d, CRC error:%d ,Rx Filter out:%d\n", txok, txfail, rxok, rxfail, rxfilterout);
1019
1020         wrqu->length = strlen(extra) + 1;
1021
1022         return 0;
1023 }
1024
1025
1026 int rtw_mp_pwrtrk(struct net_device *dev,
1027                                   struct iw_request_info *info,
1028                                   struct iw_point *wrqu, char *extra)
1029 {
1030         u8 enable;
1031         u32 thermal;
1032         s32 ret;
1033         PADAPTER padapter = rtw_netdev_priv(dev);
1034         HAL_DATA_TYPE                   *pHalData = GET_HAL_DATA(padapter);
1035         u8              input[wrqu->length];
1036
1037         if (copy_from_user(input, wrqu->pointer, wrqu->length))
1038                 return -EFAULT;
1039
1040         _rtw_memset(extra, 0, wrqu->length);
1041
1042         enable = 1;
1043         if (wrqu->length > 1) {
1044                 /* not empty string*/
1045                 if (strncmp(input, "stop", 4) == 0) {
1046                         enable = 0;
1047                         sprintf(extra, "mp tx power tracking stop");
1048                 } else if (sscanf(input, "ther=%d", &thermal) == 1) {
1049                         ret = SetThermalMeter(padapter, (u8)thermal);
1050                         if (ret == _FAIL)
1051                                 return -EPERM;
1052                         sprintf(extra, "mp tx power tracking start,target value=%d ok", thermal);
1053                 } else
1054                         return -EINVAL;
1055         }
1056
1057         ret = SetPowerTracking(padapter, enable);
1058         if (ret == _FAIL)
1059                 return -EPERM;
1060
1061         wrqu->length = strlen(extra);
1062
1063         return 0;
1064 }
1065
1066
1067
1068 int rtw_mp_psd(struct net_device *dev,
1069                            struct iw_request_info *info,
1070                            struct iw_point *wrqu, char *extra)
1071 {
1072         PADAPTER padapter = rtw_netdev_priv(dev);
1073         u8              input[wrqu->length];
1074
1075         if (copy_from_user(input, wrqu->pointer, wrqu->length))
1076                 return -EFAULT;
1077
1078         strcpy(extra, input);
1079
1080         wrqu->length = mp_query_psd(padapter, extra);
1081
1082         return 0;
1083 }
1084
1085
1086 int rtw_mp_thermal(struct net_device *dev,
1087                                    struct iw_request_info *info,
1088                                    struct iw_point *wrqu, char *extra)
1089 {
1090         u8 val;
1091         int bwrite = 1;
1092
1093 #ifdef CONFIG_RTL8188E
1094         u16 addr = EEPROM_THERMAL_METER_88E;
1095 #endif
1096 #if defined(CONFIG_RTL8812A) || defined(CONFIG_RTL8821A) || defined(CONFIG_RTL8814A)
1097         u16 addr = EEPROM_THERMAL_METER_8812;
1098 #endif
1099 #ifdef CONFIG_RTL8192E
1100         u16 addr = EEPROM_THERMAL_METER_8192E;
1101 #endif
1102 #ifdef CONFIG_RTL8723B
1103         u16 addr = EEPROM_THERMAL_METER_8723B;
1104 #endif
1105 #ifdef CONFIG_RTL8703B
1106         u16 addr = EEPROM_THERMAL_METER_8703B;
1107 #endif
1108 #ifdef CONFIG_RTL8188F
1109         u16 addr = EEPROM_THERMAL_METER_8188F;
1110 #endif
1111         u16 cnt = 1;
1112         u16 max_available_size = 0;
1113         PADAPTER padapter = rtw_netdev_priv(dev);
1114
1115         if (copy_from_user(extra, wrqu->pointer, wrqu->length))
1116                 return -EFAULT;
1117
1118         bwrite = strncmp(extra, "write", 6);/* strncmp TRUE is 0*/
1119
1120         GetThermalMeter(padapter, &val);
1121
1122         if (bwrite == 0) {
1123                 /*DBG_871X("to write val:%d",val);*/
1124                 EFUSE_GetEfuseDefinition(padapter, EFUSE_WIFI, TYPE_AVAILABLE_EFUSE_BYTES_TOTAL, (PVOID)&max_available_size, _FALSE);
1125                 if (2 > max_available_size) {
1126                         DBG_871X("no available efuse!\n");
1127                         return -EFAULT;
1128                 }
1129                 if (rtw_efuse_map_write(padapter, addr, cnt, &val) == _FAIL) {
1130                         DBG_871X("rtw_efuse_map_write error\n");
1131                         return -EFAULT;
1132                 }
1133                 sprintf(extra, " efuse write ok :%d", val);
1134         } else
1135                 sprintf(extra, "%d", val);
1136         wrqu->length = strlen(extra);
1137
1138         return 0;
1139 }
1140
1141
1142
1143 int rtw_mp_reset_stats(struct net_device *dev,
1144                                            struct iw_request_info *info,
1145                                            struct iw_point *wrqu, char *extra)
1146 {
1147         struct mp_priv *pmp_priv;
1148         struct pkt_attrib *pattrib;
1149         PADAPTER padapter = rtw_netdev_priv(dev);
1150
1151         pmp_priv = &padapter->mppriv;
1152
1153         pmp_priv->tx.sended = 0;
1154         pmp_priv->tx_pktcount = 0;
1155         pmp_priv->rx_pktcount = 0;
1156         pmp_priv->rx_pktcount_filter_out = 0;
1157         pmp_priv->rx_crcerrpktcount = 0;
1158
1159         rtw_reset_phy_rx_counters(padapter);
1160         rtw_reset_mac_rx_counters(padapter);
1161
1162         return 0;
1163 }
1164
1165
1166 int rtw_mp_dump(struct net_device *dev,
1167                                 struct iw_request_info *info,
1168                                 struct iw_point *wrqu, char *extra)
1169 {
1170         struct mp_priv *pmp_priv;
1171         struct pkt_attrib *pattrib;
1172         u32 value;
1173         u8              input[wrqu->length];
1174         u8 rf_type, path_nums = 0;
1175         u32 i, j = 1, path;
1176         PADAPTER padapter = rtw_netdev_priv(dev);
1177
1178         pmp_priv = &padapter->mppriv;
1179
1180         if (copy_from_user(input, wrqu->pointer, wrqu->length))
1181                 return -EFAULT;
1182
1183         if (strncmp(input, "all", 4) == 0) {
1184                 mac_reg_dump(RTW_DBGDUMP, padapter);
1185                 bb_reg_dump(RTW_DBGDUMP, padapter);
1186                 rf_reg_dump(RTW_DBGDUMP, padapter);
1187         }
1188         return 0;
1189 }
1190
1191
1192 int rtw_mp_phypara(struct net_device *dev,
1193                                    struct iw_request_info *info,
1194                                    struct iw_point *wrqu, char *extra)
1195 {
1196
1197         PADAPTER padapter = rtw_netdev_priv(dev);
1198         HAL_DATA_TYPE   *pHalData       = GET_HAL_DATA(padapter);
1199         char    input[wrqu->length];
1200         u32             valxcap, ret;
1201
1202         if (copy_from_user(input, wrqu->pointer, wrqu->length))
1203                 return -EFAULT;
1204
1205         DBG_871X("%s:iwpriv in=%s\n", __func__, input);
1206
1207         ret = sscanf(input, "xcap=%d", &valxcap);
1208
1209         pHalData->CrystalCap = (u8)valxcap;
1210         hal_set_crystal_cap(padapter , valxcap);
1211
1212         sprintf(extra, "Set xcap=%d", valxcap);
1213         wrqu->length = strlen(extra) + 1;
1214
1215         return 0;
1216
1217 }
1218
1219
1220 int rtw_mp_SetRFPath(struct net_device *dev,
1221                                          struct iw_request_info *info,
1222                                          union iwreq_data *wrqu, char *extra)
1223 {
1224         PADAPTER padapter = rtw_netdev_priv(dev);
1225         char    input[wrqu->data.length];
1226         int             bMain = 1, bTurnoff = 1;
1227
1228         if (copy_from_user(input, wrqu->data.pointer, wrqu->data.length))
1229                 return -EFAULT;
1230         DBG_871X("%s:iwpriv in=%s\n", __func__, input);
1231
1232         bMain = strncmp(input, "1", 2); /* strncmp TRUE is 0*/
1233         bTurnoff = strncmp(input, "0", 3); /* strncmp TRUE is 0*/
1234
1235         if (bMain == 0) {
1236                 MP_PHY_SetRFPathSwitch(padapter, _TRUE);
1237                 DBG_871X("%s:PHY_SetRFPathSwitch=TRUE\n", __func__);
1238         } else if (bTurnoff == 0) {
1239                 MP_PHY_SetRFPathSwitch(padapter, _FALSE);
1240                 DBG_871X("%s:PHY_SetRFPathSwitch=FALSE\n", __func__);
1241         }
1242
1243         return 0;
1244 }
1245
1246
1247 int rtw_mp_QueryDrv(struct net_device *dev,
1248                                         struct iw_request_info *info,
1249                                         union iwreq_data *wrqu, char *extra)
1250 {
1251         PADAPTER padapter = rtw_netdev_priv(dev);
1252         char    input[wrqu->data.length];
1253         int     qAutoLoad = 1;
1254
1255         PHAL_DATA_TYPE pHalData = GET_HAL_DATA(padapter);
1256
1257         if (copy_from_user(input, wrqu->data.pointer, wrqu->data.length))
1258                 return -EFAULT;
1259         DBG_871X("%s:iwpriv in=%s\n", __func__, input);
1260
1261         qAutoLoad = strncmp(input, "autoload", 8); /* strncmp TRUE is 0*/
1262
1263         if (qAutoLoad == 0) {
1264                 DBG_871X("%s:qAutoLoad\n", __func__);
1265
1266                 if (pHalData->bautoload_fail_flag)
1267                         sprintf(extra, "fail");
1268                 else
1269                         sprintf(extra, "ok");
1270         }
1271         wrqu->data.length = strlen(extra) + 1;
1272         return 0;
1273 }
1274
1275
1276 int rtw_mp_PwrCtlDM(struct net_device *dev,
1277                                         struct iw_request_info *info,
1278                                         struct iw_point *wrqu, char *extra)
1279 {
1280         PADAPTER padapter = rtw_netdev_priv(dev);
1281         u8              input[wrqu->length];
1282         int             bstart = 1;
1283
1284         if (copy_from_user(input, wrqu->pointer, wrqu->length))
1285                 return -EFAULT;
1286
1287         bstart = strncmp(input, "start", 5); /* strncmp TRUE is 0*/
1288         if (bstart == 0) {
1289                 sprintf(extra, "PwrCtlDM start\n");
1290                 MPT_PwrCtlDM(padapter, 1);
1291         } else {
1292                 sprintf(extra, "PwrCtlDM stop\n");
1293                 MPT_PwrCtlDM(padapter, 0);
1294         }
1295         wrqu->length = strlen(extra);
1296
1297         return 0;
1298 }
1299
1300
1301 int rtw_mp_getver(struct net_device *dev,
1302                                   struct iw_request_info *info,
1303                                   union iwreq_data *wrqu, char *extra)
1304 {
1305         PADAPTER padapter = rtw_netdev_priv(dev);
1306         struct mp_priv *pmp_priv;
1307
1308         pmp_priv = &padapter->mppriv;
1309
1310         if (copy_from_user(extra, wrqu->data.pointer, wrqu->data.length))
1311                 return -EFAULT;
1312
1313         sprintf(extra, "rtwpriv=%d\n", RTWPRIV_VER_INFO);
1314         wrqu->data.length = strlen(extra);
1315         return 0;
1316 }
1317
1318
1319 int rtw_mp_mon(struct net_device *dev,
1320                            struct iw_request_info *info,
1321                            union iwreq_data *wrqu, char *extra)
1322 {
1323         PADAPTER padapter = rtw_netdev_priv(dev);
1324         struct mp_priv *pmp_priv = &padapter->mppriv;
1325         struct mlme_priv *pmlmepriv = &padapter->mlmepriv;
1326         struct hal_ops *pHalFunc = &padapter->HalFunc;
1327         NDIS_802_11_NETWORK_INFRASTRUCTURE networkType;
1328         int bstart = 1, bstop = 1;
1329         
1330         networkType = Ndis802_11Infrastructure;
1331         if (copy_from_user(extra, wrqu->data.pointer, wrqu->data.length))
1332                 return -EFAULT;
1333
1334         rtw_pm_set_ips(padapter, IPS_NONE);
1335         LeaveAllPowerSaveMode(padapter);
1336
1337 #ifdef CONFIG_MP_INCLUDED
1338         if (init_mp_priv(padapter) == _FAIL)
1339                 DBG_871X("%s: initialize MP private data Fail!\n", __func__);
1340         padapter->mppriv.channel = 6;
1341
1342         bstart = strncmp(extra, "start", 5); /* strncmp TRUE is 0*/
1343         bstop = strncmp(extra, "stop", 4); /* strncmp TRUE is 0*/
1344         if (bstart == 0) {
1345                 mp_join(padapter, WIFI_FW_ADHOC_STATE);
1346                 SetPacketRx(padapter, _TRUE, _FALSE);
1347                 SetChannel(padapter);
1348                 pmp_priv->rx_bindicatePkt = _TRUE;
1349                 pmp_priv->bRTWSmbCfg = _TRUE;
1350                 sprintf(extra, "monitor mode start\n");
1351         } else if (bstop == 0) {
1352                 SetPacketRx(padapter, _FALSE, _FALSE);
1353                 pmp_priv->rx_bindicatePkt = _FALSE;
1354                 pmp_priv->bRTWSmbCfg = _FALSE;
1355                 padapter->registrypriv.mp_mode = 1;
1356                 pHalFunc->hal_deinit(padapter);
1357                 padapter->registrypriv.mp_mode = 0;
1358                 pHalFunc->hal_init(padapter);
1359                 /*rtw_disassoc_cmd(padapter, 0, _TRUE);*/
1360                 if (check_fwstate(pmlmepriv, _FW_LINKED) == _TRUE) {
1361                         rtw_disassoc_cmd(padapter, 500, _TRUE);
1362                         rtw_indicate_disconnect(padapter, 0, _FALSE);
1363                         /*rtw_free_assoc_resources(padapter, 1);*/
1364                 }
1365                 rtw_pm_set_ips(padapter, IPS_NORMAL);
1366                 sprintf(extra, "monitor mode Stop\n");
1367         }
1368 #endif
1369         wrqu->data.length = strlen(extra);
1370         return 0;
1371 }
1372
1373 int rtw_mp_pretx_proc(PADAPTER padapter, u8 bStartTest, char *extra)
1374 {
1375         HAL_DATA_TYPE   *pHalData       = GET_HAL_DATA(padapter);
1376         struct mp_priv *pmp_priv = &padapter->mppriv;
1377         PMPT_CONTEXT            pMptCtx = &(padapter->mppriv.MptCtx);
1378
1379                 switch (pmp_priv->mode) {
1380
1381                 case MP_PACKET_TX:
1382                                                 if (bStartTest == 0) {
1383                                                         pmp_priv->tx.stop = 1;
1384                                                         pmp_priv->mode = MP_ON;
1385                                                         sprintf(extra, "Stop continuous Tx");
1386                                                 } else if (pmp_priv->tx.stop == 1) {
1387                                                         sprintf(extra, "%s\nStart continuous DA=ffffffffffff len=1500 count=%u\n", extra, pmp_priv->tx.count);
1388                                                         pmp_priv->tx.stop = 0;
1389                                                         SetPacketTx(padapter);
1390                                                 } else {
1391                                                         return -EFAULT;
1392                                                 }
1393                                                 return 0;
1394                 case MP_SINGLE_TONE_TX:
1395                                                 if (bStartTest != 0)
1396                                                         sprintf(extra, "%s\nStart continuous DA=ffffffffffff len=1500\n infinite=yes.", extra);
1397                                                 SetSingleToneTx(padapter, (u8)bStartTest);
1398                                                 break;
1399                 case MP_CONTINUOUS_TX:
1400                                                 if (bStartTest != 0)
1401                                                         sprintf(extra, "%s\nStart continuous DA=ffffffffffff len=1500\n infinite=yes.", extra);
1402                                                 SetContinuousTx(padapter, (u8)bStartTest);
1403                                                 break;
1404                 case MP_CARRIER_SUPPRISSION_TX:
1405                                                 if (bStartTest != 0) {
1406                                                         if (HwRateToMPTRate(pmp_priv->rateidx) <= MPT_RATE_11M)
1407                                                                 sprintf(extra, "%s\nStart continuous DA=ffffffffffff len=1500\n infinite=yes.", extra);
1408                                                         else
1409                                                                 sprintf(extra, "%s\nSpecify carrier suppression but not CCK rate", extra);
1410                                                 }
1411                                                 SetCarrierSuppressionTx(padapter, (u8)bStartTest);
1412                                                 break;
1413                 case MP_SINGLE_CARRIER_TX:
1414                                         if (bStartTest != 0)
1415                                                         sprintf(extra, "%s\nStart continuous DA=ffffffffffff len=1500\n infinite=yes.", extra);
1416                                                 SetSingleCarrierTx(padapter, (u8)bStartTest);
1417                                                 break;
1418
1419                 default:
1420                                                 sprintf(extra, "Error! Continuous-Tx is not on-going.");
1421                                                 return -EFAULT;
1422                 }
1423
1424                 if (bStartTest == 1 && pmp_priv->mode != MP_ON) {
1425                         struct mp_priv *pmp_priv = &padapter->mppriv;
1426
1427                         if (pmp_priv->tx.stop == 0) {
1428                                 pmp_priv->tx.stop = 1;
1429                                 rtw_msleep_os(5);
1430                         }
1431 #ifdef CONFIG_80211N_HT
1432                         pmp_priv->tx.attrib.ht_en = 1;
1433 #endif
1434                         pmp_priv->tx.stop = 0;
1435                         pmp_priv->tx.count = 1;
1436                         SetPacketTx(padapter);
1437                 } else
1438                         pmp_priv->mode = MP_ON;
1439
1440 #if defined(CONFIG_RTL8812A)
1441                         if (IS_HARDWARE_TYPE_8812AU(padapter)) {
1442                                 /* <20130425, Kordan> Turn off OFDM Rx to prevent from CCA causing Tx hang.*/
1443                                 if (pmp_priv->mode == MP_PACKET_TX)
1444                                         PHY_SetBBReg(padapter, rCCAonSec_Jaguar, BIT3, 1);
1445                                 else
1446                                         PHY_SetBBReg(padapter, rCCAonSec_Jaguar, BIT3, 0);
1447                         }
1448 #endif
1449
1450         return 0;
1451 }
1452
1453
1454 int rtw_mp_tx(struct net_device *dev,
1455                            struct iw_request_info *info,
1456                            union iwreq_data *wrqu, char *extra)
1457 {
1458                 PADAPTER padapter = rtw_netdev_priv(dev);
1459                 HAL_DATA_TYPE   *pHalData       = GET_HAL_DATA(padapter);
1460                 struct mp_priv *pmp_priv = &padapter->mppriv;
1461                 PMPT_CONTEXT            pMptCtx = &(padapter->mppriv.MptCtx);
1462                 struct registry_priv    *pregistrypriv = &padapter->registrypriv;
1463
1464                 u32 bandwidth = 0, sg = 0, channel = 6, txpower = 40, rate = 108, ant = 0, txmode = 1, count = 0;
1465                 u8 i = 0, j = 0, bStartTest = 1, status = 0, Idx = 0, tmpU1B = 0;
1466                 u16 antenna = 0;
1467
1468                 if (copy_from_user(extra, wrqu->data.pointer, wrqu->data.length))
1469                         return -EFAULT;
1470                 DBG_871X("extra = %s\n", extra);
1471 #ifdef CONFIG_CONCURRENT_MODE
1472                         if (padapter->adapter_type == SECONDARY_ADAPTER) {
1473                                 sprintf(extra, "Error: MP mode can't support Virtual Adapter, Please to use main Adapter.\n");
1474                                 wrqu->data.length = strlen(extra);
1475                                 return 0;
1476                         }
1477 #endif
1478
1479                 if (strncmp(extra, "stop", 3) == 0) {
1480                         bStartTest = 0; /* To set Stop*/
1481                         pmp_priv->tx.stop = 1;
1482                         sprintf(extra, "Stop continuous Tx");
1483                         status = rtw_mp_pretx_proc(padapter, bStartTest, extra);
1484                         wrqu->data.length = strlen(extra);
1485                         return status;
1486                 } else if (strncmp(extra, "count", 5) == 0) {
1487                                 if (sscanf(extra, "count=%d", &count) < 1)
1488                                         DBG_871X("Got Count=%d]\n", count);
1489                                 pmp_priv->tx.count = count;
1490                                 return 0;
1491                 } else if (strncmp(extra, "setting", 7) == 0) {
1492                                 _rtw_memset(extra, 0, wrqu->data.length);
1493                                 sprintf(extra, "Current Setting :\n Channel:%d", pmp_priv->channel);
1494                                 sprintf(extra, "%s\n Bandwidth:%d", extra, pmp_priv->bandwidth);
1495                                 sprintf(extra, "%s\n Rate index:%d", extra, pmp_priv->rateidx);
1496                                 sprintf(extra, "%s\n TxPower index:%d", extra, pmp_priv->txpoweridx);
1497                                 sprintf(extra, "%s\n Antenna TxPath:%d", extra, pmp_priv->antenna_tx);
1498                                 sprintf(extra, "%s\n Antenna RxPath:%d", extra, pmp_priv->antenna_rx);
1499                                 sprintf(extra, "%s\n MP Mode:%d", extra, pmp_priv->mode);
1500                                 wrqu->data.length = strlen(extra);
1501                                 return 0;
1502 #ifdef CONFIG_MP_VHT_HW_TX_MODE
1503                 } else if (strncmp(extra, "pmact", 5) == 0) {
1504                                 if (strncmp(extra, "pmact=", 6) == 0) {
1505                                         _rtw_memset(&pMptCtx->PMacTxInfo, 0, sizeof(pMptCtx->PMacTxInfo));
1506                                         if (strncmp(extra, "pmact=start", 11) == 0) {
1507                                                 pMptCtx->PMacTxInfo.bEnPMacTx = _TRUE;
1508                                         } else {
1509                                                 pMptCtx->PMacTxInfo.bEnPMacTx = _FALSE;
1510                                                 sprintf(extra, "Set PMac Tx Mode Stop\n");
1511                                         }
1512                                         if (pMptCtx->bldpc == TRUE)
1513                                                 pMptCtx->PMacTxInfo.bLDPC = _TRUE;
1514
1515                                         if (pMptCtx->bstbc == TRUE)
1516                                                 pMptCtx->PMacTxInfo.bSTBC = _TRUE;
1517
1518                                         pMptCtx->PMacTxInfo.bSPreamble = pmp_priv->preamble;
1519                                         pMptCtx->PMacTxInfo.bSGI = pmp_priv->preamble;
1520                                         pMptCtx->PMacTxInfo.BandWidth = pmp_priv->bandwidth;
1521                                         pMptCtx->PMacTxInfo.TX_RATE = HwRateToMPTRate(pmp_priv->rateidx);
1522
1523                                         pMptCtx->PMacTxInfo.Mode = pMptCtx->HWTxmode;
1524
1525                                         pMptCtx->PMacTxInfo.NDP_sound = FALSE;/*(Adapter.PacketType == NDP_PKT)?TRUE:FALSE;*/
1526
1527                                         if (padapter->mppriv.pktInterval == 0)
1528                                                 pMptCtx->PMacTxInfo.PacketPeriod = 100;
1529                                         else
1530                                                 pMptCtx->PMacTxInfo.PacketPeriod = padapter->mppriv.pktInterval;
1531
1532                                         if (padapter->mppriv.pktLength < 1000)
1533                                                 pMptCtx->PMacTxInfo.PacketLength = 1000;
1534                                         else
1535                                                 pMptCtx->PMacTxInfo.PacketLength = padapter->mppriv.pktLength;
1536
1537                                         pMptCtx->PMacTxInfo.PacketPattern  = rtw_random32() % 0xFF;
1538
1539                                         if (padapter->mppriv.tx_pktcount != 0)
1540                                                 pMptCtx->PMacTxInfo.PacketCount = padapter->mppriv.tx_pktcount;
1541
1542                                         pMptCtx->PMacTxInfo.Ntx = 0;
1543                                         for (Idx = 16; Idx < 20; Idx++) {
1544                                                 tmpU1B = (padapter->mppriv.antenna_tx >> Idx) & 1;
1545                                                 if (tmpU1B)
1546                                                         pMptCtx->PMacTxInfo.Ntx++;
1547                                         }
1548
1549                                         _rtw_memset(pMptCtx->PMacTxInfo.MacAddress, 0xFF, ETH_ALEN);
1550
1551                                         PMAC_Get_Pkt_Param(&pMptCtx->PMacTxInfo, &pMptCtx->PMacPktInfo);
1552
1553                                         if (MPT_IS_CCK_RATE(pMptCtx->PMacTxInfo.TX_RATE)) {
1554
1555                                                 CCK_generator(&pMptCtx->PMacTxInfo, &pMptCtx->PMacPktInfo);
1556                                         } else {
1557                                                 PMAC_Nsym_generator(&pMptCtx->PMacTxInfo, &pMptCtx->PMacPktInfo);
1558                                                 /* 24 BIT*/
1559                                                 L_SIG_generator(pMptCtx->PMacPktInfo.N_sym, &pMptCtx->PMacTxInfo, &pMptCtx->PMacPktInfo);
1560                                         }
1561                                         /*      48BIT*/
1562                                         if (MPT_IS_HT_RATE(pMptCtx->PMacTxInfo.TX_RATE))
1563                                                 HT_SIG_generator(&pMptCtx->PMacTxInfo, &pMptCtx->PMacPktInfo);
1564                                         else if (MPT_IS_VHT_RATE(pMptCtx->PMacTxInfo.TX_RATE)) {
1565                                                 /*      48BIT*/
1566                                                 VHT_SIG_A_generator(&pMptCtx->PMacTxInfo, &pMptCtx->PMacPktInfo);
1567
1568                                                 /*      26/27/29 BIT  & CRC 8 BIT*/
1569                                                 VHT_SIG_B_generator(&pMptCtx->PMacTxInfo);
1570
1571                                                 /* 32 BIT*/
1572                                                 VHT_Delimiter_generator(&pMptCtx->PMacTxInfo);
1573                                         }
1574
1575                                         mpt_ProSetPMacTx(padapter);
1576                                         sprintf(extra, "Set PMac Tx Mode start\n");
1577
1578                                 } else if (strncmp(extra, "pmact,mode=", 11) == 0) {
1579                                                 int txmode = 0;
1580
1581                                                 if (sscanf(extra, "pmact,mode=%d", &txmode) > 0) {
1582                                                         if (txmode == 1) {
1583                                                                 pMptCtx->HWTxmode = CONTINUOUS_TX;
1584                                                                 sprintf(extra, "\t Config HW Tx mode = CONTINUOUS_TX\n");
1585                                                         } else if (txmode == 2) {
1586                                                                 pMptCtx->HWTxmode = OFDM_Single_Tone_TX;
1587                                                                 sprintf(extra, "\t Config HW Tx mode = OFDM_Single_Tone_TX\n");
1588                                                         } else {
1589                                                                 pMptCtx->HWTxmode = PACKETS_TX;
1590                                                                 sprintf(extra, "\t Config HW Tx mode = PACKETS_TX\n");
1591                                                         }
1592                                                 } else {
1593                                                         pMptCtx->HWTxmode = PACKETS_TX;
1594                                                         sprintf(extra, "\t Config HW Tx mode=\n 0 = PACKETS_TX\n 1 = CONTINUOUS_TX\n 2 = OFDM_Single_Tone_TX");
1595                                                 }
1596                                 } else if (strncmp(extra, "pmact,", 6) == 0) {
1597                                         int PacketPeriod = 0, PacketLength = 0, PacketCout = 0;
1598                                         int bldpc = 0, bstbc = 0;
1599
1600                                         if (sscanf(extra, "pmact,period=%d", &PacketPeriod) > 0) {
1601                                                         padapter->mppriv.pktInterval = PacketPeriod;
1602                                                         DBG_871X("PacketPeriod=%d\n", padapter->mppriv.pktInterval);
1603                                                         sprintf(extra, "PacketPeriod [1~255]= %d\n", padapter->mppriv.pktInterval);
1604
1605                                         } else if (sscanf(extra, "pmact,length=%d", &PacketLength) > 0) {
1606                                                         padapter->mppriv.pktLength = PacketLength;
1607                                                         DBG_871X("PacketPeriod=%d\n", padapter->mppriv.pktLength);
1608                                                         sprintf(extra, "PacketLength[~65535]=%d\n", padapter->mppriv.pktLength);
1609
1610                                         } else if (sscanf(extra, "pmact,count=%d", &PacketCout) > 0) {
1611                                                         padapter->mppriv.tx_pktcount = PacketCout;
1612                                                         DBG_871X("Packet Cout =%d\n", padapter->mppriv.tx_pktcount);
1613                                                         sprintf(extra, "Packet Cout =%d\n", padapter->mppriv.tx_pktcount);
1614
1615                                         } else if (sscanf(extra, "pmact,ldpc=%d", &bldpc) > 0) {
1616                                                         pMptCtx->bldpc = bldpc;
1617                                                         DBG_871X("Set LDPC =%d\n", pMptCtx->bldpc);
1618                                                         sprintf(extra, "Set LDPC =%d\n", pMptCtx->bldpc);
1619
1620                                         } else if (sscanf(extra, "pmact,stbc=%d", &bstbc) > 0) {
1621                                                         pMptCtx->bstbc = bstbc;
1622                                                         DBG_871X("Set STBC =%d\n", pMptCtx->bstbc);
1623                                                         sprintf(extra, "Set STBC =%d\n", pMptCtx->bstbc);
1624                                         } else
1625                                                 sprintf(extra, "\n period={1~255}\n length={1000~65535}\n count={0~}\n ldpc={0/1}\n stbc={0/1}");
1626
1627                                 }
1628
1629                                 wrqu->data.length = strlen(extra);
1630                                 return 0;
1631 #endif
1632                 } else {
1633
1634                         if (sscanf(extra, "ch=%d,bw=%d,rate=%d,pwr=%d,ant=%d,tx=%d", &channel, &bandwidth, &rate, &txpower, &ant, &txmode) < 6) {
1635                                         DBG_871X("Invalid format [ch=%d,bw=%d,rate=%d,pwr=%d,ant=%d,tx=%d]\n", channel, bandwidth, rate, txpower, ant, txmode);
1636                                         _rtw_memset(extra, 0, wrqu->data.length);
1637                                         sprintf(extra, "\n Please input correct format as bleow:\n");
1638                                         sprintf(extra, "%s\t ch=%d,bw=%d,rate=%d,pwr=%d,ant=%d,tx=%d\n", extra, channel, bandwidth, rate, txpower, ant, txmode);
1639                                         sprintf(extra, "%s\n [ ch : BGN = <1~14> , A or AC = <36~165> ]", extra);
1640                                         sprintf(extra, "%s\n [ bw : Bandwidth: 0 = 20M, 1 = 40M, 2 = 80M ]", extra);
1641                                         sprintf(extra, "%s\n [ rate :   CCK: 1 2 5.5 11M X 2 = < 2 4 11 22 >]", extra);
1642                                         sprintf(extra, "%s\n [          OFDM: 6 9 12 18 24 36 48 54M X 2 = < 12 18 24 36 48 72 96 108>", extra);
1643                                         sprintf(extra, "%s\n [          HT 1S2SS MCS0 ~ MCS15 : < [MCS0]=128 ~ [MCS7]=135 ~ [MCS15]=143 >", extra);
1644                                         sprintf(extra, "%s\n [          HT 3SS MCS16 ~ MCS32 : < [MCS16]=144 ~ [MCS23]=151 ~ [MCS32]=159 >", extra);
1645                                         sprintf(extra, "%s\n [          VHT 1SS MCS0 ~ MCS9 : < [MCS0]=160 ~ [MCS9]=169 >", extra);
1646                                         sprintf(extra, "%s\n [ txpower : 1~63 power index", extra);
1647                                         sprintf(extra, "%s\n [ ant : <A = 1, B = 2, C = 4, D = 8> ,2T ex: AB=3 BC=6 CD=12", extra);
1648                                         sprintf(extra, "%s\n [ txmode : < 0 = CONTINUOUS_TX, 1 = PACKET_TX, 2 = SINGLE_TONE_TX, 3 = CARRIER_SUPPRISSION_TX, 4 = SINGLE_CARRIER_TX>\n", extra);
1649                                         wrqu->data.length = strlen(extra);
1650                                         return status;
1651
1652                         } else {
1653                                 DBG_871X("Got format [ch=%d,bw=%d,rate=%d,pwr=%d,ant=%d,tx=%d]\n", channel, bandwidth, rate, txpower, ant, txmode);
1654                                 _rtw_memset(extra, 0, wrqu->data.length);
1655                                 sprintf(extra, "Change Current channel %d to channel %d", padapter->mppriv.channel , channel);
1656                                 padapter->mppriv.channel = channel;
1657                                 SetChannel(padapter);
1658                                 pHalData->CurrentChannel = channel;
1659
1660                                 if (bandwidth == 1)
1661                                         bandwidth = CHANNEL_WIDTH_40;
1662                                 else if (bandwidth == 2)
1663                                         bandwidth = CHANNEL_WIDTH_80;
1664                                 sprintf(extra, "%s\nChange Current Bandwidth %d to Bandwidth %d", extra, padapter->mppriv.bandwidth , bandwidth);
1665                                 padapter->mppriv.bandwidth = (u8)bandwidth;
1666                                 padapter->mppriv.preamble = sg;
1667                                 SetBandwidth(padapter);
1668                                 pHalData->CurrentChannelBW = bandwidth;
1669
1670                                 sprintf(extra, "%s\nSet power level :%d", extra, txpower);
1671                                 padapter->mppriv.txpoweridx = (u8)txpower;
1672                                 pMptCtx->TxPwrLevel[ODM_RF_PATH_A] = (u8)txpower;
1673                                 pMptCtx->TxPwrLevel[ODM_RF_PATH_B] = (u8)txpower;
1674                                 pMptCtx->TxPwrLevel[ODM_RF_PATH_C] = (u8)txpower;
1675                                 pMptCtx->TxPwrLevel[ODM_RF_PATH_D]  = (u8)txpower;
1676
1677                                 DBG_871X("%s: bw=%d sg=%d\n", __func__, bandwidth, sg);
1678
1679                                 if (rate <= 0x7f)
1680                                         rate = wifirate2_ratetbl_inx((u8)rate);
1681                                 else if (rate < 0xC8)
1682                                         rate = (rate - 0x80 + MPT_RATE_MCS0);
1683                                         /*HT  rate 0x80(MCS0)  ~ 0x8F(MCS15) ~ 0x9F(MCS31) 128~159
1684                                         VHT1SS~2SS rate 0xA0 (VHT1SS_MCS0 44) ~ 0xB3 (VHT2SS_MCS9 #63) 160~179
1685                                         VHT rate 0xB4 (VHT3SS_MCS0 64) ~ 0xC7 (VHT2SS_MCS9 #83) 180~199
1686                                         else
1687                                         VHT rate 0x90(VHT1SS_MCS0) ~ 0x99(VHT1SS_MCS9) 144~153
1688                                         rate =(rate - MPT_RATE_VHT1SS_MCS0);
1689                                         */
1690                                 DBG_871X("%s: rate index=%d\n", __func__, rate);
1691                                 if (rate >= MPT_RATE_LAST)
1692                                         return -EINVAL;
1693                                 sprintf(extra, "%s\nSet data rate to %d index %d", extra, padapter->mppriv.rateidx, rate);
1694
1695                                 padapter->mppriv.rateidx = rate;
1696                                 pMptCtx->MptRateIndex = rate;
1697                                 SetDataRate(padapter);
1698
1699                                 sprintf(extra, "%s\nSet Antenna Path :%d",  extra, ant);
1700                                 switch (ant) {
1701                                 case 1:
1702                                         antenna = ANTENNA_A;
1703                                         break;
1704                                 case 2:
1705                                         antenna = ANTENNA_B;
1706                                         break;
1707                                 case 4:
1708                                         antenna = ANTENNA_C;
1709                                         break;
1710                                 case 8:
1711                                         antenna = ANTENNA_D;
1712                                         break;
1713                                 case 3:
1714                                         antenna = ANTENNA_AB;
1715                                         break;
1716                                 case 5:
1717                                         antenna = ANTENNA_AC;
1718                                         break;
1719                                 case 9:
1720                                         antenna = ANTENNA_AD;
1721                                         break;
1722                                 case 6:
1723                                         antenna = ANTENNA_BC;
1724                                         break;
1725                                 case 10:
1726                                         antenna = ANTENNA_BD;
1727                                         break;
1728                                 case 12:
1729                                         antenna = ANTENNA_CD;
1730                                         break;
1731                                 case 7:
1732                                         antenna = ANTENNA_ABC;
1733                                         break;
1734                                 case 14:
1735                                         antenna = ANTENNA_BCD;
1736                                         break;
1737                                 case 11:
1738                                         antenna = ANTENNA_ABD;
1739                                         break;
1740                                 case 15:
1741                                         antenna = ANTENNA_ABCD;
1742                                         break;
1743                                 }
1744                                 DBG_871X("%s: antenna=0x%x\n", __func__, antenna);
1745                                 padapter->mppriv.antenna_tx = antenna;
1746                                 padapter->mppriv.antenna_rx = antenna;
1747                                 pHalData->AntennaTxPath = antenna;
1748                                 SetAntenna(padapter);
1749
1750                                 if (txmode == 0) {
1751                                         pmp_priv->mode = MP_CONTINUOUS_TX;
1752                                 } else if (txmode == 1) {
1753                                         pmp_priv->mode = MP_PACKET_TX;
1754                                         pmp_priv->tx.count = count;
1755                                 } else if (txmode == 2) {
1756                                         pmp_priv->mode = MP_SINGLE_TONE_TX;
1757                                 } else if (txmode == 3) {
1758                                         pmp_priv->mode = MP_CARRIER_SUPPRISSION_TX;
1759                                 } else if (txmode == 4) {
1760                                         pmp_priv->mode = MP_SINGLE_CARRIER_TX;
1761                                 }
1762
1763                         status = rtw_mp_pretx_proc(padapter, bStartTest, extra);
1764                         }
1765
1766                 }
1767
1768                 wrqu->data.length = strlen(extra);
1769                 return status;
1770 }
1771
1772
1773 int rtw_mp_rx(struct net_device *dev,
1774                            struct iw_request_info *info,
1775                            union iwreq_data *wrqu, char *extra)
1776 {
1777         PADAPTER padapter = rtw_netdev_priv(dev);
1778         HAL_DATA_TYPE   *pHalData       = GET_HAL_DATA(padapter);
1779         struct mp_priv *pmp_priv = &padapter->mppriv;
1780         PMPT_CONTEXT            pMptCtx = &(padapter->mppriv.MptCtx);
1781
1782         u32 bandwidth = 0, sg = 0, channel = 6, ant = 0;
1783         u16 antenna = 0;
1784         u8 bStartRx = 0;
1785
1786         if (copy_from_user(extra, wrqu->data.pointer, wrqu->data.length))
1787                         return -EFAULT;
1788
1789 #ifdef CONFIG_CONCURRENT_MODE
1790                 if (padapter->adapter_type == SECONDARY_ADAPTER) {
1791                         sprintf(extra, "Error: MP mode can't support Virtual Adapter, Please to use main Adapter.\n");
1792                         wrqu->data.length = strlen(extra);
1793                         return 0;
1794                 }
1795 #endif
1796
1797         if (strncmp(extra, "stop", 4) == 0) {
1798                 _rtw_memset(extra, 0, wrqu->data.length);
1799                 SetPacketRx(padapter, bStartRx, _FALSE);
1800                 pmp_priv->bmac_filter = _FALSE;
1801                 sprintf(extra, "Received packet OK:%d CRC error:%d ,Filter out:%d", padapter->mppriv.rx_pktcount, padapter->mppriv.rx_crcerrpktcount, padapter->mppriv.rx_pktcount_filter_out);
1802                 wrqu->data.length = strlen(extra);
1803                 return 0;
1804
1805         } else if (sscanf(extra, "ch=%d,bw=%d,ant=%d", &channel, &bandwidth, &ant) < 3) {
1806                 DBG_871X("Invalid format [ch=%d,bw=%d,ant=%d]\n", channel, bandwidth, ant);
1807                 _rtw_memset(extra, 0, wrqu->data.length);
1808                 sprintf(extra, "\n Please input correct format as bleow:\n");
1809                 sprintf(extra, "%s\t ch=%d,bw=%d,ant=%d\n", extra, channel, bandwidth, ant);
1810                 sprintf(extra, "%s\n [ ch : BGN = <1~14> , A or AC = <36~165> ]", extra);
1811                 sprintf(extra, "%s\n [ bw : Bandwidth: 0 = 20M, 1 = 40M, 2 = 80M ]", extra);
1812                 sprintf(extra, "%s\n [ ant : <A = 1, B = 2, C = 4, D = 8> ,2T ex: AB=3 BC=6 CD=12", extra);
1813                 wrqu->data.length = strlen(extra);
1814                 return 0;
1815
1816         } else {
1817                 bStartRx = 1;
1818                 DBG_871X("Got format [ch=%d,bw=%d,ant=%d]\n", channel, bandwidth, ant);
1819                 _rtw_memset(extra, 0, wrqu->data.length);
1820                 sprintf(extra, "Change Current channel %d to channel %d", padapter->mppriv.channel , channel);
1821                 padapter->mppriv.channel = channel;
1822                 SetChannel(padapter);
1823                 pHalData->CurrentChannel = channel;
1824
1825                 if (bandwidth == 1)
1826                         bandwidth = CHANNEL_WIDTH_40;
1827                 else if (bandwidth == 2)
1828                         bandwidth = CHANNEL_WIDTH_80;
1829                 sprintf(extra, "%s\nChange Current Bandwidth %d to Bandwidth %d", extra, padapter->mppriv.bandwidth , bandwidth);
1830                 padapter->mppriv.bandwidth = (u8)bandwidth;
1831                 padapter->mppriv.preamble = sg;
1832                 SetBandwidth(padapter);
1833                 pHalData->CurrentChannelBW = bandwidth;
1834
1835                 sprintf(extra, "%s\nSet Antenna Path :%d",  extra, ant);
1836                 switch (ant) {
1837                 case 1:
1838                         antenna = ANTENNA_A;
1839                         break;
1840                 case 2:
1841                         antenna = ANTENNA_B;
1842                         break;
1843                 case 4:
1844                         antenna = ANTENNA_C;
1845                         break;
1846                 case 8:
1847                         antenna = ANTENNA_D;
1848                         break;
1849                 case 3:
1850                         antenna = ANTENNA_AB;
1851                         break;
1852                 case 5:
1853                         antenna = ANTENNA_AC;
1854                         break;
1855                 case 9:
1856                         antenna = ANTENNA_AD;
1857                         break;
1858                 case 6:
1859                         antenna = ANTENNA_BC;
1860                         break;
1861                 case 10:
1862                         antenna = ANTENNA_BD;
1863                         break;
1864                 case 12:
1865                         antenna = ANTENNA_CD;
1866                         break;
1867                 case 7:
1868                         antenna = ANTENNA_ABC;
1869                         break;
1870                 case 14:
1871                         antenna = ANTENNA_BCD;
1872                         break;
1873                 case 11:
1874                         antenna = ANTENNA_ABD;
1875                         break;
1876                 case 15:
1877                         antenna = ANTENNA_ABCD;
1878                         break;
1879                 }
1880                 DBG_871X("%s: antenna=0x%x\n", __func__, antenna);
1881                 padapter->mppriv.antenna_tx = antenna;
1882                 padapter->mppriv.antenna_rx = antenna;
1883                 pHalData->AntennaTxPath = antenna;
1884                 SetAntenna(padapter);
1885
1886                 sprintf(extra, "%s\nstart Rx", extra);
1887                 SetPacketRx(padapter, bStartRx, _FALSE);
1888         }
1889         wrqu->data.length = strlen(extra);
1890         return 0;
1891 }
1892
1893
1894 int rtw_mp_hwtx(struct net_device *dev,
1895                                 struct iw_request_info *info,
1896                                 union iwreq_data *wrqu, char *extra)
1897 {
1898         PADAPTER padapter = rtw_netdev_priv(dev);
1899         HAL_DATA_TYPE   *pHalData       = GET_HAL_DATA(padapter);
1900         struct mp_priv *pmp_priv = &padapter->mppriv;
1901         PMPT_CONTEXT            pMptCtx = &(padapter->mppriv.MptCtx);
1902
1903 #if     defined(CONFIG_RTL8814A) || defined(CONFIG_RTL8821B) || defined(CONFIG_RTL8822B)
1904         u8              input[wrqu->data.length];
1905
1906         if (copy_from_user(input, wrqu->data.pointer, wrqu->data.length))
1907                         return -EFAULT;
1908
1909         _rtw_memset(&pMptCtx->PMacTxInfo, 0, sizeof(RT_PMAC_TX_INFO));
1910         _rtw_memcpy((void *)&pMptCtx->PMacTxInfo, (void *)input, sizeof(RT_PMAC_TX_INFO));
1911
1912         mpt_ProSetPMacTx(padapter);
1913         sprintf(extra, "Set PMac Tx Mode start\n");
1914
1915         wrqu->data.length = strlen(extra);
1916 #endif
1917         return 0;
1918
1919 }
1920
1921 int rtw_efuse_mask_file(struct net_device *dev,
1922                                                 struct iw_request_info *info,
1923                                                 union iwreq_data *wrqu, char *extra)
1924 {
1925         char *rtw_efuse_mask_file_path;
1926         u8 Status;
1927         PADAPTER padapter = rtw_netdev_priv(dev);
1928         
1929         _rtw_memset(maskfileBuffer, 0x00, sizeof(maskfileBuffer));
1930
1931         if (copy_from_user(extra, wrqu->data.pointer, wrqu->data.length))
1932                 return -EFAULT;
1933
1934         if (strncmp(extra, "off", 3) == 0 && strlen(extra) < 4) {
1935                 padapter->registrypriv.boffefusemask = 1;
1936                 sprintf(extra, "Turn off Efuse Mask\n");
1937                 wrqu->data.length = strlen(extra);
1938                 return 0;
1939         }
1940         if (strncmp(extra, "on", 2) == 0 && strlen(extra) < 3) {
1941                 padapter->registrypriv.boffefusemask = 0;
1942                 sprintf(extra, "Turn on Efuse Mask\n");
1943                 wrqu->data.length = strlen(extra);
1944                 return 0;
1945         }
1946         rtw_efuse_mask_file_path = extra;
1947
1948         if (rtw_is_file_readable(rtw_efuse_mask_file_path) == _TRUE) {
1949                 DBG_871X("%s do rtw_efuse_mask_file_read = %s! ,sizeof maskfileBuffer %zu\n", __func__, rtw_efuse_mask_file_path, sizeof(maskfileBuffer));
1950                 Status = rtw_efuse_file_read(padapter, rtw_efuse_mask_file_path, maskfileBuffer, sizeof(maskfileBuffer));
1951                 if (Status == _TRUE)
1952                         padapter->registrypriv.bFileMaskEfuse = _TRUE;
1953                 sprintf(extra, "efuse mask file read OK\n");
1954         } else {
1955                 padapter->registrypriv.bFileMaskEfuse = _FALSE;
1956                 sprintf(extra, "efuse mask file readable FAIL\n");
1957                 DBG_871X("%s rtw_is_file_readable fail!\n", __func__);
1958         }
1959         wrqu->data.length = strlen(extra);
1960         return 0;
1961 }
1962
1963
1964 int rtw_efuse_file_map(struct net_device *dev,
1965                                            struct iw_request_info *info,
1966                                            union iwreq_data *wrqu, char *extra)
1967 {
1968         char *rtw_efuse_file_map_path;
1969         u8 Status;
1970         PEFUSE_HAL pEfuseHal;
1971         PADAPTER padapter = rtw_netdev_priv(dev);
1972         HAL_DATA_TYPE   *pHalData = GET_HAL_DATA(padapter);
1973         
1974         pEfuseHal = &pHalData->EfuseHal;
1975         if (copy_from_user(extra, wrqu->data.pointer, wrqu->data.length))
1976                 return -EFAULT;
1977
1978         rtw_efuse_file_map_path = extra;
1979
1980         if (rtw_is_file_readable(rtw_efuse_file_map_path) == _TRUE) {
1981                 DBG_871X("%s do rtw_efuse_mask_file_read = %s!\n", __func__, rtw_efuse_file_map_path);
1982                 Status = rtw_efuse_file_read(padapter, rtw_efuse_file_map_path, pEfuseHal->fakeEfuseModifiedMap, sizeof(pEfuseHal->fakeEfuseModifiedMap));
1983                 if (Status == _TRUE)
1984                         sprintf(extra, "efuse file file_read OK\n");
1985                 else
1986                         sprintf(extra, "efuse file file_read FAIL\n");
1987         } else {
1988                 sprintf(extra, "efuse file readable FAIL\n");
1989                 DBG_871X("%s rtw_is_file_readable fail!\n", __func__);
1990         }
1991         wrqu->data.length = strlen(extra);
1992         return 0;
1993 }
1994
1995 #if defined(CONFIG_RTL8723B)
1996 int rtw_mp_SetBT(struct net_device *dev,
1997                                  struct iw_request_info *info,
1998                                  union iwreq_data *wrqu, char *extra)
1999 {
2000         PADAPTER padapter = rtw_netdev_priv(dev);
2001         struct hal_ops *pHalFunc = &padapter->HalFunc;
2002         HAL_DATA_TYPE   *pHalData = GET_HAL_DATA(padapter);
2003
2004         BT_REQ_CMD      BtReq;
2005         PMPT_CONTEXT    pMptCtx = &(padapter->mppriv.MptCtx);
2006         PBT_RSP_CMD     pBtRsp = (PBT_RSP_CMD)&pMptCtx->mptOutBuf[0];
2007         char    input[128];
2008         char *pch, *ptmp, *token, *tmp[2] = {0x00, 0x00};
2009         u8 setdata[100];
2010         u8 resetbt = 0x00;
2011         u8 tempval, BTStatus;
2012         u8 H2cSetbtmac[6];
2013         u8 u1H2CBtMpOperParm[4] = {0x01};
2014         int testmode = 1, ready = 1, trxparam = 1, setgen = 1, getgen = 1, testctrl = 1, testbt = 1, readtherm = 1, setbtmac = 1;
2015         u32 i = 0, ii = 0, jj = 0, kk = 0, cnts = 0, status = 0;
2016         PRT_MP_FIRMWARE pBTFirmware = NULL;
2017
2018         if (copy_from_user(extra, wrqu->data.pointer, wrqu->data.length))
2019                 return -EFAULT;
2020         if (strlen(extra) < 1)
2021                 return -EFAULT;
2022
2023         DBG_871X("%s:iwpriv in=%s\n", __func__, extra);
2024         ready = strncmp(extra, "ready", 5);
2025         testmode = strncmp(extra, "testmode", 8); /* strncmp TRUE is 0*/
2026         trxparam = strncmp(extra, "trxparam", 8);
2027         setgen = strncmp(extra, "setgen", 6);
2028         getgen = strncmp(extra, "getgen", 6);
2029         testctrl = strncmp(extra, "testctrl", 8);
2030         testbt = strncmp(extra, "testbt", 6);
2031         readtherm = strncmp(extra, "readtherm", 9);
2032         setbtmac = strncmp(extra, "setbtmac", 8);
2033
2034         if (strncmp(extra, "dlbt", 4) == 0) {
2035                 pHalData->LastHMEBoxNum = 0;
2036                 padapter->bBTFWReady = _FALSE;
2037                 rtw_write8(padapter, 0xa3, 0x05);
2038                 BTStatus = rtw_read8(padapter, 0xa0);
2039                 DBG_871X("%s: btwmap before read 0xa0 BT Status =0x%x\n", __func__, BTStatus);
2040                 if (BTStatus != 0x04) {
2041                         sprintf(extra, "BT Status not Active DLFW FAIL\n");
2042                         goto exit;
2043                 }
2044
2045                 tempval = rtw_read8(padapter, 0x6B);
2046                 tempval |= BIT7;
2047                 rtw_write8(padapter, 0x6B, tempval);
2048
2049                 /* Attention!! Between 0x6A[14] and 0x6A[15] setting need 100us delay*/
2050                 /* So don't write 0x6A[14]=1 and 0x6A[15]=0 together!*/
2051                 rtw_usleep_os(100);
2052                 /* disable BT power cut*/
2053                 /* 0x6A[14] = 0*/
2054                 tempval = rtw_read8(padapter, 0x6B);
2055                 tempval &= ~BIT6;
2056                 rtw_write8(padapter, 0x6B, tempval);
2057                 rtw_usleep_os(100);
2058                 MPT_PwrCtlDM(padapter, 0);
2059                 rtw_write32(padapter, 0xcc, (rtw_read32(padapter, 0xcc) | 0x00000004));
2060                 rtw_write32(padapter, 0x6b, (rtw_read32(padapter, 0x6b) & 0xFFFFFFEF));
2061                 rtw_msleep_os(600);
2062                 rtw_write32(padapter, 0x6b, (rtw_read32(padapter, 0x6b) | 0x00000010));
2063                 rtw_write32(padapter, 0xcc, (rtw_read32(padapter, 0xcc) & 0xFFFFFFFB));
2064                 rtw_msleep_os(1200);
2065                 pBTFirmware = (PRT_MP_FIRMWARE)rtw_zmalloc(sizeof(RT_MP_FIRMWARE));
2066                 if (pBTFirmware == NULL)
2067                         goto exit;
2068                 padapter->bBTFWReady = _FALSE;
2069                 FirmwareDownloadBT(padapter, pBTFirmware);
2070                 if (pBTFirmware)
2071                         rtw_mfree((u8 *)pBTFirmware, sizeof(RT_MP_FIRMWARE));
2072
2073                 DBG_871X("Wait for FirmwareDownloadBT fw boot!\n");
2074                 rtw_msleep_os(2000);
2075                 _rtw_memset(extra, '\0', wrqu->data.length);
2076                 BtReq.opCodeVer = 1;
2077                 BtReq.OpCode = 0;
2078                 BtReq.paraLength = 0;
2079                 mptbt_BtControlProcess(padapter, &BtReq);
2080                 rtw_msleep_os(100);
2081
2082                 DBG_8192C("FirmwareDownloadBT ready = 0x%x 0x%x", pMptCtx->mptOutBuf[4], pMptCtx->mptOutBuf[5]);
2083                 if ((pMptCtx->mptOutBuf[4] == 0x00) && (pMptCtx->mptOutBuf[5] == 0x00)) {
2084
2085                         if (padapter->mppriv.bTxBufCkFail == _TRUE)
2086                                 sprintf(extra, "check TxBuf Fail.\n");
2087                         else
2088                                 sprintf(extra, "download FW Fail.\n");
2089                 } else {
2090                         sprintf(extra, "download FW OK.\n");
2091                         goto exit;
2092                 }
2093                 goto exit;
2094         }
2095         if (strncmp(extra, "dlfw", 4) == 0) {
2096                 pHalData->LastHMEBoxNum = 0;
2097                 padapter->bBTFWReady = _FALSE;
2098                 rtw_write8(padapter, 0xa3, 0x05);
2099                 BTStatus = rtw_read8(padapter, 0xa0);
2100                 DBG_871X("%s: btwmap before read 0xa0 BT Status =0x%x\n", __func__, BTStatus);
2101                 if (BTStatus != 0x04) {
2102                         sprintf(extra, "BT Status not Active DLFW FAIL\n");
2103                         goto exit;
2104                 }
2105
2106                 tempval = rtw_read8(padapter, 0x6B);
2107                 tempval |= BIT7;
2108                 rtw_write8(padapter, 0x6B, tempval);
2109
2110                 /* Attention!! Between 0x6A[14] and 0x6A[15] setting need 100us delay*/
2111                 /* So don't write 0x6A[14]=1 and 0x6A[15]=0 together!*/
2112                 rtw_usleep_os(100);
2113                 /* disable BT power cut*/
2114                 /* 0x6A[14] = 0*/
2115                 tempval = rtw_read8(padapter, 0x6B);
2116                 tempval &= ~BIT6;
2117                 rtw_write8(padapter, 0x6B, tempval);
2118                 rtw_usleep_os(100);
2119
2120                 MPT_PwrCtlDM(padapter, 0);
2121                 rtw_write32(padapter, 0xcc, (rtw_read32(padapter, 0xcc) | 0x00000004));
2122                 rtw_write32(padapter, 0x6b, (rtw_read32(padapter, 0x6b) & 0xFFFFFFEF));
2123                 rtw_msleep_os(600);
2124                 rtw_write32(padapter, 0x6b, (rtw_read32(padapter, 0x6b) | 0x00000010));
2125                 rtw_write32(padapter, 0xcc, (rtw_read32(padapter, 0xcc) & 0xFFFFFFFB));
2126                 rtw_msleep_os(1200);
2127
2128 #if defined(CONFIG_PLATFORM_SPRD) && (MP_DRIVER == 1)
2129                 /* Pull up BT reset pin.*/
2130                 DBG_871X("%s: pull up BT reset pin when bt start mp test\n", __func__);
2131                 rtw_wifi_gpio_wlan_ctrl(WLAN_BT_PWDN_ON);
2132 #endif
2133                 DBG_871X(" FirmwareDownload!\n");
2134
2135 #if defined(CONFIG_RTL8723B)
2136                 status = rtl8723b_FirmwareDownload(padapter, _FALSE);
2137 #endif
2138                 DBG_871X("Wait for FirmwareDownloadBT fw boot!\n");
2139                 rtw_msleep_os(1000);
2140 #ifdef CONFIG_BT_COEXIST
2141                 rtw_btcoex_HaltNotify(padapter);
2142                 DBG_871X("SetBT btcoex HaltNotify !\n");
2143                 /*hal_btcoex1ant_SetAntPath(padapter);*/
2144                 rtw_btcoex_SetManualControl(padapter, _TRUE);
2145 #endif
2146                 _rtw_memset(extra, '\0', wrqu->data.length);
2147                 BtReq.opCodeVer = 1;
2148                 BtReq.OpCode = 0;
2149                 BtReq.paraLength = 0;
2150                 mptbt_BtControlProcess(padapter, &BtReq);
2151                 rtw_msleep_os(200);
2152
2153                 DBG_8192C("FirmwareDownloadBT ready = 0x%x 0x%x", pMptCtx->mptOutBuf[4], pMptCtx->mptOutBuf[5]);
2154                 if ((pMptCtx->mptOutBuf[4] == 0x00) && (pMptCtx->mptOutBuf[5] == 0x00)) {
2155                         if (padapter->mppriv.bTxBufCkFail == _TRUE)
2156                                 sprintf(extra, "check TxBuf Fail.\n");
2157                         else
2158                                 sprintf(extra, "download FW Fail.\n");
2159                 } else {
2160 #ifdef CONFIG_BT_COEXIST
2161                         rtw_btcoex_SwitchBtTRxMask(padapter);
2162 #endif
2163                         rtw_msleep_os(200);
2164                         sprintf(extra, "download FW OK.\n");
2165                         goto exit;
2166                 }
2167                 goto exit;
2168         }
2169
2170         if (strncmp(extra, "down", 4) == 0) {
2171                 DBG_871X("SetBT down for to hal_init !\n");
2172 #ifdef CONFIG_BT_COEXIST
2173                 rtw_btcoex_SetManualControl(padapter, _FALSE);
2174                 rtw_btcoex_Initialize(padapter);
2175 #endif
2176                 pHalFunc->read_adapter_info(padapter);
2177                 pHalFunc->hal_deinit(padapter);
2178                 pHalFunc->hal_init(padapter);
2179                 rtw_pm_set_ips(padapter, IPS_NONE);
2180                 LeaveAllPowerSaveMode(padapter);
2181                 MPT_PwrCtlDM(padapter, 0);
2182                 rtw_write32(padapter, 0xcc, (rtw_read32(padapter, 0xcc) | 0x00000004));
2183                 rtw_write32(padapter, 0x6b, (rtw_read32(padapter, 0x6b) & 0xFFFFFFEF));
2184                 rtw_msleep_os(600);
2185                 /*rtw_write32(padapter, 0x6a, (rtw_read32(padapter, 0x6a)& 0xFFFFFFFE));*/
2186                 rtw_write32(padapter, 0x6b, (rtw_read32(padapter, 0x6b) | 0x00000010));
2187                 rtw_write32(padapter, 0xcc, (rtw_read32(padapter, 0xcc) & 0xFFFFFFFB));
2188                 rtw_msleep_os(1200);
2189                 goto exit;
2190         }
2191         if (strncmp(extra, "disable", 7) == 0) {
2192                 DBG_871X("SetBT disable !\n");
2193                 rtw_write32(padapter, 0x6a, (rtw_read32(padapter, 0x6a) & 0xFFFFFFFB));
2194                 rtw_msleep_os(500);
2195                 goto exit;
2196         }
2197         if (strncmp(extra, "enable", 6) == 0) {
2198                 DBG_871X("SetBT enable !\n");
2199                 rtw_write32(padapter, 0x6a, (rtw_read32(padapter, 0x6a) | 0x00000004));
2200                 rtw_msleep_os(500);
2201                 goto exit;
2202         }
2203         if (strncmp(extra, "h2c", 3) == 0) {
2204                 DBG_871X("SetBT h2c !\n");
2205                 padapter->bBTFWReady = _TRUE;
2206                 rtw_hal_fill_h2c_cmd(padapter, 0x63, 1, u1H2CBtMpOperParm);
2207                 goto exit;
2208         }
2209         if (strncmp(extra, "2ant", 4) == 0) {
2210                 DBG_871X("Set BT 2ant use!\n");
2211                 PHY_SetMacReg(padapter, 0x67, BIT5, 0x1);
2212                 rtw_write32(padapter, 0x948, 0000);
2213
2214                 goto exit;
2215         }
2216
2217         if (ready != 0 && testmode != 0 && trxparam != 0 && setgen != 0 && getgen != 0 && testctrl != 0 && testbt != 0 && readtherm != 0 && setbtmac != 0)
2218                 return -EFAULT;
2219
2220         if (testbt == 0) {
2221                 BtReq.opCodeVer = 1;
2222                 BtReq.OpCode = 6;
2223                 BtReq.paraLength = cnts / 2;
2224                 goto todo;
2225         }
2226         if (ready == 0) {
2227                 BtReq.opCodeVer = 1;
2228                 BtReq.OpCode = 0;
2229                 BtReq.paraLength = 0;
2230                 goto todo;
2231         }
2232
2233         pch = extra;
2234         i = 0;
2235         while ((token = strsep(&pch, ",")) != NULL) {
2236                 if (i > 1)
2237                         break;
2238                 tmp[i] = token;
2239                 i++;
2240         }
2241
2242         if ((tmp[0] != NULL) && (tmp[1] != NULL)) {
2243                 cnts = strlen(tmp[1]);
2244                 if (cnts < 1)
2245                         return -EFAULT;
2246
2247                 DBG_871X("%s: cnts=%d\n", __func__, cnts);
2248                 DBG_871X("%s: data=%s\n", __func__, tmp[1]);
2249
2250                 for (jj = 0, kk = 0; jj < cnts; jj++, kk += 2) {
2251                         BtReq.pParamStart[jj] = key_2char2num(tmp[1][kk], tmp[1][kk + 1]);
2252                         /*                      DBG_871X("BtReq.pParamStart[%d]=0x%02x\n", jj, BtReq.pParamStart[jj]);*/
2253                 }
2254         } else 
2255                 return -EFAULT;
2256                 
2257         if (testmode == 0) {
2258                 BtReq.opCodeVer = 1;
2259                 BtReq.OpCode = 1;
2260                 BtReq.paraLength = 1;
2261         }
2262         if (trxparam == 0) {
2263                 BtReq.opCodeVer = 1;
2264                 BtReq.OpCode = 2;
2265                 BtReq.paraLength = cnts / 2;
2266         }
2267         if (setgen == 0) {
2268                 DBG_871X("%s: BT_SET_GENERAL\n", __func__);
2269                 BtReq.opCodeVer = 1;
2270                 BtReq.OpCode = 3;/*BT_SET_GENERAL       3*/
2271                 BtReq.paraLength = cnts / 2;
2272         }
2273         if (getgen == 0) {
2274                 DBG_871X("%s: BT_GET_GENERAL\n", __func__);
2275                 BtReq.opCodeVer = 1;
2276                 BtReq.OpCode = 4;/*BT_GET_GENERAL       4*/
2277                 BtReq.paraLength = cnts / 2;
2278         }
2279         if (readtherm == 0) {
2280                 DBG_871X("%s: BT_GET_GENERAL\n", __func__);
2281                 BtReq.opCodeVer = 1;
2282                 BtReq.OpCode = 4;/*BT_GET_GENERAL       4*/
2283                 BtReq.paraLength = cnts / 2;
2284         }
2285
2286         if (testctrl == 0) {
2287                 DBG_871X("%s: BT_TEST_CTRL\n", __func__);
2288                 BtReq.opCodeVer = 1;
2289                 BtReq.OpCode = 5;/*BT_TEST_CTRL 5*/
2290                 BtReq.paraLength = cnts / 2;
2291         }
2292
2293         DBG_871X("%s: Req opCodeVer=%d OpCode=%d paraLength=%d\n",
2294                          __func__, BtReq.opCodeVer, BtReq.OpCode, BtReq.paraLength);
2295
2296         if (BtReq.paraLength < 1)
2297                 goto todo;
2298         for (i = 0; i < BtReq.paraLength; i++) {
2299                 DBG_871X("%s: BtReq.pParamStart[%d] = 0x%02x\n",
2300                                  __func__, i, BtReq.pParamStart[i]);
2301         }
2302
2303 todo:
2304         _rtw_memset(extra, '\0', wrqu->data.length);
2305
2306         if (padapter->bBTFWReady == _FALSE) {
2307                 sprintf(extra, "BTFWReady = FALSE.\n");
2308                 goto exit;
2309         }
2310
2311         mptbt_BtControlProcess(padapter, &BtReq);
2312
2313         if (readtherm == 0) {
2314                 sprintf(extra, "BT thermal=");
2315                 for (i = 4; i < pMptCtx->mptOutLen; i++) {
2316                         if ((pMptCtx->mptOutBuf[i] == 0x00) && (pMptCtx->mptOutBuf[i + 1] == 0x00))
2317                                 goto exit;
2318
2319                         sprintf(extra, "%s %d ", extra, (pMptCtx->mptOutBuf[i] & 0x1f));
2320                 }
2321         } else {
2322                 for (i = 4; i < pMptCtx->mptOutLen; i++)
2323                         sprintf(extra, "%s 0x%x ", extra, pMptCtx->mptOutBuf[i]);
2324         }
2325
2326 exit:
2327         wrqu->data.length = strlen(extra) + 1;
2328         DBG_871X("-%s: output len=%d data=%s\n", __func__, wrqu->data.length, extra);
2329
2330         return status;
2331 }
2332
2333 #endif /*#ifdef CONFIG_RTL8723B*/
2334
2335 #endif