hc
2024-01-03 2f7c68cb55ecb7331f2381deb497c27155f32faf
kernel/drivers/net/wireless/broadcom/brcm80211/brcmfmac/usb.c
....@@ -1,17 +1,6 @@
1
+// SPDX-License-Identifier: ISC
12 /*
23 * Copyright (c) 2011 Broadcom Corporation
3
- *
4
- * Permission to use, copy, modify, and/or distribute this software for any
5
- * purpose with or without fee is hereby granted, provided that the above
6
- * copyright notice and this permission notice appear in all copies.
7
- *
8
- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9
- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10
- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
11
- * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12
- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
13
- * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
14
- * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
154 */
165
176 #include <linux/kernel.h>
....@@ -175,7 +164,6 @@
175164
176165 struct urb *bulk_urb; /* used for FW download */
177166
178
- bool wowl_enabled;
179167 struct brcmf_mp_device *settings;
180168 };
181169
....@@ -323,27 +311,43 @@
323311 int err = 0;
324312 int timeout = 0;
325313 struct brcmf_usbdev_info *devinfo = brcmf_usb_get_businfo(dev);
314
+ struct usb_interface *intf = to_usb_interface(dev);
326315
327316 brcmf_dbg(USB, "Enter\n");
328
- if (devinfo->bus_pub.state != BRCMFMAC_USB_STATE_UP)
329
- return -EIO;
330317
331
- if (test_and_set_bit(0, &devinfo->ctl_op))
332
- return -EIO;
318
+ err = usb_autopm_get_interface(intf);
319
+ if (err)
320
+ goto out;
321
+
322
+ if (devinfo->bus_pub.state != BRCMFMAC_USB_STATE_UP) {
323
+ err = -EIO;
324
+ goto fail;
325
+ }
326
+
327
+ if (test_and_set_bit(0, &devinfo->ctl_op)) {
328
+ err = -EIO;
329
+ goto fail;
330
+ }
333331
334332 devinfo->ctl_completed = false;
335333 err = brcmf_usb_send_ctl(devinfo, buf, len);
336334 if (err) {
337335 brcmf_err("fail %d bytes: %d\n", err, len);
338336 clear_bit(0, &devinfo->ctl_op);
339
- return err;
337
+ goto fail;
340338 }
341339 timeout = brcmf_usb_ioctl_resp_wait(devinfo);
342
- clear_bit(0, &devinfo->ctl_op);
343340 if (!timeout) {
344341 brcmf_err("Txctl wait timed out\n");
342
+ usb_kill_urb(devinfo->ctl_urb);
345343 err = -EIO;
344
+ goto fail;
346345 }
346
+ clear_bit(0, &devinfo->ctl_op);
347
+
348
+fail:
349
+ usb_autopm_put_interface(intf);
350
+out:
347351 return err;
348352 }
349353
....@@ -352,32 +356,46 @@
352356 int err = 0;
353357 int timeout = 0;
354358 struct brcmf_usbdev_info *devinfo = brcmf_usb_get_businfo(dev);
359
+ struct usb_interface *intf = to_usb_interface(dev);
355360
356361 brcmf_dbg(USB, "Enter\n");
357
- if (devinfo->bus_pub.state != BRCMFMAC_USB_STATE_UP)
358
- return -EIO;
359362
360
- if (test_and_set_bit(0, &devinfo->ctl_op))
361
- return -EIO;
363
+ err = usb_autopm_get_interface(intf);
364
+ if (err)
365
+ goto out;
366
+
367
+ if (devinfo->bus_pub.state != BRCMFMAC_USB_STATE_UP) {
368
+ err = -EIO;
369
+ goto fail;
370
+ }
371
+
372
+ if (test_and_set_bit(0, &devinfo->ctl_op)) {
373
+ err = -EIO;
374
+ goto fail;
375
+ }
362376
363377 devinfo->ctl_completed = false;
364378 err = brcmf_usb_recv_ctl(devinfo, buf, len);
365379 if (err) {
366380 brcmf_err("fail %d bytes: %d\n", err, len);
367381 clear_bit(0, &devinfo->ctl_op);
368
- return err;
382
+ goto fail;
369383 }
370384 timeout = brcmf_usb_ioctl_resp_wait(devinfo);
371385 err = devinfo->ctl_urb_status;
372
- clear_bit(0, &devinfo->ctl_op);
373386 if (!timeout) {
374387 brcmf_err("rxctl wait timed out\n");
388
+ usb_kill_urb(devinfo->ctl_urb);
375389 err = -EIO;
390
+ goto fail;
376391 }
392
+ clear_bit(0, &devinfo->ctl_op);
393
+fail:
394
+ usb_autopm_put_interface(intf);
377395 if (!err)
378396 return devinfo->ctl_urb_actual_length;
379
- else
380
- return err;
397
+out:
398
+ return err;
381399 }
382400
383401 static struct brcmf_usbreq *brcmf_usb_deq(struct brcmf_usbdev_info *devinfo,
....@@ -446,22 +464,17 @@
446464
447465 }
448466
449
-static void brcmf_usb_free_q(struct list_head *q, bool pending)
467
+static void brcmf_usb_free_q(struct list_head *q)
450468 {
451469 struct brcmf_usbreq *req, *next;
452
- int i = 0;
470
+
453471 list_for_each_entry_safe(req, next, q, list) {
454472 if (!req->urb) {
455473 brcmf_err("bad req\n");
456474 break;
457475 }
458
- i++;
459
- if (pending) {
460
- usb_kill_urb(req->urb);
461
- } else {
462
- usb_free_urb(req->urb);
463
- list_del_init(&req->list);
464
- }
476
+ usb_free_urb(req->urb);
477
+ list_del_init(&req->list);
465478 }
466479 }
467480
....@@ -509,17 +522,19 @@
509522 skb = req->skb;
510523 req->skb = NULL;
511524
512
- /* zero lenght packets indicate usb "failure". Do not refill */
525
+ /* zero length packets indicate usb "failure". Do not refill */
513526 if (urb->status != 0 || !urb->actual_length) {
514527 brcmu_pkt_buf_free_skb(skb);
515528 brcmf_usb_enq(devinfo, &devinfo->rx_freeq, req, NULL);
516529 return;
517530 }
518531
519
- if (devinfo->bus_pub.state == BRCMFMAC_USB_STATE_UP) {
532
+ if (devinfo->bus_pub.state == BRCMFMAC_USB_STATE_UP ||
533
+ devinfo->bus_pub.state == BRCMFMAC_USB_STATE_SLEEP) {
520534 skb_put(skb, urb->actual_length);
521
- brcmf_rx_frame(devinfo->dev, skb, true);
535
+ brcmf_rx_frame(devinfo->dev, skb, true, true);
522536 brcmf_usb_rx_refill(devinfo, req);
537
+ usb_mark_last_busy(urb->dev);
523538 } else {
524539 brcmu_pkt_buf_free_skb(skb);
525540 brcmf_usb_enq(devinfo, &devinfo->rx_freeq, req, NULL);
....@@ -576,7 +591,6 @@
576591 brcmf_usb_state_change(struct brcmf_usbdev_info *devinfo, int state)
577592 {
578593 struct brcmf_bus *bcmf_bus = devinfo->bus_pub.bus;
579
- int old_state;
580594
581595 brcmf_dbg(USB, "Enter, current state=%d, new state=%d\n",
582596 devinfo->bus_pub.state, state);
....@@ -584,7 +598,6 @@
584598 if (devinfo->bus_pub.state == state)
585599 return;
586600
587
- old_state = devinfo->bus_pub.state;
588601 devinfo->bus_pub.state = state;
589602
590603 /* update state of upper layer */
....@@ -605,6 +618,11 @@
605618 struct brcmf_usbreq *req;
606619 int ret;
607620 unsigned long flags;
621
+ struct usb_interface *intf = to_usb_interface(dev);
622
+
623
+ ret = usb_autopm_get_interface(intf);
624
+ if (ret)
625
+ goto out;
608626
609627 brcmf_dbg(USB, "Enter, skb=%p\n", skb);
610628 if (devinfo->bus_pub.state != BRCMFMAC_USB_STATE_UP) {
....@@ -643,9 +661,10 @@
643661 devinfo->tx_flowblock = true;
644662 }
645663 spin_unlock_irqrestore(&devinfo->tx_flowblock_lock, flags);
646
- return 0;
647664
648665 fail:
666
+ usb_autopm_put_interface(intf);
667
+out:
649668 return ret;
650669 }
651670
....@@ -1009,20 +1028,32 @@
10091028 brcmf_usb_fw_download(struct brcmf_usbdev_info *devinfo)
10101029 {
10111030 int err;
1031
+ struct usb_interface *intf;
10121032
10131033 brcmf_dbg(USB, "Enter\n");
1014
- if (devinfo == NULL)
1015
- return -ENODEV;
1034
+ if (!devinfo) {
1035
+ err = -ENODEV;
1036
+ goto out;
1037
+ }
10161038
10171039 if (!devinfo->image) {
10181040 brcmf_err("No firmware!\n");
1019
- return -ENOENT;
1041
+ err = -ENOENT;
1042
+ goto out;
10201043 }
1044
+
1045
+ intf = to_usb_interface(devinfo->dev);
1046
+ err = usb_autopm_get_interface(intf);
1047
+ if (err)
1048
+ goto out;
10211049
10221050 err = brcmf_usb_dlstart(devinfo,
10231051 (u8 *)devinfo->image, devinfo->image_len);
10241052 if (err == 0)
10251053 err = brcmf_usb_dlrun(devinfo);
1054
+
1055
+ usb_autopm_put_interface(intf);
1056
+out:
10261057 return err;
10271058 }
10281059
....@@ -1032,8 +1063,8 @@
10321063 brcmf_dbg(USB, "Enter, devinfo %p\n", devinfo);
10331064
10341065 /* free the URBS */
1035
- brcmf_usb_free_q(&devinfo->rx_freeq, false);
1036
- brcmf_usb_free_q(&devinfo->tx_freeq, false);
1066
+ brcmf_usb_free_q(&devinfo->rx_freeq);
1067
+ brcmf_usb_free_q(&devinfo->tx_freeq);
10371068
10381069 usb_free_urb(devinfo->ctl_urb);
10391070 usb_free_urb(devinfo->bulk_urb);
....@@ -1123,18 +1154,6 @@
11231154 return NULL;
11241155 }
11251156
1126
-static void brcmf_usb_wowl_config(struct device *dev, bool enabled)
1127
-{
1128
- struct brcmf_usbdev_info *devinfo = brcmf_usb_get_businfo(dev);
1129
-
1130
- brcmf_dbg(USB, "Configuring WOWL, enabled=%d\n", enabled);
1131
- devinfo->wowl_enabled = enabled;
1132
- if (enabled)
1133
- device_set_wakeup_enable(devinfo->dev, true);
1134
- else
1135
- device_set_wakeup_enable(devinfo->dev, false);
1136
-}
1137
-
11381157 static
11391158 int brcmf_usb_get_fwname(struct device *dev, const char *ext, u8 *fw_name)
11401159 {
....@@ -1161,7 +1180,6 @@
11611180 .txdata = brcmf_usb_tx,
11621181 .txctl = brcmf_usb_tx_ctlpkt,
11631182 .rxctl = brcmf_usb_rx_ctlpkt,
1164
- .wowl_config = brcmf_usb_wowl_config,
11651183 .get_fwname = brcmf_usb_get_fwname,
11661184 };
11671185
....@@ -1197,8 +1215,12 @@
11971215 if (ret)
11981216 goto error;
11991217
1218
+ ret = brcmf_alloc(devinfo->dev, devinfo->settings);
1219
+ if (ret)
1220
+ goto error;
1221
+
12001222 /* Attach to the common driver interface */
1201
- ret = brcmf_attach(devinfo->dev, devinfo->settings);
1223
+ ret = brcmf_attach(devinfo->dev);
12021224 if (ret)
12031225 goto error;
12041226
....@@ -1270,7 +1292,10 @@
12701292 }
12711293
12721294 if (!brcmf_usb_dlneeded(devinfo)) {
1273
- ret = brcmf_attach(devinfo->dev, devinfo->settings);
1295
+ ret = brcmf_alloc(devinfo->dev, devinfo->settings);
1296
+ if (ret)
1297
+ goto fail;
1298
+ ret = brcmf_attach(devinfo->dev);
12741299 if (ret)
12751300 goto fail;
12761301 /* we are done */
....@@ -1298,6 +1323,7 @@
12981323
12991324 fail:
13001325 /* Release resources in reverse order */
1326
+ brcmf_free(devinfo->dev);
13011327 kfree(bus);
13021328 brcmf_usb_detach(devinfo);
13031329 return ret;
....@@ -1311,6 +1337,7 @@
13111337 brcmf_dbg(USB, "Enter, bus_pub %p\n", devinfo);
13121338
13131339 brcmf_detach(devinfo->dev);
1340
+ brcmf_free(devinfo->dev);
13141341 kfree(devinfo->bus_pub.bus);
13151342 brcmf_usb_detach(devinfo);
13161343 }
....@@ -1340,6 +1367,8 @@
13401367 init_completion(&devinfo->dev_init_done);
13411368
13421369 usb_set_intfdata(intf, devinfo);
1370
+
1371
+ intf->needs_remote_wakeup = 1;
13431372
13441373 /* Check that the device supports only one configuration */
13451374 if (usb->descriptor.bNumConfigurations != 1) {
....@@ -1454,10 +1483,8 @@
14541483
14551484 brcmf_dbg(USB, "Enter\n");
14561485 devinfo->bus_pub.state = BRCMFMAC_USB_STATE_SLEEP;
1457
- if (devinfo->wowl_enabled)
1458
- brcmf_cancel_all_urbs(devinfo);
1459
- else
1460
- brcmf_detach(&usb->dev);
1486
+ brcmf_cancel_all_urbs(devinfo);
1487
+ device_set_wakeup_enable(devinfo->dev, true);
14611488 return 0;
14621489 }
14631490
....@@ -1470,11 +1497,10 @@
14701497 struct brcmf_usbdev_info *devinfo = brcmf_usb_get_businfo(&usb->dev);
14711498
14721499 brcmf_dbg(USB, "Enter\n");
1473
- if (!devinfo->wowl_enabled)
1474
- return brcmf_attach(devinfo->dev, devinfo->settings);
14751500
14761501 devinfo->bus_pub.state = BRCMFMAC_USB_STATE_UP;
14771502 brcmf_usb_rx_fill_all(devinfo);
1503
+ device_set_wakeup_enable(devinfo->dev, false);
14781504 return 0;
14791505 }
14801506
....@@ -1531,6 +1557,7 @@
15311557 .suspend = brcmf_usb_suspend,
15321558 .resume = brcmf_usb_resume,
15331559 .reset_resume = brcmf_usb_reset_resume,
1560
+ .supports_autosuspend = true,
15341561 .disable_hub_initiated_lpm = 1,
15351562 };
15361563
....@@ -1551,11 +1578,14 @@
15511578 brcmf_dbg(USB, "Enter\n");
15521579 ret = driver_for_each_device(drv, NULL, NULL,
15531580 brcmf_usb_reset_device);
1581
+ if (ret)
1582
+ brcmf_err("failed to reset all usb devices %d\n", ret);
1583
+
15541584 usb_deregister(&brcmf_usbdrvr);
15551585 }
15561586
1557
-void brcmf_usb_register(void)
1587
+int brcmf_usb_register(void)
15581588 {
15591589 brcmf_dbg(USB, "Enter\n");
1560
- usb_register(&brcmf_usbdrvr);
1590
+ return usb_register(&brcmf_usbdrvr);
15611591 }