^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Host Controller Driver for the Elan Digital Systems U132 adapter
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) * Copyright(C) 2006 Elan Digital Systems Limited
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) * http://www.elandigitalsystems.com
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) * Author and Maintainer - Tony Olech - Elan Digital Systems
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) * tony.olech@elandigitalsystems.com
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) * This driver was written by Tony Olech(tony.olech@elandigitalsystems.com)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) * based on various USB host drivers in the 2.6.15 linux kernel
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) * with constant reference to the 3rd Edition of Linux Device Drivers
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) * published by O'Reilly
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) * The U132 adapter is a USB to CardBus adapter specifically designed
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) * for PC cards that contain an OHCI host controller. Typical PC cards
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) * are the Orange Mobile 3G Option GlobeTrotter Fusion card.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) * The U132 adapter will *NOT *work with PC cards that do not contain
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) * an OHCI controller. A simple way to test whether a PC card has an
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) * OHCI controller as an interface is to insert the PC card directly
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) * into a laptop(or desktop) with a CardBus slot and if "lspci" shows
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) * a new USB controller and "lsusb -v" shows a new OHCI Host Controller
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) * then there is a good chance that the U132 adapter will support the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) * PC card.(you also need the specific client driver for the PC card)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) * Please inform the Author and Maintainer about any PC cards that
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) * contain OHCI Host Controller and work when directly connected to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) * an embedded CardBus slot but do not work when they are connected
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) * via an ELAN U132 adapter.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) #include <linux/moduleparam.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) #include <linux/delay.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) #include <linux/ioport.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) #include <linux/pci_ids.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) #include <linux/sched.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) #include <linux/errno.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) #include <linux/init.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) #include <linux/timer.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) #include <linux/list.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) #include <linux/interrupt.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) #include <linux/usb.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) #include <linux/usb/hcd.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) #include <linux/workqueue.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) #include <linux/platform_device.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) #include <linux/mutex.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) #include <asm/io.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) #include <asm/irq.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) #include <asm/byteorder.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) /* FIXME ohci.h is ONLY for internal use by the OHCI driver.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) * If you're going to try stuff like this, you need to split
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) * out shareable stuff (register declarations?) into its own
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) * file, maybe name <linux/usb/ohci.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) #include "ohci.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) #define OHCI_CONTROL_INIT OHCI_CTRL_CBSR
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) #define OHCI_INTR_INIT (OHCI_INTR_MIE | OHCI_INTR_UE | OHCI_INTR_RD | \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) OHCI_INTR_WDH)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) MODULE_AUTHOR("Tony Olech - Elan Digital Systems Limited");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) MODULE_DESCRIPTION("U132 USB Host Controller Driver");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) MODULE_LICENSE("GPL");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) #define INT_MODULE_PARM(n, v) static int n = v;module_param(n, int, 0444)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) INT_MODULE_PARM(testing, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) /* Some boards misreport power switching/overcurrent*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) static bool distrust_firmware = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) module_param(distrust_firmware, bool, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) MODULE_PARM_DESC(distrust_firmware, "true to distrust firmware power/overcurrent"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) "t setup");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) static DECLARE_WAIT_QUEUE_HEAD(u132_hcd_wait);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) * u132_module_lock exists to protect access to global variables
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) static struct mutex u132_module_lock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) static int u132_exiting;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) static int u132_instances;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) * end of the global variables protected by u132_module_lock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) static struct workqueue_struct *workqueue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) #define MAX_U132_PORTS 7
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) #define MAX_U132_ADDRS 128
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) #define MAX_U132_UDEVS 4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) #define MAX_U132_ENDPS 100
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) #define MAX_U132_RINGS 4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) static const char *cc_to_text[16] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) "No Error ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) "CRC Error ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) "Bit Stuff ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) "Data Togg ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) "Stall ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) "DevNotResp ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) "PIDCheck ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) "UnExpPID ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) "DataOver ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) "DataUnder ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) "(for hw) ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) "(for hw) ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) "BufferOver ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) "BuffUnder ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) "(for HCD) ",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) "(for HCD) "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) struct u132_port {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) struct u132 *u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) int reset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) int enable;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) int power;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) int Status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) struct u132_addr {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) u8 address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) struct u132_udev {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) struct kref kref;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) struct usb_device *usb_device;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) u8 enumeration;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) u8 udev_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) u8 usb_addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) u8 portnumber;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) u8 endp_number_in[16];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) u8 endp_number_out[16];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) #define ENDP_QUEUE_SHIFT 3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) #define ENDP_QUEUE_SIZE (1<<ENDP_QUEUE_SHIFT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) #define ENDP_QUEUE_MASK (ENDP_QUEUE_SIZE-1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) struct u132_urbq {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) struct list_head urb_more;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) struct urb *urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) struct u132_spin {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) spinlock_t slock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) struct u132_endp {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) struct kref kref;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) u8 udev_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) u8 endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) u8 usb_addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) u8 usb_endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) struct u132 *u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) struct list_head endp_ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) struct u132_ring *ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) unsigned toggle_bits:2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) unsigned active:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) unsigned delayed:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) unsigned input:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) unsigned output:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) unsigned pipetype:2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) unsigned dequeueing:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) unsigned edset_flush:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) unsigned spare_bits:14;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) unsigned long jiffies;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) struct usb_host_endpoint *hep;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) struct u132_spin queue_lock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) u16 queue_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) u16 queue_last;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) u16 queue_next;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) struct urb *urb_list[ENDP_QUEUE_SIZE];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) struct list_head urb_more;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) struct delayed_work scheduler;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) struct u132_ring {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) unsigned in_use:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) unsigned length:7;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) u8 number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) struct u132 *u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) struct u132_endp *curr_endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) struct delayed_work scheduler;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) struct u132 {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) struct kref kref;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) struct mutex sw_lock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) struct mutex scheduler_lock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) struct u132_platform_data *board;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) struct platform_device *platform_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) struct u132_ring ring[MAX_U132_RINGS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) int sequence_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) int going;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) int power;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) int reset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) int num_ports;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) u32 hc_control;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) u32 hc_fminterval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) u32 hc_roothub_status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) u32 hc_roothub_a;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) u32 hc_roothub_portstatus[MAX_ROOT_PORTS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) int flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) unsigned long next_statechange;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) struct delayed_work monitor;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) int num_endpoints;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) struct u132_addr addr[MAX_U132_ADDRS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) struct u132_udev udev[MAX_U132_UDEVS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) struct u132_port port[MAX_U132_PORTS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) struct u132_endp *endp[MAX_U132_ENDPS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) * these cannot be inlines because we need the structure offset!!
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) * Does anyone have a better way?????
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) #define ftdi_read_pcimem(pdev, member, data) usb_ftdi_elan_read_pcimem(pdev, \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) offsetof(struct ohci_regs, member), 0, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) #define ftdi_write_pcimem(pdev, member, data) usb_ftdi_elan_write_pcimem(pdev, \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) offsetof(struct ohci_regs, member), 0, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) #define u132_read_pcimem(u132, member, data) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) usb_ftdi_elan_read_pcimem(u132->platform_dev, offsetof(struct \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) ohci_regs, member), 0, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) #define u132_write_pcimem(u132, member, data) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) usb_ftdi_elan_write_pcimem(u132->platform_dev, offsetof(struct \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) ohci_regs, member), 0, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) static inline struct u132 *udev_to_u132(struct u132_udev *udev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) u8 udev_number = udev->udev_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) return container_of(udev, struct u132, udev[udev_number]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) static inline struct u132 *hcd_to_u132(struct usb_hcd *hcd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) return (struct u132 *)(hcd->hcd_priv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) static inline struct usb_hcd *u132_to_hcd(struct u132 *u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) return container_of((void *)u132, struct usb_hcd, hcd_priv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) static inline void u132_disable(struct u132 *u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) u132_to_hcd(u132)->state = HC_STATE_HALT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) #define kref_to_u132(d) container_of(d, struct u132, kref)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) #define kref_to_u132_endp(d) container_of(d, struct u132_endp, kref)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) #define kref_to_u132_udev(d) container_of(d, struct u132_udev, kref)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) #include "../misc/usb_u132.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) static const char hcd_name[] = "u132_hcd";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) #define PORT_C_MASK ((USB_PORT_STAT_C_CONNECTION | USB_PORT_STAT_C_ENABLE | \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) USB_PORT_STAT_C_SUSPEND | USB_PORT_STAT_C_OVERCURRENT | \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) USB_PORT_STAT_C_RESET) << 16)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) static void u132_hcd_delete(struct kref *kref)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) struct u132 *u132 = kref_to_u132(kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) struct platform_device *pdev = u132->platform_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) struct usb_hcd *hcd = u132_to_hcd(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) u132->going += 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) mutex_lock(&u132_module_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) u132_instances -= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) mutex_unlock(&u132_module_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) dev_warn(&u132->platform_dev->dev, "FREEING the hcd=%p and thus the u13"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) "2=%p going=%d pdev=%p\n", hcd, u132, u132->going, pdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) usb_put_hcd(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) static inline void u132_u132_put_kref(struct u132 *u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) kref_put(&u132->kref, u132_hcd_delete);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) static inline void u132_u132_init_kref(struct u132 *u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) kref_init(&u132->kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) static void u132_udev_delete(struct kref *kref)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) struct u132_udev *udev = kref_to_u132_udev(kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) udev->udev_number = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) udev->usb_device = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) udev->usb_addr = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) udev->enumeration = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) static inline void u132_udev_put_kref(struct u132 *u132, struct u132_udev *udev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) kref_put(&udev->kref, u132_udev_delete);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) static inline void u132_udev_get_kref(struct u132 *u132, struct u132_udev *udev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) kref_get(&udev->kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) static inline void u132_udev_init_kref(struct u132 *u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) struct u132_udev *udev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) kref_init(&udev->kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) static inline void u132_ring_put_kref(struct u132 *u132, struct u132_ring *ring)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) kref_put(&u132->kref, u132_hcd_delete);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) static void u132_ring_requeue_work(struct u132 *u132, struct u132_ring *ring,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) unsigned int delta)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) if (delta > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) if (queue_delayed_work(workqueue, &ring->scheduler, delta))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) } else if (queue_delayed_work(workqueue, &ring->scheduler, 0))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) kref_put(&u132->kref, u132_hcd_delete);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) static void u132_ring_queue_work(struct u132 *u132, struct u132_ring *ring,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) unsigned int delta)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) kref_get(&u132->kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) u132_ring_requeue_work(u132, ring, delta);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) static void u132_ring_cancel_work(struct u132 *u132, struct u132_ring *ring)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) if (cancel_delayed_work(&ring->scheduler))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) kref_put(&u132->kref, u132_hcd_delete);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) static void u132_endp_delete(struct kref *kref)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) struct u132_endp *endp = kref_to_u132_endp(kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) u8 usb_addr = endp->usb_addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) u8 usb_endp = endp->usb_endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) u8 address = u132->addr[usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) struct u132_udev *udev = &u132->udev[address];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) u8 endp_number = endp->endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) struct usb_host_endpoint *hep = endp->hep;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) struct u132_ring *ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) struct list_head *head = &endp->endp_ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) ring->length -= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) if (endp == ring->curr_endp) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) if (list_empty(head)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) ring->curr_endp = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) list_del(head);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) struct u132_endp *next_endp = list_entry(head->next,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) struct u132_endp, endp_ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) ring->curr_endp = next_endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) list_del(head);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) list_del(head);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) if (endp->input) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) udev->endp_number_in[usb_endp] = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) u132_udev_put_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) if (endp->output) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) udev->endp_number_out[usb_endp] = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) u132_udev_put_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) u132->endp[endp_number - 1] = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) hep->hcpriv = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) kfree(endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) u132_u132_put_kref(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) static inline void u132_endp_put_kref(struct u132 *u132, struct u132_endp *endp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) kref_put(&endp->kref, u132_endp_delete);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) static inline void u132_endp_get_kref(struct u132 *u132, struct u132_endp *endp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) kref_get(&endp->kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) static inline void u132_endp_init_kref(struct u132 *u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) struct u132_endp *endp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) kref_init(&endp->kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) kref_get(&u132->kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) static void u132_endp_queue_work(struct u132 *u132, struct u132_endp *endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) unsigned int delta)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) if (queue_delayed_work(workqueue, &endp->scheduler, delta))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) kref_get(&endp->kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) static void u132_endp_cancel_work(struct u132 *u132, struct u132_endp *endp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) if (cancel_delayed_work(&endp->scheduler))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) kref_put(&endp->kref, u132_endp_delete);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) static inline void u132_monitor_put_kref(struct u132 *u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) kref_put(&u132->kref, u132_hcd_delete);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) static void u132_monitor_queue_work(struct u132 *u132, unsigned int delta)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) if (queue_delayed_work(workqueue, &u132->monitor, delta))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) kref_get(&u132->kref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) static void u132_monitor_requeue_work(struct u132 *u132, unsigned int delta)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) if (!queue_delayed_work(workqueue, &u132->monitor, delta))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) kref_put(&u132->kref, u132_hcd_delete);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) static void u132_monitor_cancel_work(struct u132 *u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) if (cancel_delayed_work(&u132->monitor))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) kref_put(&u132->kref, u132_hcd_delete);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) static int read_roothub_info(struct u132 *u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) u32 revision;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) retval = u132_read_pcimem(u132, revision, &revision);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) dev_err(&u132->platform_dev->dev, "error %d accessing device co"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) "ntrol\n", retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) } else if ((revision & 0xFF) == 0x10) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) } else if ((revision & 0xFF) == 0x11) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) dev_err(&u132->platform_dev->dev, "device revision is not valid"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) " %08X\n", revision);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) retval = u132_read_pcimem(u132, control, &u132->hc_control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) dev_err(&u132->platform_dev->dev, "error %d accessing device co"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) "ntrol\n", retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) retval = u132_read_pcimem(u132, roothub.status,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) &u132->hc_roothub_status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) dev_err(&u132->platform_dev->dev, "error %d accessing device re"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) "g roothub.status\n", retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) retval = u132_read_pcimem(u132, roothub.a, &u132->hc_roothub_a);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) dev_err(&u132->platform_dev->dev, "error %d accessing device re"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) "g roothub.a\n", retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) int I = u132->num_ports;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) int i = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) while (I-- > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) retval = u132_read_pcimem(u132, roothub.portstatus[i],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) &u132->hc_roothub_portstatus[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) dev_err(&u132->platform_dev->dev, "error %d acc"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) "essing device roothub.portstatus[%d]\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) , retval, i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) i += 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) static void u132_hcd_monitor_work(struct work_struct *work)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) struct u132 *u132 = container_of(work, struct u132, monitor.work);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) u132_monitor_put_kref(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) dev_err(&u132->platform_dev->dev, "device is being removed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) u132_monitor_put_kref(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) mutex_lock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) retval = read_roothub_info(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) struct usb_hcd *hcd = u132_to_hcd(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) u132_disable(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) u132->going = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) mutex_unlock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) usb_hc_died(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) ftdi_elan_gone_away(u132->platform_dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) u132_monitor_put_kref(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) u132_monitor_requeue_work(u132, 500);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) mutex_unlock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) static void u132_hcd_giveback_urb(struct u132 *u132, struct u132_endp *endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) struct urb *urb, int status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) struct u132_ring *ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) unsigned long irqs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) struct usb_hcd *hcd = u132_to_hcd(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) urb->error_count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) spin_lock_irqsave(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) usb_hcd_unlink_urb_from_ep(hcd, urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) endp->queue_next += 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) if (ENDP_QUEUE_SIZE > --endp->queue_size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) endp->active = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) struct list_head *next = endp->urb_more.next;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) struct u132_urbq *urbq = list_entry(next, struct u132_urbq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) list_del(next);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) endp->urb_list[ENDP_QUEUE_MASK & endp->queue_last++] =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) urbq->urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) endp->active = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) kfree(urbq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) ring->in_use = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) u132_ring_cancel_work(u132, ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) u132_ring_queue_work(u132, ring, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) usb_hcd_giveback_urb(hcd, urb, status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) static void u132_hcd_forget_urb(struct u132 *u132, struct u132_endp *endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) struct urb *urb, int status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) static void u132_hcd_abandon_urb(struct u132 *u132, struct u132_endp *endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) struct urb *urb, int status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) unsigned long irqs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) struct usb_hcd *hcd = u132_to_hcd(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) urb->error_count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) spin_lock_irqsave(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) usb_hcd_unlink_urb_from_ep(hcd, urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) endp->queue_next += 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) if (ENDP_QUEUE_SIZE > --endp->queue_size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) endp->active = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) struct list_head *next = endp->urb_more.next;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) struct u132_urbq *urbq = list_entry(next, struct u132_urbq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) list_del(next);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) endp->urb_list[ENDP_QUEUE_MASK & endp->queue_last++] =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) urbq->urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) endp->active = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) kfree(urbq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) usb_hcd_giveback_urb(hcd, urb, status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) static inline int edset_input(struct u132 *u132, struct u132_ring *ring,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) struct u132_endp *endp, struct urb *urb, u8 address, u8 toggle_bits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) void (*callback) (void *endp, struct urb *urb, u8 *buf, int len,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) int toggle_bits, int error_count, int condition_code, int repeat_number,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) int halted, int skipped, int actual, int non_null))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) return usb_ftdi_elan_edset_input(u132->platform_dev, ring->number, endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) urb, address, endp->usb_endp, toggle_bits, callback);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) static inline int edset_setup(struct u132 *u132, struct u132_ring *ring,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) struct u132_endp *endp, struct urb *urb, u8 address, u8 toggle_bits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) void (*callback) (void *endp, struct urb *urb, u8 *buf, int len,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) int toggle_bits, int error_count, int condition_code, int repeat_number,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) int halted, int skipped, int actual, int non_null))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) return usb_ftdi_elan_edset_setup(u132->platform_dev, ring->number, endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) urb, address, endp->usb_endp, toggle_bits, callback);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) static inline int edset_single(struct u132 *u132, struct u132_ring *ring,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) struct u132_endp *endp, struct urb *urb, u8 address, u8 toggle_bits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) void (*callback) (void *endp, struct urb *urb, u8 *buf, int len,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) int toggle_bits, int error_count, int condition_code, int repeat_number,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) int halted, int skipped, int actual, int non_null))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) return usb_ftdi_elan_edset_single(u132->platform_dev, ring->number,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) endp, urb, address, endp->usb_endp, toggle_bits, callback);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) static inline int edset_output(struct u132 *u132, struct u132_ring *ring,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) struct u132_endp *endp, struct urb *urb, u8 address, u8 toggle_bits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) void (*callback) (void *endp, struct urb *urb, u8 *buf, int len,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603) int toggle_bits, int error_count, int condition_code, int repeat_number,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) int halted, int skipped, int actual, int non_null))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) return usb_ftdi_elan_edset_output(u132->platform_dev, ring->number,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) endp, urb, address, endp->usb_endp, toggle_bits, callback);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) * must not LOCK sw_lock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615) static void u132_hcd_interrupt_recv(void *data, struct urb *urb, u8 *buf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) struct u132_udev *udev = &u132->udev[address];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) struct u132_ring *ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) u8 *u = urb->transfer_buffer + urb->actual_length;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) u8 *b = buf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) int L = len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) while (L-- > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) *u++ = *b++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) urb->actual_length += len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) if ((condition_code == TD_CC_NOERROR) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) (urb->transfer_buffer_length > urb->actual_length)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) endp->toggle_bits = toggle_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) usb_settoggle(udev->usb_device, endp->usb_endp, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) 1 & toggle_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) if (urb->actual_length > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) retval = edset_single(u132, ring, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) address, endp->toggle_bits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661) u132_hcd_interrupt_recv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) u132_hcd_giveback_urb(u132, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664) retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666) ring->in_use = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667) endp->active = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) endp->jiffies = jiffies +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669) msecs_to_jiffies(urb->interval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) u132_ring_cancel_work(u132, ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) u132_ring_queue_work(u132, ring, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) } else if ((condition_code == TD_DATAUNDERRUN) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) ((urb->transfer_flags & URB_SHORT_NOT_OK) == 0)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) endp->toggle_bits = toggle_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679) usb_settoggle(udev->usb_device, endp->usb_endp, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) 1 & toggle_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) if (condition_code == TD_CC_NOERROR) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686) endp->toggle_bits = toggle_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) usb_settoggle(udev->usb_device, endp->usb_endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) 0, 1 & toggle_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) } else if (condition_code == TD_CC_STALL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690) endp->toggle_bits = 0x2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691) usb_settoggle(udev->usb_device, endp->usb_endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) endp->toggle_bits = 0x2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) usb_settoggle(udev->usb_device, endp->usb_endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) dev_err(&u132->platform_dev->dev, "urb=%p givin"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698) "g back INTERRUPT %s\n", urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) cc_to_text[condition_code]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) u132_hcd_giveback_urb(u132, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703) cc_to_error[condition_code]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) static void u132_hcd_bulk_output_sent(void *data, struct urb *urb, u8 *buf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716) int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 730) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 731) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 732) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 741) struct u132_ring *ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 742) urb->actual_length += len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 743) endp->toggle_bits = toggle_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) if (urb->transfer_buffer_length > urb->actual_length) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747) retval = edset_output(u132, ring, endp, urb, address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) endp->toggle_bits, u132_hcd_bulk_output_sent);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766) static void u132_hcd_bulk_input_recv(void *data, struct urb *urb, u8 *buf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767) int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773) struct u132_udev *udev = &u132->udev[address];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) struct u132_ring *ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794) u8 *u = urb->transfer_buffer + urb->actual_length;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795) u8 *b = buf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796) int L = len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798) while (L-- > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799) *u++ = *b++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801) urb->actual_length += len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) if ((condition_code == TD_CC_NOERROR) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803) (urb->transfer_buffer_length > urb->actual_length)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805) endp->toggle_bits = toggle_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) usb_settoggle(udev->usb_device, endp->usb_endp, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) 1 & toggle_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809) retval = usb_ftdi_elan_edset_input(u132->platform_dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) ring->number, endp, urb, address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 811) endp->usb_endp, endp->toggle_bits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 812) u132_hcd_bulk_input_recv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 813) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 814) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 815) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 816) } else if (condition_code == TD_CC_NOERROR) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 817) endp->toggle_bits = toggle_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 818) usb_settoggle(udev->usb_device, endp->usb_endp, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 819) 1 & toggle_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 820) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 821) u132_hcd_giveback_urb(u132, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 822) cc_to_error[condition_code]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 823) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 824) } else if ((condition_code == TD_DATAUNDERRUN) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 825) ((urb->transfer_flags & URB_SHORT_NOT_OK) == 0)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 826) endp->toggle_bits = toggle_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 827) usb_settoggle(udev->usb_device, endp->usb_endp, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 828) 1 & toggle_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 829) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 830) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 831) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 832) } else if (condition_code == TD_DATAUNDERRUN) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 833) endp->toggle_bits = toggle_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 834) usb_settoggle(udev->usb_device, endp->usb_endp, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 835) 1 & toggle_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 836) dev_warn(&u132->platform_dev->dev, "urb=%p(SHORT NOT OK"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 837) ") giving back BULK IN %s\n", urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 838) cc_to_text[condition_code]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 839) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 840) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 841) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 842) } else if (condition_code == TD_CC_STALL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 843) endp->toggle_bits = 0x2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 844) usb_settoggle(udev->usb_device, endp->usb_endp, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 845) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 846) u132_hcd_giveback_urb(u132, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 847) cc_to_error[condition_code]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 848) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 849) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 850) endp->toggle_bits = 0x2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 851) usb_settoggle(udev->usb_device, endp->usb_endp, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 852) dev_err(&u132->platform_dev->dev, "urb=%p giving back B"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 853) "ULK IN code=%d %s\n", urb, condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 854) cc_to_text[condition_code]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 855) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 856) u132_hcd_giveback_urb(u132, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 857) cc_to_error[condition_code]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 858) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 859) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 860) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 861) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 862) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 863) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 864) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 865) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 866) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 867) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 868)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 869) static void u132_hcd_configure_empty_sent(void *data, struct urb *urb, u8 *buf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 870) int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 871) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 872) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 873) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 874) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 875) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 876) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 877) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 878) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 879) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 880) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 881) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 882) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 883) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 884) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 885) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 886) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 887) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 888) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 889) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 890) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 891) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 892) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 893) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 894) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 895) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 896) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 897) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 898) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 899) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 900) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 901) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 902) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 903) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 904) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 905)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 906) static void u132_hcd_configure_input_recv(void *data, struct urb *urb, u8 *buf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 907) int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 908) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 909) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 910) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 911) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 912) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 913) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 914) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 915) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 916) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 917) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 918) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 919) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 920) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 921) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 922) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 923) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 924) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 925) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 926) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 927) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 928) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 929) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 930) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 931) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 932) struct u132_ring *ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 933) u8 *u = urb->transfer_buffer;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 934) u8 *b = buf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 935) int L = len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 936)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 937) while (L-- > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 938) *u++ = *b++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 939)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 940) urb->actual_length = len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 941) if ((condition_code == TD_CC_NOERROR) || ((condition_code ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 942) TD_DATAUNDERRUN) && ((urb->transfer_flags &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 943) URB_SHORT_NOT_OK) == 0))) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 944) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 945) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 946) retval = usb_ftdi_elan_edset_empty(u132->platform_dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 947) ring->number, endp, urb, address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 948) endp->usb_endp, 0x3,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 949) u132_hcd_configure_empty_sent);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 950) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 951) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 952) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 953) } else if (condition_code == TD_CC_STALL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 954) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 955) dev_warn(&u132->platform_dev->dev, "giving back SETUP I"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 956) "NPUT STALL urb %p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 957) u132_hcd_giveback_urb(u132, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 958) cc_to_error[condition_code]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 959) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 960) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 961) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 962) dev_err(&u132->platform_dev->dev, "giving back SETUP IN"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 963) "PUT %s urb %p\n", cc_to_text[condition_code],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 964) urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 965) u132_hcd_giveback_urb(u132, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 966) cc_to_error[condition_code]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 967) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 968) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 969) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 970) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 971) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 972) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 973) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 974) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 975) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 976) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 977)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 978) static void u132_hcd_configure_empty_recv(void *data, struct urb *urb, u8 *buf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 979) int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 980) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 981) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 982) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 983) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 984) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 985) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 986) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 987) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 988) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 989) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 990) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 991) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 992) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 993) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 994) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 995) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 996) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 997) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 998) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 999) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1000) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1001) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1002) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1003) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1004) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1005) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1006) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1007) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1008) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1009) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1010) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1011) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1012) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1013) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1014)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1015) static void u132_hcd_configure_setup_sent(void *data, struct urb *urb, u8 *buf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1016) int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1017) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1018) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1019) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1020) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1021) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1022) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1023) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1024) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1025) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1026) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1027) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1028) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1029) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1030) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1031) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1032) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1033) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1034) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1035) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1036) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1037) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1038) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1039) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1040) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1041) if (usb_pipein(urb->pipe)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1042) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1043) struct u132_ring *ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1044) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1045) retval = usb_ftdi_elan_edset_input(u132->platform_dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1046) ring->number, endp, urb, address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1047) endp->usb_endp, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1048) u132_hcd_configure_input_recv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1049) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1050) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1051) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1052) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1053) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1054) struct u132_ring *ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1055) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1056) retval = usb_ftdi_elan_edset_input(u132->platform_dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1057) ring->number, endp, urb, address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1058) endp->usb_endp, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1059) u132_hcd_configure_empty_recv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1060) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1061) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1062) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1063) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1064) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1065) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1066) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1067) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1068) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1069) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1070) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1071) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1072)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1073) static void u132_hcd_enumeration_empty_recv(void *data, struct urb *urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1074) u8 *buf, int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1075) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1076) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1077) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1078) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1079) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1080) struct u132_udev *udev = &u132->udev[address];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1081) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1082) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1083) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1084) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1085) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1086) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1087) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1088) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1089) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1090) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1091) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1092) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1093) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1094) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1095) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1096) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1097) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1098) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1099) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1100) u132->addr[0].address = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1101) endp->usb_addr = udev->usb_addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1102) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1103) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1104) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1105) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1106) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1107) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1108) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1109) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1110) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1111) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1112) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1113)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1114) static void u132_hcd_enumeration_address_sent(void *data, struct urb *urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1115) u8 *buf, int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1116) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1117) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1118) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1119) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1120) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1121) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1122) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1123) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1124) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1125) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1126) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1127) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1128) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1129) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1130) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1131) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1132) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1133) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1134) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1135) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1136) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1137) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1138) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1139) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1140) struct u132_ring *ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1141) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1142) retval = usb_ftdi_elan_edset_input(u132->platform_dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1143) ring->number, endp, urb, 0, endp->usb_endp, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1144) u132_hcd_enumeration_empty_recv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1145) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1146) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1147) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1148) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1149) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1150) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1151) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1152) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1153) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1154) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1155) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1156)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1157) static void u132_hcd_initial_empty_sent(void *data, struct urb *urb, u8 *buf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1158) int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1159) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1160) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1161) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1162) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1163) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1164) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1165) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1166) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1167) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1168) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1169) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1170) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1171) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1172) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1173) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1174) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1175) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1176) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1177) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1178) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1179) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1180) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1181) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1182) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1183) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1184) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1185) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1186) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1187) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1188) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1189) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1190) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1191) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1192) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1193)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1194) static void u132_hcd_initial_input_recv(void *data, struct urb *urb, u8 *buf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1195) int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1196) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1197) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1198) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1199) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1200) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1201) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1202) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1203) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1204) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1205) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1206) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1207) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1208) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1209) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1210) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1211) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1212) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1213) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1214) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1215) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1216) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1217) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1218) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1219) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1220) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1221) struct u132_ring *ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1222) u8 *u = urb->transfer_buffer;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1223) u8 *b = buf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1224) int L = len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1225)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1226) while (L-- > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1227) *u++ = *b++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1228)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1229) urb->actual_length = len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1230) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1231) retval = usb_ftdi_elan_edset_empty(u132->platform_dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1232) ring->number, endp, urb, address, endp->usb_endp, 0x3,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1233) u132_hcd_initial_empty_sent);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1234) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1235) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1236) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1237) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1238) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1239) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1240) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1241) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1242) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1243) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1244) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1245)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1246) static void u132_hcd_initial_setup_sent(void *data, struct urb *urb, u8 *buf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1247) int len, int toggle_bits, int error_count, int condition_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1248) int repeat_number, int halted, int skipped, int actual, int non_null)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1249) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1250) struct u132_endp *endp = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1251) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1252) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1253) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1254) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1255) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1256) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1257) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1258) u132_hcd_forget_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1259) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1260) } else if (endp->dequeueing) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1261) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1262) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1263) u132_hcd_giveback_urb(u132, endp, urb, -EINTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1264) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1265) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1266) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1267) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1268) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1269) u132_hcd_giveback_urb(u132, endp, urb, -ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1270) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1271) } else if (!urb->unlinked) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1272) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1273) struct u132_ring *ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1274) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1275) retval = usb_ftdi_elan_edset_input(u132->platform_dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1276) ring->number, endp, urb, address, endp->usb_endp, 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1277) u132_hcd_initial_input_recv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1278) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1279) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1280) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1281) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1282) dev_err(&u132->platform_dev->dev, "CALLBACK called urb=%p "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1283) "unlinked=%d\n", urb, urb->unlinked);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1284) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1285) u132_hcd_giveback_urb(u132, endp, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1286) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1287) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1288) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1289)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1290) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1291) * this work function is only executed from the work queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1292) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1293) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1294) static void u132_hcd_ring_work_scheduler(struct work_struct *work)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1295) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1296) struct u132_ring *ring =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1297) container_of(work, struct u132_ring, scheduler.work);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1298) struct u132 *u132 = ring->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1299) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1300) if (ring->in_use) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1301) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1302) u132_ring_put_kref(u132, ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1303) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1304) } else if (ring->curr_endp) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1305) struct u132_endp *endp, *last_endp = ring->curr_endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1306) unsigned long wakeup = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1307) list_for_each_entry(endp, &last_endp->endp_ring, endp_ring) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1308) if (endp->queue_next == endp->queue_last) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1309) } else if ((endp->delayed == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1310) || time_after_eq(jiffies, endp->jiffies)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1311) ring->curr_endp = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1312) u132_endp_cancel_work(u132, last_endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1313) u132_endp_queue_work(u132, last_endp, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1314) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1315) u132_ring_put_kref(u132, ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1316) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1317) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1318) unsigned long delta = endp->jiffies - jiffies;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1319) if (delta > wakeup)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1320) wakeup = delta;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1321) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1322) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1323) if (last_endp->queue_next == last_endp->queue_last) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1324) } else if ((last_endp->delayed == 0) || time_after_eq(jiffies,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1325) last_endp->jiffies)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1326) u132_endp_cancel_work(u132, last_endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1327) u132_endp_queue_work(u132, last_endp, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1328) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1329) u132_ring_put_kref(u132, ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1330) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1331) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1332) unsigned long delta = last_endp->jiffies - jiffies;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1333) if (delta > wakeup)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1334) wakeup = delta;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1335) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1336) if (wakeup > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1337) u132_ring_requeue_work(u132, ring, wakeup);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1338) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1339) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1340) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1341) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1342) u132_ring_put_kref(u132, ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1343) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1344) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1345) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1346) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1347) u132_ring_put_kref(u132, ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1348) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1349) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1350) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1351)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1352) static void u132_hcd_endp_work_scheduler(struct work_struct *work)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1353) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1354) struct u132_ring *ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1355) struct u132_endp *endp =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1356) container_of(work, struct u132_endp, scheduler.work);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1357) struct u132 *u132 = endp->u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1358) mutex_lock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1359) ring = endp->ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1360) if (endp->edset_flush) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1361) endp->edset_flush = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1362) if (endp->dequeueing)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1363) usb_ftdi_elan_edset_flush(u132->platform_dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1364) ring->number, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1365) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1366) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1367) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1368) } else if (endp->active) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1369) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1370) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1371) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1372) } else if (ring->in_use) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1373) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1374) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1375) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1376) } else if (endp->queue_next == endp->queue_last) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1377) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1378) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1379) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1380) } else if (endp->pipetype == PIPE_INTERRUPT) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1381) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1382) if (ring->in_use) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1383) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1384) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1385) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1386) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1387) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1388) struct urb *urb = endp->urb_list[ENDP_QUEUE_MASK &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1389) endp->queue_next];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1390) endp->active = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1391) ring->curr_endp = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1392) ring->in_use = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1393) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1394) retval = edset_single(u132, ring, endp, urb, address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1395) endp->toggle_bits, u132_hcd_interrupt_recv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1396) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1397) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1398) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1399) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1400) } else if (endp->pipetype == PIPE_CONTROL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1401) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1402) if (ring->in_use) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1403) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1404) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1405) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1406) } else if (address == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1407) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1408) struct urb *urb = endp->urb_list[ENDP_QUEUE_MASK &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1409) endp->queue_next];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1410) endp->active = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1411) ring->curr_endp = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1412) ring->in_use = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1413) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1414) retval = edset_setup(u132, ring, endp, urb, address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1415) 0x2, u132_hcd_initial_setup_sent);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1416) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1417) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1418) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1419) } else if (endp->usb_addr == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1420) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1421) struct urb *urb = endp->urb_list[ENDP_QUEUE_MASK &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1422) endp->queue_next];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1423) endp->active = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1424) ring->curr_endp = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1425) ring->in_use = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1426) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1427) retval = edset_setup(u132, ring, endp, urb, 0, 0x2,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1428) u132_hcd_enumeration_address_sent);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1429) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1430) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1431) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1432) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1433) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1434) struct urb *urb = endp->urb_list[ENDP_QUEUE_MASK &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1435) endp->queue_next];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1436) address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1437) endp->active = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1438) ring->curr_endp = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1439) ring->in_use = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1440) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1441) retval = edset_setup(u132, ring, endp, urb, address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1442) 0x2, u132_hcd_configure_setup_sent);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1443) if (retval != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1444) u132_hcd_giveback_urb(u132, endp, urb, retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1445) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1446) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1447) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1448) if (endp->input) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1449) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1450) if (ring->in_use) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1451) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1452) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1453) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1454) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1455) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1456) struct urb *urb = endp->urb_list[
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1457) ENDP_QUEUE_MASK & endp->queue_next];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1458) endp->active = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1459) ring->curr_endp = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1460) ring->in_use = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1461) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1462) retval = edset_input(u132, ring, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1463) address, endp->toggle_bits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1464) u132_hcd_bulk_input_recv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1465) if (retval == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1466) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1467) u132_hcd_giveback_urb(u132, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1468) retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1469) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1470) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1471) } else { /* output pipe */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1472) u8 address = u132->addr[endp->usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1473) if (ring->in_use) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1474) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1475) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1476) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1477) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1478) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1479) struct urb *urb = endp->urb_list[
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1480) ENDP_QUEUE_MASK & endp->queue_next];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1481) endp->active = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1482) ring->curr_endp = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1483) ring->in_use = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1484) mutex_unlock(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1485) retval = edset_output(u132, ring, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1486) address, endp->toggle_bits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1487) u132_hcd_bulk_output_sent);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1488) if (retval == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1489) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1490) u132_hcd_giveback_urb(u132, endp, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1491) retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1492) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1493) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1494) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1495) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1496) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1497) #ifdef CONFIG_PM
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1498)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1499) static void port_power(struct u132 *u132, int pn, int is_on)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1500) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1501) u132->port[pn].power = is_on;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1502) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1503)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1504) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1505)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1506) static void u132_power(struct u132 *u132, int is_on)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1507) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1508) struct usb_hcd *hcd = u132_to_hcd(u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1509) ; /* hub is inactive unless the port is powered */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1510) if (is_on) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1511) if (u132->power)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1512) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1513) u132->power = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1514) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1515) u132->power = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1516) hcd->state = HC_STATE_HALT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1517) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1518) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1519)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1520) static int u132_periodic_reinit(struct u132 *u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1521) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1522) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1523) u32 fi = u132->hc_fminterval & 0x03fff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1524) u32 fit;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1525) u32 fminterval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1526) retval = u132_read_pcimem(u132, fminterval, &fminterval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1527) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1528) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1529) fit = fminterval & FIT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1530) retval = u132_write_pcimem(u132, fminterval,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1531) (fit ^ FIT) | u132->hc_fminterval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1532) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1533) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1534) return u132_write_pcimem(u132, periodicstart,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1535) ((9 * fi) / 10) & 0x3fff);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1536) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1537)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1538) static char *hcfs2string(int state)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1539) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1540) switch (state) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1541) case OHCI_USB_RESET:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1542) return "reset";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1543) case OHCI_USB_RESUME:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1544) return "resume";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1545) case OHCI_USB_OPER:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1546) return "operational";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1547) case OHCI_USB_SUSPEND:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1548) return "suspend";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1549) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1550) return "?";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1551) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1552)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1553) static int u132_init(struct u132 *u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1554) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1555) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1556) u32 control;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1557) u132_disable(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1558) u132->next_statechange = jiffies;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1559) retval = u132_write_pcimem(u132, intrdisable, OHCI_INTR_MIE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1560) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1561) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1562) retval = u132_read_pcimem(u132, control, &control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1563) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1564) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1565) if (u132->num_ports == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1566) u32 rh_a = -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1567) retval = u132_read_pcimem(u132, roothub.a, &rh_a);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1568) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1569) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1570) u132->num_ports = rh_a & RH_A_NDP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1571) retval = read_roothub_info(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1572) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1573) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1574) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1575) if (u132->num_ports > MAX_U132_PORTS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1576) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1577)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1578) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1579) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1580)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1581)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1582) /* Start an OHCI controller, set the BUS operational
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1583) * resets USB and controller
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1584) * enable interrupts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1585) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1586) static int u132_run(struct u132 *u132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1587) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1588) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1589) u32 control;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1590) u32 status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1591) u32 fminterval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1592) u32 periodicstart;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1593) u32 cmdstatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1594) u32 roothub_a;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1595) int mask = OHCI_INTR_INIT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1596) int first = u132->hc_fminterval == 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1597) int sleep_time = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1598) int reset_timeout = 30; /* ... allow extra time */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1599) u132_disable(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1600) if (first) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1601) u32 temp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1602) retval = u132_read_pcimem(u132, fminterval, &temp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1603) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1604) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1605) u132->hc_fminterval = temp & 0x3fff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1606) u132->hc_fminterval |= FSMP(u132->hc_fminterval) << 16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1607) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1608) retval = u132_read_pcimem(u132, control, &u132->hc_control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1609) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1610) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1611) dev_info(&u132->platform_dev->dev, "resetting from state '%s', control "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1612) "= %08X\n", hcfs2string(u132->hc_control & OHCI_CTRL_HCFS),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1613) u132->hc_control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1614) switch (u132->hc_control & OHCI_CTRL_HCFS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1615) case OHCI_USB_OPER:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1616) sleep_time = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1617) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1618) case OHCI_USB_SUSPEND:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1619) case OHCI_USB_RESUME:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1620) u132->hc_control &= OHCI_CTRL_RWC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1621) u132->hc_control |= OHCI_USB_RESUME;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1622) sleep_time = 10;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1623) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1624) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1625) u132->hc_control &= OHCI_CTRL_RWC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1626) u132->hc_control |= OHCI_USB_RESET;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1627) sleep_time = 50;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1628) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1629) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1630) retval = u132_write_pcimem(u132, control, u132->hc_control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1631) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1632) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1633) retval = u132_read_pcimem(u132, control, &control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1634) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1635) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1636) msleep(sleep_time);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1637) retval = u132_read_pcimem(u132, roothub.a, &roothub_a);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1638) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1639) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1640) if (!(roothub_a & RH_A_NPS)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1641) int temp; /* power down each port */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1642) for (temp = 0; temp < u132->num_ports; temp++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1643) retval = u132_write_pcimem(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1644) roothub.portstatus[temp], RH_PS_LSDA);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1645) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1646) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1647) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1648) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1649) retval = u132_read_pcimem(u132, control, &control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1650) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1651) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1652) retry:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1653) retval = u132_read_pcimem(u132, cmdstatus, &status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1654) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1655) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1656) retval = u132_write_pcimem(u132, cmdstatus, OHCI_HCR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1657) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1658) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1659) extra: {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1660) retval = u132_read_pcimem(u132, cmdstatus, &status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1661) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1662) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1663) if (0 != (status & OHCI_HCR)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1664) if (--reset_timeout == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1665) dev_err(&u132->platform_dev->dev, "USB HC reset"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1666) " timed out!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1667) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1668) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1669) msleep(5);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1670) goto extra;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1671) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1672) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1673) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1674) if (u132->flags & OHCI_QUIRK_INITRESET) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1675) retval = u132_write_pcimem(u132, control, u132->hc_control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1676) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1677) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1678) retval = u132_read_pcimem(u132, control, &control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1679) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1680) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1681) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1682) retval = u132_write_pcimem(u132, ed_controlhead, 0x00000000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1683) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1684) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1685) retval = u132_write_pcimem(u132, ed_bulkhead, 0x11000000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1686) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1687) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1688) retval = u132_write_pcimem(u132, hcca, 0x00000000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1689) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1690) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1691) retval = u132_periodic_reinit(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1692) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1693) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1694) retval = u132_read_pcimem(u132, fminterval, &fminterval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1695) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1696) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1697) retval = u132_read_pcimem(u132, periodicstart, &periodicstart);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1698) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1699) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1700) if (0 == (fminterval & 0x3fff0000) || 0 == periodicstart) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1701) if (!(u132->flags & OHCI_QUIRK_INITRESET)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1702) u132->flags |= OHCI_QUIRK_INITRESET;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1703) goto retry;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1704) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1705) dev_err(&u132->platform_dev->dev, "init err(%08x %04x)"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1706) "\n", fminterval, periodicstart);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1707) } /* start controller operations */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1708) u132->hc_control &= OHCI_CTRL_RWC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1709) u132->hc_control |= OHCI_CONTROL_INIT | OHCI_CTRL_BLE | OHCI_USB_OPER;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1710) retval = u132_write_pcimem(u132, control, u132->hc_control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1711) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1712) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1713) retval = u132_write_pcimem(u132, cmdstatus, OHCI_BLF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1714) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1715) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1716) retval = u132_read_pcimem(u132, cmdstatus, &cmdstatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1717) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1718) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1719) retval = u132_read_pcimem(u132, control, &control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1720) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1721) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1722) u132_to_hcd(u132)->state = HC_STATE_RUNNING;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1723) retval = u132_write_pcimem(u132, roothub.status, RH_HS_DRWE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1724) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1725) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1726) retval = u132_write_pcimem(u132, intrstatus, mask);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1727) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1728) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1729) retval = u132_write_pcimem(u132, intrdisable,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1730) OHCI_INTR_MIE | OHCI_INTR_OC | OHCI_INTR_RHSC | OHCI_INTR_FNO |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1731) OHCI_INTR_UE | OHCI_INTR_RD | OHCI_INTR_SF | OHCI_INTR_WDH |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1732) OHCI_INTR_SO);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1733) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1734) return retval; /* handle root hub init quirks ... */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1735) retval = u132_read_pcimem(u132, roothub.a, &roothub_a);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1736) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1737) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1738) roothub_a &= ~(RH_A_PSM | RH_A_OCPM);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1739) if (u132->flags & OHCI_QUIRK_SUPERIO) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1740) roothub_a |= RH_A_NOCP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1741) roothub_a &= ~(RH_A_POTPGT | RH_A_NPS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1742) retval = u132_write_pcimem(u132, roothub.a, roothub_a);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1743) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1744) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1745) } else if ((u132->flags & OHCI_QUIRK_AMD756) || distrust_firmware) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1746) roothub_a |= RH_A_NPS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1747) retval = u132_write_pcimem(u132, roothub.a, roothub_a);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1748) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1749) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1750) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1751) retval = u132_write_pcimem(u132, roothub.status, RH_HS_LPSC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1752) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1753) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1754) retval = u132_write_pcimem(u132, roothub.b,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1755) (roothub_a & RH_A_NPS) ? 0 : RH_B_PPCM);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1756) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1757) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1758) retval = u132_read_pcimem(u132, control, &control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1759) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1760) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1761) mdelay((roothub_a >> 23) & 0x1fe);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1762) u132_to_hcd(u132)->state = HC_STATE_RUNNING;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1763) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1764) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1765)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1766) static void u132_hcd_stop(struct usb_hcd *hcd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1767) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1768) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1769) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1770) dev_err(&u132->platform_dev->dev, "u132 device %p(hcd=%p) has b"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1771) "een removed %d\n", u132, hcd, u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1772) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1773) dev_err(&u132->platform_dev->dev, "device hcd=%p is being remov"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1774) "ed\n", hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1775) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1776) mutex_lock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1777) msleep(100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1778) u132_power(u132, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1779) mutex_unlock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1780) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1781) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1782)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1783) static int u132_hcd_start(struct usb_hcd *hcd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1784) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1785) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1786) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1787) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1788) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1789) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1790) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1791) dev_err(&u132->platform_dev->dev, "device is being removed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1792) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1793) } else if (hcd->self.controller) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1794) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1795) struct platform_device *pdev =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1796) to_platform_device(hcd->self.controller);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1797) u16 vendor = ((struct u132_platform_data *)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1798) dev_get_platdata(&pdev->dev))->vendor;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1799) u16 device = ((struct u132_platform_data *)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1800) dev_get_platdata(&pdev->dev))->device;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1801) mutex_lock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1802) msleep(10);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1803) if (vendor == PCI_VENDOR_ID_AMD && device == 0x740c) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1804) u132->flags = OHCI_QUIRK_AMD756;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1805) } else if (vendor == PCI_VENDOR_ID_OPTI && device == 0xc861) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1806) dev_err(&u132->platform_dev->dev, "WARNING: OPTi workar"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1807) "ounds unavailable\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1808) } else if (vendor == PCI_VENDOR_ID_COMPAQ && device == 0xa0f8)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1809) u132->flags |= OHCI_QUIRK_ZFMICRO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1810) retval = u132_run(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1811) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1812) u132_disable(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1813) u132->going = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1814) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1815) msleep(100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1816) mutex_unlock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1817) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1818) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1819) dev_err(&u132->platform_dev->dev, "platform_device missing\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1820) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1821) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1822) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1823)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1824) static int u132_hcd_reset(struct usb_hcd *hcd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1825) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1826) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1827) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1828) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1829) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1830) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1831) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1832) dev_err(&u132->platform_dev->dev, "device is being removed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1833) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1834) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1835) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1836) mutex_lock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1837) retval = u132_init(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1838) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1839) u132_disable(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1840) u132->going = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1841) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1842) mutex_unlock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1843) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1844) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1845) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1846)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1847) static int create_endpoint_and_queue_int(struct u132 *u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1848) struct u132_udev *udev, struct urb *urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1849) struct usb_device *usb_dev, u8 usb_addr, u8 usb_endp, u8 address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1850) gfp_t mem_flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1851) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1852) struct u132_ring *ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1853) unsigned long irqs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1854) int rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1855) u8 endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1856) struct u132_endp *endp = kmalloc(sizeof(struct u132_endp), mem_flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1857)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1858) if (!endp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1859) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1860)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1861) spin_lock_init(&endp->queue_lock.slock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1862) spin_lock_irqsave(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1863) rc = usb_hcd_link_urb_to_ep(u132_to_hcd(u132), urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1864) if (rc) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1865) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1866) kfree(endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1867) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1868) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1869)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1870) endp_number = ++u132->num_endpoints;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1871) urb->ep->hcpriv = u132->endp[endp_number - 1] = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1872) INIT_DELAYED_WORK(&endp->scheduler, u132_hcd_endp_work_scheduler);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1873) INIT_LIST_HEAD(&endp->urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1874) ring = endp->ring = &u132->ring[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1875) if (ring->curr_endp) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1876) list_add_tail(&endp->endp_ring, &ring->curr_endp->endp_ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1877) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1878) INIT_LIST_HEAD(&endp->endp_ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1879) ring->curr_endp = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1880) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1881) ring->length += 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1882) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1883) endp->edset_flush = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1884) endp->active = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1885) endp->delayed = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1886) endp->endp_number = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1887) endp->u132 = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1888) endp->hep = urb->ep;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1889) endp->pipetype = usb_pipetype(urb->pipe);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1890) u132_endp_init_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1891) if (usb_pipein(urb->pipe)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1892) endp->toggle_bits = 0x2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1893) usb_settoggle(udev->usb_device, usb_endp, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1894) endp->input = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1895) endp->output = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1896) udev->endp_number_in[usb_endp] = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1897) u132_udev_get_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1898) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1899) endp->toggle_bits = 0x2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1900) usb_settoggle(udev->usb_device, usb_endp, 1, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1901) endp->input = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1902) endp->output = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1903) udev->endp_number_out[usb_endp] = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1904) u132_udev_get_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1905) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1906) urb->hcpriv = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1907) endp->delayed = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1908) endp->jiffies = jiffies + msecs_to_jiffies(urb->interval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1909) endp->udev_number = address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1910) endp->usb_addr = usb_addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1911) endp->usb_endp = usb_endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1912) endp->queue_size = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1913) endp->queue_last = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1914) endp->queue_next = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1915) endp->urb_list[ENDP_QUEUE_MASK & endp->queue_last++] = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1916) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1917) u132_endp_queue_work(u132, endp, msecs_to_jiffies(urb->interval));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1918) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1919) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1920)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1921) static int queue_int_on_old_endpoint(struct u132 *u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1922) struct u132_udev *udev, struct urb *urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1923) struct usb_device *usb_dev, struct u132_endp *endp, u8 usb_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1924) u8 usb_endp, u8 address)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1925) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1926) urb->hcpriv = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1927) endp->delayed = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1928) endp->jiffies = jiffies + msecs_to_jiffies(urb->interval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1929) if (endp->queue_size++ < ENDP_QUEUE_SIZE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1930) endp->urb_list[ENDP_QUEUE_MASK & endp->queue_last++] = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1931) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1932) struct u132_urbq *urbq = kmalloc(sizeof(struct u132_urbq),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1933) GFP_ATOMIC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1934) if (urbq == NULL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1935) endp->queue_size -= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1936) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1937) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1938) list_add_tail(&urbq->urb_more, &endp->urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1939) urbq->urb = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1940) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1941) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1942) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1943) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1944)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1945) static int create_endpoint_and_queue_bulk(struct u132 *u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1946) struct u132_udev *udev, struct urb *urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1947) struct usb_device *usb_dev, u8 usb_addr, u8 usb_endp, u8 address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1948) gfp_t mem_flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1949) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1950) int ring_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1951) struct u132_ring *ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1952) unsigned long irqs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1953) int rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1954) u8 endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1955) struct u132_endp *endp = kmalloc(sizeof(struct u132_endp), mem_flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1956)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1957) if (!endp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1958) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1959)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1960) spin_lock_init(&endp->queue_lock.slock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1961) spin_lock_irqsave(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1962) rc = usb_hcd_link_urb_to_ep(u132_to_hcd(u132), urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1963) if (rc) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1964) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1965) kfree(endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1966) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1967) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1968)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1969) endp_number = ++u132->num_endpoints;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1970) urb->ep->hcpriv = u132->endp[endp_number - 1] = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1971) INIT_DELAYED_WORK(&endp->scheduler, u132_hcd_endp_work_scheduler);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1972) INIT_LIST_HEAD(&endp->urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1973) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1974) endp->edset_flush = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1975) endp->active = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1976) endp->delayed = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1977) endp->endp_number = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1978) endp->u132 = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1979) endp->hep = urb->ep;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1980) endp->pipetype = usb_pipetype(urb->pipe);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1981) u132_endp_init_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1982) if (usb_pipein(urb->pipe)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1983) endp->toggle_bits = 0x2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1984) usb_settoggle(udev->usb_device, usb_endp, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1985) ring_number = 3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1986) endp->input = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1987) endp->output = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1988) udev->endp_number_in[usb_endp] = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1989) u132_udev_get_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1990) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1991) endp->toggle_bits = 0x2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1992) usb_settoggle(udev->usb_device, usb_endp, 1, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1993) ring_number = 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1994) endp->input = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1995) endp->output = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1996) udev->endp_number_out[usb_endp] = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1997) u132_udev_get_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1998) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1999) ring = endp->ring = &u132->ring[ring_number - 1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2000) if (ring->curr_endp) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2001) list_add_tail(&endp->endp_ring, &ring->curr_endp->endp_ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2002) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2003) INIT_LIST_HEAD(&endp->endp_ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2004) ring->curr_endp = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2005) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2006) ring->length += 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2007) urb->hcpriv = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2008) endp->udev_number = address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2009) endp->usb_addr = usb_addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2010) endp->usb_endp = usb_endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2011) endp->queue_size = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2012) endp->queue_last = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2013) endp->queue_next = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2014) endp->urb_list[ENDP_QUEUE_MASK & endp->queue_last++] = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2015) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2016) u132_endp_queue_work(u132, endp, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2017) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2018) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2019)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2020) static int queue_bulk_on_old_endpoint(struct u132 *u132, struct u132_udev *udev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2021) struct urb *urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2022) struct usb_device *usb_dev, struct u132_endp *endp, u8 usb_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2023) u8 usb_endp, u8 address)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2024) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2025) urb->hcpriv = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2026) if (endp->queue_size++ < ENDP_QUEUE_SIZE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2027) endp->urb_list[ENDP_QUEUE_MASK & endp->queue_last++] = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2028) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2029) struct u132_urbq *urbq = kmalloc(sizeof(struct u132_urbq),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2030) GFP_ATOMIC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2031) if (urbq == NULL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2032) endp->queue_size -= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2033) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2034) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2035) list_add_tail(&urbq->urb_more, &endp->urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2036) urbq->urb = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2037) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2038) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2039) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2040) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2041)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2042) static int create_endpoint_and_queue_control(struct u132 *u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2043) struct urb *urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2044) struct usb_device *usb_dev, u8 usb_addr, u8 usb_endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2045) gfp_t mem_flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2046) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2047) struct u132_ring *ring;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2048) unsigned long irqs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2049) int rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2050) u8 endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2051) struct u132_endp *endp = kmalloc(sizeof(struct u132_endp), mem_flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2052)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2053) if (!endp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2054) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2055)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2056) spin_lock_init(&endp->queue_lock.slock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2057) spin_lock_irqsave(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2058) rc = usb_hcd_link_urb_to_ep(u132_to_hcd(u132), urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2059) if (rc) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2060) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2061) kfree(endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2062) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2063) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2064)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2065) endp_number = ++u132->num_endpoints;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2066) urb->ep->hcpriv = u132->endp[endp_number - 1] = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2067) INIT_DELAYED_WORK(&endp->scheduler, u132_hcd_endp_work_scheduler);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2068) INIT_LIST_HEAD(&endp->urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2069) ring = endp->ring = &u132->ring[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2070) if (ring->curr_endp) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2071) list_add_tail(&endp->endp_ring, &ring->curr_endp->endp_ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2072) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2073) INIT_LIST_HEAD(&endp->endp_ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2074) ring->curr_endp = endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2075) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2076) ring->length += 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2077) endp->dequeueing = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2078) endp->edset_flush = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2079) endp->active = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2080) endp->delayed = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2081) endp->endp_number = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2082) endp->u132 = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2083) endp->hep = urb->ep;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2084) u132_endp_init_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2085) u132_endp_get_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2086) if (usb_addr == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2087) u8 address = u132->addr[usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2088) struct u132_udev *udev = &u132->udev[address];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2089) endp->udev_number = address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2090) endp->usb_addr = usb_addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2091) endp->usb_endp = usb_endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2092) endp->input = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2093) endp->output = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2094) endp->pipetype = usb_pipetype(urb->pipe);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2095) u132_udev_init_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2096) u132_udev_get_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2097) udev->endp_number_in[usb_endp] = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2098) udev->endp_number_out[usb_endp] = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2099) urb->hcpriv = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2100) endp->queue_size = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2101) endp->queue_last = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2102) endp->queue_next = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2103) endp->urb_list[ENDP_QUEUE_MASK & endp->queue_last++] = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2104) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2105) u132_endp_queue_work(u132, endp, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2106) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2107) } else { /*(usb_addr > 0) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2108) u8 address = u132->addr[usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2109) struct u132_udev *udev = &u132->udev[address];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2110) endp->udev_number = address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2111) endp->usb_addr = usb_addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2112) endp->usb_endp = usb_endp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2113) endp->input = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2114) endp->output = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2115) endp->pipetype = usb_pipetype(urb->pipe);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2116) u132_udev_get_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2117) udev->enumeration = 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2118) udev->endp_number_in[usb_endp] = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2119) udev->endp_number_out[usb_endp] = endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2120) urb->hcpriv = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2121) endp->queue_size = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2122) endp->queue_last = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2123) endp->queue_next = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2124) endp->urb_list[ENDP_QUEUE_MASK & endp->queue_last++] = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2125) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2126) u132_endp_queue_work(u132, endp, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2127) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2128) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2129) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2130)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2131) static int queue_control_on_old_endpoint(struct u132 *u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2132) struct urb *urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2133) struct usb_device *usb_dev, struct u132_endp *endp, u8 usb_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2134) u8 usb_endp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2135) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2136) if (usb_addr == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2137) if (usb_pipein(urb->pipe)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2138) urb->hcpriv = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2139) if (endp->queue_size++ < ENDP_QUEUE_SIZE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2140) endp->urb_list[ENDP_QUEUE_MASK &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2141) endp->queue_last++] = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2142) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2143) struct u132_urbq *urbq =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2144) kmalloc(sizeof(struct u132_urbq),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2145) GFP_ATOMIC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2146) if (urbq == NULL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2147) endp->queue_size -= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2148) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2149) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2150) list_add_tail(&urbq->urb_more,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2151) &endp->urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2152) urbq->urb = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2153) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2154) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2155) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2156) } else { /* usb_pipeout(urb->pipe) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2157) struct u132_addr *addr = &u132->addr[usb_dev->devnum];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2158) int I = MAX_U132_UDEVS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2159) int i = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2160) while (--I > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2161) struct u132_udev *udev = &u132->udev[++i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2162) if (udev->usb_device) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2163) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2164) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2165) udev->enumeration = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2166) u132->addr[0].address = i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2167) endp->udev_number = i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2168) udev->udev_number = i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2169) udev->usb_addr = usb_dev->devnum;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2170) u132_udev_init_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2171) udev->endp_number_in[usb_endp] =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2172) endp->endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2173) u132_udev_get_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2174) udev->endp_number_out[usb_endp] =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2175) endp->endp_number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2176) udev->usb_device = usb_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2177) ((u8 *) (urb->setup_packet))[2] =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2178) addr->address = i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2179) u132_udev_get_kref(u132, udev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2180) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2181) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2182) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2183) if (I == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2184) dev_err(&u132->platform_dev->dev, "run out of d"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2185) "evice space\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2186) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2187) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2188) urb->hcpriv = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2189) if (endp->queue_size++ < ENDP_QUEUE_SIZE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2190) endp->urb_list[ENDP_QUEUE_MASK &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2191) endp->queue_last++] = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2192) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2193) struct u132_urbq *urbq =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2194) kmalloc(sizeof(struct u132_urbq),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2195) GFP_ATOMIC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2196) if (urbq == NULL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2197) endp->queue_size -= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2198) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2199) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2200) list_add_tail(&urbq->urb_more,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2201) &endp->urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2202) urbq->urb = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2203) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2204) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2205) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2206) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2207) } else { /*(usb_addr > 0) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2208) u8 address = u132->addr[usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2209) struct u132_udev *udev = &u132->udev[address];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2210) urb->hcpriv = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2211) if (udev->enumeration != 2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2212) udev->enumeration = 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2213) if (endp->queue_size++ < ENDP_QUEUE_SIZE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2214) endp->urb_list[ENDP_QUEUE_MASK & endp->queue_last++] =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2215) urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2216) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2217) struct u132_urbq *urbq =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2218) kmalloc(sizeof(struct u132_urbq), GFP_ATOMIC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2219) if (urbq == NULL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2220) endp->queue_size -= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2221) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2222) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2223) list_add_tail(&urbq->urb_more, &endp->urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2224) urbq->urb = urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2225) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2226) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2227) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2228) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2229) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2230)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2231) static int u132_urb_enqueue(struct usb_hcd *hcd, struct urb *urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2232) gfp_t mem_flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2233) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2234) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2235) if (irqs_disabled()) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2236) if (gfpflags_allow_blocking(mem_flags)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2237) printk(KERN_ERR "invalid context for function that might sleep\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2238) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2239) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2240) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2241) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2242) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2243) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2244) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2245) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2246) dev_err(&u132->platform_dev->dev, "device is being removed "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2247) "urb=%p\n", urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2248) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2249) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2250) u8 usb_addr = usb_pipedevice(urb->pipe);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2251) u8 usb_endp = usb_pipeendpoint(urb->pipe);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2252) struct usb_device *usb_dev = urb->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2253) if (usb_pipetype(urb->pipe) == PIPE_INTERRUPT) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2254) u8 address = u132->addr[usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2255) struct u132_udev *udev = &u132->udev[address];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2256) struct u132_endp *endp = urb->ep->hcpriv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2257) urb->actual_length = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2258) if (endp) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2259) unsigned long irqs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2260) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2261) spin_lock_irqsave(&endp->queue_lock.slock,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2262) irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2263) retval = usb_hcd_link_urb_to_ep(hcd, urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2264) if (retval == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2265) retval = queue_int_on_old_endpoint(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2266) u132, udev, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2267) usb_dev, endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2268) usb_addr, usb_endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2269) address);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2270) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2271) usb_hcd_unlink_urb_from_ep(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2272) hcd, urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2273) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2274) spin_unlock_irqrestore(&endp->queue_lock.slock,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2275) irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2276) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2277) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2278) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2279) u132_endp_queue_work(u132, endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2280) msecs_to_jiffies(urb->interval))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2281) ;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2282) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2283) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2284) } else if (u132->num_endpoints == MAX_U132_ENDPS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2285) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2286) } else { /*(endp == NULL) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2287) return create_endpoint_and_queue_int(u132, udev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2288) urb, usb_dev, usb_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2289) usb_endp, address, mem_flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2290) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2291) } else if (usb_pipetype(urb->pipe) == PIPE_ISOCHRONOUS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2292) dev_err(&u132->platform_dev->dev, "the hardware does no"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2293) "t support PIPE_ISOCHRONOUS\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2294) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2295) } else if (usb_pipetype(urb->pipe) == PIPE_BULK) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2296) u8 address = u132->addr[usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2297) struct u132_udev *udev = &u132->udev[address];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2298) struct u132_endp *endp = urb->ep->hcpriv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2299) urb->actual_length = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2300) if (endp) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2301) unsigned long irqs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2302) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2303) spin_lock_irqsave(&endp->queue_lock.slock,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2304) irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2305) retval = usb_hcd_link_urb_to_ep(hcd, urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2306) if (retval == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2307) retval = queue_bulk_on_old_endpoint(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2308) u132, udev, urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2309) usb_dev, endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2310) usb_addr, usb_endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2311) address);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2312) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2313) usb_hcd_unlink_urb_from_ep(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2314) hcd, urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2315) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2316) spin_unlock_irqrestore(&endp->queue_lock.slock,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2317) irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2318) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2319) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2320) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2321) u132_endp_queue_work(u132, endp, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2322) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2323) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2324) } else if (u132->num_endpoints == MAX_U132_ENDPS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2325) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2326) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2327) return create_endpoint_and_queue_bulk(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2328) udev, urb, usb_dev, usb_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2329) usb_endp, address, mem_flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2330) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2331) struct u132_endp *endp = urb->ep->hcpriv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2332) u16 urb_size = 8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2333) u8 *b = urb->setup_packet;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2334) int i = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2335) char data[30 * 3 + 4];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2336) char *d = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2337) int m = (sizeof(data) - 1) / 3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2338) int l = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2339) data[0] = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2340) while (urb_size-- > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2341) if (i > m) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2342) } else if (i++ < m) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2343) int w = sprintf(d, " %02X", *b++);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2344) d += w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2345) l += w;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2346) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2347) d += sprintf(d, " ..");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2348) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2349) if (endp) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2350) unsigned long irqs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2351) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2352) spin_lock_irqsave(&endp->queue_lock.slock,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2353) irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2354) retval = usb_hcd_link_urb_to_ep(hcd, urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2355) if (retval == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2356) retval = queue_control_on_old_endpoint(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2357) u132, urb, usb_dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2358) endp, usb_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2359) usb_endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2360) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2361) usb_hcd_unlink_urb_from_ep(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2362) hcd, urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2363) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2364) spin_unlock_irqrestore(&endp->queue_lock.slock,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2365) irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2366) if (retval) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2367) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2368) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2369) u132_endp_queue_work(u132, endp, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2370) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2371) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2372) } else if (u132->num_endpoints == MAX_U132_ENDPS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2373) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2374) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2375) return create_endpoint_and_queue_control(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2376) urb, usb_dev, usb_addr, usb_endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2377) mem_flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2378) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2379) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2380) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2381)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2382) static int dequeue_from_overflow_chain(struct u132 *u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2383) struct u132_endp *endp, struct urb *urb)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2384) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2385) struct u132_urbq *urbq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2386)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2387) list_for_each_entry(urbq, &endp->urb_more, urb_more) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2388) if (urbq->urb == urb) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2389) struct usb_hcd *hcd = u132_to_hcd(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2390) list_del(&urbq->urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2391) endp->queue_size -= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2392) urb->error_count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2393) usb_hcd_giveback_urb(hcd, urb, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2394) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2395) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2396) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2397) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2398) dev_err(&u132->platform_dev->dev, "urb=%p not found in endp[%d]=%p ring"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2399) "[%d] %c%c usb_endp=%d usb_addr=%d size=%d next=%04X last=%04X"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2400) "\n", urb, endp->endp_number, endp, endp->ring->number,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2401) endp->input ? 'I' : ' ', endp->output ? 'O' : ' ',
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2402) endp->usb_endp, endp->usb_addr, endp->queue_size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2403) endp->queue_next, endp->queue_last);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2404) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2405) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2406)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2407) static int u132_endp_urb_dequeue(struct u132 *u132, struct u132_endp *endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2408) struct urb *urb, int status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2409) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2410) unsigned long irqs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2411) int rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2412)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2413) spin_lock_irqsave(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2414) rc = usb_hcd_check_unlink_urb(u132_to_hcd(u132), urb, status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2415) if (rc) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2416) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2417) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2418) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2419) if (endp->queue_size == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2420) dev_err(&u132->platform_dev->dev, "urb=%p not found in endp[%d]"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2421) "=%p ring[%d] %c%c usb_endp=%d usb_addr=%d\n", urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2422) endp->endp_number, endp, endp->ring->number,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2423) endp->input ? 'I' : ' ', endp->output ? 'O' : ' ',
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2424) endp->usb_endp, endp->usb_addr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2425) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2426) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2427) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2428) if (urb == endp->urb_list[ENDP_QUEUE_MASK & endp->queue_next]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2429) if (endp->active) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2430) endp->dequeueing = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2431) endp->edset_flush = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2432) u132_endp_queue_work(u132, endp, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2433) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2434) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2435) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2436) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2437) u132_hcd_abandon_urb(u132, endp, urb, status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2438) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2439) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2440) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2441) u16 queue_list = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2442) u16 queue_size = endp->queue_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2443) u16 queue_scan = endp->queue_next;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2444) struct urb **urb_slot = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2445) while (++queue_list < ENDP_QUEUE_SIZE && --queue_size > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2446) if (urb == endp->urb_list[ENDP_QUEUE_MASK &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2447) ++queue_scan]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2448) urb_slot = &endp->urb_list[ENDP_QUEUE_MASK &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2449) queue_scan];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2450) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2451) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2452) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2453) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2454) while (++queue_list < ENDP_QUEUE_SIZE && --queue_size > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2455) *urb_slot = endp->urb_list[ENDP_QUEUE_MASK &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2456) ++queue_scan];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2457) urb_slot = &endp->urb_list[ENDP_QUEUE_MASK &
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2458) queue_scan];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2459) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2460) if (urb_slot) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2461) struct usb_hcd *hcd = u132_to_hcd(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2462)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2463) usb_hcd_unlink_urb_from_ep(hcd, urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2464) endp->queue_size -= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2465) if (list_empty(&endp->urb_more)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2466) spin_unlock_irqrestore(&endp->queue_lock.slock,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2467) irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2468) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2469) struct list_head *next = endp->urb_more.next;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2470) struct u132_urbq *urbq = list_entry(next,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2471) struct u132_urbq, urb_more);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2472) list_del(next);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2473) *urb_slot = urbq->urb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2474) spin_unlock_irqrestore(&endp->queue_lock.slock,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2475) irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2476) kfree(urbq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2477) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2478) urb->error_count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2479) usb_hcd_giveback_urb(hcd, urb, status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2480) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2481) } else if (list_empty(&endp->urb_more)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2482) dev_err(&u132->platform_dev->dev, "urb=%p not found in "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2483) "endp[%d]=%p ring[%d] %c%c usb_endp=%d usb_addr"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2484) "=%d size=%d next=%04X last=%04X\n", urb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2485) endp->endp_number, endp, endp->ring->number,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2486) endp->input ? 'I' : ' ',
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2487) endp->output ? 'O' : ' ', endp->usb_endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2488) endp->usb_addr, endp->queue_size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2489) endp->queue_next, endp->queue_last);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2490) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2491) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2492) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2493) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2494)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2495) usb_hcd_unlink_urb_from_ep(u132_to_hcd(u132), urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2496) retval = dequeue_from_overflow_chain(u132, endp,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2497) urb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2498) spin_unlock_irqrestore(&endp->queue_lock.slock, irqs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2499) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2500) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2501) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2502) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2503)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2504) static int u132_urb_dequeue(struct usb_hcd *hcd, struct urb *urb, int status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2505) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2506) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2507) if (u132->going > 2) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2508) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2509) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2510) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2511) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2512) u8 usb_addr = usb_pipedevice(urb->pipe);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2513) u8 usb_endp = usb_pipeendpoint(urb->pipe);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2514) u8 address = u132->addr[usb_addr].address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2515) struct u132_udev *udev = &u132->udev[address];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2516) if (usb_pipein(urb->pipe)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2517) u8 endp_number = udev->endp_number_in[usb_endp];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2518) struct u132_endp *endp = u132->endp[endp_number - 1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2519) return u132_endp_urb_dequeue(u132, endp, urb, status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2520) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2521) u8 endp_number = udev->endp_number_out[usb_endp];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2522) struct u132_endp *endp = u132->endp[endp_number - 1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2523) return u132_endp_urb_dequeue(u132, endp, urb, status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2524) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2525) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2526) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2527)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2528) static void u132_endpoint_disable(struct usb_hcd *hcd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2529) struct usb_host_endpoint *hep)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2530) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2531) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2532) if (u132->going > 2) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2533) dev_err(&u132->platform_dev->dev, "u132 device %p(hcd=%p hep=%p"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2534) ") has been removed %d\n", u132, hcd, hep,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2535) u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2536) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2537) struct u132_endp *endp = hep->hcpriv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2538) if (endp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2539) u132_endp_put_kref(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2540) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2541) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2542)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2543) static int u132_get_frame(struct usb_hcd *hcd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2544) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2545) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2546) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2547) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2548) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2549) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2550) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2551) dev_err(&u132->platform_dev->dev, "device is being removed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2552) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2553) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2554) dev_err(&u132->platform_dev->dev, "TODO: u132_get_frame\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2555) mdelay(100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2556) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2557) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2558) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2559)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2560) static int u132_roothub_descriptor(struct u132 *u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2561) struct usb_hub_descriptor *desc)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2562) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2563) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2564) u16 temp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2565) u32 rh_a = -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2566) u32 rh_b = -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2567) retval = u132_read_pcimem(u132, roothub.a, &rh_a);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2568) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2569) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2570) desc->bDescriptorType = USB_DT_HUB;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2571) desc->bPwrOn2PwrGood = (rh_a & RH_A_POTPGT) >> 24;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2572) desc->bHubContrCurrent = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2573) desc->bNbrPorts = u132->num_ports;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2574) temp = 1 + (u132->num_ports / 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2575) desc->bDescLength = 7 + 2 * temp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2576) temp = HUB_CHAR_COMMON_LPSM | HUB_CHAR_COMMON_OCPM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2577) if (rh_a & RH_A_NPS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2578) temp |= HUB_CHAR_NO_LPSM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2579) if (rh_a & RH_A_PSM)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2580) temp |= HUB_CHAR_INDV_PORT_LPSM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2581) if (rh_a & RH_A_NOCP)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2582) temp |= HUB_CHAR_NO_OCPM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2583) else if (rh_a & RH_A_OCPM)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2584) temp |= HUB_CHAR_INDV_PORT_OCPM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2585) desc->wHubCharacteristics = cpu_to_le16(temp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2586) retval = u132_read_pcimem(u132, roothub.b, &rh_b);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2587) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2588) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2589) memset(desc->u.hs.DeviceRemovable, 0xff,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2590) sizeof(desc->u.hs.DeviceRemovable));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2591) desc->u.hs.DeviceRemovable[0] = rh_b & RH_B_DR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2592) if (u132->num_ports > 7) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2593) desc->u.hs.DeviceRemovable[1] = (rh_b & RH_B_DR) >> 8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2594) desc->u.hs.DeviceRemovable[2] = 0xff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2595) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2596) desc->u.hs.DeviceRemovable[1] = 0xff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2597) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2598) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2599)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2600) static int u132_roothub_status(struct u132 *u132, __le32 *desc)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2601) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2602) u32 rh_status = -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2603) int ret_status = u132_read_pcimem(u132, roothub.status, &rh_status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2604) *desc = cpu_to_le32(rh_status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2605) return ret_status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2606) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2607)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2608) static int u132_roothub_portstatus(struct u132 *u132, __le32 *desc, u16 wIndex)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2609) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2610) if (wIndex == 0 || wIndex > u132->num_ports) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2611) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2612) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2613) int port = wIndex - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2614) u32 rh_portstatus = -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2615) int ret_portstatus = u132_read_pcimem(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2616) roothub.portstatus[port], &rh_portstatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2617) *desc = cpu_to_le32(rh_portstatus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2618) if (*(u16 *) (desc + 2)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2619) dev_info(&u132->platform_dev->dev, "Port %d Status Chan"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2620) "ge = %08X\n", port, *desc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2621) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2622) return ret_portstatus;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2623) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2624) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2625)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2626)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2627) /* this timer value might be vendor-specific ... */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2628) #define PORT_RESET_HW_MSEC 10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2629) #define PORT_RESET_MSEC 10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2630) /* wrap-aware logic morphed from <linux/jiffies.h> */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2631) #define tick_before(t1, t2) ((s16)(((s16)(t1))-((s16)(t2))) < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2632) static int u132_roothub_portreset(struct u132 *u132, int port_index)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2633) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2634) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2635) u32 fmnumber;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2636) u16 now;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2637) u16 reset_done;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2638) retval = u132_read_pcimem(u132, fmnumber, &fmnumber);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2639) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2640) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2641) now = fmnumber;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2642) reset_done = now + PORT_RESET_MSEC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2643) do {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2644) u32 portstat;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2645) do {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2646) retval = u132_read_pcimem(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2647) roothub.portstatus[port_index], &portstat);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2648) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2649) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2650) if (RH_PS_PRS & portstat)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2651) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2652) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2653) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2654) } while (tick_before(now, reset_done));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2655) if (RH_PS_PRS & portstat)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2656) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2657) if (RH_PS_CCS & portstat) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2658) if (RH_PS_PRSC & portstat) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2659) retval = u132_write_pcimem(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2660) roothub.portstatus[port_index],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2661) RH_PS_PRSC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2662) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2663) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2664) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2665) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2666) break; /* start the next reset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2667) sleep till it's probably done */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2668) retval = u132_write_pcimem(u132, roothub.portstatus[port_index],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2669) RH_PS_PRS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2670) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2671) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2672) msleep(PORT_RESET_HW_MSEC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2673) retval = u132_read_pcimem(u132, fmnumber, &fmnumber);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2674) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2675) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2676) now = fmnumber;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2677) } while (tick_before(now, reset_done));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2678) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2679) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2680)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2681) static int u132_roothub_setportfeature(struct u132 *u132, u16 wValue,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2682) u16 wIndex)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2683) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2684) if (wIndex == 0 || wIndex > u132->num_ports) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2685) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2686) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2687) int port_index = wIndex - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2688) struct u132_port *port = &u132->port[port_index];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2689) port->Status &= ~(1 << wValue);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2690) switch (wValue) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2691) case USB_PORT_FEAT_SUSPEND:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2692) return u132_write_pcimem(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2693) roothub.portstatus[port_index], RH_PS_PSS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2694) case USB_PORT_FEAT_POWER:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2695) return u132_write_pcimem(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2696) roothub.portstatus[port_index], RH_PS_PPS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2697) case USB_PORT_FEAT_RESET:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2698) return u132_roothub_portreset(u132, port_index);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2699) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2700) return -EPIPE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2701) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2702) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2703) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2704)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2705) static int u132_roothub_clearportfeature(struct u132 *u132, u16 wValue,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2706) u16 wIndex)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2707) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2708) if (wIndex == 0 || wIndex > u132->num_ports) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2709) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2710) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2711) int port_index = wIndex - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2712) u32 temp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2713) struct u132_port *port = &u132->port[port_index];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2714) port->Status &= ~(1 << wValue);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2715) switch (wValue) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2716) case USB_PORT_FEAT_ENABLE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2717) temp = RH_PS_CCS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2718) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2719) case USB_PORT_FEAT_C_ENABLE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2720) temp = RH_PS_PESC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2721) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2722) case USB_PORT_FEAT_SUSPEND:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2723) temp = RH_PS_POCI;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2724) if ((u132->hc_control & OHCI_CTRL_HCFS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2725) != OHCI_USB_OPER) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2726) dev_err(&u132->platform_dev->dev, "TODO resume_"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2727) "root_hub\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2728) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2729) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2730) case USB_PORT_FEAT_C_SUSPEND:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2731) temp = RH_PS_PSSC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2732) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2733) case USB_PORT_FEAT_POWER:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2734) temp = RH_PS_LSDA;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2735) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2736) case USB_PORT_FEAT_C_CONNECTION:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2737) temp = RH_PS_CSC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2738) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2739) case USB_PORT_FEAT_C_OVER_CURRENT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2740) temp = RH_PS_OCIC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2741) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2742) case USB_PORT_FEAT_C_RESET:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2743) temp = RH_PS_PRSC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2744) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2745) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2746) return -EPIPE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2747) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2748) return u132_write_pcimem(u132, roothub.portstatus[port_index],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2749) temp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2750) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2751) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2752)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2753)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2754) /* the virtual root hub timer IRQ checks for hub status*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2755) static int u132_hub_status_data(struct usb_hcd *hcd, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2756) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2757) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2758) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2759) dev_err(&u132->platform_dev->dev, "device hcd=%p has been remov"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2760) "ed %d\n", hcd, u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2761) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2762) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2763) dev_err(&u132->platform_dev->dev, "device hcd=%p is being remov"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2764) "ed\n", hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2765) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2766) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2767) int i, changed = 0, length = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2768) if (u132->flags & OHCI_QUIRK_AMD756) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2769) if ((u132->hc_roothub_a & RH_A_NDP) > MAX_ROOT_PORTS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2770) dev_err(&u132->platform_dev->dev, "bogus NDP, r"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2771) "ereads as NDP=%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2772) u132->hc_roothub_a & RH_A_NDP);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2773) goto done;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2774) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2775) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2776) if (u132->hc_roothub_status & (RH_HS_LPSC | RH_HS_OCIC))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2777) buf[0] = changed = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2778) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2779) buf[0] = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2780) if (u132->num_ports > 7) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2781) buf[1] = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2782) length++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2783) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2784) for (i = 0; i < u132->num_ports; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2785) if (u132->hc_roothub_portstatus[i] & (RH_PS_CSC |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2786) RH_PS_PESC | RH_PS_PSSC | RH_PS_OCIC |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2787) RH_PS_PRSC)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2788) changed = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2789) if (i < 7)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2790) buf[0] |= 1 << (i + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2791) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2792) buf[1] |= 1 << (i - 7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2793) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2794) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2795) if (!(u132->hc_roothub_portstatus[i] & RH_PS_CCS))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2796) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2797)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2798) if ((u132->hc_roothub_portstatus[i] & RH_PS_PSS))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2799) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2800) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2801) done:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2802) return changed ? length : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2803) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2804) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2805)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2806) static int u132_hub_control(struct usb_hcd *hcd, u16 typeReq, u16 wValue,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2807) u16 wIndex, char *buf, u16 wLength)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2808) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2809) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2810) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2811) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2812) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2813) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2814) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2815) dev_err(&u132->platform_dev->dev, "device is being removed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2816) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2817) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2818) int retval = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2819) mutex_lock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2820) switch (typeReq) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2821) case ClearHubFeature:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2822) switch (wValue) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2823) case C_HUB_OVER_CURRENT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2824) case C_HUB_LOCAL_POWER:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2825) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2826) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2827) goto stall;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2828) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2829) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2830) case SetHubFeature:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2831) switch (wValue) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2832) case C_HUB_OVER_CURRENT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2833) case C_HUB_LOCAL_POWER:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2834) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2835) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2836) goto stall;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2837) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2838) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2839) case ClearPortFeature:{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2840) retval = u132_roothub_clearportfeature(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2841) wValue, wIndex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2842) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2843) goto error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2844) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2845) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2846) case GetHubDescriptor:{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2847) retval = u132_roothub_descriptor(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2848) (struct usb_hub_descriptor *)buf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2849) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2850) goto error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2851) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2852) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2853) case GetHubStatus:{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2854) retval = u132_roothub_status(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2855) (__le32 *) buf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2856) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2857) goto error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2858) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2859) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2860) case GetPortStatus:{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2861) retval = u132_roothub_portstatus(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2862) (__le32 *) buf, wIndex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2863) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2864) goto error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2865) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2866) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2867) case SetPortFeature:{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2868) retval = u132_roothub_setportfeature(u132,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2869) wValue, wIndex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2870) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2871) goto error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2872) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2873) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2874) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2875) goto stall;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2876) error:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2877) u132_disable(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2878) u132->going = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2879) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2880) stall:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2881) retval = -EPIPE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2882) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2883) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2884) mutex_unlock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2885) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2886) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2887) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2888)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2889) static int u132_start_port_reset(struct usb_hcd *hcd, unsigned port_num)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2890) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2891) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2892) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2893) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2894) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2895) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2896) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2897) dev_err(&u132->platform_dev->dev, "device is being removed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2898) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2899) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2900) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2901) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2902)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2903)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2904) #ifdef CONFIG_PM
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2905) static int u132_bus_suspend(struct usb_hcd *hcd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2906) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2907) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2908) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2909) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2910) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2911) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2912) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2913) dev_err(&u132->platform_dev->dev, "device is being removed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2914) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2915) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2916) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2917) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2918)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2919) static int u132_bus_resume(struct usb_hcd *hcd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2920) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2921) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2922) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2923) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2924) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2925) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2926) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2927) dev_err(&u132->platform_dev->dev, "device is being removed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2928) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2929) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2930) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2931) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2932)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2933) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2934) #define u132_bus_suspend NULL
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2935) #define u132_bus_resume NULL
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2936) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2937) static const struct hc_driver u132_hc_driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2938) .description = hcd_name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2939) .hcd_priv_size = sizeof(struct u132),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2940) .irq = NULL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2941) .flags = HCD_USB11 | HCD_MEMORY,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2942) .reset = u132_hcd_reset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2943) .start = u132_hcd_start,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2944) .stop = u132_hcd_stop,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2945) .urb_enqueue = u132_urb_enqueue,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2946) .urb_dequeue = u132_urb_dequeue,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2947) .endpoint_disable = u132_endpoint_disable,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2948) .get_frame_number = u132_get_frame,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2949) .hub_status_data = u132_hub_status_data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2950) .hub_control = u132_hub_control,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2951) .bus_suspend = u132_bus_suspend,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2952) .bus_resume = u132_bus_resume,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2953) .start_port_reset = u132_start_port_reset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2954) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2955)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2956) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2957) * This function may be called by the USB core whilst the "usb_all_devices_rwsem"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2958) * is held for writing, thus this module must not call usb_remove_hcd()
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2959) * synchronously - but instead should immediately stop activity to the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2960) * device and asynchronously call usb_remove_hcd()
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2961) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2962) static int u132_remove(struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2963) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2964) struct usb_hcd *hcd = platform_get_drvdata(pdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2965) if (hcd) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2966) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2967) if (u132->going++ > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2968) dev_err(&u132->platform_dev->dev, "already being remove"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2969) "d\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2970) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2971) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2972) int rings = MAX_U132_RINGS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2973) int endps = MAX_U132_ENDPS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2974) dev_err(&u132->platform_dev->dev, "removing device u132"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2975) ".%d\n", u132->sequence_num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2976) msleep(100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2977) mutex_lock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2978) u132_monitor_cancel_work(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2979) while (rings-- > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2980) struct u132_ring *ring = &u132->ring[rings];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2981) u132_ring_cancel_work(u132, ring);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2982) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2983) while (endps-- > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2984) struct u132_endp *endp = u132->endp[endps];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2985) if (endp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2986) u132_endp_cancel_work(u132, endp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2987) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2988) u132->going += 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2989) printk(KERN_INFO "removing device u132.%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2990) u132->sequence_num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2991) mutex_unlock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2992) usb_remove_hcd(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2993) u132_u132_put_kref(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2994) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2995) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2996) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2997) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2998) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2999)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3000) static void u132_initialise(struct u132 *u132, struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3001) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3002) int rings = MAX_U132_RINGS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3003) int ports = MAX_U132_PORTS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3004) int addrs = MAX_U132_ADDRS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3005) int udevs = MAX_U132_UDEVS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3006) int endps = MAX_U132_ENDPS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3007) u132->board = dev_get_platdata(&pdev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3008) u132->platform_dev = pdev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3009) u132->power = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3010) u132->reset = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3011) mutex_init(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3012) mutex_init(&u132->scheduler_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3013) while (rings-- > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3014) struct u132_ring *ring = &u132->ring[rings];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3015) ring->u132 = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3016) ring->number = rings + 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3017) ring->length = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3018) ring->curr_endp = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3019) INIT_DELAYED_WORK(&ring->scheduler,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3020) u132_hcd_ring_work_scheduler);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3021) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3022) mutex_lock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3023) INIT_DELAYED_WORK(&u132->monitor, u132_hcd_monitor_work);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3024) while (ports-- > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3025) struct u132_port *port = &u132->port[ports];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3026) port->u132 = u132;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3027) port->reset = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3028) port->enable = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3029) port->power = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3030) port->Status = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3031) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3032) while (addrs-- > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3033) struct u132_addr *addr = &u132->addr[addrs];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3034) addr->address = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3035) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3036) while (udevs-- > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3037) struct u132_udev *udev = &u132->udev[udevs];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3038) int i = ARRAY_SIZE(udev->endp_number_in);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3039) int o = ARRAY_SIZE(udev->endp_number_out);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3040) udev->usb_device = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3041) udev->udev_number = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3042) udev->usb_addr = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3043) udev->portnumber = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3044) while (i-- > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3045) udev->endp_number_in[i] = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3046)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3047) while (o-- > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3048) udev->endp_number_out[o] = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3049)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3050) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3051) while (endps-- > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3052) u132->endp[endps] = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3053)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3054) mutex_unlock(&u132->sw_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3055) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3056)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3057) static int u132_probe(struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3058) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3059) struct usb_hcd *hcd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3060) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3061) u32 control;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3062) u32 rh_a = -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3063)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3064) msleep(100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3065) if (u132_exiting > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3066) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3067)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3068) retval = ftdi_write_pcimem(pdev, intrdisable, OHCI_INTR_MIE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3069) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3070) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3071) retval = ftdi_read_pcimem(pdev, control, &control);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3072) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3073) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3074) retval = ftdi_read_pcimem(pdev, roothub.a, &rh_a);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3075) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3076) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3077)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3078) hcd = usb_create_hcd(&u132_hc_driver, &pdev->dev, dev_name(&pdev->dev));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3079) if (!hcd) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3080) printk(KERN_ERR "failed to create the usb hcd struct for U132\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3081) );
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3082) ftdi_elan_gone_away(pdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3083) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3084) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3085) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3086) retval = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3087) hcd->rsrc_start = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3088) mutex_lock(&u132_module_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3089) u132->sequence_num = ++u132_instances;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3090) mutex_unlock(&u132_module_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3091) u132_u132_init_kref(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3092) u132_initialise(u132, pdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3093) hcd->product_desc = "ELAN U132 Host Controller";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3094) retval = usb_add_hcd(hcd, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3095) if (retval != 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3096) dev_err(&u132->platform_dev->dev, "init error %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3097) retval);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3098) u132_u132_put_kref(u132);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3099) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3100) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3101) device_wakeup_enable(hcd->self.controller);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3102) u132_monitor_queue_work(u132, 100);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3103) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3104) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3105) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3106) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3107)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3108)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3109) #ifdef CONFIG_PM
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3110) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3111) * for this device there's no useful distinction between the controller
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3112) * and its root hub.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3113) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3114) static int u132_suspend(struct platform_device *pdev, pm_message_t state)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3115) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3116) struct usb_hcd *hcd = platform_get_drvdata(pdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3117) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3118) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3119) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3120) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3121) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3122) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3123) dev_err(&u132->platform_dev->dev, "device is being removed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3124) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3125) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3126) int retval = 0, ports;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3127)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3128) switch (state.event) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3129) case PM_EVENT_FREEZE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3130) retval = u132_bus_suspend(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3131) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3132) case PM_EVENT_SUSPEND:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3133) case PM_EVENT_HIBERNATE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3134) ports = MAX_U132_PORTS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3135) while (ports-- > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3136) port_power(u132, ports, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3137) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3138) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3139) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3140) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3141) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3142) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3143)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3144) static int u132_resume(struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3145) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3146) struct usb_hcd *hcd = platform_get_drvdata(pdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3147) struct u132 *u132 = hcd_to_u132(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3148) if (u132->going > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3149) dev_err(&u132->platform_dev->dev, "device has been removed %d\n"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3150) , u132->going);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3151) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3152) } else if (u132->going > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3153) dev_err(&u132->platform_dev->dev, "device is being removed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3154) return -ESHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3155) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3156) int retval = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3157) if (!u132->port[0].power) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3158) int ports = MAX_U132_PORTS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3159) while (ports-- > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3160) port_power(u132, ports, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3161) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3162) retval = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3163) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3164) retval = u132_bus_resume(hcd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3165) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3166) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3167) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3168) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3169)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3170) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3171) #define u132_suspend NULL
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3172) #define u132_resume NULL
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3173) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3174) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3175) * this driver is loaded explicitly by ftdi_u132
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3176) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3177) * the platform_driver struct is static because it is per type of module
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3178) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3179) static struct platform_driver u132_platform_driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3180) .probe = u132_probe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3181) .remove = u132_remove,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3182) .suspend = u132_suspend,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3183) .resume = u132_resume,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3184) .driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3185) .name = hcd_name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3186) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3187) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3188) static int __init u132_hcd_init(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3189) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3190) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3191) u132_instances = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3192) u132_exiting = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3193) mutex_init(&u132_module_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3194) if (usb_disabled())
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3195) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3196) printk(KERN_INFO "driver %s\n", hcd_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3197) workqueue = create_singlethread_workqueue("u132");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3198) if (!workqueue)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3199) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3200) retval = platform_driver_register(&u132_platform_driver);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3201) if (retval)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3202) destroy_workqueue(workqueue);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3203)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3204) return retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3205) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3206)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3207)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3208) module_init(u132_hcd_init);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3209) static void __exit u132_hcd_exit(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3210) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3211) mutex_lock(&u132_module_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3212) u132_exiting += 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3213) mutex_unlock(&u132_module_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3214) platform_driver_unregister(&u132_platform_driver);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3215) printk(KERN_INFO "u132-hcd driver deregistered\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3216) wait_event(u132_hcd_wait, u132_instances == 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3217) flush_workqueue(workqueue);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3218) destroy_workqueue(workqueue);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3219) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3220)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3221)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3222) module_exit(u132_hcd_exit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3223) MODULE_LICENSE("GPL");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3224) MODULE_ALIAS("platform:u132_hcd");