1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22#include <linux/string.h>
23#include "r8192U.h"
24#include "r8192U_hw.h"
25
26#include "dot11d.h"
27#include "r8192U_wx.h"
28
29#define RATE_COUNT 12
30static const u32 rtl8180_rates[] = {1000000, 2000000, 5500000, 11000000,
31 6000000, 9000000, 12000000, 18000000, 24000000, 36000000, 48000000, 54000000};
32
33
34#ifndef ENETDOWN
35#define ENETDOWN 1
36#endif
37
38static int r8192_wx_get_freq(struct net_device *dev,
39 struct iw_request_info *a,
40 union iwreq_data *wrqu, char *b)
41{
42 struct r8192_priv *priv = ieee80211_priv(dev);
43
44 return ieee80211_wx_get_freq(priv->ieee80211, a, wrqu, b);
45}
46
47
48static int r8192_wx_get_mode(struct net_device *dev, struct iw_request_info *a,
49 union iwreq_data *wrqu, char *b)
50{
51 struct r8192_priv *priv = ieee80211_priv(dev);
52
53 return ieee80211_wx_get_mode(priv->ieee80211, a, wrqu, b);
54}
55
56
57
58static int r8192_wx_get_rate(struct net_device *dev,
59 struct iw_request_info *info,
60 union iwreq_data *wrqu, char *extra)
61{
62 struct r8192_priv *priv = ieee80211_priv(dev);
63
64 return ieee80211_wx_get_rate(priv->ieee80211, info, wrqu, extra);
65}
66
67
68
69static int r8192_wx_set_rate(struct net_device *dev,
70 struct iw_request_info *info,
71 union iwreq_data *wrqu, char *extra)
72{
73 int ret;
74 struct r8192_priv *priv = ieee80211_priv(dev);
75
76 down(&priv->wx_sem);
77
78 ret = ieee80211_wx_set_rate(priv->ieee80211, info, wrqu, extra);
79
80 up(&priv->wx_sem);
81
82 return ret;
83}
84
85
86static int r8192_wx_set_rts(struct net_device *dev,
87 struct iw_request_info *info,
88 union iwreq_data *wrqu, char *extra)
89{
90 int ret;
91 struct r8192_priv *priv = ieee80211_priv(dev);
92
93 down(&priv->wx_sem);
94
95 ret = ieee80211_wx_set_rts(priv->ieee80211, info, wrqu, extra);
96
97 up(&priv->wx_sem);
98
99 return ret;
100}
101
102static int r8192_wx_get_rts(struct net_device *dev,
103 struct iw_request_info *info,
104 union iwreq_data *wrqu, char *extra)
105{
106 struct r8192_priv *priv = ieee80211_priv(dev);
107
108 return ieee80211_wx_get_rts(priv->ieee80211, info, wrqu, extra);
109}
110
111static int r8192_wx_set_power(struct net_device *dev,
112 struct iw_request_info *info,
113 union iwreq_data *wrqu, char *extra)
114{
115 int ret;
116 struct r8192_priv *priv = ieee80211_priv(dev);
117
118 down(&priv->wx_sem);
119
120 ret = ieee80211_wx_set_power(priv->ieee80211, info, wrqu, extra);
121
122 up(&priv->wx_sem);
123
124 return ret;
125}
126
127static int r8192_wx_get_power(struct net_device *dev,
128 struct iw_request_info *info,
129 union iwreq_data *wrqu, char *extra)
130{
131 struct r8192_priv *priv = ieee80211_priv(dev);
132
133 return ieee80211_wx_get_power(priv->ieee80211, info, wrqu, extra);
134}
135
136static int r8192_wx_force_reset(struct net_device *dev,
137 struct iw_request_info *info,
138 union iwreq_data *wrqu, char *extra)
139{
140 struct r8192_priv *priv = ieee80211_priv(dev);
141
142 down(&priv->wx_sem);
143
144 netdev_dbg(dev, "%s(): force reset ! extra is %d\n", __func__, *extra);
145 priv->force_reset = *extra;
146 up(&priv->wx_sem);
147 return 0;
148
149}
150
151
152static int r8192_wx_set_rawtx(struct net_device *dev,
153 struct iw_request_info *info,
154 union iwreq_data *wrqu, char *extra)
155{
156 struct r8192_priv *priv = ieee80211_priv(dev);
157 int ret;
158
159 down(&priv->wx_sem);
160
161 ret = ieee80211_wx_set_rawtx(priv->ieee80211, info, wrqu, extra);
162
163 up(&priv->wx_sem);
164
165 return ret;
166
167}
168
169static int r8192_wx_set_crcmon(struct net_device *dev,
170 struct iw_request_info *info,
171 union iwreq_data *wrqu, char *extra)
172{
173 struct r8192_priv *priv = ieee80211_priv(dev);
174 int *parms = (int *)extra;
175 int enable = (parms[0] > 0);
176
177 down(&priv->wx_sem);
178
179 if (enable)
180 priv->crcmon = 1;
181 else
182 priv->crcmon = 0;
183
184 DMESG("bad CRC in monitor mode are %s",
185 priv->crcmon ? "accepted" : "rejected");
186
187 up(&priv->wx_sem);
188
189 return 0;
190}
191
192static int r8192_wx_set_mode(struct net_device *dev, struct iw_request_info *a,
193 union iwreq_data *wrqu, char *b)
194{
195 struct r8192_priv *priv = ieee80211_priv(dev);
196 int ret;
197
198 down(&priv->wx_sem);
199
200 ret = ieee80211_wx_set_mode(priv->ieee80211, a, wrqu, b);
201
202 rtl8192_set_rxconf(dev);
203
204 up(&priv->wx_sem);
205 return ret;
206}
207
208struct iw_range_with_scan_capa {
209
210 __u32 throughput;
211
212
213
214
215
216
217
218
219 __u32 min_nwid;
220 __u32 max_nwid;
221
222
223 __u16 old_num_channels;
224 __u8 old_num_frequency;
225
226
227 __u8 scan_capa;
228};
229static int rtl8180_wx_get_range(struct net_device *dev,
230 struct iw_request_info *info,
231 union iwreq_data *wrqu, char *extra)
232{
233 struct iw_range *range = (struct iw_range *)extra;
234 struct iw_range_with_scan_capa *tmp = (struct iw_range_with_scan_capa *)range;
235 struct r8192_priv *priv = ieee80211_priv(dev);
236 u16 val;
237 int i;
238
239 wrqu->data.length = sizeof(*range);
240 memset(range, 0, sizeof(*range));
241
242
243
244
245
246
247
248
249
250
251 range->throughput = 5 * 1000 * 1000;
252
253
254
255
256
257
258
259
260
261
262 if (priv->rf_set_sens != NULL)
263 range->sensitivity = priv->max_sens;
264
265 range->max_qual.qual = 100;
266
267 range->max_qual.level = 0;
268 range->max_qual.noise = 0x100 - 98;
269 range->max_qual.updated = 7;
270
271 range->avg_qual.qual = 92;
272
273 range->avg_qual.level = 0x100 - 78;
274 range->avg_qual.noise = 0;
275 range->avg_qual.updated = 7;
276
277 range->num_bitrates = RATE_COUNT;
278
279 for (i = 0; i < RATE_COUNT && i < IW_MAX_BITRATES; i++)
280 range->bitrate[i] = rtl8180_rates[i];
281
282 range->min_frag = MIN_FRAG_THRESHOLD;
283 range->max_frag = MAX_FRAG_THRESHOLD;
284
285 range->min_pmp = 0;
286 range->max_pmp = 5000000;
287 range->min_pmt = 0;
288 range->max_pmt = 65535*1000;
289 range->pmp_flags = IW_POWER_PERIOD;
290 range->pmt_flags = IW_POWER_TIMEOUT;
291 range->pm_capa = IW_POWER_PERIOD | IW_POWER_TIMEOUT | IW_POWER_ALL_R;
292
293 range->we_version_compiled = WIRELESS_EXT;
294 range->we_version_source = 16;
295
296
297
298
299
300
301
302
303
304
305 for (i = 0, val = 0; i < 14; i++) {
306
307
308 if ((GET_DOT11D_INFO(priv->ieee80211)->channel_map)[i+1]) {
309 range->freq[val].i = i + 1;
310 range->freq[val].m = ieee80211_wlan_frequencies[i] * 100000;
311 range->freq[val].e = 1;
312 val++;
313 } else {
314
315
316 }
317
318 if (val == IW_MAX_FREQUENCIES)
319 break;
320 }
321 range->num_frequency = val;
322 range->num_channels = val;
323 range->enc_capa = IW_ENC_CAPA_WPA|IW_ENC_CAPA_WPA2|
324 IW_ENC_CAPA_CIPHER_TKIP|IW_ENC_CAPA_CIPHER_CCMP;
325 tmp->scan_capa = 0x01;
326 return 0;
327}
328
329
330static int r8192_wx_set_scan(struct net_device *dev, struct iw_request_info *a,
331 union iwreq_data *wrqu, char *b)
332{
333 struct r8192_priv *priv = ieee80211_priv(dev);
334 struct ieee80211_device *ieee = priv->ieee80211;
335 int ret = 0;
336
337 if (!priv->up)
338 return -ENETDOWN;
339
340 if (priv->ieee80211->LinkDetectInfo.bBusyTraffic)
341 return -EAGAIN;
342 if (wrqu->data.flags & IW_SCAN_THIS_ESSID) {
343 struct iw_scan_req *req = (struct iw_scan_req *)b;
344
345 if (req->essid_len) {
346 ieee->current_network.ssid_len = req->essid_len;
347 memcpy(ieee->current_network.ssid, req->essid, req->essid_len);
348 }
349 }
350
351 down(&priv->wx_sem);
352 if (priv->ieee80211->state != IEEE80211_LINKED) {
353 priv->ieee80211->scanning = 0;
354 ieee80211_softmac_scan_syncro(priv->ieee80211);
355 ret = 0;
356 } else {
357 ret = ieee80211_wx_set_scan(priv->ieee80211, a, wrqu, b);
358 }
359 up(&priv->wx_sem);
360 return ret;
361}
362
363
364static int r8192_wx_get_scan(struct net_device *dev, struct iw_request_info *a,
365 union iwreq_data *wrqu, char *b)
366{
367
368 int ret;
369 struct r8192_priv *priv = ieee80211_priv(dev);
370
371 if (!priv->up)
372 return -ENETDOWN;
373
374 down(&priv->wx_sem);
375
376 ret = ieee80211_wx_get_scan(priv->ieee80211, a, wrqu, b);
377
378 up(&priv->wx_sem);
379
380 return ret;
381}
382
383static int r8192_wx_set_essid(struct net_device *dev,
384 struct iw_request_info *a,
385 union iwreq_data *wrqu, char *b)
386{
387 struct r8192_priv *priv = ieee80211_priv(dev);
388 int ret;
389
390 down(&priv->wx_sem);
391
392 ret = ieee80211_wx_set_essid(priv->ieee80211, a, wrqu, b);
393
394 up(&priv->wx_sem);
395
396 return ret;
397}
398
399
400
401
402static int r8192_wx_get_essid(struct net_device *dev,
403 struct iw_request_info *a,
404 union iwreq_data *wrqu, char *b)
405{
406 int ret;
407 struct r8192_priv *priv = ieee80211_priv(dev);
408
409 down(&priv->wx_sem);
410
411 ret = ieee80211_wx_get_essid(priv->ieee80211, a, wrqu, b);
412
413 up(&priv->wx_sem);
414
415 return ret;
416}
417
418
419static int r8192_wx_set_freq(struct net_device *dev, struct iw_request_info *a,
420 union iwreq_data *wrqu, char *b)
421{
422 int ret;
423 struct r8192_priv *priv = ieee80211_priv(dev);
424
425 down(&priv->wx_sem);
426
427 ret = ieee80211_wx_set_freq(priv->ieee80211, a, wrqu, b);
428
429 up(&priv->wx_sem);
430 return ret;
431}
432
433static int r8192_wx_get_name(struct net_device *dev,
434 struct iw_request_info *info,
435 union iwreq_data *wrqu, char *extra)
436{
437 struct r8192_priv *priv = ieee80211_priv(dev);
438
439 return ieee80211_wx_get_name(priv->ieee80211, info, wrqu, extra);
440}
441
442
443static int r8192_wx_set_frag(struct net_device *dev,
444 struct iw_request_info *info,
445 union iwreq_data *wrqu, char *extra)
446{
447 struct r8192_priv *priv = ieee80211_priv(dev);
448
449 if (wrqu->frag.disabled)
450 priv->ieee80211->fts = DEFAULT_FRAG_THRESHOLD;
451 else {
452 if (wrqu->frag.value < MIN_FRAG_THRESHOLD ||
453 wrqu->frag.value > MAX_FRAG_THRESHOLD)
454 return -EINVAL;
455
456 priv->ieee80211->fts = wrqu->frag.value & ~0x1;
457 }
458
459 return 0;
460}
461
462
463static int r8192_wx_get_frag(struct net_device *dev,
464 struct iw_request_info *info,
465 union iwreq_data *wrqu, char *extra)
466{
467 struct r8192_priv *priv = ieee80211_priv(dev);
468
469 wrqu->frag.value = priv->ieee80211->fts;
470 wrqu->frag.fixed = 0;
471 wrqu->frag.disabled = (wrqu->frag.value == DEFAULT_FRAG_THRESHOLD);
472
473 return 0;
474}
475
476
477static int r8192_wx_set_wap(struct net_device *dev,
478 struct iw_request_info *info,
479 union iwreq_data *awrq,
480 char *extra)
481{
482
483 int ret;
484 struct r8192_priv *priv = ieee80211_priv(dev);
485
486 down(&priv->wx_sem);
487
488 ret = ieee80211_wx_set_wap(priv->ieee80211, info, awrq, extra);
489
490 up(&priv->wx_sem);
491
492 return ret;
493
494}
495
496
497static int r8192_wx_get_wap(struct net_device *dev,
498 struct iw_request_info *info,
499 union iwreq_data *wrqu, char *extra)
500{
501 struct r8192_priv *priv = ieee80211_priv(dev);
502
503 return ieee80211_wx_get_wap(priv->ieee80211, info, wrqu, extra);
504}
505
506
507static int r8192_wx_get_enc(struct net_device *dev,
508 struct iw_request_info *info,
509 union iwreq_data *wrqu, char *key)
510{
511 struct r8192_priv *priv = ieee80211_priv(dev);
512
513 return ieee80211_wx_get_encode(priv->ieee80211, info, wrqu, key);
514}
515
516static int r8192_wx_set_enc(struct net_device *dev,
517 struct iw_request_info *info,
518 union iwreq_data *wrqu, char *key)
519{
520 struct r8192_priv *priv = ieee80211_priv(dev);
521 struct ieee80211_device *ieee = priv->ieee80211;
522 int ret;
523 u32 hwkey[4] = {0, 0, 0, 0};
524 u8 mask = 0xff;
525 u32 key_idx = 0;
526 u8 zero_addr[4][6] = { {0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
527 {0x00, 0x00, 0x00, 0x00, 0x00, 0x01},
528 {0x00, 0x00, 0x00, 0x00, 0x00, 0x02},
529 {0x00, 0x00, 0x00, 0x00, 0x00, 0x03} };
530 int i;
531
532 if (!priv->up)
533 return -ENETDOWN;
534
535 down(&priv->wx_sem);
536
537 RT_TRACE(COMP_SEC, "Setting SW wep key");
538 ret = ieee80211_wx_set_encode(priv->ieee80211, info, wrqu, key);
539
540 up(&priv->wx_sem);
541
542
543
544
545 if (wrqu->encoding.length != 0) {
546
547 for (i = 0; i < 4; i++) {
548 hwkey[i] |= key[4*i+0]&mask;
549 if (i == 1 && (4*i+1) == wrqu->encoding.length)
550 mask = 0x00;
551 if (i == 3 && (4*i+1) == wrqu->encoding.length)
552 mask = 0x00;
553 hwkey[i] |= (key[4*i+1]&mask)<<8;
554 hwkey[i] |= (key[4*i+2]&mask)<<16;
555 hwkey[i] |= (key[4*i+3]&mask)<<24;
556 }
557
558 #define CONF_WEP40 0x4
559 #define CONF_WEP104 0x14
560
561 switch (wrqu->encoding.flags & IW_ENCODE_INDEX) {
562 case 0:
563 key_idx = ieee->tx_keyidx;
564 break;
565 case 1:
566 key_idx = 0;
567 break;
568 case 2:
569 key_idx = 1;
570 break;
571 case 3:
572 key_idx = 2;
573 break;
574 case 4:
575 key_idx = 3;
576 break;
577 default:
578 break;
579 }
580
581 if (wrqu->encoding.length == 0x5) {
582 ieee->pairwise_key_type = KEY_TYPE_WEP40;
583 EnableHWSecurityConfig8192(dev);
584
585 setKey(dev,
586 key_idx,
587 key_idx,
588 KEY_TYPE_WEP40,
589 zero_addr[key_idx],
590 0,
591 hwkey);
592
593 }
594
595 else if (wrqu->encoding.length == 0xd) {
596 ieee->pairwise_key_type = KEY_TYPE_WEP104;
597 EnableHWSecurityConfig8192(dev);
598
599 setKey(dev,
600 key_idx,
601 key_idx,
602 KEY_TYPE_WEP104,
603 zero_addr[key_idx],
604 0,
605 hwkey);
606
607 } else {
608 printk("wrong type in WEP, not WEP40 and WEP104\n");
609 }
610
611 }
612
613 return ret;
614}
615
616
617static int r8192_wx_set_scan_type(struct net_device *dev, struct iw_request_info *aa,
618 union iwreq_data *wrqu, char *p)
619{
620
621 struct r8192_priv *priv = ieee80211_priv(dev);
622 int *parms = (int *)p;
623 int mode = parms[0];
624
625 priv->ieee80211->active_scan = mode;
626
627 return 1;
628}
629
630
631
632static int r8192_wx_set_retry(struct net_device *dev,
633 struct iw_request_info *info,
634 union iwreq_data *wrqu, char *extra)
635{
636 struct r8192_priv *priv = ieee80211_priv(dev);
637 int err = 0;
638
639 down(&priv->wx_sem);
640
641 if (wrqu->retry.flags & IW_RETRY_LIFETIME ||
642 wrqu->retry.disabled){
643 err = -EINVAL;
644 goto exit;
645 }
646 if (!(wrqu->retry.flags & IW_RETRY_LIMIT)) {
647 err = -EINVAL;
648 goto exit;
649 }
650
651 if (wrqu->retry.value > R8180_MAX_RETRY) {
652 err = -EINVAL;
653 goto exit;
654 }
655 if (wrqu->retry.flags & IW_RETRY_MAX) {
656 priv->retry_rts = wrqu->retry.value;
657 DMESG("Setting retry for RTS/CTS data to %d", wrqu->retry.value);
658
659 } else {
660 priv->retry_data = wrqu->retry.value;
661 DMESG("Setting retry for non RTS/CTS data to %d", wrqu->retry.value);
662 }
663
664
665
666
667
668
669
670 rtl8192_commit(dev);
671exit:
672 up(&priv->wx_sem);
673
674 return err;
675}
676
677static int r8192_wx_get_retry(struct net_device *dev,
678 struct iw_request_info *info,
679 union iwreq_data *wrqu, char *extra)
680{
681 struct r8192_priv *priv = ieee80211_priv(dev);
682
683
684 wrqu->retry.disabled = 0;
685
686 if ((wrqu->retry.flags & IW_RETRY_TYPE) ==
687 IW_RETRY_LIFETIME)
688 return -EINVAL;
689
690 if (wrqu->retry.flags & IW_RETRY_MAX) {
691 wrqu->retry.flags = IW_RETRY_LIMIT | IW_RETRY_MAX;
692 wrqu->retry.value = priv->retry_rts;
693 } else {
694 wrqu->retry.flags = IW_RETRY_LIMIT | IW_RETRY_MIN;
695 wrqu->retry.value = priv->retry_data;
696 }
697
698
699 return 0;
700}
701
702static int r8192_wx_get_sens(struct net_device *dev,
703 struct iw_request_info *info,
704 union iwreq_data *wrqu, char *extra)
705{
706 struct r8192_priv *priv = ieee80211_priv(dev);
707
708 if (priv->rf_set_sens == NULL)
709 return -1;
710 wrqu->sens.value = priv->sens;
711 return 0;
712}
713
714
715static int r8192_wx_set_sens(struct net_device *dev,
716 struct iw_request_info *info,
717 union iwreq_data *wrqu, char *extra)
718{
719
720 struct r8192_priv *priv = ieee80211_priv(dev);
721 short err = 0;
722
723 down(&priv->wx_sem);
724 if (priv->rf_set_sens == NULL) {
725 err = -1;
726 goto exit;
727 }
728 if (priv->rf_set_sens(dev, wrqu->sens.value) == 0)
729 priv->sens = wrqu->sens.value;
730 else
731 err = -EINVAL;
732
733exit:
734 up(&priv->wx_sem);
735
736 return err;
737}
738
739
740static int r8192_wx_set_enc_ext(struct net_device *dev,
741 struct iw_request_info *info,
742 union iwreq_data *wrqu, char *extra)
743{
744 int ret = 0;
745 struct r8192_priv *priv = ieee80211_priv(dev);
746 struct ieee80211_device *ieee = priv->ieee80211;
747
748
749 down(&priv->wx_sem);
750 ret = ieee80211_wx_set_encode_ext(priv->ieee80211, info, wrqu, extra);
751
752 {
753 u8 broadcast_addr[6] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
754 u8 zero[6] = {0};
755 u32 key[4] = {0};
756 struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
757 struct iw_point *encoding = &wrqu->encoding;
758 u8 idx = 0, alg = 0, group = 0;
759
760 if ((encoding->flags & IW_ENCODE_DISABLED) || ext->alg == IW_ENCODE_ALG_NONE)
761
762 goto end_hw_sec;
763
764
765 alg = (ext->alg == IW_ENCODE_ALG_CCMP)?KEY_TYPE_CCMP:ext->alg;
766 idx = encoding->flags & IW_ENCODE_INDEX;
767 if (idx)
768 idx--;
769 group = ext->ext_flags & IW_ENCODE_EXT_GROUP_KEY;
770
771 if ((!group) || (IW_MODE_ADHOC == ieee->iw_mode) || (alg == KEY_TYPE_WEP40)) {
772 if ((ext->key_len == 13) && (alg == KEY_TYPE_WEP40))
773 alg = KEY_TYPE_WEP104;
774 ieee->pairwise_key_type = alg;
775 EnableHWSecurityConfig8192(dev);
776 }
777 memcpy((u8 *)key, ext->key, 16);
778
779 if ((alg & KEY_TYPE_WEP40) && (ieee->auth_mode != 2)) {
780
781 setKey(dev,
782 idx,
783 idx,
784 alg,
785 zero,
786 0,
787 key);
788 } else if (group) {
789 ieee->group_key_type = alg;
790 setKey(dev,
791 idx,
792 idx,
793 alg,
794 broadcast_addr,
795 0,
796 key);
797 } else {
798 setKey(dev,
799 4,
800 idx,
801 alg,
802 (u8 *)ieee->ap_mac_addr,
803 0,
804 key);
805 }
806
807
808 }
809
810end_hw_sec:
811
812 up(&priv->wx_sem);
813 return ret;
814
815}
816static int r8192_wx_set_auth(struct net_device *dev,
817 struct iw_request_info *info,
818 union iwreq_data *data, char *extra)
819{
820 int ret = 0;
821 struct r8192_priv *priv = ieee80211_priv(dev);
822
823 down(&priv->wx_sem);
824 ret = ieee80211_wx_set_auth(priv->ieee80211, info, &(data->param), extra);
825 up(&priv->wx_sem);
826 return ret;
827}
828
829static int r8192_wx_set_mlme(struct net_device *dev,
830 struct iw_request_info *info,
831 union iwreq_data *wrqu, char *extra)
832{
833
834 int ret = 0;
835 struct r8192_priv *priv = ieee80211_priv(dev);
836
837 down(&priv->wx_sem);
838 ret = ieee80211_wx_set_mlme(priv->ieee80211, info, wrqu, extra);
839
840 up(&priv->wx_sem);
841 return ret;
842}
843
844static int r8192_wx_set_gen_ie(struct net_device *dev,
845 struct iw_request_info *info,
846 union iwreq_data *data, char *extra)
847{
848 int ret = 0;
849 struct r8192_priv *priv = ieee80211_priv(dev);
850
851 down(&priv->wx_sem);
852 ret = ieee80211_wx_set_gen_ie(priv->ieee80211, extra, data->data.length);
853 up(&priv->wx_sem);
854 return ret;
855
856
857}
858
859static int dummy(struct net_device *dev, struct iw_request_info *a,
860 union iwreq_data *wrqu, char *b)
861{
862 return -1;
863}
864
865
866static iw_handler r8192_wx_handlers[] = {
867 NULL,
868 r8192_wx_get_name,
869 dummy,
870 dummy,
871 r8192_wx_set_freq,
872 r8192_wx_get_freq,
873 r8192_wx_set_mode,
874 r8192_wx_get_mode,
875 r8192_wx_set_sens,
876 r8192_wx_get_sens,
877 NULL,
878 rtl8180_wx_get_range,
879 NULL,
880 NULL,
881 NULL,
882 NULL,
883 dummy,
884 dummy,
885 NULL,
886 NULL,
887 r8192_wx_set_wap,
888 r8192_wx_get_wap,
889 r8192_wx_set_mlme,
890 dummy,
891 r8192_wx_set_scan,
892 r8192_wx_get_scan,
893 r8192_wx_set_essid,
894 r8192_wx_get_essid,
895 dummy,
896 dummy,
897 NULL,
898 NULL,
899 r8192_wx_set_rate,
900 r8192_wx_get_rate,
901 r8192_wx_set_rts,
902 r8192_wx_get_rts,
903 r8192_wx_set_frag,
904 r8192_wx_get_frag,
905 dummy,
906 dummy,
907 r8192_wx_set_retry,
908 r8192_wx_get_retry,
909 r8192_wx_set_enc,
910 r8192_wx_get_enc,
911 r8192_wx_set_power,
912 r8192_wx_get_power,
913 NULL,
914 NULL,
915 r8192_wx_set_gen_ie,
916 NULL,
917
918 r8192_wx_set_auth,
919 NULL,
920 r8192_wx_set_enc_ext,
921 NULL,
922 NULL,
923 NULL,
924
925};
926
927
928static const struct iw_priv_args r8192_private_args[] = {
929
930 {
931 SIOCIWFIRSTPRIV + 0x0,
932 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, 0, "badcrc"
933 },
934
935 {
936 SIOCIWFIRSTPRIV + 0x1,
937 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, 0, "activescan"
938
939 },
940 {
941 SIOCIWFIRSTPRIV + 0x2,
942 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, 0, "rawtx"
943 },
944 {
945 SIOCIWFIRSTPRIV + 0x3,
946 IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, 0, "forcereset"
947
948 }
949
950};
951
952
953static iw_handler r8192_private_handler[] = {
954 r8192_wx_set_crcmon,
955 r8192_wx_set_scan_type,
956 r8192_wx_set_rawtx,
957 r8192_wx_force_reset,
958};
959
960struct iw_statistics *r8192_get_wireless_stats(struct net_device *dev)
961{
962 struct r8192_priv *priv = ieee80211_priv(dev);
963 struct ieee80211_device *ieee = priv->ieee80211;
964 struct iw_statistics *wstats = &priv->wstats;
965 int tmp_level = 0;
966 int tmp_qual = 0;
967 int tmp_noise = 0;
968
969 if (ieee->state < IEEE80211_LINKED) {
970 wstats->qual.qual = 0;
971 wstats->qual.level = 0;
972 wstats->qual.noise = 0;
973 wstats->qual.updated = IW_QUAL_ALL_UPDATED | IW_QUAL_DBM;
974 return wstats;
975 }
976
977 tmp_level = (&ieee->current_network)->stats.rssi;
978 tmp_qual = (&ieee->current_network)->stats.signal;
979 tmp_noise = (&ieee->current_network)->stats.noise;
980
981 wstats->qual.level = tmp_level;
982 wstats->qual.qual = tmp_qual;
983 wstats->qual.noise = tmp_noise;
984 wstats->qual.updated = IW_QUAL_ALL_UPDATED | IW_QUAL_DBM;
985 return wstats;
986}
987
988
989struct iw_handler_def r8192_wx_handlers_def = {
990 .standard = r8192_wx_handlers,
991 .num_standard = ARRAY_SIZE(r8192_wx_handlers),
992 .private = r8192_private_handler,
993 .num_private = ARRAY_SIZE(r8192_private_handler),
994 .num_private_args = sizeof(r8192_private_args) / sizeof(struct iw_priv_args),
995 .get_wireless_stats = r8192_get_wireless_stats,
996 .private_args = (struct iw_priv_args *)r8192_private_args,
997};
998