1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17#include "unifi_priv.h"
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
65
66
67
68
69
70
71
72
73
74
75
76
77#define UNIFI_SME_MGT_SHORT_TIMEOUT 10000
78#define UNIFI_SME_MGT_LONG_TIMEOUT 19000
79#define UNIFI_SME_SYS_LONG_TIMEOUT 10000
80
81#ifdef UNIFI_DEBUG
82# define sme_wait_for_reply(priv, t) _sme_wait_for_reply(priv, t, __func__)
83#else
84# define sme_wait_for_reply(priv, t) _sme_wait_for_reply(priv, t, NULL)
85#endif
86
87static int
88sme_init_request(unifi_priv_t *priv)
89{
90 if (priv == NULL) {
91 unifi_error(priv, "sme_init_request: Invalid priv\n");
92 return -EIO;
93 }
94
95 unifi_trace(priv, UDBG5, "sme_init_request: wait sem\n");
96
97
98 if (down_interruptible(&priv->sme_sem)) {
99 unifi_error(priv, "sme_init_request: Failed to get SME semaphore\n");
100 return -EIO;
101 }
102 unifi_trace(priv, UDBG5, "sme_init_request: got sem: pending\n");
103
104 priv->sme_reply.request_status = SME_REQUEST_PENDING;
105
106 return 0;
107
108}
109
110
111void
112uf_sme_complete_request(unifi_priv_t *priv, CsrResult reply_status, const char *func)
113{
114 if (priv == NULL) {
115 unifi_error(priv, "sme_complete_request: Invalid priv\n");
116 return;
117 }
118
119 if (priv->sme_reply.request_status != SME_REQUEST_PENDING) {
120 unifi_notice(priv,
121 "sme_complete_request: request not pending %s (s:%d)\n",
122 (func ? func : ""), priv->sme_reply.request_status);
123 return;
124 }
125 unifi_trace(priv, UDBG5,
126 "sme_complete_request: completed %s (s:%d)\n",
127 (func ? func : ""), priv->sme_reply.request_status);
128
129 priv->sme_reply.request_status = SME_REQUEST_RECEIVED;
130 priv->sme_reply.reply_status = reply_status;
131
132 wake_up_interruptible(&priv->sme_request_wq);
133
134 return;
135}
136
137
138void
139uf_sme_cancel_request(unifi_priv_t *priv, CsrResult reply_status)
140{
141
142
143
144
145 if (priv == NULL) {
146 unifi_error(priv, "sme_cancel_request: Invalid priv\n");
147 return;
148 }
149
150
151 if (priv->sme_reply.request_status != SME_REQUEST_PENDING) {
152 unifi_trace(priv, UDBG5,
153 "sme_cancel_request: no request was pending (s:%d)\n",
154 priv->sme_reply.request_status);
155
156 return;
157 }
158 unifi_trace(priv, UDBG5,
159 "sme_cancel_request: request cancelled (s:%d)\n",
160 priv->sme_reply.request_status);
161
162
163 priv->sme_reply.request_status = SME_REQUEST_CANCELLED;
164 priv->sme_reply.reply_status = reply_status;
165
166 wake_up_interruptible(&priv->sme_request_wq);
167
168 return;
169}
170
171
172static int
173_sme_wait_for_reply(unifi_priv_t *priv,
174 unsigned long timeout, const char *func)
175{
176 long r;
177
178 unifi_trace(priv, UDBG5, "sme_wait_for_reply: %s sleep\n", func ? func : "");
179 r = wait_event_interruptible_timeout(priv->sme_request_wq,
180 (priv->sme_reply.request_status != SME_REQUEST_PENDING),
181 msecs_to_jiffies(timeout));
182 unifi_trace(priv, UDBG5, "sme_wait_for_reply: %s awake (%d)\n", func ? func : "", r);
183
184 if (r == -ERESTARTSYS) {
185
186 unifi_info(priv, "ERESTARTSYS in _sme_wait_for_reply\n");
187 up(&priv->sme_sem);
188 return r;
189 }
190 if (priv->sme_reply.request_status == SME_REQUEST_CANCELLED) {
191 unifi_trace(priv, UDBG5, "Cancelled waiting for SME to reply (%s s:%d, t:%d, r:%d)\n",
192 (func ? func : ""), priv->sme_reply.request_status, timeout, r);
193
194
195 up(&priv->sme_sem);
196 return -EIO;
197 }
198 if ((r == 0) && (priv->sme_reply.request_status != SME_REQUEST_RECEIVED)) {
199 unifi_notice(priv, "Timeout waiting for SME to reply (%s s:%d, t:%d)\n",
200 (func ? func : ""), priv->sme_reply.request_status, timeout);
201
202 priv->sme_reply.request_status = SME_REQUEST_TIMEDOUT;
203
204
205 up(&priv->sme_sem);
206
207 return -ETIMEDOUT;
208 }
209
210 unifi_trace(priv, UDBG5, "sme_wait_for_reply: %s received (%d)\n",
211 func ? func : "", r);
212
213
214 up(&priv->sme_sem);
215
216 return 0;
217}
218
219
220
221
222#ifdef CSR_SUPPORT_WEXT
223int sme_mgt_wifi_on(unifi_priv_t *priv)
224{
225 u16 numElements;
226 CsrWifiSmeDataBlock* dataList;
227#ifdef CSR_SUPPORT_WEXT_AP
228 int r;
229#endif
230
231 if (priv->smepriv == NULL) {
232 unifi_error(priv, "sme_mgt_wifi_on: invalid smepriv\n");
233 return -EIO;
234 }
235
236 if (priv->mib_data.length) {
237 numElements = 1;
238 dataList = &priv->mib_data;
239 } else {
240 numElements = 0;
241 dataList = NULL;
242 }
243
244#ifdef CSR_SUPPORT_WEXT_AP
245 r = sme_init_request(priv);
246 if (r) {
247 return -EIO;
248 }
249#endif
250 CsrWifiSmeWifiOnReqSend(0, priv->sta_mac_address, numElements, dataList);
251#ifdef CSR_SUPPORT_WEXT_AP
252 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_LONG_TIMEOUT);
253 unifi_trace(priv, UDBG4,
254 "sme_mgt_wifi_on: unifi_mgt_wifi_oo_req <-- (r=%d, status=%d)\n",
255 r, priv->sme_reply.reply_status);
256 return convert_sme_error(priv->sme_reply.reply_status);
257#else
258 return 0;
259#endif
260}
261
262
263int sme_mgt_wifi_off(unifi_priv_t *priv)
264{
265 int r;
266
267 if (priv->smepriv == NULL) {
268 unifi_error(priv, "sme_mgt_wifi_off: invalid smepriv\n");
269 return -EIO;
270 }
271
272 r = sme_init_request(priv);
273 if (r)
274 return -EIO;
275
276
277 CsrWifiSmeWifiOffReqSend(0);
278
279 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_LONG_TIMEOUT);
280 if (r)
281 return r;
282
283 unifi_trace(priv, UDBG4,
284 "sme_mgt_wifi_off: unifi_mgt_wifi_off_req <-- (r=%d, status=%d)\n",
285 r, priv->sme_reply.reply_status);
286 return convert_sme_error(priv->sme_reply.reply_status);
287
288}
289
290int sme_mgt_key(unifi_priv_t *priv, CsrWifiSmeKey *sme_key,
291 CsrWifiSmeListAction action)
292{
293 int r;
294
295 if (priv->smepriv == NULL) {
296 unifi_error(priv, "sme_mgt_key: invalid smepriv\n");
297 return -EIO;
298 }
299
300 r = sme_init_request(priv);
301 if (r)
302 return -EIO;
303
304 CsrWifiSmeKeyReqSend(0, CSR_WIFI_INTERFACE_IN_USE, action, *sme_key);
305
306 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
307 if (r)
308 return r;
309
310 return convert_sme_error(priv->sme_reply.reply_status);
311}
312
313
314int sme_mgt_scan_full(unifi_priv_t *priv,
315 CsrWifiSsid *specific_ssid,
316 int num_channels,
317 unsigned char *channel_list)
318{
319 CsrWifiMacAddress bcastAddress = {{0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }};
320 u8 is_active = (num_channels > 0) ? TRUE : FALSE;
321 int r;
322
323 if (priv->smepriv == NULL) {
324 unifi_error(priv, "sme_mgt_scan_full: invalid smepriv\n");
325 return -EIO;
326 }
327
328 unifi_trace(priv, UDBG4, "sme_mgt_scan_full: -->\n");
329
330 r = sme_init_request(priv);
331 if (r)
332 return -EIO;
333
334
335 if (is_active) {
336 unifi_trace(priv, UDBG1,
337 "channel list - num_channels: %d, active scan\n",
338 num_channels);
339 }
340
341 CsrWifiSmeScanFullReqSend(0,
342 specific_ssid->length?1:0,
343 specific_ssid,
344 bcastAddress,
345 is_active,
346 CSR_WIFI_SME_BSS_TYPE_ANY_BSS,
347 CSR_WIFI_SME_SCAN_TYPE_ALL,
348 (u16)num_channels, channel_list,
349 0, NULL);
350
351 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_LONG_TIMEOUT);
352 if (r)
353 return r;
354
355 unifi_trace(priv, UDBG4, "sme_mgt_scan_full: <-- (status=%d)\n", priv->sme_reply.reply_status);
356 if (priv->sme_reply.reply_status == CSR_WIFI_RESULT_UNAVAILABLE)
357 return 0;
358 else
359 return convert_sme_error(priv->sme_reply.reply_status);
360}
361
362
363int sme_mgt_scan_results_get_async(unifi_priv_t *priv,
364 struct iw_request_info *info,
365 char *scan_results,
366 long scan_results_len)
367{
368 u16 scan_result_list_count;
369 CsrWifiSmeScanResult *scan_result_list;
370 CsrWifiSmeScanResult *scan_result;
371 int r;
372 int i;
373 char *current_ev = scan_results;
374
375 if (priv->smepriv == NULL) {
376 unifi_error(priv, "sme_mgt_scan_results_get_async: invalid smepriv\n");
377 return -EIO;
378 }
379
380 r = sme_init_request(priv);
381 if (r)
382 return -EIO;
383
384 CsrWifiSmeScanResultsGetReqSend(0);
385 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_LONG_TIMEOUT);
386 if (r)
387 return r;
388
389 scan_result_list_count = priv->sme_reply.reply_scan_results_count;
390 scan_result_list = priv->sme_reply.reply_scan_results;
391 unifi_trace(priv, UDBG2,
392 "scan_results: Scan returned %d, numElements=%d\n",
393 r, scan_result_list_count);
394
395
396 for (i = 0; i < scan_result_list_count; ++i) {
397 scan_result = &scan_result_list[i];
398
399 unifi_trace(priv, UDBG2, "Scan Result: %.*s\n",
400 scan_result->ssid.length,
401 scan_result->ssid.ssid);
402
403 r = unifi_translate_scan(priv->netdev[0], info,
404 current_ev,
405 scan_results + scan_results_len,
406 scan_result, i+1);
407
408 if (r < 0) {
409 kfree(scan_result_list);
410 priv->sme_reply.reply_scan_results_count = 0;
411 priv->sme_reply.reply_scan_results = NULL;
412 return r;
413 }
414
415 current_ev += r;
416 }
417
418
419
420
421
422
423 kfree(scan_result_list);
424 priv->sme_reply.reply_scan_results_count = 0;
425 priv->sme_reply.reply_scan_results = NULL;
426
427 unifi_trace(priv, UDBG2,
428 "scan_results: Scan translated to %d bytes\n",
429 current_ev - scan_results);
430 return (current_ev - scan_results);
431}
432
433
434int sme_mgt_connect(unifi_priv_t *priv)
435{
436 int r;
437
438 if (priv->smepriv == NULL) {
439 unifi_error(priv, "sme_mgt_connect: invalid smepriv\n");
440 return -EIO;
441 }
442
443 unifi_trace(priv, UDBG2, "sme_mgt_connect: %.*s\n",
444 priv->connection_config.ssid.length,
445 priv->connection_config.ssid.ssid);
446
447 r = sme_init_request(priv);
448 if (r)
449 return -EIO;
450
451 CsrWifiSmeConnectReqSend(0, CSR_WIFI_INTERFACE_IN_USE, priv->connection_config);
452 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
453 if (r)
454 return r;
455
456 if (priv->sme_reply.reply_status)
457 unifi_trace(priv, UDBG1, "sme_mgt_connect: failed with SME status %d\n",
458 priv->sme_reply.reply_status);
459
460 return convert_sme_error(priv->sme_reply.reply_status);
461}
462
463
464int sme_mgt_disconnect(unifi_priv_t *priv)
465{
466 int r;
467
468 if (priv->smepriv == NULL) {
469 unifi_error(priv, "sme_mgt_disconnect: invalid smepriv\n");
470 return -EIO;
471 }
472
473 r = sme_init_request(priv);
474 if (r)
475 return -EIO;
476
477 CsrWifiSmeDisconnectReqSend(0, CSR_WIFI_INTERFACE_IN_USE);
478 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
479 if (r)
480 return r;
481
482 unifi_trace(priv, UDBG4, "sme_mgt_disconnect: <-- (status=%d)\n", priv->sme_reply.reply_status);
483 return convert_sme_error(priv->sme_reply.reply_status);
484}
485
486
487int sme_mgt_pmkid(unifi_priv_t *priv,
488 CsrWifiSmeListAction action,
489 CsrWifiSmePmkidList *pmkid_list)
490{
491 int r;
492
493 if (priv->smepriv == NULL) {
494 unifi_error(priv, "sme_mgt_pmkid: invalid smepriv\n");
495 return -EIO;
496 }
497
498 r = sme_init_request(priv);
499 if (r)
500 return -EIO;
501
502 CsrWifiSmePmkidReqSend(0, CSR_WIFI_INTERFACE_IN_USE, action,
503 pmkid_list->pmkidsCount, pmkid_list->pmkids);
504 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
505 if (r)
506 return r;
507
508 unifi_trace(priv, UDBG4, "sme_mgt_pmkid: <-- (status=%d)\n", priv->sme_reply.reply_status);
509 return convert_sme_error(priv->sme_reply.reply_status);
510}
511
512
513int sme_mgt_mib_get(unifi_priv_t *priv,
514 unsigned char *varbind, int *length)
515{
516 int r;
517
518 if (priv->smepriv == NULL) {
519 unifi_error(priv, "sme_mgt_mib_get: invalid smepriv\n");
520 return -EIO;
521 }
522
523 r = sme_init_request(priv);
524 if (r)
525 return -EIO;
526
527 priv->mib_cfm_buffer = varbind;
528 priv->mib_cfm_buffer_length = MAX_VARBIND_LENGTH;
529
530 CsrWifiSmeMibGetReqSend(0, *length, varbind);
531 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
532 if (r) {
533 priv->mib_cfm_buffer_length = 0;
534 priv->mib_cfm_buffer = NULL;
535 return r;
536 }
537
538 *length = priv->mib_cfm_buffer_length;
539
540 priv->mib_cfm_buffer_length = 0;
541 priv->mib_cfm_buffer = NULL;
542 unifi_trace(priv, UDBG4, "sme_mgt_mib_get: <-- (status=%d)\n", priv->sme_reply.reply_status);
543 return convert_sme_error(priv->sme_reply.reply_status);
544}
545
546int sme_mgt_mib_set(unifi_priv_t *priv,
547 unsigned char *varbind, int length)
548{
549 int r;
550
551 if (priv->smepriv == NULL) {
552 unifi_error(priv, "sme_mgt_mib_get: invalid smepriv\n");
553 return -EIO;
554 }
555
556 r = sme_init_request(priv);
557 if (r)
558 return -EIO;
559
560 CsrWifiSmeMibSetReqSend(0, length, varbind);
561 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
562 if (r)
563 return r;
564
565 unifi_trace(priv, UDBG4, "sme_mgt_mib_set: <-- (status=%d)\n", priv->sme_reply.reply_status);
566 return convert_sme_error(priv->sme_reply.reply_status);
567}
568
569#endif
570
571int sme_mgt_power_config_set(unifi_priv_t *priv, CsrWifiSmePowerConfig *powerConfig)
572{
573#ifdef CSR_SME_USERSPACE
574 int r;
575
576 if (priv->smepriv == NULL) {
577 unifi_error(priv, "sme_mgt_set_value_async: invalid smepriv\n");
578 return -EIO;
579 }
580
581 r = sme_init_request(priv);
582 if (r)
583 return -EIO;
584
585 CsrWifiSmePowerConfigSetReqSend(0, *powerConfig);
586
587 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
588 if (r)
589 return r;
590
591 unifi_trace(priv, UDBG4,
592 "sme_mgt_set_value_async: unifi_mgt_set_value_req <-- (r=%d status=%d)\n",
593 r, priv->sme_reply.reply_status);
594 return convert_sme_error(priv->sme_reply.reply_status);
595#else
596 CsrResult status;
597 if (priv->smepriv == NULL) {
598 unifi_error(priv, "sme_mgt_set_value: invalid smepriv\n");
599 return -EIO;
600 }
601 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
602 status = CsrWifiSmeMgtPowerConfigSetReq(priv->smepriv, *powerConfig);
603 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
604 return convert_sme_error(status);
605#endif
606}
607
608int sme_mgt_sme_config_set(unifi_priv_t *priv, CsrWifiSmeStaConfig *staConfig, CsrWifiSmeDeviceConfig *deviceConfig)
609{
610#ifdef CSR_SME_USERSPACE
611 int r;
612
613 if (priv->smepriv == NULL) {
614 unifi_error(priv, "sme_mgt_sme_config_set: invalid smepriv\n");
615 return -EIO;
616 }
617
618 r = sme_init_request(priv);
619 if (r)
620 return -EIO;
621
622 CsrWifiSmeSmeStaConfigSetReqSend(0, CSR_WIFI_INTERFACE_IN_USE, *staConfig);
623 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
624 if (r)
625 return r;
626
627 unifi_trace(priv, UDBG4,
628 "sme_mgt_sme_config_set: CsrWifiSmeSmeStaConfigSetReq <-- (r=%d status=%d)\n",
629 r, priv->sme_reply.reply_status);
630
631 r = sme_init_request(priv);
632 if (r)
633 return -EIO;
634
635 CsrWifiSmeSmeCommonConfigSetReqSend(0, *deviceConfig);
636 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
637 if (r)
638 return r;
639
640 unifi_trace(priv, UDBG4,
641 "sme_mgt_sme_config_set: CsrWifiSmeSmeCommonConfigSetReq <-- (r=%d status=%d)\n",
642 r, priv->sme_reply.reply_status);
643
644 return convert_sme_error(priv->sme_reply.reply_status);
645#else
646 CsrResult status;
647 if (priv->smepriv == NULL) {
648 unifi_error(priv, "sme_mgt_sme_config_set: invalid smepriv\n");
649 return -EIO;
650 }
651 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
652 status = CsrWifiSmeMgtSmeConfigSetReq(priv->smepriv, *staConfig);
653 status = CsrWifiSmeMgtDeviceConfigSetReq(priv->smepriv, *deviceConfig);
654 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
655 return convert_sme_error(status);
656#endif
657}
658
659#ifdef CSR_SUPPORT_WEXT
660
661int sme_mgt_mib_config_set(unifi_priv_t *priv, CsrWifiSmeMibConfig *mibConfig)
662{
663#ifdef CSR_SME_USERSPACE
664 int r;
665
666 if (priv->smepriv == NULL) {
667 unifi_error(priv, "sme_mgt_mib_config_set: invalid smepriv\n");
668 return -EIO;
669 }
670
671 r = sme_init_request(priv);
672 if (r)
673 return -EIO;
674
675 CsrWifiSmeMibConfigSetReqSend(0, *mibConfig);
676
677 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
678 if (r)
679 return r;
680
681 unifi_trace(priv, UDBG4,
682 "sme_mgt_mib_config_set: unifi_mgt_set_mib_config_req <-- (r=%d status=%d)\n",
683 r, priv->sme_reply.reply_status);
684 return convert_sme_error(priv->sme_reply.reply_status);
685#else
686 CsrResult status;
687 if (priv->smepriv == NULL) {
688 unifi_error(priv, "sme_mgt_mib_config_set: invalid smepriv\n");
689 return -EIO;
690 }
691 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
692 status = CsrWifiSmeMgtMibConfigSetReq(priv->smepriv, *mibConfig);
693 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
694 return convert_sme_error(status);
695#endif
696}
697
698int sme_mgt_coex_config_set(unifi_priv_t *priv, CsrWifiSmeCoexConfig *coexConfig)
699{
700#ifdef CSR_SME_USERSPACE
701 int r;
702
703 if (priv->smepriv == NULL) {
704 unifi_error(priv, "sme_mgt_coex_config_set: invalid smepriv\n");
705 return -EIO;
706 }
707
708 r = sme_init_request(priv);
709 if (r)
710 return -EIO;
711
712 CsrWifiSmeCoexConfigSetReqSend(0, *coexConfig);
713
714 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
715 if (r)
716 return r;
717
718 unifi_trace(priv, UDBG4,
719 "sme_mgt_coex_config_set: unifi_mgt_set_mib_config_req <-- (r=%d status=%d)\n",
720 r, priv->sme_reply.reply_status);
721 return convert_sme_error(priv->sme_reply.reply_status);
722#else
723 CsrResult status;
724 if (priv->smepriv == NULL) {
725 unifi_error(priv, "sme_mgt_coex_config_set: invalid smepriv\n");
726 return -EIO;
727 }
728 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
729 status = CsrWifiSmeMgtCoexConfigSetReq(priv->smepriv, *coexConfig);
730 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
731 return convert_sme_error(status);
732#endif
733}
734
735#endif
736
737int sme_mgt_host_config_set(unifi_priv_t *priv, CsrWifiSmeHostConfig *hostConfig)
738{
739#ifdef CSR_SME_USERSPACE
740 int r;
741
742 if (priv->smepriv == NULL) {
743 unifi_error(priv, "sme_mgt_host_config_set: invalid smepriv\n");
744 return -EIO;
745 }
746
747 r = sme_init_request(priv);
748 if (r)
749 return -EIO;
750
751 CsrWifiSmeHostConfigSetReqSend(0, CSR_WIFI_INTERFACE_IN_USE, *hostConfig);
752
753 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
754 if (r)
755 return r;
756
757 unifi_trace(priv, UDBG4,
758 "sme_mgt_host_config_set: unifi_mgt_set_host_config_req <-- (r=%d status=%d)\n",
759 r, priv->sme_reply.reply_status);
760 return convert_sme_error(priv->sme_reply.reply_status);
761#else
762 CsrResult status;
763 if (priv->smepriv == NULL) {
764 unifi_error(priv, "sme_mgt_host_config_set: invalid smepriv\n");
765 return -EIO;
766 }
767 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
768 status = CsrWifiSmeMgtHostConfigSetReq(priv->smepriv, *hostConfig);
769 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
770 return convert_sme_error(status);
771#endif
772}
773
774#ifdef CSR_SUPPORT_WEXT
775
776int sme_mgt_versions_get(unifi_priv_t *priv, CsrWifiSmeVersions *versions)
777{
778#ifdef CSR_SME_USERSPACE
779 int r;
780
781 if (priv->smepriv == NULL) {
782 unifi_error(priv, "sme_mgt_versions_get: invalid smepriv\n");
783 return -EIO;
784 }
785
786 unifi_trace(priv, UDBG4, "sme_mgt_versions_get: unifi_mgt_versions_get_req -->\n");
787 r = sme_init_request(priv);
788 if (r)
789 return -EIO;
790
791 CsrWifiSmeVersionsGetReqSend(0);
792
793 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
794 if (r)
795 return r;
796
797
798 if (versions != NULL) {
799 memcpy((unsigned char*)versions,
800 (unsigned char*)&priv->sme_reply.versions,
801 sizeof(CsrWifiSmeVersions));
802 }
803
804 unifi_trace(priv, UDBG4,
805 "sme_mgt_versions_get: unifi_mgt_versions_get_req <-- (r=%d status=%d)\n",
806 r, priv->sme_reply.reply_status);
807
808 return convert_sme_error(priv->sme_reply.reply_status);
809#else
810 CsrResult status;
811 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
812 status = CsrWifiSmeMgtVersionsGetReq(priv->smepriv, versions);
813 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
814 return convert_sme_error(status);
815#endif
816}
817
818#endif
819
820int sme_mgt_power_config_get(unifi_priv_t *priv, CsrWifiSmePowerConfig *powerConfig)
821{
822#ifdef CSR_SME_USERSPACE
823 int r;
824
825 if (priv->smepriv == NULL) {
826 unifi_error(priv, "sme_mgt_power_config_get: invalid smepriv\n");
827 return -EIO;
828 }
829
830 unifi_trace(priv, UDBG4, "sme_mgt_power_config_get: unifi_mgt_power_config_req -->\n");
831 r = sme_init_request(priv);
832 if (r)
833 return -EIO;
834
835 CsrWifiSmePowerConfigGetReqSend(0);
836
837 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
838 if (r)
839 return r;
840
841
842 if (powerConfig != NULL) {
843 memcpy((unsigned char*)powerConfig,
844 (unsigned char*)&priv->sme_reply.powerConfig,
845 sizeof(CsrWifiSmePowerConfig));
846 }
847
848 unifi_trace(priv, UDBG4,
849 "sme_mgt_get_versions: unifi_mgt_power_config_req <-- (r=%d status=%d)\n",
850 r, priv->sme_reply.reply_status);
851
852 return convert_sme_error(priv->sme_reply.reply_status);
853#else
854 CsrResult status;
855 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
856 status = CsrWifiSmeMgtPowerConfigGetReq(priv->smepriv, powerConfig);
857 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
858 return convert_sme_error(status);
859#endif
860}
861
862int sme_mgt_host_config_get(unifi_priv_t *priv, CsrWifiSmeHostConfig *hostConfig)
863{
864#ifdef CSR_SME_USERSPACE
865 int r;
866
867 if (priv->smepriv == NULL) {
868 unifi_error(priv, "sme_mgt_host_config_get: invalid smepriv\n");
869 return -EIO;
870 }
871
872 unifi_trace(priv, UDBG4, "sme_mgt_host_config_get: unifi_mgt_host_config_get_req -->\n");
873 r = sme_init_request(priv);
874 if (r)
875 return -EIO;
876
877 CsrWifiSmeHostConfigGetReqSend(0, CSR_WIFI_INTERFACE_IN_USE);
878
879 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
880 if (r)
881 return r;
882
883
884 if (hostConfig != NULL)
885 memcpy((unsigned char*)hostConfig,
886 (unsigned char*)&priv->sme_reply.hostConfig,
887 sizeof(CsrWifiSmeHostConfig));
888
889 unifi_trace(priv, UDBG4,
890 "sme_mgt_host_config_get: unifi_mgt_host_config_get_req <-- (r=%d status=%d)\n",
891 r, priv->sme_reply.reply_status);
892
893 return convert_sme_error(priv->sme_reply.reply_status);
894#else
895 CsrResult status;
896 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
897 status = CsrWifiSmeMgtHostConfigGetReq(priv->smepriv, hostConfig);
898 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
899 return convert_sme_error(status);
900#endif
901}
902
903int sme_mgt_sme_config_get(unifi_priv_t *priv, CsrWifiSmeStaConfig *staConfig, CsrWifiSmeDeviceConfig *deviceConfig)
904{
905#ifdef CSR_SME_USERSPACE
906 int r;
907
908 if (priv->smepriv == NULL) {
909 unifi_error(priv, "sme_mgt_sme_config_get: invalid smepriv\n");
910 return -EIO;
911 }
912
913 unifi_trace(priv, UDBG4, "sme_mgt_sme_config_get: unifi_mgt_sme_config_get_req -->\n");
914
915
916 r = sme_init_request(priv);
917 if (r)
918 return -EIO;
919
920 CsrWifiSmeSmeCommonConfigGetReqSend(0);
921 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
922 if (r)
923 return r;
924
925
926 if (deviceConfig != NULL)
927 memcpy((unsigned char*)deviceConfig,
928 (unsigned char*)&priv->sme_reply.deviceConfig,
929 sizeof(CsrWifiSmeDeviceConfig));
930
931
932 r = sme_init_request(priv);
933 if (r)
934 return -EIO;
935
936 CsrWifiSmeSmeStaConfigGetReqSend(0, CSR_WIFI_INTERFACE_IN_USE);
937 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
938 if (r)
939 return r;
940
941
942 if (staConfig != NULL)
943 memcpy((unsigned char*)staConfig,
944 (unsigned char*)&priv->sme_reply.staConfig,
945 sizeof(CsrWifiSmeStaConfig));
946
947 unifi_trace(priv, UDBG4,
948 "sme_mgt_sme_config_get: unifi_mgt_sme_config_get_req <-- (r=%d status=%d)\n",
949 r, priv->sme_reply.reply_status);
950
951 return convert_sme_error(priv->sme_reply.reply_status);
952#else
953 CsrResult status;
954 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
955 status = CsrWifiSmeMgtSmeConfigGetReq(priv->smepriv, staConfig);
956 status = CsrWifiSmeMgtDeviceConfigGetReq(priv->smepriv, deviceConfig);
957 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
958 return convert_sme_error(status);
959#endif
960}
961
962int sme_mgt_coex_info_get(unifi_priv_t *priv, CsrWifiSmeCoexInfo *coexInfo)
963{
964#ifdef CSR_SME_USERSPACE
965 int r;
966
967 if (priv->smepriv == NULL) {
968 unifi_error(priv, "sme_mgt_coex_info_get: invalid smepriv\n");
969 return -EIO;
970 }
971
972 unifi_trace(priv, UDBG4, "sme_mgt_coex_info_get: unifi_mgt_coex_info_get_req -->\n");
973 r = sme_init_request(priv);
974 if (r)
975 return -EIO;
976
977 CsrWifiSmeCoexInfoGetReqSend(0);
978
979 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
980 if (r)
981 return r;
982
983
984 if (coexInfo != NULL)
985 memcpy((unsigned char*)coexInfo,
986 (unsigned char*)&priv->sme_reply.coexInfo,
987 sizeof(CsrWifiSmeCoexInfo));
988
989 unifi_trace(priv, UDBG4,
990 "sme_mgt_coex_info_get: unifi_mgt_coex_info_get_req <-- (r=%d status=%d)\n",
991 r, priv->sme_reply.reply_status);
992
993 return convert_sme_error(priv->sme_reply.reply_status);
994#else
995 CsrResult status;
996 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
997 status = CsrWifiSmeMgtCoexInfoGetReq(priv->smepriv, coexInfo);
998 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
999 return convert_sme_error(status);
1000#endif
1001}
1002
1003#ifdef CSR_SUPPORT_WEXT
1004
1005int sme_mgt_coex_config_get(unifi_priv_t *priv, CsrWifiSmeCoexConfig *coexConfig)
1006{
1007#ifdef CSR_SME_USERSPACE
1008 int r;
1009
1010 if (priv->smepriv == NULL) {
1011 unifi_error(priv, "sme_mgt_coex_config_get: invalid smepriv\n");
1012 return -EIO;
1013 }
1014
1015 unifi_trace(priv, UDBG4, "sme_mgt_coex_config_get: unifi_mgt_coex_config_get_req -->\n");
1016 r = sme_init_request(priv);
1017 if (r)
1018 return -EIO;
1019
1020 CsrWifiSmeCoexConfigGetReqSend(0);
1021
1022 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
1023 if (r)
1024 return r;
1025
1026
1027 if (coexConfig != NULL)
1028 memcpy((unsigned char*)coexConfig,
1029 (unsigned char*)&priv->sme_reply.coexConfig,
1030 sizeof(CsrWifiSmeCoexConfig));
1031
1032 unifi_trace(priv, UDBG4,
1033 "sme_mgt_coex_config_get: unifi_mgt_coex_config_get_req <-- (r=%d status=%d)\n",
1034 r, priv->sme_reply.reply_status);
1035
1036 return convert_sme_error(priv->sme_reply.reply_status);
1037#else
1038 CsrResult status;
1039 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
1040 status = CsrWifiSmeMgtCoexConfigGetReq(priv->smepriv, coexConfig);
1041 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
1042 return convert_sme_error(status);
1043#endif
1044}
1045
1046int sme_mgt_mib_config_get(unifi_priv_t *priv, CsrWifiSmeMibConfig *mibConfig)
1047{
1048#ifdef CSR_SME_USERSPACE
1049 int r;
1050
1051 if (priv->smepriv == NULL) {
1052 unifi_error(priv, "sme_mgt_mib_config_get: invalid smepriv\n");
1053 return -EIO;
1054 }
1055
1056 unifi_trace(priv, UDBG4, "sme_mgt_mib_config_get: unifi_mgt_mib_config_get_req -->\n");
1057 r = sme_init_request(priv);
1058 if (r)
1059 return -EIO;
1060
1061 CsrWifiSmeMibConfigGetReqSend(0);
1062
1063 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
1064 if (r)
1065 return r;
1066
1067
1068 if (mibConfig != NULL)
1069 memcpy((unsigned char*)mibConfig,
1070 (unsigned char*)&priv->sme_reply.mibConfig,
1071 sizeof(CsrWifiSmeMibConfig));
1072
1073 unifi_trace(priv, UDBG4,
1074 "sme_mgt_mib_config_get: unifi_mgt_mib_config_get_req <-- (r=%d status=%d)\n",
1075 r, priv->sme_reply.reply_status);
1076
1077 return convert_sme_error(priv->sme_reply.reply_status);
1078#else
1079 CsrResult status;
1080 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
1081 status = CsrWifiSmeMgtMibConfigGetReq(priv->smepriv, mibConfig);
1082 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
1083 return convert_sme_error(status);
1084#endif
1085}
1086
1087int sme_mgt_connection_info_get(unifi_priv_t *priv, CsrWifiSmeConnectionInfo *connectionInfo)
1088{
1089#ifdef CSR_SME_USERSPACE
1090 int r;
1091
1092 if (priv->smepriv == NULL) {
1093 unifi_error(priv, "sme_mgt_connection_info_get: invalid smepriv\n");
1094 return -EIO;
1095 }
1096
1097 unifi_trace(priv, UDBG4, "sme_mgt_connection_info_get: unifi_mgt_connection_info_get_req -->\n");
1098 r = sme_init_request(priv);
1099 if (r)
1100 return -EIO;
1101
1102 CsrWifiSmeConnectionInfoGetReqSend(0, CSR_WIFI_INTERFACE_IN_USE);
1103
1104 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
1105 if (r)
1106 return r;
1107
1108
1109 if (connectionInfo != NULL)
1110 memcpy((unsigned char*)connectionInfo,
1111 (unsigned char*)&priv->sme_reply.connectionInfo,
1112 sizeof(CsrWifiSmeConnectionInfo));
1113
1114 unifi_trace(priv, UDBG4,
1115 "sme_mgt_connection_info_get: unifi_mgt_connection_info_get_req <-- (r=%d status=%d)\n",
1116 r, priv->sme_reply.reply_status);
1117
1118 return convert_sme_error(priv->sme_reply.reply_status);
1119#else
1120 CsrResult status;
1121 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
1122 status = CsrWifiSmeMgtConnectionInfoGetReq(priv->smepriv, connectionInfo);
1123 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
1124 return convert_sme_error(status);
1125#endif
1126}
1127
1128int sme_mgt_connection_config_get(unifi_priv_t *priv, CsrWifiSmeConnectionConfig *connectionConfig)
1129{
1130#ifdef CSR_SME_USERSPACE
1131 int r;
1132
1133 if (priv->smepriv == NULL) {
1134 unifi_error(priv, "sme_mgt_connection_config_get: invalid smepriv\n");
1135 return -EIO;
1136 }
1137
1138 unifi_trace(priv, UDBG4, "sme_mgt_connection_config_get: unifi_mgt_connection_config_get_req -->\n");
1139 r = sme_init_request(priv);
1140 if (r)
1141 return -EIO;
1142
1143 CsrWifiSmeConnectionConfigGetReqSend(0, CSR_WIFI_INTERFACE_IN_USE);
1144
1145 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
1146 if (r)
1147 return r;
1148
1149
1150 if (connectionConfig != NULL)
1151 memcpy((unsigned char*)connectionConfig,
1152 (unsigned char*)&priv->sme_reply.connectionConfig,
1153 sizeof(CsrWifiSmeConnectionConfig));
1154
1155 unifi_trace(priv, UDBG4,
1156 "sme_mgt_connection_config_get: unifi_mgt_connection_config_get_req <-- (r=%d status=%d)\n",
1157 r, priv->sme_reply.reply_status);
1158
1159 return convert_sme_error(priv->sme_reply.reply_status);
1160#else
1161 CsrResult status;
1162 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
1163 status = CsrWifiSmeMgtConnectionConfigGetReq(priv->smepriv, connectionConfig);
1164 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
1165 return convert_sme_error(status);
1166#endif
1167}
1168
1169int sme_mgt_connection_stats_get(unifi_priv_t *priv, CsrWifiSmeConnectionStats *connectionStats)
1170{
1171#ifdef CSR_SME_USERSPACE
1172 int r;
1173
1174 if (priv->smepriv == NULL) {
1175 unifi_error(priv, "sme_mgt_connection_stats_get: invalid smepriv\n");
1176 return -EIO;
1177 }
1178
1179 unifi_trace(priv, UDBG4, "sme_mgt_connection_stats_get: unifi_mgt_connection_stats_get_req -->\n");
1180 r = sme_init_request(priv);
1181 if (r)
1182 return -EIO;
1183
1184 CsrWifiSmeConnectionStatsGetReqSend(0, CSR_WIFI_INTERFACE_IN_USE);
1185
1186 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
1187 if (r)
1188 return r;
1189
1190
1191 if (connectionStats != NULL)
1192 memcpy((unsigned char*)connectionStats,
1193 (unsigned char*)&priv->sme_reply.connectionStats,
1194 sizeof(CsrWifiSmeConnectionStats));
1195
1196 unifi_trace(priv, UDBG4,
1197 "sme_mgt_connection_stats_get: unifi_mgt_connection_stats_get_req <-- (r=%d status=%d)\n",
1198 r, priv->sme_reply.reply_status);
1199
1200 return convert_sme_error(priv->sme_reply.reply_status);
1201#else
1202 CsrResult status;
1203 CsrWifiSmeMgtClaimSyncAccess(priv->smepriv);
1204 status = CsrWifiSmeMgtConnectionStatsGetReq(priv->smepriv, connectionStats);
1205 CsrWifiSmeMgtReleaseSyncAccess(priv->smepriv);
1206 return convert_sme_error(status);
1207#endif
1208}
1209
1210#endif
1211
1212int sme_mgt_packet_filter_set(unifi_priv_t *priv)
1213{
1214 CsrWifiIp4Address ipAddress = {{0xFF, 0xFF, 0xFF, 0xFF }};
1215 if (priv->smepriv == NULL) {
1216 unifi_error(priv, "sme_mgt_packet_filter_set: invalid smepriv\n");
1217 return -EIO;
1218 }
1219 if (priv->packet_filters.arp_filter) {
1220 ipAddress.a[0] = (priv->sta_ip_address ) & 0xFF;
1221 ipAddress.a[1] = (priv->sta_ip_address >> 8) & 0xFF;
1222 ipAddress.a[2] = (priv->sta_ip_address >> 16) & 0xFF;
1223 ipAddress.a[3] = (priv->sta_ip_address >> 24) & 0xFF;
1224 }
1225
1226 unifi_trace(priv, UDBG5,
1227 "sme_mgt_packet_filter_set: IP address %d.%d.%d.%d\n",
1228 ipAddress.a[0], ipAddress.a[1],
1229 ipAddress.a[2], ipAddress.a[3]);
1230
1231
1232 CsrWifiSmePacketFilterSetReqSend(0, CSR_WIFI_INTERFACE_IN_USE,
1233 priv->packet_filters.tclas_ies_length,
1234 priv->filter_tclas_ies,
1235 priv->packet_filters.filter_mode,
1236 ipAddress);
1237 return 0;
1238}
1239
1240int sme_mgt_tspec(unifi_priv_t *priv, CsrWifiSmeListAction action,
1241 u32 tid, CsrWifiSmeDataBlock *tspec, CsrWifiSmeDataBlock *tclas)
1242{
1243 int r;
1244
1245 if (priv->smepriv == NULL) {
1246 unifi_error(priv, "sme_mgt_tspec: invalid smepriv\n");
1247 return -EIO;
1248 }
1249
1250 r = sme_init_request(priv);
1251 if (r)
1252 return -EIO;
1253
1254 CsrWifiSmeTspecReqSend(0, CSR_WIFI_INTERFACE_IN_USE,
1255 action, tid, TRUE, 0,
1256 tspec->length, tspec->data,
1257 tclas->length, tclas->data);
1258 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
1259 if (r)
1260 return r;
1261
1262 unifi_trace(priv, UDBG4, "sme_mgt_tspec: <-- (status=%d)\n", priv->sme_reply.reply_status);
1263 return convert_sme_error(priv->sme_reply.reply_status);
1264}
1265
1266
1267
1268int sme_sys_suspend(unifi_priv_t *priv)
1269{
1270 int r;
1271 CsrResult csrResult;
1272
1273 if (priv->smepriv == NULL) {
1274 unifi_error(priv, "sme_sys_suspend: invalid smepriv\n");
1275 return -EIO;
1276 }
1277
1278 r = sme_init_request(priv);
1279 if (r)
1280 return -EIO;
1281
1282
1283 CsrWifiRouterCtrlSuspendIndSend(priv->CSR_WIFI_SME_IFACEQUEUE,0, 0, priv->wol_suspend);
1284 r = sme_wait_for_reply(priv, UNIFI_SME_SYS_LONG_TIMEOUT);
1285 if (r) {
1286
1287 unifi_notice(priv,
1288 "suspend: SME did not reply %s, ",
1289 (priv->ptest_mode | priv->wol_suspend) ? "leave powered" : "power off UniFi anyway\n");
1290
1291
1292 if (!priv->ptest_mode) {
1293
1294 CsrSdioClaim(priv->sdio);
1295 unifi_trace(priv, UDBG1, "Force deep sleep");
1296 csrResult = unifi_force_low_power_mode(priv->card);
1297
1298
1299 if (!priv->wol_suspend) {
1300 unifi_trace(priv, UDBG1, "Power off\n");
1301 CsrSdioPowerOff(priv->sdio);
1302 }
1303 CsrSdioRelease(priv->sdio);
1304 }
1305 }
1306
1307 if (priv->wol_suspend) {
1308 unifi_trace(priv, UDBG1, "UniFi left powered for WOL\n");
1309
1310
1311
1312
1313
1314
1315
1316 if (csr_sdio_linux_remove_irq(priv->sdio)) {
1317 unifi_notice(priv, "WOL csr_sdio_linux_remove_irq failed\n");
1318 }
1319
1320 if (enable_wol == UNIFI_WOL_SDIO) {
1321
1322
1323
1324 unifi_trace(priv, UDBG1, "Enable card SDIO interrupt for SDIO WOL\n");
1325
1326 CsrSdioClaim(priv->sdio);
1327 csrResult = CsrSdioInterruptEnable(priv->sdio);
1328 CsrSdioRelease(priv->sdio);
1329
1330 if (csrResult != CSR_RESULT_SUCCESS) {
1331 unifi_error(priv, "WOL CsrSdioInterruptEnable failed %d\n", csrResult);
1332 }
1333 } else {
1334 unifi_trace(priv, UDBG1, "Disabled card SDIO interrupt for PIO WOL\n");
1335 }
1336
1337
1338
1339
1340
1341 priv->bh_thread.block_thread = 1;
1342
1343 unifi_trace(priv, UDBG1, "unifi_suspend: suspended BH");
1344 }
1345
1346
1347 priv->init_progress = UNIFI_INIT_NONE;
1348
1349 unifi_trace(priv, UDBG1, "sme_sys_suspend: <-- (r=%d status=%d)\n", r, priv->sme_reply.reply_status);
1350 return convert_sme_error(priv->sme_reply.reply_status);
1351}
1352
1353
1354int sme_sys_resume(unifi_priv_t *priv)
1355{
1356 int r;
1357
1358 unifi_trace(priv, UDBG1, "sme_sys_resume %s\n", priv->wol_suspend ? "warm" : "");
1359
1360 if (priv->smepriv == NULL) {
1361 unifi_error(priv, "sme_sys_resume: invalid smepriv\n");
1362 return -EIO;
1363 }
1364
1365 r = sme_init_request(priv);
1366 if (r)
1367 return -EIO;
1368
1369 CsrWifiRouterCtrlResumeIndSend(priv->CSR_WIFI_SME_IFACEQUEUE,0, priv->wol_suspend);
1370
1371 r = sme_wait_for_reply(priv, UNIFI_SME_SYS_LONG_TIMEOUT);
1372 if (r)
1373 unifi_notice(priv,
1374 "resume: SME did not reply, return success anyway\n");
1375
1376 return 0;
1377}
1378
1379#ifdef CSR_SUPPORT_WEXT_AP
1380int sme_ap_stop(unifi_priv_t *priv,u16 interface_tag)
1381{
1382 int r;
1383
1384 if (priv->smepriv == NULL) {
1385 unifi_error(priv, "sme_ap_stop: invalid smepriv\n");
1386 return -EIO;
1387 }
1388
1389 r = sme_init_request(priv);
1390 if (r)
1391 return -EIO;
1392
1393 CsrWifiNmeApStopReqSend(0,interface_tag);
1394
1395 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
1396 if (r)
1397 return r;
1398
1399 unifi_trace(priv, UDBG4,
1400 "sme_ap_stop <-- (r=%d status=%d)\n",
1401 r, priv->sme_reply.reply_status);
1402 return convert_sme_error(priv->sme_reply.reply_status);
1403
1404}
1405
1406int sme_ap_start(unifi_priv_t *priv,u16 interface_tag,
1407 CsrWifiSmeApConfig_t * ap_config)
1408{
1409 int r;
1410 CsrWifiSmeApP2pGoConfig p2p_go_param;
1411 memset(&p2p_go_param,0,sizeof(CsrWifiSmeApP2pGoConfig));
1412
1413 if (priv->smepriv == NULL) {
1414 unifi_error(priv, "sme_ap_start: invalid smepriv\n");
1415 return -EIO;
1416 }
1417
1418 r = sme_init_request(priv);
1419 if (r)
1420 return -EIO;
1421
1422 CsrWifiNmeApStartReqSend(0,interface_tag,CSR_WIFI_AP_TYPE_LEGACY,FALSE,
1423 ap_config->ssid,1,ap_config->channel,
1424 ap_config->credentials,ap_config->max_connections,
1425 p2p_go_param,FALSE);
1426
1427 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
1428 if (r)
1429 return r;
1430
1431 unifi_trace(priv, UDBG4,
1432 "sme_ap_start <-- (r=%d status=%d)\n",
1433 r, priv->sme_reply.reply_status);
1434 return convert_sme_error(priv->sme_reply.reply_status);
1435}
1436
1437int sme_ap_config(unifi_priv_t *priv,
1438 CsrWifiSmeApMacConfig *ap_mac_config,
1439 CsrWifiNmeApConfig *group_security_config)
1440{
1441 int r;
1442 CsrWifiSmeApP2pGoConfig p2p_go_param;
1443 memset(&p2p_go_param,0,sizeof(CsrWifiSmeApP2pGoConfig));
1444
1445 if (priv->smepriv == NULL) {
1446 unifi_error(priv, "sme_ap_config: invalid smepriv\n");
1447 return -EIO;
1448 }
1449
1450 r = sme_init_request(priv);
1451 if (r)
1452 return -EIO;
1453
1454 CsrWifiNmeApConfigSetReqSend(0,*group_security_config,
1455 *ap_mac_config);
1456
1457 r = sme_wait_for_reply(priv, UNIFI_SME_MGT_SHORT_TIMEOUT);
1458 if (r)
1459 return r;
1460
1461 unifi_trace(priv, UDBG4,
1462 "sme_ap_config <-- (r=%d status=%d)\n",
1463 r, priv->sme_reply.reply_status);
1464 return convert_sme_error(priv->sme_reply.reply_status);
1465}
1466#endif
1467