1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64#include <wl_version.h>
65
66#include <linux/if_arp.h>
67#include <linux/ioport.h>
68#include <linux/slab.h>
69#include <linux/delay.h>
70#include <linux/uaccess.h>
71
72#include <debug.h>
73#include <hcf.h>
74#include <hcfdef.h>
75
76#include <wl_if.h>
77#include <wl_internal.h>
78#include <wl_enc.h>
79#include <wl_main.h>
80#include <wl_priv.h>
81#include <wl_util.h>
82#include <wl_netdev.h>
83
84int wvlan_uil_connect(struct uilreq *urq, struct wl_private *lp);
85int wvlan_uil_disconnect(struct uilreq *urq, struct wl_private *lp);
86int wvlan_uil_action(struct uilreq *urq, struct wl_private *lp);
87int wvlan_uil_block(struct uilreq *urq, struct wl_private *lp);
88int wvlan_uil_unblock(struct uilreq *urq, struct wl_private *lp);
89int wvlan_uil_send_diag_msg(struct uilreq *urq, struct wl_private *lp);
90int wvlan_uil_put_info(struct uilreq *urq, struct wl_private *lp);
91int wvlan_uil_get_info(struct uilreq *urq, struct wl_private *lp);
92
93int cfg_driver_info(struct uilreq *urq, struct wl_private *lp);
94int cfg_driver_identity(struct uilreq *urq, struct wl_private *lp);
95
96
97
98
99
100#if DBG
101extern dbg_info_t *DbgInfo;
102#endif
103
104
105
106
107
108
109#ifdef USE_UIL
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130int wvlan_uil(struct uilreq *urq, struct wl_private *lp)
131{
132 int ioctl_ret = 0;
133
134
135 DBG_FUNC("wvlan_uil");
136 DBG_ENTER(DbgInfo);
137
138 switch (urq->command) {
139 case UIL_FUN_CONNECT:
140 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_UIL -- WVLAN2_UIL_CONNECT\n");
141 ioctl_ret = wvlan_uil_connect(urq, lp);
142 break;
143 case UIL_FUN_DISCONNECT:
144 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_UIL -- WVLAN2_UIL_DISCONNECT\n");
145 ioctl_ret = wvlan_uil_disconnect(urq, lp);
146 break;
147 case UIL_FUN_ACTION:
148 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_UIL -- WVLAN2_UIL_ACTION\n");
149 ioctl_ret = wvlan_uil_action(urq, lp);
150 break;
151 case UIL_FUN_SEND_DIAG_MSG:
152 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_UIL -- WVLAN2_UIL_SEND_DIAG_MSG\n");
153 ioctl_ret = wvlan_uil_send_diag_msg(urq, lp);
154 break;
155 case UIL_FUN_GET_INFO:
156 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_UIL -- WVLAN2_UIL_GET_INFO\n");
157 ioctl_ret = wvlan_uil_get_info(urq, lp);
158 break;
159 case UIL_FUN_PUT_INFO:
160 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_UIL -- WVLAN2_UIL_PUT_INFO\n");
161 ioctl_ret = wvlan_uil_put_info(urq, lp);
162 break;
163 default:
164 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_UIL -- UNSUPPORTED UIL CODE: 0x%X", urq->command);
165 ioctl_ret = -EOPNOTSUPP;
166 break;
167 }
168 DBG_LEAVE(DbgInfo);
169 return ioctl_ret;
170}
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195int wvlan_uil_connect(struct uilreq *urq, struct wl_private *lp)
196{
197 int result = 0;
198
199
200
201 DBG_FUNC("wvlan_uil_connect");
202 DBG_ENTER(DbgInfo);
203
204
205 if (!(lp->flags & WVLAN2_UIL_CONNECTED)) {
206 lp->flags |= WVLAN2_UIL_CONNECTED;
207 urq->hcfCtx = &(lp->hcfCtx);
208 urq->result = UIL_SUCCESS;
209 } else {
210 DBG_WARNING(DbgInfo, "UIL_ERR_IN_USE\n");
211 urq->result = UIL_ERR_IN_USE;
212 }
213
214 DBG_LEAVE(DbgInfo);
215 return result;
216}
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241int wvlan_uil_disconnect(struct uilreq *urq, struct wl_private *lp)
242{
243 int result = 0;
244
245
246
247 DBG_FUNC("wvlan_uil_disconnect");
248 DBG_ENTER(DbgInfo);
249
250
251 if (urq->hcfCtx == &(lp->hcfCtx)) {
252 if (lp->flags & WVLAN2_UIL_CONNECTED) {
253 lp->flags &= ~WVLAN2_UIL_CONNECTED;
254
255
256
257
258
259
260 }
261
262 urq->hcfCtx = NULL;
263 urq->result = UIL_SUCCESS;
264 } else {
265 DBG_ERROR(DbgInfo, "UIL_ERR_WRONG_IFB\n");
266 urq->result = UIL_ERR_WRONG_IFB;
267 }
268
269 DBG_LEAVE(DbgInfo);
270 return result;
271}
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296int wvlan_uil_action(struct uilreq *urq, struct wl_private *lp)
297{
298 int result = 0;
299 ltv_t *ltv;
300
301
302
303 DBG_FUNC("wvlan_uil_action");
304 DBG_ENTER(DbgInfo);
305
306
307 if (urq->hcfCtx == &(lp->hcfCtx)) {
308
309 ltv = (ltv_t *)urq->data;
310 if (ltv != NULL) {
311
312
313 switch (ltv->typ) {
314 case UIL_ACT_BLOCK:
315 DBG_TRACE(DbgInfo, "UIL_ACT_BLOCK\n");
316 result = wvlan_uil_block(urq, lp);
317 break;
318 case UIL_ACT_UNBLOCK:
319 DBG_TRACE(DbgInfo, "UIL_ACT_UNBLOCK\n");
320 result = wvlan_uil_unblock(urq, lp);
321 break;
322 case UIL_ACT_SCAN:
323 DBG_TRACE(DbgInfo, "UIL_ACT_SCAN\n");
324 urq->result = hcf_action(&(lp->hcfCtx), MDD_ACT_SCAN);
325 break;
326 case UIL_ACT_APPLY:
327 DBG_TRACE(DbgInfo, "UIL_ACT_APPLY\n");
328 urq->result = wl_apply(lp);
329 break;
330 case UIL_ACT_RESET:
331 DBG_TRACE(DbgInfo, "UIL_ACT_RESET\n");
332 urq->result = wl_go(lp);
333 break;
334 default:
335 DBG_WARNING(DbgInfo, "Unknown action code: 0x%x\n", ltv->typ);
336 break;
337 }
338 } else {
339 DBG_ERROR(DbgInfo, "Bad LTV for this action\n");
340 urq->result = UIL_ERR_LEN;
341 }
342 } else {
343 DBG_ERROR(DbgInfo, "UIL_ERR_WRONG_IFB\n");
344 urq->result = UIL_ERR_WRONG_IFB;
345 }
346
347 DBG_LEAVE(DbgInfo);
348 return result;
349}
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376int wvlan_uil_block(struct uilreq *urq, struct wl_private *lp)
377{
378 int result = 0;
379
380
381
382 DBG_FUNC("wvlan_uil_block");
383 DBG_ENTER(DbgInfo);
384
385 if (urq->hcfCtx == &(lp->hcfCtx)) {
386 if (capable(CAP_NET_ADMIN)) {
387 lp->flags |= WVLAN2_UIL_BUSY;
388 netif_stop_queue(lp->dev);
389 WL_WDS_NETIF_STOP_QUEUE(lp);
390 urq->result = UIL_SUCCESS;
391 } else {
392 DBG_ERROR(DbgInfo, "EPERM\n");
393 urq->result = UIL_FAILURE;
394 result = -EPERM;
395 }
396 } else {
397 DBG_ERROR(DbgInfo, "UIL_ERR_WRONG_IFB\n");
398 urq->result = UIL_ERR_WRONG_IFB;
399 }
400
401 DBG_LEAVE(DbgInfo);
402 return result;
403}
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428int wvlan_uil_unblock(struct uilreq *urq, struct wl_private *lp)
429{
430 int result = 0;
431
432
433
434 DBG_FUNC("wvlan_uil_unblock");
435 DBG_ENTER(DbgInfo);
436
437 if (urq->hcfCtx == &(lp->hcfCtx)) {
438 if (capable(CAP_NET_ADMIN)) {
439 if (lp->flags & WVLAN2_UIL_BUSY) {
440 lp->flags &= ~WVLAN2_UIL_BUSY;
441 netif_wake_queue(lp->dev);
442 WL_WDS_NETIF_WAKE_QUEUE(lp);
443 }
444 } else {
445 DBG_ERROR(DbgInfo, "EPERM\n");
446 urq->result = UIL_FAILURE;
447 result = -EPERM;
448 }
449 } else {
450 DBG_ERROR(DbgInfo, "UIL_ERR_WRONG_IFB\n");
451 urq->result = UIL_ERR_WRONG_IFB;
452 }
453
454 DBG_LEAVE(DbgInfo);
455 return result;
456}
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481int wvlan_uil_send_diag_msg(struct uilreq *urq, struct wl_private *lp)
482{
483 int result = 0;
484 DESC_STRCT Descp[1];
485
486
487
488 DBG_FUNC("wvlan_uil_send_diag_msg");
489 DBG_ENTER(DbgInfo);
490
491 if (urq->hcfCtx == &(lp->hcfCtx)) {
492 if (capable(CAP_NET_ADMIN)) {
493 if ((urq->data != NULL) && (urq->len != 0)) {
494 if (lp->hcfCtx.IFB_RscInd != 0) {
495 u_char *data;
496
497
498 result = verify_area(VERIFY_READ, urq->data, urq->len);
499 if (result != 0) {
500 DBG_ERROR(DbgInfo, "verify_area failed, result: %d\n", result);
501 urq->result = UIL_FAILURE;
502 DBG_LEAVE(DbgInfo);
503 return result;
504 }
505
506 data = kmalloc(urq->len, GFP_KERNEL);
507 if (data != NULL) {
508 memset(Descp, 0, sizeof(DESC_STRCT));
509 memcpy(data, urq->data, urq->len);
510
511 Descp[0].buf_addr = (wci_bufp)data;
512 Descp[0].BUF_CNT = urq->len;
513 Descp[0].next_desc_addr = 0;
514
515 hcf_send_msg(&(lp->hcfCtx), &Descp[0], HCF_PORT_0);
516 kfree(data);
517 } else {
518 DBG_ERROR(DbgInfo, "ENOMEM\n");
519 urq->result = UIL_FAILURE;
520 result = -ENOMEM;
521 DBG_LEAVE(DbgInfo);
522 return result;
523 }
524
525 } else {
526 urq->result = UIL_ERR_BUSY;
527 }
528
529 } else {
530 urq->result = UIL_FAILURE;
531 }
532 } else {
533 DBG_ERROR(DbgInfo, "EPERM\n");
534 urq->result = UIL_FAILURE;
535 result = -EPERM;
536 }
537 } else {
538 DBG_ERROR(DbgInfo, "UIL_ERR_WRONG_IFB\n");
539 urq->result = UIL_ERR_WRONG_IFB;
540 }
541
542 DBG_LEAVE(DbgInfo);
543 return result;
544}
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567int wvlan_uil_put_info(struct uilreq *urq, struct wl_private *lp)
568{
569 int result = 0;
570 ltv_t *pLtv;
571 bool_t ltvAllocated = FALSE;
572 ENCSTRCT sEncryption;
573 size_t len;
574
575#ifdef USE_WDS
576 hcf_16 hcfPort = HCF_PORT_0;
577#endif
578
579 DBG_FUNC("wvlan_uil_put_info");
580 DBG_ENTER(DbgInfo);
581
582
583 if (urq->hcfCtx == &(lp->hcfCtx)) {
584 if (capable(CAP_NET_ADMIN)) {
585 if ((urq->data != NULL) && (urq->len != 0)) {
586
587 if (urq->len < (sizeof(hcf_16) * 2)) {
588 urq->len = sizeof(lp->ltvRecord);
589 urq->result = UIL_ERR_LEN;
590 DBG_ERROR(DbgInfo, "No Length/Type in LTV!!!\n");
591 DBG_ERROR(DbgInfo, "UIL_ERR_LEN\n");
592 DBG_LEAVE(DbgInfo);
593 return result;
594 }
595
596
597 result = verify_area(VERIFY_READ, urq->data, urq->len);
598 if (result != 0) {
599 urq->result = UIL_FAILURE;
600 DBG_ERROR(DbgInfo, "verify_area(), VERIFY_READ FAILED\n");
601 DBG_LEAVE(DbgInfo);
602 return result;
603 }
604
605
606 copy_from_user(&(lp->ltvRecord), urq->data, sizeof(hcf_16) * 2);
607
608
609
610 if (((lp->ltvRecord.len + 1) * sizeof(hcf_16)) > urq->len) {
611 urq->len = sizeof(lp->ltvRecord);
612 urq->result = UIL_ERR_LEN;
613 DBG_ERROR(DbgInfo, "UIL_ERR_LEN\n");
614 DBG_LEAVE(DbgInfo);
615 return result;
616 }
617
618
619
620
621 if (urq->len > sizeof(lp->ltvRecord)) {
622 pLtv = kmalloc(urq->len, GFP_KERNEL);
623 if (pLtv != NULL) {
624 ltvAllocated = TRUE;
625 } else {
626 DBG_ERROR(DbgInfo, "Alloc FAILED\n");
627 urq->len = sizeof(lp->ltvRecord);
628 urq->result = UIL_ERR_LEN;
629 result = -ENOMEM;
630 DBG_LEAVE(DbgInfo);
631 return result;
632 }
633 } else {
634 pLtv = &(lp->ltvRecord);
635 }
636
637
638
639 copy_from_user(pLtv, urq->data, urq->len);
640
641
642
643
644
645 switch (pLtv->typ) {
646 case CFG_CNF_PORT_TYPE:
647 lp->PortType = pLtv->u.u16[0];
648 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
649 break;
650 case CFG_CNF_OWN_MAC_ADDR:
651
652 break;
653 case CFG_CNF_OWN_CHANNEL:
654 lp->Channel = pLtv->u.u16[0];
655 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
656 break;
657
658
659
660 case CFG_CNF_OWN_ATIM_WINDOW:
661 lp->atimWindow = pLtv->u.u16[0];
662 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
663 break;
664 case CFG_CNF_SYSTEM_SCALE:
665 lp->DistanceBetweenAPs = pLtv->u.u16[0];
666 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
667
668 case CFG_CNF_MAX_DATA_LEN:
669
670
671 break;
672 case CFG_CNF_PM_ENABLED:
673 lp->PMEnabled = pLtv->u.u16[0];
674 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
675 break;
676 case CFG_CNF_MCAST_RX:
677 lp->MulticastReceive = pLtv->u.u16[0];
678 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
679 break;
680 case CFG_CNF_MAX_SLEEP_DURATION:
681 lp->MaxSleepDuration = pLtv->u.u16[0];
682 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
683 break;
684 case CFG_CNF_HOLDOVER_DURATION:
685 lp->holdoverDuration = pLtv->u.u16[0];
686 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
687 break;
688 case CFG_CNF_OWN_NAME:
689 memset(lp->StationName, 0, sizeof(lp->StationName));
690 len = min_t(size_t, pLtv->u.u16[0], sizeof(lp->StationName));
691 strlcpy(lp->StationName, &pLtv->u.u8[2], len);
692 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
693 break;
694 case CFG_CNF_LOAD_BALANCING:
695 lp->loadBalancing = pLtv->u.u16[0];
696 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
697 break;
698 case CFG_CNF_MEDIUM_DISTRIBUTION:
699 lp->mediumDistribution = pLtv->u.u16[0];
700 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
701 break;
702#ifdef WARP
703 case CFG_CNF_TX_POW_LVL:
704 lp->txPowLevel = pLtv->u.u16[0];
705 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
706 break;
707
708
709 case CFG_SUPPORTED_RATE_SET_CNTL:
710 lp->srsc[0] = pLtv->u.u16[0];
711 lp->srsc[1] = pLtv->u.u16[1];
712 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
713 pLtv->u.u16[1] = CNV_INT_TO_LITTLE(pLtv->u.u16[1]);
714 break;
715 case CFG_BASIC_RATE_SET_CNTL:
716 lp->brsc[0] = pLtv->u.u16[0];
717 lp->brsc[1] = pLtv->u.u16[1];
718 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
719 pLtv->u.u16[1] = CNV_INT_TO_LITTLE(pLtv->u.u16[1]);
720 break;
721 case CFG_CNF_CONNECTION_CNTL:
722 lp->connectionControl = pLtv->u.u16[0];
723 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
724 break;
725
726#endif
727
728#if 1
729
730
731 case CFG_CNF_OWN_DTIM_PERIOD:
732 lp->DTIMPeriod = pLtv->u.u16[0];
733 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
734 break;
735#ifdef WARP
736 case CFG_CNF_OWN_BEACON_INTERVAL:
737 lp->ownBeaconInterval = pLtv->u.u16[0];
738 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
739 break;
740#endif
741 case CFG_COEXISTENSE_BEHAVIOUR:
742 lp->coexistence = pLtv->u.u16[0];
743 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
744 break;
745#ifdef USE_WDS
746 case CFG_CNF_WDS_ADDR1:
747 memcpy(&lp->wds_port[0].wdsAddress, &pLtv->u.u8[0], ETH_ALEN);
748 hcfPort = HCF_PORT_1;
749 break;
750 case CFG_CNF_WDS_ADDR2:
751 memcpy(&lp->wds_port[1].wdsAddress, &pLtv->u.u8[0], ETH_ALEN);
752 hcfPort = HCF_PORT_2;
753 break;
754 case CFG_CNF_WDS_ADDR3:
755 memcpy(&lp->wds_port[2].wdsAddress, &pLtv->u.u8[0], ETH_ALEN);
756 hcfPort = HCF_PORT_3;
757 break;
758 case CFG_CNF_WDS_ADDR4:
759 memcpy(&lp->wds_port[3].wdsAddress, &pLtv->u.u8[0], ETH_ALEN);
760 hcfPort = HCF_PORT_4;
761 break;
762 case CFG_CNF_WDS_ADDR5:
763 memcpy(&lp->wds_port[4].wdsAddress, &pLtv->u.u8[0], ETH_ALEN);
764 hcfPort = HCF_PORT_5;
765 break;
766 case CFG_CNF_WDS_ADDR6:
767 memcpy(&lp->wds_port[5].wdsAddress, &pLtv->u.u8[0], ETH_ALEN);
768 hcfPort = HCF_PORT_6;
769 break;
770#endif
771
772 case CFG_CNF_MCAST_PM_BUF:
773 lp->multicastPMBuffering = pLtv->u.u16[0];
774 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
775 break;
776 case CFG_CNF_REJECT_ANY:
777 lp->RejectAny = pLtv->u.u16[0];
778 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
779 break;
780#endif
781
782 case CFG_CNF_ENCRYPTION:
783 lp->EnableEncryption = pLtv->u.u16[0];
784 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
785 break;
786 case CFG_CNF_AUTHENTICATION:
787 lp->authentication = pLtv->u.u16[0];
788 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
789 break;
790#if 1
791
792
793
794
795
796
797 case CFG_CNF_MCAST_RATE:
798
799 break;
800 case CFG_CNF_INTRA_BSS_RELAY:
801 lp->intraBSSRelay = pLtv->u.u16[0];
802 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
803 break;
804#endif
805
806 case CFG_CNF_MICRO_WAVE:
807
808 break;
809
810
811
812
813
814
815
816
817
818
819
820
821 case CFG_CNF_OWN_SSID:
822
823 case CFG_DESIRED_SSID:
824 memset(lp->NetworkName, 0, sizeof(lp->NetworkName));
825 memcpy((void *)lp->NetworkName, (void *)&pLtv->u.u8[2], (size_t)pLtv->u.u16[0]);
826 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
827
828
829 if ((strlen(&pLtv->u.u8[2]) == 0) ||
830 (strcmp(&pLtv->u.u8[2], "ANY") == 0) ||
831 (strcmp(&pLtv->u.u8[2], "any") == 0)) {
832
833
834 pLtv->u.u16[0] = 0;
835 pLtv->u.u8[2] = 0;
836 }
837 break;
838 case CFG_GROUP_ADDR:
839
840 break;
841 case CFG_CREATE_IBSS:
842 lp->CreateIBSS = pLtv->u.u16[0];
843 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
844 break;
845 case CFG_RTS_THRH:
846 lp->RTSThreshold = pLtv->u.u16[0];
847 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
848 break;
849 case CFG_TX_RATE_CNTL:
850 lp->TxRateControl[0] = pLtv->u.u16[0];
851 lp->TxRateControl[1] = pLtv->u.u16[1];
852 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
853 pLtv->u.u16[1] = CNV_INT_TO_LITTLE(pLtv->u.u16[1]);
854 break;
855 case CFG_PROMISCUOUS_MODE:
856
857 break;
858
859
860
861#if 1
862
863 case CFG_RTS_THRH0:
864 lp->RTSThreshold = pLtv->u.u16[0];
865 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
866 break;
867 case CFG_TX_RATE_CNTL0:
868
869 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
870 break;
871#ifdef USE_WDS
872 case CFG_RTS_THRH1:
873 lp->wds_port[0].rtsThreshold = pLtv->u.u16[0];
874 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
875 hcfPort = HCF_PORT_1;
876 break;
877 case CFG_RTS_THRH2:
878 lp->wds_port[1].rtsThreshold = pLtv->u.u16[0];
879 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
880 hcfPort = HCF_PORT_2;
881 break;
882 case CFG_RTS_THRH3:
883 lp->wds_port[2].rtsThreshold = pLtv->u.u16[0];
884 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
885 hcfPort = HCF_PORT_3;
886 break;
887 case CFG_RTS_THRH4:
888 lp->wds_port[3].rtsThreshold = pLtv->u.u16[0];
889 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
890 hcfPort = HCF_PORT_4;
891 break;
892 case CFG_RTS_THRH5:
893 lp->wds_port[4].rtsThreshold = pLtv->u.u16[0];
894 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
895 hcfPort = HCF_PORT_5;
896 break;
897 case CFG_RTS_THRH6:
898 lp->wds_port[5].rtsThreshold = pLtv->u.u16[0];
899 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
900 hcfPort = HCF_PORT_6;
901 break;
902 case CFG_TX_RATE_CNTL1:
903 lp->wds_port[0].txRateCntl = pLtv->u.u16[0];
904 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
905 hcfPort = HCF_PORT_1;
906 break;
907 case CFG_TX_RATE_CNTL2:
908 lp->wds_port[1].txRateCntl = pLtv->u.u16[0];
909 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
910 hcfPort = HCF_PORT_2;
911 break;
912 case CFG_TX_RATE_CNTL3:
913 lp->wds_port[2].txRateCntl = pLtv->u.u16[0];
914 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
915 hcfPort = HCF_PORT_3;
916 break;
917 case CFG_TX_RATE_CNTL4:
918 lp->wds_port[3].txRateCntl = pLtv->u.u16[0];
919 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
920 hcfPort = HCF_PORT_4;
921 break;
922 case CFG_TX_RATE_CNTL5:
923 lp->wds_port[4].txRateCntl = pLtv->u.u16[0];
924 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
925 hcfPort = HCF_PORT_5;
926 break;
927 case CFG_TX_RATE_CNTL6:
928 lp->wds_port[5].txRateCntl = pLtv->u.u16[0];
929 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
930 hcfPort = HCF_PORT_6;
931 break;
932#endif
933#endif
934
935 case CFG_DEFAULT_KEYS:
936 {
937 CFG_DEFAULT_KEYS_STRCT *pKeys = (CFG_DEFAULT_KEYS_STRCT *)pLtv;
938
939 pKeys->key[0].len = CNV_INT_TO_LITTLE(pKeys->key[0].len);
940 pKeys->key[1].len = CNV_INT_TO_LITTLE(pKeys->key[1].len);
941 pKeys->key[2].len = CNV_INT_TO_LITTLE(pKeys->key[2].len);
942 pKeys->key[3].len = CNV_INT_TO_LITTLE(pKeys->key[3].len);
943
944 memcpy((void *)&(lp->DefaultKeys), (void *)pKeys,
945 sizeof(CFG_DEFAULT_KEYS_STRCT));
946 }
947 break;
948 case CFG_TX_KEY_ID:
949 lp->TransmitKeyID = pLtv->u.u16[0];
950 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
951 break;
952 case CFG_SCAN_SSID:
953
954 break;
955 case CFG_TICK_TIME:
956
957 break;
958
959 case CFG_MAX_LOAD_TIME:
960 case CFG_DL_BUF:
961
962 case CFG_NIC_SERIAL_NUMBER:
963 case CFG_NIC_IDENTITY:
964 case CFG_NIC_MFI_SUP_RANGE:
965 case CFG_NIC_CFI_SUP_RANGE:
966 case CFG_NIC_TEMP_TYPE:
967 case CFG_NIC_PROFILE:
968 case CFG_FW_IDENTITY:
969 case CFG_FW_SUP_RANGE:
970 case CFG_MFI_ACT_RANGES_STA:
971 case CFG_CFI_ACT_RANGES_STA:
972 case CFG_PORT_STAT:
973 case CFG_CUR_SSID:
974 case CFG_CUR_BSSID:
975 case CFG_COMMS_QUALITY:
976 case CFG_CUR_TX_RATE:
977 case CFG_CUR_BEACON_INTERVAL:
978 case CFG_CUR_SCALE_THRH:
979 case CFG_PROTOCOL_RSP_TIME:
980 case CFG_CUR_SHORT_RETRY_LIMIT:
981 case CFG_CUR_LONG_RETRY_LIMIT:
982 case CFG_MAX_TX_LIFETIME:
983 case CFG_MAX_RX_LIFETIME:
984 case CFG_CF_POLLABLE:
985 case CFG_AUTHENTICATION_ALGORITHMS:
986 case CFG_PRIVACY_OPT_IMPLEMENTED:
987
988
989
990
991
992
993
994
995
996 case CFG_NIC_MAC_ADDR:
997 case CFG_PCF_INFO:
998
999 case CFG_PHY_TYPE:
1000 case CFG_CUR_CHANNEL:
1001
1002
1003 case CFG_SUPPORTED_DATA_RATES:
1004 break;
1005 case CFG_AP_MODE:
1006
1007 DBG_ERROR(DbgInfo, "set CFG_AP_MODE no longer supported\n");
1008 break;
1009 case CFG_ENCRYPT_STRING:
1010
1011 memset(lp->szEncryption, 0, sizeof(lp->szEncryption));
1012 memcpy((void *)lp->szEncryption, (void *)&pLtv->u.u8[0],
1013 (pLtv->len * sizeof(hcf_16)));
1014 wl_wep_decode(CRYPT_CODE, &sEncryption,
1015 lp->szEncryption);
1016
1017
1018
1019
1020
1021
1022
1023
1024 lp->TransmitKeyID = sEncryption.wTxKeyID + 1;
1025 lp->EnableEncryption = sEncryption.wEnabled;
1026
1027 memcpy(&lp->DefaultKeys, &sEncryption.EncStr,
1028 sizeof(CFG_DEFAULT_KEYS_STRCT));
1029 break;
1030
1031
1032
1033
1034
1035
1036 case CFG_DRIVER_ENABLE:
1037 lp->driverEnable = pLtv->u.u16[0];
1038 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
1039 break;
1040 case CFG_WOLAS_ENABLE:
1041 lp->wolasEnable = pLtv->u.u16[0];
1042 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
1043 break;
1044 case CFG_SET_WPA_AUTH_KEY_MGMT_SUITE:
1045 lp->AuthKeyMgmtSuite = pLtv->u.u16[0];
1046 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
1047 break;
1048 case CFG_DISASSOCIATE_ADDR:
1049 pLtv->u.u16[ETH_ALEN / 2] = CNV_INT_TO_LITTLE(pLtv->u.u16[ETH_ALEN / 2]);
1050 break;
1051 case CFG_ADD_TKIP_DEFAULT_KEY:
1052 case CFG_REMOVE_TKIP_DEFAULT_KEY:
1053
1054 pLtv->u.u16[0] = CNV_INT_TO_LITTLE(pLtv->u.u16[0]);
1055 break;
1056 case CFG_ADD_TKIP_MAPPED_KEY:
1057 break;
1058 case CFG_REMOVE_TKIP_MAPPED_KEY:
1059 break;
1060
1061 case CFG_MB_INFO:
1062 case CFG_IFB:
1063 default:
1064 break;
1065 }
1066
1067
1068
1069
1070
1071 switch (pLtv->typ) {
1072 case CFG_CNF_PORT_TYPE:
1073 case CFG_CNF_OWN_MAC_ADDR:
1074 case CFG_CNF_OWN_CHANNEL:
1075 case CFG_CNF_OWN_SSID:
1076 case CFG_CNF_OWN_ATIM_WINDOW:
1077 case CFG_CNF_SYSTEM_SCALE:
1078 case CFG_CNF_MAX_DATA_LEN:
1079 case CFG_CNF_PM_ENABLED:
1080 case CFG_CNF_MCAST_RX:
1081 case CFG_CNF_MAX_SLEEP_DURATION:
1082 case CFG_CNF_HOLDOVER_DURATION:
1083 case CFG_CNF_OWN_NAME:
1084 case CFG_CNF_LOAD_BALANCING:
1085 case CFG_CNF_MEDIUM_DISTRIBUTION:
1086#ifdef WARP
1087 case CFG_CNF_TX_POW_LVL:
1088 case CFG_CNF_CONNECTION_CNTL:
1089
1090#endif
1091#if 1
1092
1093 case CFG_CNF_OWN_DTIM_PERIOD:
1094#ifdef WARP
1095 case CFG_CNF_OWN_BEACON_INTERVAL:
1096#endif
1097#ifdef USE_WDS
1098 case CFG_CNF_WDS_ADDR1:
1099 case CFG_CNF_WDS_ADDR2:
1100 case CFG_CNF_WDS_ADDR3:
1101 case CFG_CNF_WDS_ADDR4:
1102 case CFG_CNF_WDS_ADDR5:
1103 case CFG_CNF_WDS_ADDR6:
1104#endif
1105 case CFG_CNF_MCAST_PM_BUF:
1106 case CFG_CNF_REJECT_ANY:
1107#endif
1108
1109 case CFG_CNF_ENCRYPTION:
1110 case CFG_CNF_AUTHENTICATION:
1111#if 1
1112
1113
1114 case CFG_CNF_EXCL_UNENCRYPTED:
1115 case CFG_CNF_MCAST_RATE:
1116 case CFG_CNF_INTRA_BSS_RELAY:
1117#endif
1118
1119 case CFG_CNF_MICRO_WAVE:
1120
1121
1122
1123
1124
1125 case CFG_AP_MODE:
1126 case CFG_ENCRYPT_STRING:
1127
1128 case CFG_WOLAS_ENABLE:
1129 case CFG_MB_INFO:
1130 case CFG_IFB:
1131 break;
1132
1133 case CFG_DRIVER_ENABLE:
1134 if (lp->driverEnable) {
1135 hcf_cntl(&(lp->hcfCtx), HCF_CNTL_ENABLE | HCF_PORT_0);
1136 hcf_cntl(&(lp->hcfCtx), HCF_CNTL_CONNECT);
1137 } else {
1138 hcf_cntl(&(lp->hcfCtx), HCF_CNTL_DISABLE | HCF_PORT_0);
1139 hcf_cntl(&(lp->hcfCtx), HCF_CNTL_DISCONNECT);
1140 }
1141 break;
1142 default:
1143 wl_act_int_off(lp);
1144 urq->result = hcf_put_info(&(lp->hcfCtx), (LTVP) pLtv);
1145 wl_act_int_on(lp);
1146 break;
1147 }
1148
1149 if (ltvAllocated)
1150 kfree(pLtv);
1151 } else {
1152 urq->result = UIL_FAILURE;
1153 }
1154 } else {
1155 DBG_ERROR(DbgInfo, "EPERM\n");
1156 urq->result = UIL_FAILURE;
1157 result = -EPERM;
1158 }
1159 } else {
1160 DBG_ERROR(DbgInfo, "UIL_ERR_WRONG_IFB\n");
1161 urq->result = UIL_ERR_WRONG_IFB;
1162 }
1163
1164 DBG_LEAVE(DbgInfo);
1165 return result;
1166}
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
1183
1184
1185
1186
1187
1188
1189
1190int wvlan_uil_get_info(struct uilreq *urq, struct wl_private *lp)
1191{
1192 int result = 0;
1193 int i;
1194
1195
1196 DBG_FUNC("wvlan_uil_get_info");
1197 DBG_ENTER(DbgInfo);
1198
1199 if (urq->hcfCtx == &(lp->hcfCtx)) {
1200 if ((urq->data != NULL) && (urq->len != 0)) {
1201 ltv_t *pLtv;
1202 bool_t ltvAllocated = FALSE;
1203
1204
1205 if (urq->len < (sizeof(hcf_16) * 2)) {
1206 urq->len = sizeof(lp->ltvRecord);
1207 DBG_ERROR(DbgInfo, "No Length/Type in LTV!!!\n");
1208 DBG_ERROR(DbgInfo, "UIL_ERR_LEN\n");
1209 urq->result = UIL_ERR_LEN;
1210 DBG_LEAVE(DbgInfo);
1211 return result;
1212 }
1213
1214
1215 result = verify_area(VERIFY_READ, urq->data, sizeof(hcf_16) * 2);
1216 if (result != 0) {
1217 DBG_ERROR(DbgInfo, "verify_area(), VERIFY_READ FAILED\n");
1218 urq->result = UIL_FAILURE;
1219 DBG_LEAVE(DbgInfo);
1220 return result;
1221 }
1222
1223
1224 result = copy_from_user(&(lp->ltvRecord), urq->data, sizeof(hcf_16) * 2);
1225
1226
1227
1228 if (((lp->ltvRecord.len + 1) * sizeof(hcf_16)) > urq->len) {
1229 DBG_ERROR(DbgInfo, "Incoming LTV too big\n");
1230 urq->len = sizeof(lp->ltvRecord);
1231 urq->result = UIL_ERR_LEN;
1232 DBG_LEAVE(DbgInfo);
1233 return result;
1234 }
1235
1236
1237 switch (lp->ltvRecord.typ) {
1238 case CFG_NIC_IDENTITY:
1239 memcpy(&lp->ltvRecord.u.u8[0], &lp->NICIdentity, sizeof(lp->NICIdentity));
1240 break;
1241 case CFG_PRI_IDENTITY:
1242 memcpy(&lp->ltvRecord.u.u8[0], &lp->PrimaryIdentity, sizeof(lp->PrimaryIdentity));
1243 break;
1244 case CFG_AP_MODE:
1245 DBG_ERROR(DbgInfo, "set CFG_AP_MODE no longer supported, so is get useful ????\n");
1246 lp->ltvRecord.u.u16[0] =
1247 CNV_INT_TO_LITTLE(lp->hcfCtx.IFB_FWIdentity.comp_id) == COMP_ID_FW_AP;
1248 break;
1249
1250 case CFG_ENCRYPT_STRING:
1251 case CFG_COUNTRY_STRING:
1252 case CFG_DRIVER_ENABLE:
1253 case CFG_WOLAS_ENABLE:
1254
1255 urq->result = UIL_FAILURE;
1256 break;
1257 case CFG_DRV_INFO:
1258 DBG_TRACE(DbgInfo, "Intercept CFG_DRV_INFO\n");
1259 result = cfg_driver_info(urq, lp);
1260 break;
1261 case CFG_DRV_IDENTITY:
1262 DBG_TRACE(DbgInfo, "Intercept CFG_DRV_IDENTITY\n");
1263 result = cfg_driver_identity(urq, lp);
1264 break;
1265 case CFG_IFB:
1266
1267 if (!capable(CAP_NET_ADMIN)) {
1268 result = -EPERM;
1269 break;
1270 }
1271
1272
1273
1274 case CFG_FW_IDENTITY:
1275 default:
1276
1277
1278 result = verify_area(VERIFY_WRITE, urq->data, urq->len);
1279 if (result != 0) {
1280 DBG_ERROR(DbgInfo, "verify_area(), VERIFY_WRITE FAILED\n");
1281 urq->result = UIL_FAILURE;
1282 break;
1283 }
1284
1285
1286
1287
1288 if (urq->len > sizeof(lp->ltvRecord)) {
1289 pLtv = kmalloc(urq->len, GFP_KERNEL);
1290 if (pLtv != NULL) {
1291 ltvAllocated = TRUE;
1292
1293
1294 memcpy(pLtv, &(lp->ltvRecord), sizeof(hcf_16) * 2);
1295 } else {
1296 urq->len = sizeof(lp->ltvRecord);
1297 urq->result = UIL_ERR_LEN;
1298 DBG_ERROR(DbgInfo, "kmalloc FAILED\n");
1299 DBG_ERROR(DbgInfo, "UIL_ERR_LEN\n");
1300 result = -ENOMEM;
1301 break;
1302 }
1303 } else {
1304 pLtv = &(lp->ltvRecord);
1305 }
1306
1307 wl_act_int_off(lp);
1308 urq->result = hcf_get_info(&(lp->hcfCtx), (LTVP) pLtv);
1309 wl_act_int_on(lp);
1310
1311
1312
1313
1314
1315
1316
1317
1318
1319
1320 break;
1321 }
1322
1323
1324 switch (lp->ltvRecord.typ) {
1325
1326 case CFG_CNF_PORT_TYPE:
1327 case CFG_CNF_OWN_CHANNEL:
1328 case CFG_CNF_OWN_ATIM_WINDOW:
1329 case CFG_CNF_SYSTEM_SCALE:
1330 case CFG_CNF_MAX_DATA_LEN:
1331 case CFG_CNF_PM_ENABLED:
1332 case CFG_CNF_MCAST_RX:
1333 case CFG_CNF_MAX_SLEEP_DURATION:
1334 case CFG_CNF_HOLDOVER_DURATION:
1335 case CFG_CNF_OWN_DTIM_PERIOD:
1336 case CFG_CNF_MCAST_PM_BUF:
1337 case CFG_CNF_REJECT_ANY:
1338 case CFG_CNF_ENCRYPTION:
1339 case CFG_CNF_AUTHENTICATION:
1340 case CFG_CNF_EXCL_UNENCRYPTED:
1341 case CFG_CNF_INTRA_BSS_RELAY:
1342 case CFG_CNF_MICRO_WAVE:
1343 case CFG_CNF_LOAD_BALANCING:
1344 case CFG_CNF_MEDIUM_DISTRIBUTION:
1345#ifdef WARP
1346 case CFG_CNF_TX_POW_LVL:
1347 case CFG_CNF_CONNECTION_CNTL:
1348 case CFG_CNF_OWN_BEACON_INTERVAL:
1349 case CFG_COEXISTENSE_BEHAVIOUR:
1350
1351#endif
1352 case CFG_CREATE_IBSS:
1353 case CFG_RTS_THRH:
1354 case CFG_PROMISCUOUS_MODE:
1355
1356 case CFG_RTS_THRH0:
1357 case CFG_RTS_THRH1:
1358 case CFG_RTS_THRH2:
1359 case CFG_RTS_THRH3:
1360 case CFG_RTS_THRH4:
1361 case CFG_RTS_THRH5:
1362 case CFG_RTS_THRH6:
1363 case CFG_TX_RATE_CNTL0:
1364 case CFG_TX_RATE_CNTL1:
1365 case CFG_TX_RATE_CNTL2:
1366 case CFG_TX_RATE_CNTL3:
1367 case CFG_TX_RATE_CNTL4:
1368 case CFG_TX_RATE_CNTL5:
1369 case CFG_TX_RATE_CNTL6:
1370 case CFG_TX_KEY_ID:
1371 case CFG_TICK_TIME:
1372 case CFG_MAX_LOAD_TIME:
1373 case CFG_NIC_TEMP_TYPE:
1374 case CFG_PORT_STAT:
1375 case CFG_CUR_TX_RATE:
1376 case CFG_CUR_BEACON_INTERVAL:
1377 case CFG_PROTOCOL_RSP_TIME:
1378 case CFG_CUR_SHORT_RETRY_LIMIT:
1379 case CFG_CUR_LONG_RETRY_LIMIT:
1380 case CFG_MAX_TX_LIFETIME:
1381 case CFG_MAX_RX_LIFETIME:
1382 case CFG_CF_POLLABLE:
1383 case CFG_PRIVACY_OPT_IMPLEMENTED:
1384
1385
1386
1387
1388
1389
1390
1391
1392
1393 case CFG_PHY_TYPE:
1394 case CFG_CUR_CHANNEL:
1395
1396
1397
1398
1399
1400 case CFG_CNF_OWN_SSID:
1401 case CFG_CNF_OWN_NAME:
1402
1403 case CFG_DESIRED_SSID:
1404 case CFG_SCAN_SSID:
1405 case CFG_CUR_SSID:
1406 lp->ltvRecord.u.u16[0] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[0]);
1407 break;
1408
1409 case CFG_CNF_OWN_MAC_ADDR:
1410
1411 case CFG_CNF_WDS_ADDR1:
1412 case CFG_CNF_WDS_ADDR2:
1413 case CFG_CNF_WDS_ADDR3:
1414 case CFG_CNF_WDS_ADDR4:
1415 case CFG_CNF_WDS_ADDR5:
1416 case CFG_CNF_WDS_ADDR6:
1417 case CFG_GROUP_ADDR:
1418 case CFG_NIC_SERIAL_NUMBER:
1419 case CFG_CUR_BSSID:
1420 case CFG_NIC_MAC_ADDR:
1421 case CFG_SUPPORTED_DATA_RATES:
1422 break;
1423
1424
1425
1426
1427
1428
1429
1430
1431
1432
1433
1434
1435 case CFG_DEFAULT_KEYS:
1436 {
1437 CFG_DEFAULT_KEYS_STRCT *pKeys = (CFG_DEFAULT_KEYS_STRCT *)&lp->ltvRecord.u.u8[0];
1438
1439 pKeys[0].len = CNV_INT_TO_LITTLE(pKeys[0].len);
1440 pKeys[1].len = CNV_INT_TO_LITTLE(pKeys[1].len);
1441 pKeys[2].len = CNV_INT_TO_LITTLE(pKeys[2].len);
1442 pKeys[3].len = CNV_INT_TO_LITTLE(pKeys[3].len);
1443 }
1444 break;
1445 case CFG_CNF_MCAST_RATE:
1446 case CFG_TX_RATE_CNTL:
1447 case CFG_SUPPORTED_RATE_SET_CNTL:
1448 case CFG_BASIC_RATE_SET_CNTL:
1449 lp->ltvRecord.u.u16[0] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[0]);
1450 lp->ltvRecord.u.u16[1] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[1]);
1451 break;
1452 case CFG_DL_BUF:
1453 case CFG_NIC_IDENTITY:
1454 case CFG_COMMS_QUALITY:
1455 case CFG_PCF_INFO:
1456 lp->ltvRecord.u.u16[0] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[0]);
1457 lp->ltvRecord.u.u16[1] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[1]);
1458 lp->ltvRecord.u.u16[2] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[2]);
1459 break;
1460 case CFG_FW_IDENTITY:
1461 lp->ltvRecord.u.u16[0] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[0]);
1462 lp->ltvRecord.u.u16[1] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[1]);
1463 lp->ltvRecord.u.u16[2] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[2]);
1464 lp->ltvRecord.u.u16[3] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[3]);
1465 break;
1466
1467 case CFG_NIC_MFI_SUP_RANGE:
1468 case CFG_NIC_CFI_SUP_RANGE:
1469 case CFG_NIC_PROFILE:
1470 case CFG_FW_SUP_RANGE:
1471 lp->ltvRecord.u.u16[0] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[0]);
1472 lp->ltvRecord.u.u16[1] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[1]);
1473 lp->ltvRecord.u.u16[2] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[2]);
1474 lp->ltvRecord.u.u16[3] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[3]);
1475 lp->ltvRecord.u.u16[4] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[4]);
1476 break;
1477 case CFG_MFI_ACT_RANGES_STA:
1478 case CFG_CFI_ACT_RANGES_STA:
1479 case CFG_CUR_SCALE_THRH:
1480 case CFG_AUTHENTICATION_ALGORITHMS:
1481 for (i = 0; i < (lp->ltvRecord.len - 1); i++)
1482 lp->ltvRecord.u.u16[i] = CNV_INT_TO_LITTLE(lp->ltvRecord.u.u16[i]);
1483 break;
1484
1485 case CFG_PRI_IDENTITY:
1486 break;
1487 case CFG_MB_INFO:
1488
1489 break;
1490
1491 case CFG_IFB:
1492 case CFG_DRV_INFO:
1493 case CFG_AP_MODE:
1494 case CFG_ENCRYPT_STRING:
1495 case CFG_COUNTRY_STRING:
1496 case CFG_DRIVER_ENABLE:
1497 case CFG_WOLAS_ENABLE:
1498 default:
1499 break;
1500 }
1501
1502
1503 copy_to_user(urq->data, &(lp->ltvRecord), urq->len);
1504
1505 if (ltvAllocated)
1506 kfree(&(lp->ltvRecord));
1507 urq->result = UIL_SUCCESS;
1508 } else {
1509 urq->result = UIL_FAILURE;
1510 }
1511 } else {
1512 DBG_ERROR(DbgInfo, "UIL_ERR_WRONG_IFB\n");
1513 urq->result = UIL_ERR_WRONG_IFB;
1514 }
1515
1516 DBG_LEAVE(DbgInfo);
1517 return result;
1518}
1519
1520
1521
1522
1523
1524
1525
1526
1527
1528
1529
1530
1531
1532
1533
1534
1535
1536
1537
1538
1539
1540
1541
1542
1543
1544int cfg_driver_info(struct uilreq *urq, struct wl_private *lp)
1545{
1546 int result = 0;
1547
1548
1549
1550 DBG_FUNC("cfg_driver_info");
1551 DBG_ENTER(DbgInfo);
1552
1553
1554
1555 if (urq->len < sizeof(lp->driverInfo)) {
1556 urq->len = sizeof(lp->driverInfo);
1557 urq->result = UIL_ERR_LEN;
1558 DBG_LEAVE(DbgInfo);
1559 return result;
1560 }
1561
1562
1563 result = verify_area(VERIFY_WRITE, urq->data, sizeof(lp->driverInfo));
1564 if (result != 0) {
1565 urq->result = UIL_FAILURE;
1566 DBG_LEAVE(DbgInfo);
1567 return result;
1568 }
1569
1570 lp->driverInfo.card_stat = lp->hcfCtx.IFB_CardStat;
1571
1572
1573 urq->result = UIL_SUCCESS;
1574 copy_to_user(urq->data, &(lp->driverInfo), sizeof(lp->driverInfo));
1575
1576 DBG_LEAVE(DbgInfo);
1577 return result;
1578}
1579
1580
1581
1582
1583
1584
1585
1586
1587
1588
1589
1590
1591
1592
1593
1594
1595
1596
1597
1598
1599
1600
1601
1602
1603int cfg_driver_identity(struct uilreq *urq, struct wl_private *lp)
1604{
1605 int result = 0;
1606
1607
1608
1609 DBG_FUNC("wvlan_driver_identity");
1610 DBG_ENTER(DbgInfo);
1611
1612
1613
1614 if (urq->len < sizeof(lp->driverIdentity)) {
1615 urq->len = sizeof(lp->driverIdentity);
1616 urq->result = UIL_ERR_LEN;
1617 DBG_LEAVE(DbgInfo);
1618 return result;
1619 }
1620
1621
1622 result = verify_area(VERIFY_WRITE, urq->data, sizeof(lp->driverIdentity));
1623 if (result != 0) {
1624 urq->result = UIL_FAILURE;
1625 DBG_LEAVE(DbgInfo);
1626 return result;
1627 }
1628
1629
1630 urq->result = UIL_SUCCESS;
1631 copy_to_user(urq->data, &(lp->driverIdentity), sizeof(lp->driverIdentity));
1632
1633 DBG_LEAVE(DbgInfo);
1634 return result;
1635}
1636
1637
1638
1639#endif
1640
1641
1642
1643
1644
1645#ifdef WIRELESS_EXT
1646
1647
1648
1649
1650
1651
1652
1653
1654
1655
1656
1657
1658
1659
1660
1661
1662
1663
1664
1665
1666
1667int wvlan_set_netname(struct net_device *dev,
1668 struct iw_request_info *info,
1669 union iwreq_data *wrqu,
1670 char *extra)
1671{
1672 struct wl_private *lp = wl_priv(dev);
1673 unsigned long flags;
1674 int ret = 0;
1675
1676
1677
1678 DBG_FUNC("wvlan_set_netname");
1679 DBG_ENTER(DbgInfo);
1680
1681 wl_lock(lp, &flags);
1682
1683 memset(lp->NetworkName, 0, sizeof(lp->NetworkName));
1684 memcpy(lp->NetworkName, extra, wrqu->data.length);
1685
1686
1687 wl_apply(lp);
1688 wl_unlock(lp, &flags);
1689
1690 DBG_LEAVE(DbgInfo);
1691 return ret;
1692}
1693
1694
1695
1696
1697
1698
1699
1700
1701
1702
1703
1704
1705
1706
1707
1708
1709
1710
1711
1712
1713
1714
1715
1716
1717int wvlan_get_netname(struct net_device *dev,
1718 struct iw_request_info *info,
1719 union iwreq_data *wrqu,
1720 char *extra)
1721{
1722 struct wl_private *lp = wl_priv(dev);
1723 unsigned long flags;
1724 int ret = 0;
1725 int status = -1;
1726 wvName_t *pName;
1727
1728
1729
1730 DBG_FUNC("wvlan_get_netname");
1731 DBG_ENTER(DbgInfo);
1732
1733 wl_lock(lp, &flags);
1734
1735
1736 lp->ltvRecord.len = 1 + (sizeof(*pName) / sizeof(hcf_16));
1737 lp->ltvRecord.typ = CFG_CUR_SSID;
1738
1739 status = hcf_get_info(&(lp->hcfCtx), (LTVP)&(lp->ltvRecord));
1740
1741 if (status == HCF_SUCCESS) {
1742 pName = (wvName_t *)&(lp->ltvRecord.u.u32);
1743
1744 memset(extra, '\0', HCF_MAX_NAME_LEN);
1745 wrqu->data.length = pName->length;
1746
1747 memcpy(extra, pName->name, pName->length);
1748 } else {
1749 ret = -EFAULT;
1750 }
1751
1752 wl_unlock(lp, &flags);
1753
1754 DBG_LEAVE(DbgInfo);
1755 return ret;
1756}
1757
1758
1759
1760
1761
1762
1763
1764
1765
1766
1767
1768
1769
1770
1771
1772
1773
1774
1775
1776
1777
1778
1779
1780
1781int wvlan_set_station_nickname(struct net_device *dev,
1782 struct iw_request_info *info,
1783 union iwreq_data *wrqu,
1784 char *extra)
1785{
1786 struct wl_private *lp = wl_priv(dev);
1787 unsigned long flags;
1788 size_t len;
1789 int ret = 0;
1790
1791
1792
1793 DBG_FUNC("wvlan_set_station_nickname");
1794 DBG_ENTER(DbgInfo);
1795
1796 wl_lock(lp, &flags);
1797
1798 memset(lp->StationName, 0, sizeof(lp->StationName));
1799 len = min_t(size_t, wrqu->data.length, sizeof(lp->StationName));
1800 strlcpy(lp->StationName, extra, len);
1801
1802
1803 wl_apply(lp);
1804 wl_unlock(lp, &flags);
1805
1806 DBG_LEAVE(DbgInfo);
1807 return ret;
1808}
1809
1810
1811
1812
1813
1814
1815
1816
1817
1818
1819
1820
1821
1822
1823
1824
1825
1826
1827
1828
1829
1830
1831
1832
1833int wvlan_get_station_nickname(struct net_device *dev,
1834 struct iw_request_info *info,
1835 union iwreq_data *wrqu,
1836 char *extra)
1837{
1838 struct wl_private *lp = wl_priv(dev);
1839 unsigned long flags;
1840 int ret = 0;
1841 int status = -1;
1842 wvName_t *pName;
1843
1844
1845
1846 DBG_FUNC("wvlan_get_station_nickname");
1847 DBG_ENTER(DbgInfo);
1848
1849 wl_lock(lp, &flags);
1850
1851
1852 lp->ltvRecord.len = 1 + (sizeof(*pName) / sizeof(hcf_16));
1853 lp->ltvRecord.typ = CFG_CNF_OWN_NAME;
1854
1855 status = hcf_get_info(&(lp->hcfCtx), (LTVP)&(lp->ltvRecord));
1856
1857 if (status == HCF_SUCCESS) {
1858 pName = (wvName_t *)&(lp->ltvRecord.u.u32);
1859
1860 memset(extra, '\0', HCF_MAX_NAME_LEN);
1861 wrqu->data.length = pName->length;
1862 memcpy(extra, pName->name, pName->length);
1863 } else {
1864 ret = -EFAULT;
1865 }
1866
1867 wl_unlock(lp, &flags);
1868
1869
1870 DBG_LEAVE(DbgInfo);
1871 return ret;
1872}
1873
1874
1875
1876
1877
1878
1879
1880
1881
1882
1883
1884
1885
1886
1887
1888
1889
1890
1891
1892
1893
1894
1895
1896
1897int wvlan_set_porttype(struct net_device *dev,
1898 struct iw_request_info *info,
1899 union iwreq_data *wrqu,
1900 char *extra)
1901{
1902 struct wl_private *lp = wl_priv(dev);
1903 unsigned long flags;
1904 int ret = 0;
1905 hcf_16 portType;
1906
1907
1908
1909 DBG_FUNC("wvlan_set_porttype");
1910 DBG_ENTER(DbgInfo);
1911
1912 wl_lock(lp, &flags);
1913
1914
1915 portType = *((__u32 *)extra);
1916
1917 if (!((portType == 1) || (portType == 3))) {
1918 ret = -EINVAL;
1919 goto out_unlock;
1920 }
1921
1922 lp->PortType = portType;
1923
1924
1925 wl_apply(lp);
1926
1927out_unlock:
1928 wl_unlock(lp, &flags);
1929
1930
1931 DBG_LEAVE(DbgInfo);
1932 return ret;
1933}
1934
1935
1936
1937
1938
1939
1940
1941
1942
1943
1944
1945
1946
1947
1948
1949
1950
1951
1952
1953
1954
1955
1956
1957int wvlan_get_porttype(struct net_device *dev,
1958 struct iw_request_info *info,
1959 union iwreq_data *wrqu,
1960 char *extra)
1961{
1962 struct wl_private *lp = wl_priv(dev);
1963 unsigned long flags;
1964 int ret = 0;
1965 int status = -1;
1966 hcf_16 *pPortType;
1967 __u32 *pData = (__u32 *)extra;
1968
1969
1970
1971 DBG_FUNC("wvlan_get_porttype");
1972 DBG_ENTER(DbgInfo);
1973
1974 wl_lock(lp, &flags);
1975
1976
1977 lp->ltvRecord.len = 1 + (sizeof(*pPortType) / sizeof(hcf_16));
1978 lp->ltvRecord.typ = CFG_CNF_PORT_TYPE;
1979
1980 status = hcf_get_info(&(lp->hcfCtx), (LTVP)&(lp->ltvRecord));
1981
1982 if (status == HCF_SUCCESS) {
1983 pPortType = (hcf_16 *)&(lp->ltvRecord.u.u32);
1984
1985 *pData = CNV_LITTLE_TO_INT(*pPortType);
1986 } else {
1987 ret = -EFAULT;
1988 }
1989
1990 wl_unlock(lp, &flags);
1991
1992
1993 DBG_LEAVE(DbgInfo);
1994 return ret;
1995}
1996
1997
1998#endif
1999
2000
2001
2002
2003#ifdef USE_RTS
2004
2005
2006
2007
2008
2009
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023int wvlan_rts(struct rtsreq *rrq, __u32 io_base)
2024{
2025 int ioctl_ret = 0;
2026
2027
2028
2029 DBG_FUNC("wvlan_rts");
2030 DBG_ENTER(DbgInfo);
2031
2032
2033 DBG_PRINT("io_base: 0x%08x\n", io_base);
2034
2035 switch (rrq->typ) {
2036 case WL_IOCTL_RTS_READ:
2037 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_RTS -- WL_IOCTL_RTS_READ\n");
2038 rrq->data[0] = IN_PORT_WORD(io_base + rrq->reg);
2039 DBG_TRACE(DbgInfo, " reg 0x%04x ==> 0x%04x\n", rrq->reg, CNV_LITTLE_TO_SHORT(rrq->data[0]));
2040 break;
2041 case WL_IOCTL_RTS_WRITE:
2042 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_RTS -- WL_IOCTL_RTS_WRITE\n");
2043 OUT_PORT_WORD(io_base + rrq->reg, rrq->data[0]);
2044 DBG_TRACE(DbgInfo, " reg 0x%04x <== 0x%04x\n", rrq->reg, CNV_LITTLE_TO_SHORT(rrq->data[0]));
2045 break;
2046 case WL_IOCTL_RTS_BATCH_READ:
2047 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_RTS -- WL_IOCTL_RTS_BATCH_READ\n");
2048 IN_PORT_STRING_16(io_base + rrq->reg, rrq->data, rrq->len);
2049 DBG_TRACE(DbgInfo, " reg 0x%04x ==> %d bytes\n", rrq->reg, rrq->len * sizeof(__u16));
2050 break;
2051 case WL_IOCTL_RTS_BATCH_WRITE:
2052 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_RTS -- WL_IOCTL_RTS_BATCH_WRITE\n");
2053 OUT_PORT_STRING_16(io_base + rrq->reg, rrq->data, rrq->len);
2054 DBG_TRACE(DbgInfo, " reg 0x%04x <== %d bytes\n", rrq->reg, rrq->len * sizeof(__u16));
2055 break;
2056 default:
2057
2058 DBG_TRACE(DbgInfo, "IOCTL: WVLAN2_IOCTL_RTS -- UNSUPPORTED RTS CODE: 0x%X", rrq->typ);
2059 ioctl_ret = -EOPNOTSUPP;
2060 break;
2061 }
2062
2063 DBG_LEAVE(DbgInfo);
2064 return ioctl_ret;
2065}
2066
2067
2068#endif
2069