diff options
271 files changed, 11292 insertions, 3548 deletions
diff --git a/Documentation/ABI/stable/sysfs-class-udc b/Documentation/ABI/stable/sysfs-class-udc new file mode 100644 index 000000000000..85d3dac2e204 --- /dev/null +++ b/Documentation/ABI/stable/sysfs-class-udc | |||
| @@ -0,0 +1,93 @@ | |||
| 1 | What: /sys/class/udc/<udc>/a_alt_hnp_support | ||
| 2 | Date: June 2011 | ||
| 3 | KernelVersion: 3.1 | ||
| 4 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 5 | Description: | ||
| 6 | Indicates if an OTG A-Host supports HNP at an alternate port. | ||
| 7 | Users: | ||
| 8 | |||
| 9 | What: /sys/class/udc/<udc>/a_hnp_support | ||
| 10 | Date: June 2011 | ||
| 11 | KernelVersion: 3.1 | ||
| 12 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 13 | Description: | ||
| 14 | Indicates if an OTG A-Host supports HNP at this port. | ||
| 15 | Users: | ||
| 16 | |||
| 17 | What: /sys/class/udc/<udc>/b_hnp_enable | ||
| 18 | Date: June 2011 | ||
| 19 | KernelVersion: 3.1 | ||
| 20 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 21 | Description: | ||
| 22 | Indicates if an OTG A-Host enabled HNP support. | ||
| 23 | Users: | ||
| 24 | |||
| 25 | What: /sys/class/udc/<udc>/current_speed | ||
| 26 | Date: June 2011 | ||
| 27 | KernelVersion: 3.1 | ||
| 28 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 29 | Description: | ||
| 30 | Indicates the current negotiated speed at this port. | ||
| 31 | Users: | ||
| 32 | |||
| 33 | What: /sys/class/udc/<udc>/is_a_peripheral | ||
| 34 | Date: June 2011 | ||
| 35 | KernelVersion: 3.1 | ||
| 36 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 37 | Description: | ||
| 38 | Indicates that this port is the default Host on an OTG session | ||
| 39 | but HNP was used to switch roles. | ||
| 40 | Users: | ||
| 41 | |||
| 42 | What: /sys/class/udc/<udc>/is_otg | ||
| 43 | Date: June 2011 | ||
| 44 | KernelVersion: 3.1 | ||
| 45 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 46 | Description: | ||
| 47 | Indicates that this port support OTG. | ||
| 48 | Users: | ||
| 49 | |||
| 50 | What: /sys/class/udc/<udc>/maximum_speed | ||
| 51 | Date: June 2011 | ||
| 52 | KernelVersion: 3.1 | ||
| 53 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 54 | Description: | ||
| 55 | Indicates the maximum USB speed supported by this port. | ||
| 56 | Users: | ||
| 57 | |||
| 58 | What: /sys/class/udc/<udc>/maximum_speed | ||
| 59 | Date: June 2011 | ||
| 60 | KernelVersion: 3.1 | ||
| 61 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 62 | Description: | ||
| 63 | Indicates the maximum USB speed supported by this port. | ||
| 64 | Users: | ||
| 65 | |||
| 66 | What: /sys/class/udc/<udc>/soft_connect | ||
| 67 | Date: June 2011 | ||
| 68 | KernelVersion: 3.1 | ||
| 69 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 70 | Description: | ||
| 71 | Allows users to disconnect data pullup resistors thus causing a | ||
| 72 | logical disconnection from the USB Host. | ||
| 73 | Users: | ||
| 74 | |||
| 75 | What: /sys/class/udc/<udc>/srp | ||
| 76 | Date: June 2011 | ||
| 77 | KernelVersion: 3.1 | ||
| 78 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 79 | Description: | ||
| 80 | Allows users to manually start Session Request Protocol. | ||
| 81 | Users: | ||
| 82 | |||
| 83 | What: /sys/class/udc/<udc>/state | ||
| 84 | Date: June 2011 | ||
| 85 | KernelVersion: 3.1 | ||
| 86 | Contact: Felipe Balbi <balbi@kernel.org> | ||
| 87 | Description: | ||
| 88 | Indicates current state of the USB Device Controller. Valid | ||
| 89 | states are: 'not-attached', 'attached', 'powered', | ||
| 90 | 'reconnecting', 'unauthenticated', 'default', 'addressed', | ||
| 91 | 'configured', and 'suspended'; however not all USB Device | ||
| 92 | Controllers support reporting all states. | ||
| 93 | Users: | ||
diff --git a/Documentation/ABI/testing/configfs-usb-gadget-hid b/Documentation/ABI/testing/configfs-usb-gadget-hid new file mode 100644 index 000000000000..f12e00e6baa3 --- /dev/null +++ b/Documentation/ABI/testing/configfs-usb-gadget-hid | |||
| @@ -0,0 +1,11 @@ | |||
| 1 | What: /config/usb-gadget/gadget/functions/hid.name | ||
| 2 | Date: Nov 2014 | ||
| 3 | KernelVersion: 3.19 | ||
| 4 | Description: | ||
| 5 | The attributes: | ||
| 6 | |||
| 7 | protocol - HID protocol to use | ||
| 8 | report_desc - blob corresponding to HID report descriptors | ||
| 9 | except the data passed through /dev/hidg<N> | ||
| 10 | report_length - HID report length | ||
| 11 | subclass - HID device subclass to use | ||
diff --git a/Documentation/ABI/testing/configfs-usb-gadget-midi b/Documentation/ABI/testing/configfs-usb-gadget-midi new file mode 100644 index 000000000000..6b341df7249c --- /dev/null +++ b/Documentation/ABI/testing/configfs-usb-gadget-midi | |||
| @@ -0,0 +1,12 @@ | |||
| 1 | What: /config/usb-gadget/gadget/functions/midi.name | ||
| 2 | Date: Nov 2014 | ||
| 3 | KernelVersion: 3.19 | ||
| 4 | Description: | ||
| 5 | The attributes: | ||
| 6 | |||
| 7 | index - index value for the USB MIDI adapter | ||
| 8 | id - ID string for the USB MIDI adapter | ||
| 9 | buflen - MIDI buffer length | ||
| 10 | qlen - USB read request queue length | ||
| 11 | in_ports - number of MIDI input ports | ||
| 12 | out_ports - number of MIDI output ports | ||
diff --git a/Documentation/devicetree/bindings/ata/marvell.txt b/Documentation/devicetree/bindings/ata/marvell.txt index 1c8351604d38..b460edd12766 100644 --- a/Documentation/devicetree/bindings/ata/marvell.txt +++ b/Documentation/devicetree/bindings/ata/marvell.txt | |||
| @@ -6,11 +6,17 @@ Required Properties: | |||
| 6 | - interrupts : Interrupt controller is using | 6 | - interrupts : Interrupt controller is using |
| 7 | - nr-ports : Number of SATA ports in use. | 7 | - nr-ports : Number of SATA ports in use. |
| 8 | 8 | ||
| 9 | Optional Properties: | ||
| 10 | - phys : List of phandles to sata phys | ||
| 11 | - phy-names : Should be "0", "1", etc, one number per phandle | ||
| 12 | |||
| 9 | Example: | 13 | Example: |
| 10 | 14 | ||
| 11 | sata@80000 { | 15 | sata@80000 { |
| 12 | compatible = "marvell,orion-sata"; | 16 | compatible = "marvell,orion-sata"; |
| 13 | reg = <0x80000 0x5000>; | 17 | reg = <0x80000 0x5000>; |
| 14 | interrupts = <21>; | 18 | interrupts = <21>; |
| 19 | phys = <&sata_phy0>, <&sata_phy1>; | ||
| 20 | phy-names = "0", "1"; | ||
| 15 | nr-ports = <2>; | 21 | nr-ports = <2>; |
| 16 | } | 22 | } |
diff --git a/Documentation/devicetree/bindings/phy/berlin-sata-phy.txt b/Documentation/devicetree/bindings/phy/berlin-sata-phy.txt index 88f8c23384c0..c0155f842f62 100644 --- a/Documentation/devicetree/bindings/phy/berlin-sata-phy.txt +++ b/Documentation/devicetree/bindings/phy/berlin-sata-phy.txt | |||
| @@ -2,7 +2,9 @@ Berlin SATA PHY | |||
| 2 | --------------- | 2 | --------------- |
| 3 | 3 | ||
| 4 | Required properties: | 4 | Required properties: |
| 5 | - compatible: should be "marvell,berlin2q-sata-phy" | 5 | - compatible: should be one of |
| 6 | "marvell,berlin2-sata-phy" | ||
| 7 | "marvell,berlin2q-sata-phy" | ||
| 6 | - address-cells: should be 1 | 8 | - address-cells: should be 1 |
| 7 | - size-cells: should be 0 | 9 | - size-cells: should be 0 |
| 8 | - phy-cells: from the generic PHY bindings, must be 1 | 10 | - phy-cells: from the generic PHY bindings, must be 1 |
diff --git a/Documentation/devicetree/bindings/phy/berlin-usb-phy.txt b/Documentation/devicetree/bindings/phy/berlin-usb-phy.txt new file mode 100644 index 000000000000..be33780f668e --- /dev/null +++ b/Documentation/devicetree/bindings/phy/berlin-usb-phy.txt | |||
| @@ -0,0 +1,16 @@ | |||
| 1 | * Marvell Berlin USB PHY | ||
| 2 | |||
| 3 | Required properties: | ||
| 4 | - compatible: "marvell,berlin2-usb-phy" or "marvell,berlin2cd-usb-phy" | ||
| 5 | - reg: base address and length of the registers | ||
| 6 | - #phys-cells: should be 0 | ||
| 7 | - resets: reference to the reset controller | ||
| 8 | |||
| 9 | Example: | ||
| 10 | |||
| 11 | usb-phy@f774000 { | ||
| 12 | compatible = "marvell,berlin2-usb-phy"; | ||
| 13 | reg = <0xf774000 0x128>; | ||
| 14 | #phy-cells = <0>; | ||
| 15 | resets = <&chip 0x104 14>; | ||
| 16 | }; | ||
diff --git a/Documentation/devicetree/bindings/phy/phy-miphy28lp.txt b/Documentation/devicetree/bindings/phy/phy-miphy28lp.txt new file mode 100644 index 000000000000..46a135dae6b3 --- /dev/null +++ b/Documentation/devicetree/bindings/phy/phy-miphy28lp.txt | |||
| @@ -0,0 +1,128 @@ | |||
| 1 | STMicroelectronics STi MIPHY28LP PHY binding | ||
| 2 | ============================================ | ||
| 3 | |||
| 4 | This binding describes a miphy device that is used to control PHY hardware | ||
| 5 | for SATA, PCIe or USB3. | ||
| 6 | |||
| 7 | Required properties (controller (parent) node): | ||
| 8 | - compatible : Should be "st,miphy28lp-phy". | ||
| 9 | - st,syscfg : Should be a phandle of the system configuration register group | ||
| 10 | which contain the SATA, PCIe or USB3 mode setting bits. | ||
| 11 | |||
| 12 | Required nodes : A sub-node is required for each channel the controller | ||
| 13 | provides. Address range information including the usual | ||
| 14 | 'reg' and 'reg-names' properties are used inside these | ||
| 15 | nodes to describe the controller's topology. These nodes | ||
| 16 | are translated by the driver's .xlate() function. | ||
| 17 | |||
| 18 | Required properties (port (child) node): | ||
| 19 | - #phy-cells : Should be 1 (See second example) | ||
| 20 | Cell after port phandle is device type from: | ||
| 21 | - PHY_TYPE_SATA | ||
| 22 | - PHY_TYPE_PCI | ||
| 23 | - PHY_TYPE_USB3 | ||
| 24 | - reg : Address and length of the register set for the device. | ||
| 25 | - reg-names : The names of the register addresses corresponding to the registers | ||
| 26 | filled in "reg". It can also contain the offset of the system configuration | ||
| 27 | registers used as glue-logic to setup the device for SATA/PCIe or USB3 | ||
| 28 | devices. | ||
| 29 | - resets : phandle to the parent reset controller. | ||
| 30 | - reset-names : Associated name must be "miphy-sw-rst". | ||
| 31 | |||
| 32 | Optional properties (port (child) node): | ||
| 33 | - st,osc-rdy : to check the MIPHY0_OSC_RDY status in the glue-logic. This | ||
| 34 | is not available in all the MiPHY. For example, for STiH407, only the | ||
| 35 | MiPHY0 has this bit. | ||
| 36 | - st,osc-force-ext : to select the external oscillator. This can change from | ||
| 37 | different MiPHY inside the same SoC. | ||
| 38 | - st,sata_gen : to select which SATA_SPDMODE has to be set in the SATA system config | ||
| 39 | register. | ||
| 40 | - st,px_rx_pol_inv : to invert polarity of RXn/RXp (respectively negative line and positive | ||
| 41 | line). | ||
| 42 | - st,scc-on : enable ssc to reduce effects of EMI (only for sata or PCIe). | ||
| 43 | - st,tx-impedance-comp : to compensate tx impedance avoiding out of range values. | ||
| 44 | |||
| 45 | example: | ||
| 46 | |||
| 47 | miphy28lp_phy: miphy28lp@9b22000 { | ||
| 48 | compatible = "st,miphy28lp-phy"; | ||
| 49 | st,syscfg = <&syscfg_core>; | ||
| 50 | #address-cells = <1>; | ||
| 51 | #size-cells = <1>; | ||
| 52 | ranges; | ||
| 53 | |||
| 54 | phy_port0: port@9b22000 { | ||
| 55 | reg = <0x9b22000 0xff>, | ||
| 56 | <0x9b09000 0xff>, | ||
| 57 | <0x9b04000 0xff>, | ||
| 58 | <0x114 0x4>, /* sysctrl MiPHY cntrl */ | ||
| 59 | <0x818 0x4>, /* sysctrl MiPHY status*/ | ||
| 60 | <0xe0 0x4>, /* sysctrl PCIe */ | ||
| 61 | <0xec 0x4>; /* sysctrl SATA */ | ||
| 62 | reg-names = "sata-up", | ||
| 63 | "pcie-up", | ||
| 64 | "pipew", | ||
| 65 | "miphy-ctrl-glue", | ||
| 66 | "miphy-status-glue", | ||
| 67 | "pcie-glue", | ||
| 68 | "sata-glue"; | ||
| 69 | #phy-cells = <1>; | ||
| 70 | st,osc-rdy; | ||
| 71 | reset-names = "miphy-sw-rst"; | ||
| 72 | resets = <&softreset STIH407_MIPHY0_SOFTRESET>; | ||
| 73 | }; | ||
| 74 | |||
| 75 | phy_port1: port@9b2a000 { | ||
| 76 | reg = <0x9b2a000 0xff>, | ||
| 77 | <0x9b19000 0xff>, | ||
| 78 | <0x9b14000 0xff>, | ||
| 79 | <0x118 0x4>, | ||
| 80 | <0x81c 0x4>, | ||
| 81 | <0xe4 0x4>, | ||
| 82 | <0xf0 0x4>; | ||
| 83 | reg-names = "sata-up", | ||
| 84 | "pcie-up", | ||
| 85 | "pipew", | ||
| 86 | "miphy-ctrl-glue", | ||
| 87 | "miphy-status-glue", | ||
| 88 | "pcie-glue", | ||
| 89 | "sata-glue"; | ||
| 90 | #phy-cells = <1>; | ||
| 91 | st,osc-force-ext; | ||
| 92 | reset-names = "miphy-sw-rst"; | ||
| 93 | resets = <&softreset STIH407_MIPHY1_SOFTRESET>; | ||
| 94 | }; | ||
| 95 | |||
| 96 | phy_port2: port@8f95000 { | ||
| 97 | reg = <0x8f95000 0xff>, | ||
| 98 | <0x8f90000 0xff>, | ||
| 99 | <0x11c 0x4>, | ||
| 100 | <0x820 0x4>; | ||
| 101 | reg-names = "pipew", | ||
| 102 | "usb3-up", | ||
| 103 | "miphy-ctrl-glue", | ||
| 104 | "miphy-status-glue"; | ||
| 105 | #phy-cells = <1>; | ||
| 106 | reset-names = "miphy-sw-rst"; | ||
| 107 | resets = <&softreset STIH407_MIPHY2_SOFTRESET>; | ||
| 108 | }; | ||
| 109 | }; | ||
| 110 | |||
| 111 | |||
| 112 | Specifying phy control of devices | ||
| 113 | ================================= | ||
| 114 | |||
| 115 | Device nodes should specify the configuration required in their "phys" | ||
| 116 | property, containing a phandle to the miphy device node and an index | ||
| 117 | specifying which configuration to use, as described in phy-bindings.txt. | ||
| 118 | |||
| 119 | example: | ||
| 120 | sata0: sata@9b20000 { | ||
| 121 | ... | ||
| 122 | phys = <&phy_port0 PHY_TYPE_SATA>; | ||
| 123 | ... | ||
| 124 | }; | ||
| 125 | |||
| 126 | Macro definitions for the supported miphy configuration can be found in: | ||
| 127 | |||
| 128 | include/dt-bindings/phy/phy-miphy28lp.h | ||
diff --git a/Documentation/devicetree/bindings/phy/phy-mvebu.txt b/Documentation/devicetree/bindings/phy/phy-mvebu.txt new file mode 100644 index 000000000000..f95b6260a3b3 --- /dev/null +++ b/Documentation/devicetree/bindings/phy/phy-mvebu.txt | |||
| @@ -0,0 +1,43 @@ | |||
| 1 | * Marvell MVEBU SATA PHY | ||
| 2 | |||
| 3 | Power control for the SATA phy found on Marvell MVEBU SoCs. | ||
| 4 | |||
| 5 | This document extends the binding described in phy-bindings.txt | ||
| 6 | |||
| 7 | Required properties : | ||
| 8 | |||
| 9 | - reg : Offset and length of the register set for the SATA device | ||
| 10 | - compatible : Should be "marvell,mvebu-sata-phy" | ||
| 11 | - clocks : phandle of clock and specifier that supplies the device | ||
| 12 | - clock-names : Should be "sata" | ||
| 13 | |||
| 14 | Example: | ||
| 15 | sata-phy@84000 { | ||
| 16 | compatible = "marvell,mvebu-sata-phy"; | ||
| 17 | reg = <0x84000 0x0334>; | ||
| 18 | clocks = <&gate_clk 15>; | ||
| 19 | clock-names = "sata"; | ||
| 20 | #phy-cells = <0>; | ||
| 21 | status = "ok"; | ||
| 22 | }; | ||
| 23 | |||
| 24 | Armada 375 USB cluster | ||
| 25 | ---------------------- | ||
| 26 | |||
| 27 | Armada 375 comes with an USB2 host and device controller and an USB3 | ||
| 28 | controller. The USB cluster control register allows to manage common | ||
| 29 | features of both USB controllers. | ||
| 30 | |||
| 31 | Required properties: | ||
| 32 | |||
| 33 | - compatible: "marvell,armada-375-usb-cluster" | ||
| 34 | - reg: Should contain usb cluster register location and length. | ||
| 35 | - #phy-cells : from the generic phy bindings, must be 1. Possible | ||
| 36 | values are 1 (USB2), 2 (USB3). | ||
| 37 | |||
| 38 | Example: | ||
| 39 | usbcluster: usb-cluster@18400 { | ||
| 40 | compatible = "marvell,armada-375-usb-cluster"; | ||
| 41 | reg = <0x18400 0x4>; | ||
| 42 | #phy-cells = <1> | ||
| 43 | }; | ||
diff --git a/Documentation/devicetree/bindings/phy/samsung-phy.txt b/Documentation/devicetree/bindings/phy/samsung-phy.txt index 15e0f2c7130f..d5bad920827f 100644 --- a/Documentation/devicetree/bindings/phy/samsung-phy.txt +++ b/Documentation/devicetree/bindings/phy/samsung-phy.txt | |||
| @@ -128,6 +128,7 @@ Required properties: | |||
| 128 | - compatible : Should be set to one of the following supported values: | 128 | - compatible : Should be set to one of the following supported values: |
| 129 | - "samsung,exynos5250-usbdrd-phy" - for exynos5250 SoC, | 129 | - "samsung,exynos5250-usbdrd-phy" - for exynos5250 SoC, |
| 130 | - "samsung,exynos5420-usbdrd-phy" - for exynos5420 SoC. | 130 | - "samsung,exynos5420-usbdrd-phy" - for exynos5420 SoC. |
| 131 | - "samsung,exynos7-usbdrd-phy" - for exynos7 SoC. | ||
| 131 | - reg : Register offset and length of USB DRD PHY register set; | 132 | - reg : Register offset and length of USB DRD PHY register set; |
| 132 | - clocks: Clock IDs array as required by the controller | 133 | - clocks: Clock IDs array as required by the controller |
| 133 | - clock-names: names of clocks correseponding to IDs in the clock property; | 134 | - clock-names: names of clocks correseponding to IDs in the clock property; |
| @@ -138,6 +139,11 @@ Required properties: | |||
| 138 | PHY operations, associated by phy name. It is used to | 139 | PHY operations, associated by phy name. It is used to |
| 139 | determine bit values for clock settings register. | 140 | determine bit values for clock settings register. |
| 140 | For Exynos5420 this is given as 'sclk_usbphy30' in CMU. | 141 | For Exynos5420 this is given as 'sclk_usbphy30' in CMU. |
| 142 | - optional clocks: Exynos7 SoC has now following additional | ||
| 143 | gate clocks available: | ||
| 144 | - phy_pipe: for PIPE3 phy | ||
| 145 | - phy_utmi: for UTMI+ phy | ||
| 146 | - itp: for ITP generation | ||
| 141 | - samsung,pmu-syscon: phandle for PMU system controller interface, used to | 147 | - samsung,pmu-syscon: phandle for PMU system controller interface, used to |
| 142 | control pmu registers for power isolation. | 148 | control pmu registers for power isolation. |
| 143 | - #phy-cells : from the generic PHY bindings, must be 1; | 149 | - #phy-cells : from the generic PHY bindings, must be 1; |
diff --git a/Documentation/devicetree/bindings/usb/ci-hdrc-usb2.txt b/Documentation/devicetree/bindings/usb/ci-hdrc-usb2.txt new file mode 100644 index 000000000000..27f8b1e5ee46 --- /dev/null +++ b/Documentation/devicetree/bindings/usb/ci-hdrc-usb2.txt | |||
| @@ -0,0 +1,24 @@ | |||
| 1 | * USB2 ChipIdea USB controller for ci13xxx | ||
| 2 | |||
| 3 | Required properties: | ||
| 4 | - compatible: should be "chipidea,usb2" | ||
| 5 | - reg: base address and length of the registers | ||
| 6 | - interrupts: interrupt for the USB controller | ||
| 7 | |||
| 8 | Optional properties: | ||
| 9 | - clocks: reference to the USB clock | ||
| 10 | - phys: reference to the USB PHY | ||
| 11 | - phy-names: should be "usb-phy" | ||
| 12 | - vbus-supply: reference to the VBUS regulator | ||
| 13 | |||
| 14 | Example: | ||
| 15 | |||
| 16 | usb@f7ed0000 { | ||
| 17 | compatible = "chipidea,usb2"; | ||
| 18 | reg = <0xf7ed0000 0x10000>; | ||
| 19 | interrupts = <GIC_SPI 11 IRQ_TYPE_LEVEL_HIGH>; | ||
| 20 | clocks = <&chip CLKID_USB0>; | ||
| 21 | phys = <&usb_phy0>; | ||
| 22 | phy-names = "usb-phy"; | ||
| 23 | vbus-supply = <®_usb0_vbus>; | ||
| 24 | }; | ||
diff --git a/Documentation/devicetree/bindings/usb/dwc3.txt b/Documentation/devicetree/bindings/usb/dwc3.txt index 471366d6a129..cd7f0454e13a 100644 --- a/Documentation/devicetree/bindings/usb/dwc3.txt +++ b/Documentation/devicetree/bindings/usb/dwc3.txt | |||
| @@ -14,6 +14,29 @@ Optional properties: | |||
| 14 | - phys: from the *Generic PHY* bindings | 14 | - phys: from the *Generic PHY* bindings |
| 15 | - phy-names: from the *Generic PHY* bindings | 15 | - phy-names: from the *Generic PHY* bindings |
| 16 | - tx-fifo-resize: determines if the FIFO *has* to be reallocated. | 16 | - tx-fifo-resize: determines if the FIFO *has* to be reallocated. |
| 17 | - snps,disable_scramble_quirk: true when SW should disable data scrambling. | ||
| 18 | Only really useful for FPGA builds. | ||
| 19 | - snps,has-lpm-erratum: true when DWC3 was configured with LPM Erratum enabled | ||
| 20 | - snps,lpm-nyet-threshold: LPM NYET threshold | ||
| 21 | - snps,u2exit_lfps_quirk: set if we want to enable u2exit lfps quirk | ||
| 22 | - snps,u2ss_inp3_quirk: set if we enable P3 OK for U2/SS Inactive quirk | ||
| 23 | - snps,req_p1p2p3_quirk: when set, the core will always request for | ||
| 24 | P1/P2/P3 transition sequence. | ||
| 25 | - snps,del_p1p2p3_quirk: when set core will delay P1/P2/P3 until a certain | ||
| 26 | amount of 8B10B errors occur. | ||
| 27 | - snps,del_phy_power_chg_quirk: when set core will delay PHY power change | ||
| 28 | from P0 to P1/P2/P3. | ||
| 29 | - snps,lfps_filter_quirk: when set core will filter LFPS reception. | ||
| 30 | - snps,rx_detect_poll_quirk: when set core will disable a 400us delay to start | ||
| 31 | Polling LFPS after RX.Detect. | ||
| 32 | - snps,tx_de_emphasis_quirk: when set core will set Tx de-emphasis value. | ||
| 33 | - snps,tx_de_emphasis: the value driven to the PHY is controlled by the | ||
| 34 | LTSSM during USB3 Compliance mode. | ||
| 35 | - snps,dis_u3_susphy_quirk: when set core will disable USB3 suspend phy. | ||
| 36 | - snps,dis_u2_susphy_quirk: when set core will disable USB2 suspend phy. | ||
| 37 | - snps,is-utmi-l1-suspend: true when DWC3 asserts output signal | ||
| 38 | utmi_l1_suspend_n, false when asserts utmi_sleep_n | ||
| 39 | - snps,hird-threshold: HIRD threshold | ||
| 17 | 40 | ||
| 18 | This is usually a subnode to DWC3 glue to which it is connected. | 41 | This is usually a subnode to DWC3 glue to which it is connected. |
| 19 | 42 | ||
diff --git a/Documentation/devicetree/bindings/usb/exynos-usb.txt b/Documentation/devicetree/bindings/usb/exynos-usb.txt index a3b5990d0f2c..9b4dbe3b2acc 100644 --- a/Documentation/devicetree/bindings/usb/exynos-usb.txt +++ b/Documentation/devicetree/bindings/usb/exynos-usb.txt | |||
| @@ -82,8 +82,10 @@ Example: | |||
| 82 | 82 | ||
| 83 | DWC3 | 83 | DWC3 |
| 84 | Required properties: | 84 | Required properties: |
| 85 | - compatible: should be "samsung,exynos5250-dwusb3" for USB 3.0 DWC3 | 85 | - compatible: should be one of the following - |
| 86 | controller. | 86 | "samsung,exynos5250-dwusb3": for USB 3.0 DWC3 controller on |
| 87 | Exynos5250/5420. | ||
| 88 | "samsung,exynos7-dwusb3": for USB 3.0 DWC3 controller on Exynos7. | ||
| 87 | - #address-cells, #size-cells : should be '1' if the device has sub-nodes | 89 | - #address-cells, #size-cells : should be '1' if the device has sub-nodes |
| 88 | with 'reg' property. | 90 | with 'reg' property. |
| 89 | - ranges: allows valid 1:1 translation between child's address space and | 91 | - ranges: allows valid 1:1 translation between child's address space and |
diff --git a/Documentation/devicetree/bindings/usb/pxa-usb.txt b/Documentation/devicetree/bindings/usb/pxa-usb.txt index 79729a948d5a..9c331799b87c 100644 --- a/Documentation/devicetree/bindings/usb/pxa-usb.txt +++ b/Documentation/devicetree/bindings/usb/pxa-usb.txt | |||
| @@ -29,3 +29,25 @@ Example: | |||
| 29 | marvell,port-mode = <2>; /* PMM_GLOBAL_MODE */ | 29 | marvell,port-mode = <2>; /* PMM_GLOBAL_MODE */ |
| 30 | }; | 30 | }; |
| 31 | 31 | ||
| 32 | UDC | ||
| 33 | |||
| 34 | Required properties: | ||
| 35 | - compatible: Should be "marvell,pxa270-udc" for USB controllers | ||
| 36 | used in device mode. | ||
| 37 | - reg: usb device MMIO address space | ||
| 38 | - interrupts: single interrupt generated by the UDC IP | ||
| 39 | - clocks: input clock of the UDC IP (see clock-bindings.txt) | ||
| 40 | |||
| 41 | Optional properties: | ||
| 42 | - gpios: | ||
| 43 | - gpio activated to control the USB D+ pullup (see gpio.txt) | ||
| 44 | |||
| 45 | Example: | ||
| 46 | |||
| 47 | pxa27x_udc: udc@40600000 { | ||
| 48 | compatible = "marvell,pxa270-udc"; | ||
| 49 | reg = <0x40600000 0x10000>; | ||
| 50 | interrupts = <11>; | ||
| 51 | clocks = <&pxa2xx_clks 11>; | ||
| 52 | gpios = <&gpio 22 GPIO_ACTIVE_LOW>; | ||
| 53 | }; | ||
diff --git a/Documentation/devicetree/bindings/usb/usb-ohci.txt b/Documentation/devicetree/bindings/usb/usb-ohci.txt index b968a1aea995..19233b7365e1 100644 --- a/Documentation/devicetree/bindings/usb/usb-ohci.txt +++ b/Documentation/devicetree/bindings/usb/usb-ohci.txt | |||
| @@ -9,6 +9,8 @@ Optional properties: | |||
| 9 | - big-endian-regs : boolean, set this for hcds with big-endian registers | 9 | - big-endian-regs : boolean, set this for hcds with big-endian registers |
| 10 | - big-endian-desc : boolean, set this for hcds with big-endian descriptors | 10 | - big-endian-desc : boolean, set this for hcds with big-endian descriptors |
| 11 | - big-endian : boolean, for hcds with big-endian-regs + big-endian-desc | 11 | - big-endian : boolean, for hcds with big-endian-regs + big-endian-desc |
| 12 | - no-big-frame-no : boolean, set if frame_no lives in bits [15:0] of HCCA | ||
| 13 | - num-ports : u32, to override the detected port count | ||
| 12 | - clocks : a list of phandle + clock specifier pairs | 14 | - clocks : a list of phandle + clock specifier pairs |
| 13 | - phys : phandle + phy specifier pair | 15 | - phys : phandle + phy specifier pair |
| 14 | - phy-names : "usb" | 16 | - phy-names : "usb" |
diff --git a/Documentation/phy.txt b/Documentation/phy.txt index c6594af94d25..371361c69a4b 100644 --- a/Documentation/phy.txt +++ b/Documentation/phy.txt | |||
| @@ -54,18 +54,14 @@ The PHY driver should create the PHY in order for other peripheral controllers | |||
| 54 | to make use of it. The PHY framework provides 2 APIs to create the PHY. | 54 | to make use of it. The PHY framework provides 2 APIs to create the PHY. |
| 55 | 55 | ||
| 56 | struct phy *phy_create(struct device *dev, struct device_node *node, | 56 | struct phy *phy_create(struct device *dev, struct device_node *node, |
| 57 | const struct phy_ops *ops, | 57 | const struct phy_ops *ops); |
| 58 | struct phy_init_data *init_data); | ||
| 59 | struct phy *devm_phy_create(struct device *dev, struct device_node *node, | 58 | struct phy *devm_phy_create(struct device *dev, struct device_node *node, |
| 60 | const struct phy_ops *ops, | 59 | const struct phy_ops *ops); |
| 61 | struct phy_init_data *init_data); | ||
| 62 | 60 | ||
| 63 | The PHY drivers can use one of the above 2 APIs to create the PHY by passing | 61 | The PHY drivers can use one of the above 2 APIs to create the PHY by passing |
| 64 | the device pointer, phy ops and init_data. | 62 | the device pointer and phy ops. |
| 65 | phy_ops is a set of function pointers for performing PHY operations such as | 63 | phy_ops is a set of function pointers for performing PHY operations such as |
| 66 | init, exit, power_on and power_off. *init_data* is mandatory to get a reference | 64 | init, exit, power_on and power_off. |
| 67 | to the PHY in the case of non-dt boot. See section *Board File Initialization* | ||
| 68 | on how init_data should be used. | ||
| 69 | 65 | ||
| 70 | Inorder to dereference the private data (in phy_ops), the phy provider driver | 66 | Inorder to dereference the private data (in phy_ops), the phy provider driver |
| 71 | can use phy_set_drvdata() after creating the PHY and use phy_get_drvdata() in | 67 | can use phy_set_drvdata() after creating the PHY and use phy_get_drvdata() in |
| @@ -137,42 +133,18 @@ There are exported APIs like phy_pm_runtime_get, phy_pm_runtime_get_sync, | |||
| 137 | phy_pm_runtime_put, phy_pm_runtime_put_sync, phy_pm_runtime_allow and | 133 | phy_pm_runtime_put, phy_pm_runtime_put_sync, phy_pm_runtime_allow and |
| 138 | phy_pm_runtime_forbid for performing PM operations. | 134 | phy_pm_runtime_forbid for performing PM operations. |
| 139 | 135 | ||
| 140 | 8. Board File Initialization | 136 | 8. PHY Mappings |
| 141 | 137 | ||
| 142 | Certain board file initialization is necessary in order to get a reference | 138 | In order to get reference to a PHY without help from DeviceTree, the framework |
| 143 | to the PHY in the case of non-dt boot. | 139 | offers lookups which can be compared to clkdev that allow clk structures to be |
| 144 | Say we have a single device that implements 3 PHYs that of USB, SATA and PCIe, | 140 | bound to devices. A lookup can be made be made during runtime when a handle to |
| 145 | then in the board file the following initialization should be done. | 141 | the struct phy already exists. |
| 146 | 142 | ||
| 147 | struct phy_consumer consumers[] = { | 143 | The framework offers the following API for registering and unregistering the |
| 148 | PHY_CONSUMER("dwc3.0", "usb"), | 144 | lookups. |
| 149 | PHY_CONSUMER("pcie.0", "pcie"), | 145 | |
| 150 | PHY_CONSUMER("sata.0", "sata"), | 146 | int phy_create_lookup(struct phy *phy, const char *con_id, const char *dev_id); |
| 151 | }; | 147 | void phy_remove_lookup(struct phy *phy, const char *con_id, const char *dev_id); |
| 152 | PHY_CONSUMER takes 2 parameters, first is the device name of the controller | ||
| 153 | (PHY consumer) and second is the port name. | ||
| 154 | |||
| 155 | struct phy_init_data init_data = { | ||
| 156 | .consumers = consumers, | ||
| 157 | .num_consumers = ARRAY_SIZE(consumers), | ||
| 158 | }; | ||
| 159 | |||
| 160 | static const struct platform_device pipe3_phy_dev = { | ||
| 161 | .name = "pipe3-phy", | ||
| 162 | .id = -1, | ||
| 163 | .dev = { | ||
| 164 | .platform_data = { | ||
| 165 | .init_data = &init_data, | ||
| 166 | }, | ||
| 167 | }, | ||
| 168 | }; | ||
| 169 | |||
| 170 | then, while doing phy_create, the PHY driver should pass this init_data | ||
| 171 | phy_create(dev, ops, pdata->init_data); | ||
| 172 | |||
| 173 | and the controller driver (phy consumer) should pass the port name along with | ||
| 174 | the device to get a reference to the PHY | ||
| 175 | phy_get(dev, "pcie"); | ||
| 176 | 148 | ||
| 177 | 9. DeviceTree Binding | 149 | 9. DeviceTree Binding |
| 178 | 150 | ||
diff --git a/Documentation/usb/gadget_hid.txt b/Documentation/usb/gadget_hid.txt index 12696c2e43fb..7a0fb8e16e27 100644 --- a/Documentation/usb/gadget_hid.txt +++ b/Documentation/usb/gadget_hid.txt | |||
| @@ -74,6 +74,13 @@ static struct platform_device my_hid = { | |||
| 74 | You can add as many HID functions as you want, only limited by | 74 | You can add as many HID functions as you want, only limited by |
| 75 | the amount of interrupt endpoints your gadget driver supports. | 75 | the amount of interrupt endpoints your gadget driver supports. |
| 76 | 76 | ||
| 77 | Configuration with configfs | ||
| 78 | |||
| 79 | Instead of adding fake platform devices and drivers in order to pass | ||
| 80 | some data to the kernel, if HID is a part of a gadget composed with | ||
| 81 | configfs the hidg_func_descriptor.report_desc is passed to the kernel | ||
| 82 | by writing the appropriate stream of bytes to a configfs attribute. | ||
| 83 | |||
| 77 | Send and receive HID reports | 84 | Send and receive HID reports |
| 78 | 85 | ||
| 79 | HID reports can be sent/received using read/write on the | 86 | HID reports can be sent/received using read/write on the |
diff --git a/Documentation/usb/usb-serial.txt b/Documentation/usb/usb-serial.txt index 5bd7926185e8..947fa62bccf2 100644 --- a/Documentation/usb/usb-serial.txt +++ b/Documentation/usb/usb-serial.txt | |||
| @@ -145,7 +145,7 @@ Keyspan PDA Serial Adapter | |||
| 145 | Single port DB-9 serial adapter, pushed as a PDA adapter for iMacs (mostly | 145 | Single port DB-9 serial adapter, pushed as a PDA adapter for iMacs (mostly |
| 146 | sold in Macintosh catalogs, comes in a translucent white/green dongle). | 146 | sold in Macintosh catalogs, comes in a translucent white/green dongle). |
| 147 | Fairly simple device. Firmware is homebrew. | 147 | Fairly simple device. Firmware is homebrew. |
| 148 | This driver also works for the Xircom/Entrgra single port serial adapter. | 148 | This driver also works for the Xircom/Entrega single port serial adapter. |
| 149 | 149 | ||
| 150 | Current status: | 150 | Current status: |
| 151 | Things that work: | 151 | Things that work: |
diff --git a/arch/arm/boot/dts/am4372.dtsi b/arch/arm/boot/dts/am4372.dtsi index d42d7865dd53..b62a1cd776cd 100644 --- a/arch/arm/boot/dts/am4372.dtsi +++ b/arch/arm/boot/dts/am4372.dtsi | |||
| @@ -843,6 +843,8 @@ | |||
| 843 | maximum-speed = "high-speed"; | 843 | maximum-speed = "high-speed"; |
| 844 | dr_mode = "otg"; | 844 | dr_mode = "otg"; |
| 845 | status = "disabled"; | 845 | status = "disabled"; |
| 846 | snps,dis_u3_susphy_quirk; | ||
| 847 | snps,dis_u2_susphy_quirk; | ||
| 846 | }; | 848 | }; |
| 847 | }; | 849 | }; |
| 848 | 850 | ||
| @@ -865,6 +867,8 @@ | |||
| 865 | maximum-speed = "high-speed"; | 867 | maximum-speed = "high-speed"; |
| 866 | dr_mode = "otg"; | 868 | dr_mode = "otg"; |
| 867 | status = "disabled"; | 869 | status = "disabled"; |
| 870 | snps,dis_u3_susphy_quirk; | ||
| 871 | snps,dis_u2_susphy_quirk; | ||
| 868 | }; | 872 | }; |
| 869 | }; | 873 | }; |
| 870 | 874 | ||
diff --git a/arch/arm/mach-omap2/twl-common.c b/arch/arm/mach-omap2/twl-common.c index b0d54dae1bcb..4457e731f7a4 100644 --- a/arch/arm/mach-omap2/twl-common.c +++ b/arch/arm/mach-omap2/twl-common.c | |||
| @@ -91,18 +91,8 @@ void __init omap_pmic_late_init(void) | |||
| 91 | } | 91 | } |
| 92 | 92 | ||
| 93 | #if defined(CONFIG_ARCH_OMAP3) | 93 | #if defined(CONFIG_ARCH_OMAP3) |
| 94 | struct phy_consumer consumers[] = { | ||
| 95 | PHY_CONSUMER("musb-hdrc.0", "usb"), | ||
| 96 | }; | ||
| 97 | |||
| 98 | struct phy_init_data init_data = { | ||
| 99 | .consumers = consumers, | ||
| 100 | .num_consumers = ARRAY_SIZE(consumers), | ||
| 101 | }; | ||
| 102 | |||
| 103 | static struct twl4030_usb_data omap3_usb_pdata = { | 94 | static struct twl4030_usb_data omap3_usb_pdata = { |
| 104 | .usb_mode = T2_USB_MODE_ULPI, | 95 | .usb_mode = T2_USB_MODE_ULPI, |
| 105 | .init_data = &init_data, | ||
| 106 | }; | 96 | }; |
| 107 | 97 | ||
| 108 | static int omap3_batt_table[] = { | 98 | static int omap3_batt_table[] = { |
diff --git a/arch/mips/cavium-octeon/octeon-platform.c b/arch/mips/cavium-octeon/octeon-platform.c index 6df0f4d8f197..b67ddf0f8bcd 100644 --- a/arch/mips/cavium-octeon/octeon-platform.c +++ b/arch/mips/cavium-octeon/octeon-platform.c | |||
| @@ -7,22 +7,27 @@ | |||
| 7 | * Copyright (C) 2008 Wind River Systems | 7 | * Copyright (C) 2008 Wind River Systems |
| 8 | */ | 8 | */ |
| 9 | 9 | ||
| 10 | #include <linux/delay.h> | ||
| 10 | #include <linux/init.h> | 11 | #include <linux/init.h> |
| 11 | #include <linux/irq.h> | 12 | #include <linux/irq.h> |
| 12 | #include <linux/i2c.h> | 13 | #include <linux/i2c.h> |
| 13 | #include <linux/usb.h> | 14 | #include <linux/usb.h> |
| 14 | #include <linux/dma-mapping.h> | 15 | #include <linux/dma-mapping.h> |
| 15 | #include <linux/module.h> | 16 | #include <linux/module.h> |
| 17 | #include <linux/mutex.h> | ||
| 16 | #include <linux/slab.h> | 18 | #include <linux/slab.h> |
| 17 | #include <linux/platform_device.h> | 19 | #include <linux/platform_device.h> |
| 18 | #include <linux/of_platform.h> | 20 | #include <linux/of_platform.h> |
| 19 | #include <linux/of_fdt.h> | 21 | #include <linux/of_fdt.h> |
| 20 | #include <linux/libfdt.h> | 22 | #include <linux/libfdt.h> |
| 23 | #include <linux/usb/ehci_pdriver.h> | ||
| 24 | #include <linux/usb/ohci_pdriver.h> | ||
| 21 | 25 | ||
| 22 | #include <asm/octeon/octeon.h> | 26 | #include <asm/octeon/octeon.h> |
| 23 | #include <asm/octeon/cvmx-rnm-defs.h> | 27 | #include <asm/octeon/cvmx-rnm-defs.h> |
| 24 | #include <asm/octeon/cvmx-helper.h> | 28 | #include <asm/octeon/cvmx-helper.h> |
| 25 | #include <asm/octeon/cvmx-helper-board.h> | 29 | #include <asm/octeon/cvmx-helper-board.h> |
| 30 | #include <asm/octeon/cvmx-uctlx-defs.h> | ||
| 26 | 31 | ||
| 27 | /* Octeon Random Number Generator. */ | 32 | /* Octeon Random Number Generator. */ |
| 28 | static int __init octeon_rng_device_init(void) | 33 | static int __init octeon_rng_device_init(void) |
| @@ -68,6 +73,229 @@ device_initcall(octeon_rng_device_init); | |||
| 68 | 73 | ||
| 69 | #ifdef CONFIG_USB | 74 | #ifdef CONFIG_USB |
| 70 | 75 | ||
| 76 | static DEFINE_MUTEX(octeon2_usb_clocks_mutex); | ||
| 77 | |||
| 78 | static int octeon2_usb_clock_start_cnt; | ||
| 79 | |||
| 80 | static void octeon2_usb_clocks_start(void) | ||
| 81 | { | ||
| 82 | u64 div; | ||
| 83 | union cvmx_uctlx_if_ena if_ena; | ||
| 84 | union cvmx_uctlx_clk_rst_ctl clk_rst_ctl; | ||
| 85 | union cvmx_uctlx_uphy_ctl_status uphy_ctl_status; | ||
| 86 | union cvmx_uctlx_uphy_portx_ctl_status port_ctl_status; | ||
| 87 | int i; | ||
| 88 | unsigned long io_clk_64_to_ns; | ||
| 89 | |||
| 90 | |||
| 91 | mutex_lock(&octeon2_usb_clocks_mutex); | ||
| 92 | |||
| 93 | octeon2_usb_clock_start_cnt++; | ||
| 94 | if (octeon2_usb_clock_start_cnt != 1) | ||
| 95 | goto exit; | ||
| 96 | |||
| 97 | io_clk_64_to_ns = 64000000000ull / octeon_get_io_clock_rate(); | ||
| 98 | |||
| 99 | /* | ||
| 100 | * Step 1: Wait for voltages stable. That surely happened | ||
| 101 | * before starting the kernel. | ||
| 102 | * | ||
| 103 | * Step 2: Enable SCLK of UCTL by writing UCTL0_IF_ENA[EN] = 1 | ||
| 104 | */ | ||
| 105 | if_ena.u64 = 0; | ||
| 106 | if_ena.s.en = 1; | ||
| 107 | cvmx_write_csr(CVMX_UCTLX_IF_ENA(0), if_ena.u64); | ||
| 108 | |||
| 109 | /* Step 3: Configure the reference clock, PHY, and HCLK */ | ||
| 110 | clk_rst_ctl.u64 = cvmx_read_csr(CVMX_UCTLX_CLK_RST_CTL(0)); | ||
| 111 | |||
| 112 | /* | ||
| 113 | * If the UCTL looks like it has already been started, skip | ||
| 114 | * the initialization, otherwise bus errors are obtained. | ||
| 115 | */ | ||
| 116 | if (clk_rst_ctl.s.hrst) | ||
| 117 | goto end_clock; | ||
| 118 | /* 3a */ | ||
| 119 | clk_rst_ctl.s.p_por = 1; | ||
| 120 | clk_rst_ctl.s.hrst = 0; | ||
| 121 | clk_rst_ctl.s.p_prst = 0; | ||
| 122 | clk_rst_ctl.s.h_clkdiv_rst = 0; | ||
| 123 | clk_rst_ctl.s.o_clkdiv_rst = 0; | ||
| 124 | clk_rst_ctl.s.h_clkdiv_en = 0; | ||
| 125 | clk_rst_ctl.s.o_clkdiv_en = 0; | ||
| 126 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 127 | |||
| 128 | /* 3b */ | ||
| 129 | /* 12MHz crystal. */ | ||
| 130 | clk_rst_ctl.s.p_refclk_sel = 0; | ||
| 131 | clk_rst_ctl.s.p_refclk_div = 0; | ||
| 132 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 133 | |||
| 134 | /* 3c */ | ||
| 135 | div = octeon_get_io_clock_rate() / 130000000ull; | ||
| 136 | |||
| 137 | switch (div) { | ||
| 138 | case 0: | ||
| 139 | div = 1; | ||
| 140 | break; | ||
| 141 | case 1: | ||
| 142 | case 2: | ||
| 143 | case 3: | ||
| 144 | case 4: | ||
| 145 | break; | ||
| 146 | case 5: | ||
| 147 | div = 4; | ||
| 148 | break; | ||
| 149 | case 6: | ||
| 150 | case 7: | ||
| 151 | div = 6; | ||
| 152 | break; | ||
| 153 | case 8: | ||
| 154 | case 9: | ||
| 155 | case 10: | ||
| 156 | case 11: | ||
| 157 | div = 8; | ||
| 158 | break; | ||
| 159 | default: | ||
| 160 | div = 12; | ||
| 161 | break; | ||
| 162 | } | ||
| 163 | clk_rst_ctl.s.h_div = div; | ||
| 164 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 165 | /* Read it back, */ | ||
| 166 | clk_rst_ctl.u64 = cvmx_read_csr(CVMX_UCTLX_CLK_RST_CTL(0)); | ||
| 167 | clk_rst_ctl.s.h_clkdiv_en = 1; | ||
| 168 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 169 | /* 3d */ | ||
| 170 | clk_rst_ctl.s.h_clkdiv_rst = 1; | ||
| 171 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 172 | |||
| 173 | /* 3e: delay 64 io clocks */ | ||
| 174 | ndelay(io_clk_64_to_ns); | ||
| 175 | |||
| 176 | /* | ||
| 177 | * Step 4: Program the power-on reset field in the UCTL | ||
| 178 | * clock-reset-control register. | ||
| 179 | */ | ||
| 180 | clk_rst_ctl.s.p_por = 0; | ||
| 181 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 182 | |||
| 183 | /* Step 5: Wait 1 ms for the PHY clock to start. */ | ||
| 184 | mdelay(1); | ||
| 185 | |||
| 186 | /* | ||
| 187 | * Step 6: Program the reset input from automatic test | ||
| 188 | * equipment field in the UPHY CSR | ||
| 189 | */ | ||
| 190 | uphy_ctl_status.u64 = cvmx_read_csr(CVMX_UCTLX_UPHY_CTL_STATUS(0)); | ||
| 191 | uphy_ctl_status.s.ate_reset = 1; | ||
| 192 | cvmx_write_csr(CVMX_UCTLX_UPHY_CTL_STATUS(0), uphy_ctl_status.u64); | ||
| 193 | |||
| 194 | /* Step 7: Wait for at least 10ns. */ | ||
| 195 | ndelay(10); | ||
| 196 | |||
| 197 | /* Step 8: Clear the ATE_RESET field in the UPHY CSR. */ | ||
| 198 | uphy_ctl_status.s.ate_reset = 0; | ||
| 199 | cvmx_write_csr(CVMX_UCTLX_UPHY_CTL_STATUS(0), uphy_ctl_status.u64); | ||
| 200 | |||
| 201 | /* | ||
| 202 | * Step 9: Wait for at least 20ns for UPHY to output PHY clock | ||
| 203 | * signals and OHCI_CLK48 | ||
| 204 | */ | ||
| 205 | ndelay(20); | ||
| 206 | |||
| 207 | /* Step 10: Configure the OHCI_CLK48 and OHCI_CLK12 clocks. */ | ||
| 208 | /* 10a */ | ||
| 209 | clk_rst_ctl.s.o_clkdiv_rst = 1; | ||
| 210 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 211 | |||
| 212 | /* 10b */ | ||
| 213 | clk_rst_ctl.s.o_clkdiv_en = 1; | ||
| 214 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 215 | |||
| 216 | /* 10c */ | ||
| 217 | ndelay(io_clk_64_to_ns); | ||
| 218 | |||
| 219 | /* | ||
| 220 | * Step 11: Program the PHY reset field: | ||
| 221 | * UCTL0_CLK_RST_CTL[P_PRST] = 1 | ||
| 222 | */ | ||
| 223 | clk_rst_ctl.s.p_prst = 1; | ||
| 224 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 225 | |||
| 226 | /* Step 12: Wait 1 uS. */ | ||
| 227 | udelay(1); | ||
| 228 | |||
| 229 | /* Step 13: Program the HRESET_N field: UCTL0_CLK_RST_CTL[HRST] = 1 */ | ||
| 230 | clk_rst_ctl.s.hrst = 1; | ||
| 231 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 232 | |||
| 233 | end_clock: | ||
| 234 | /* Now we can set some other registers. */ | ||
| 235 | |||
| 236 | for (i = 0; i <= 1; i++) { | ||
| 237 | port_ctl_status.u64 = | ||
| 238 | cvmx_read_csr(CVMX_UCTLX_UPHY_PORTX_CTL_STATUS(i, 0)); | ||
| 239 | /* Set txvreftune to 15 to obtain compliant 'eye' diagram. */ | ||
| 240 | port_ctl_status.s.txvreftune = 15; | ||
| 241 | port_ctl_status.s.txrisetune = 1; | ||
| 242 | port_ctl_status.s.txpreemphasistune = 1; | ||
| 243 | cvmx_write_csr(CVMX_UCTLX_UPHY_PORTX_CTL_STATUS(i, 0), | ||
| 244 | port_ctl_status.u64); | ||
| 245 | } | ||
| 246 | |||
| 247 | /* Set uSOF cycle period to 60,000 bits. */ | ||
| 248 | cvmx_write_csr(CVMX_UCTLX_EHCI_FLA(0), 0x20ull); | ||
| 249 | exit: | ||
| 250 | mutex_unlock(&octeon2_usb_clocks_mutex); | ||
| 251 | } | ||
| 252 | |||
| 253 | static void octeon2_usb_clocks_stop(void) | ||
| 254 | { | ||
| 255 | mutex_lock(&octeon2_usb_clocks_mutex); | ||
| 256 | octeon2_usb_clock_start_cnt--; | ||
| 257 | mutex_unlock(&octeon2_usb_clocks_mutex); | ||
| 258 | } | ||
| 259 | |||
| 260 | static int octeon_ehci_power_on(struct platform_device *pdev) | ||
| 261 | { | ||
| 262 | octeon2_usb_clocks_start(); | ||
| 263 | return 0; | ||
| 264 | } | ||
| 265 | |||
| 266 | static void octeon_ehci_power_off(struct platform_device *pdev) | ||
| 267 | { | ||
| 268 | octeon2_usb_clocks_stop(); | ||
| 269 | } | ||
| 270 | |||
| 271 | static struct usb_ehci_pdata octeon_ehci_pdata = { | ||
| 272 | /* Octeon EHCI matches CPU endianness. */ | ||
| 273 | #ifdef __BIG_ENDIAN | ||
| 274 | .big_endian_mmio = 1, | ||
| 275 | #endif | ||
| 276 | .power_on = octeon_ehci_power_on, | ||
| 277 | .power_off = octeon_ehci_power_off, | ||
| 278 | }; | ||
| 279 | |||
| 280 | static void __init octeon_ehci_hw_start(void) | ||
| 281 | { | ||
| 282 | union cvmx_uctlx_ehci_ctl ehci_ctl; | ||
| 283 | |||
| 284 | octeon2_usb_clocks_start(); | ||
| 285 | |||
| 286 | ehci_ctl.u64 = cvmx_read_csr(CVMX_UCTLX_EHCI_CTL(0)); | ||
| 287 | /* Use 64-bit addressing. */ | ||
| 288 | ehci_ctl.s.ehci_64b_addr_en = 1; | ||
| 289 | ehci_ctl.s.l2c_addr_msb = 0; | ||
| 290 | ehci_ctl.s.l2c_buff_emod = 1; /* Byte swapped. */ | ||
| 291 | ehci_ctl.s.l2c_desc_emod = 1; /* Byte swapped. */ | ||
| 292 | cvmx_write_csr(CVMX_UCTLX_EHCI_CTL(0), ehci_ctl.u64); | ||
| 293 | |||
| 294 | octeon2_usb_clocks_stop(); | ||
| 295 | } | ||
| 296 | |||
| 297 | static u64 octeon_ehci_dma_mask = DMA_BIT_MASK(64); | ||
| 298 | |||
| 71 | static int __init octeon_ehci_device_init(void) | 299 | static int __init octeon_ehci_device_init(void) |
| 72 | { | 300 | { |
| 73 | struct platform_device *pd; | 301 | struct platform_device *pd; |
| @@ -88,7 +316,7 @@ static int __init octeon_ehci_device_init(void) | |||
| 88 | if (octeon_is_simulation() || usb_disabled()) | 316 | if (octeon_is_simulation() || usb_disabled()) |
| 89 | return 0; /* No USB in the simulator. */ | 317 | return 0; /* No USB in the simulator. */ |
| 90 | 318 | ||
| 91 | pd = platform_device_alloc("octeon-ehci", 0); | 319 | pd = platform_device_alloc("ehci-platform", 0); |
| 92 | if (!pd) { | 320 | if (!pd) { |
| 93 | ret = -ENOMEM; | 321 | ret = -ENOMEM; |
| 94 | goto out; | 322 | goto out; |
| @@ -105,6 +333,10 @@ static int __init octeon_ehci_device_init(void) | |||
| 105 | if (ret) | 333 | if (ret) |
| 106 | goto fail; | 334 | goto fail; |
| 107 | 335 | ||
| 336 | pd->dev.dma_mask = &octeon_ehci_dma_mask; | ||
| 337 | pd->dev.platform_data = &octeon_ehci_pdata; | ||
| 338 | octeon_ehci_hw_start(); | ||
| 339 | |||
| 108 | ret = platform_device_add(pd); | 340 | ret = platform_device_add(pd); |
| 109 | if (ret) | 341 | if (ret) |
| 110 | goto fail; | 342 | goto fail; |
| @@ -117,6 +349,41 @@ out: | |||
| 117 | } | 349 | } |
| 118 | device_initcall(octeon_ehci_device_init); | 350 | device_initcall(octeon_ehci_device_init); |
| 119 | 351 | ||
| 352 | static int octeon_ohci_power_on(struct platform_device *pdev) | ||
| 353 | { | ||
| 354 | octeon2_usb_clocks_start(); | ||
| 355 | return 0; | ||
| 356 | } | ||
| 357 | |||
| 358 | static void octeon_ohci_power_off(struct platform_device *pdev) | ||
| 359 | { | ||
| 360 | octeon2_usb_clocks_stop(); | ||
| 361 | } | ||
| 362 | |||
| 363 | static struct usb_ohci_pdata octeon_ohci_pdata = { | ||
| 364 | /* Octeon OHCI matches CPU endianness. */ | ||
| 365 | #ifdef __BIG_ENDIAN | ||
| 366 | .big_endian_mmio = 1, | ||
| 367 | #endif | ||
| 368 | .power_on = octeon_ohci_power_on, | ||
| 369 | .power_off = octeon_ohci_power_off, | ||
| 370 | }; | ||
| 371 | |||
| 372 | static void __init octeon_ohci_hw_start(void) | ||
| 373 | { | ||
| 374 | union cvmx_uctlx_ohci_ctl ohci_ctl; | ||
| 375 | |||
| 376 | octeon2_usb_clocks_start(); | ||
| 377 | |||
| 378 | ohci_ctl.u64 = cvmx_read_csr(CVMX_UCTLX_OHCI_CTL(0)); | ||
| 379 | ohci_ctl.s.l2c_addr_msb = 0; | ||
| 380 | ohci_ctl.s.l2c_buff_emod = 1; /* Byte swapped. */ | ||
| 381 | ohci_ctl.s.l2c_desc_emod = 1; /* Byte swapped. */ | ||
| 382 | cvmx_write_csr(CVMX_UCTLX_OHCI_CTL(0), ohci_ctl.u64); | ||
| 383 | |||
| 384 | octeon2_usb_clocks_stop(); | ||
| 385 | } | ||
| 386 | |||
| 120 | static int __init octeon_ohci_device_init(void) | 387 | static int __init octeon_ohci_device_init(void) |
| 121 | { | 388 | { |
| 122 | struct platform_device *pd; | 389 | struct platform_device *pd; |
| @@ -137,7 +404,7 @@ static int __init octeon_ohci_device_init(void) | |||
| 137 | if (octeon_is_simulation() || usb_disabled()) | 404 | if (octeon_is_simulation() || usb_disabled()) |
| 138 | return 0; /* No USB in the simulator. */ | 405 | return 0; /* No USB in the simulator. */ |
| 139 | 406 | ||
| 140 | pd = platform_device_alloc("octeon-ohci", 0); | 407 | pd = platform_device_alloc("ohci-platform", 0); |
| 141 | if (!pd) { | 408 | if (!pd) { |
| 142 | ret = -ENOMEM; | 409 | ret = -ENOMEM; |
| 143 | goto out; | 410 | goto out; |
| @@ -154,6 +421,9 @@ static int __init octeon_ohci_device_init(void) | |||
| 154 | if (ret) | 421 | if (ret) |
| 155 | goto fail; | 422 | goto fail; |
| 156 | 423 | ||
| 424 | pd->dev.platform_data = &octeon_ohci_pdata; | ||
| 425 | octeon_ohci_hw_start(); | ||
| 426 | |||
| 157 | ret = platform_device_add(pd); | 427 | ret = platform_device_add(pd); |
| 158 | if (ret) | 428 | if (ret) |
| 159 | goto fail; | 429 | goto fail; |
diff --git a/arch/mips/configs/cavium_octeon_defconfig b/arch/mips/configs/cavium_octeon_defconfig index b2476a1c4aaa..e57058d4ec22 100644 --- a/arch/mips/configs/cavium_octeon_defconfig +++ b/arch/mips/configs/cavium_octeon_defconfig | |||
| @@ -120,6 +120,9 @@ CONFIG_SPI_OCTEON=y | |||
| 120 | # CONFIG_HWMON is not set | 120 | # CONFIG_HWMON is not set |
| 121 | CONFIG_WATCHDOG=y | 121 | CONFIG_WATCHDOG=y |
| 122 | # CONFIG_USB_SUPPORT is not set | 122 | # CONFIG_USB_SUPPORT is not set |
| 123 | CONFIG_USB_EHCI_BIG_ENDIAN_MMIO=y | ||
| 124 | CONFIG_USB_OHCI_BIG_ENDIAN_MMIO=y | ||
| 125 | CONFIG_USB_OHCI_LITTLE_ENDIAN=y | ||
| 123 | CONFIG_RTC_CLASS=y | 126 | CONFIG_RTC_CLASS=y |
| 124 | CONFIG_RTC_DRV_DS1307=y | 127 | CONFIG_RTC_DRV_DS1307=y |
| 125 | CONFIG_STAGING=y | 128 | CONFIG_STAGING=y |
diff --git a/drivers/pci/quirks.c b/drivers/pci/quirks.c index 90acb32c85b1..ed6f89b6efe5 100644 --- a/drivers/pci/quirks.c +++ b/drivers/pci/quirks.c | |||
| @@ -379,6 +379,26 @@ static void quirk_ati_exploding_mce(struct pci_dev *dev) | |||
| 379 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_RS100, quirk_ati_exploding_mce); | 379 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_RS100, quirk_ati_exploding_mce); |
| 380 | 380 | ||
| 381 | /* | 381 | /* |
| 382 | * In the AMD NL platform, this device ([1022:7912]) has a class code of | ||
| 383 | * PCI_CLASS_SERIAL_USB_XHCI (0x0c0330), which means the xhci driver will | ||
| 384 | * claim it. | ||
| 385 | * But the dwc3 driver is a more specific driver for this device, and we'd | ||
| 386 | * prefer to use it instead of xhci. To prevent xhci from claiming the | ||
| 387 | * device, change the class code to 0x0c03fe, which the PCI r3.0 spec | ||
| 388 | * defines as "USB device (not host controller)". The dwc3 driver can then | ||
| 389 | * claim it based on its Vendor and Device ID. | ||
| 390 | */ | ||
| 391 | static void quirk_amd_nl_class(struct pci_dev *pdev) | ||
| 392 | { | ||
| 393 | /* | ||
| 394 | * Use 'USB Device' (0x0c03fe) instead of PCI header provided | ||
| 395 | */ | ||
| 396 | pdev->class = 0x0c03fe; | ||
| 397 | } | ||
| 398 | DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_NL_USB, | ||
| 399 | quirk_amd_nl_class); | ||
| 400 | |||
| 401 | /* | ||
| 382 | * Let's make the southbridge information explicit instead | 402 | * Let's make the southbridge information explicit instead |
| 383 | * of having to worry about people probing the ACPI areas, | 403 | * of having to worry about people probing the ACPI areas, |
| 384 | * for example.. (Yes, it happens, and if you read the wrong | 404 | * for example.. (Yes, it happens, and if you read the wrong |
diff --git a/drivers/phy/Kconfig b/drivers/phy/Kconfig index 2a436e607f99..ccad8809ecb1 100644 --- a/drivers/phy/Kconfig +++ b/drivers/phy/Kconfig | |||
| @@ -15,6 +15,13 @@ config GENERIC_PHY | |||
| 15 | phy users can obtain reference to the PHY. All the users of this | 15 | phy users can obtain reference to the PHY. All the users of this |
| 16 | framework should select this config. | 16 | framework should select this config. |
| 17 | 17 | ||
| 18 | config PHY_BERLIN_USB | ||
| 19 | tristate "Marvell Berlin USB PHY Driver" | ||
| 20 | depends on ARCH_BERLIN && RESET_CONTROLLER && HAS_IOMEM && OF | ||
| 21 | select GENERIC_PHY | ||
| 22 | help | ||
| 23 | Enable this to support the USB PHY on Marvell Berlin SoCs. | ||
| 24 | |||
| 18 | config PHY_BERLIN_SATA | 25 | config PHY_BERLIN_SATA |
| 19 | tristate "Marvell Berlin SATA PHY driver" | 26 | tristate "Marvell Berlin SATA PHY driver" |
| 20 | depends on ARCH_BERLIN && HAS_IOMEM && OF | 27 | depends on ARCH_BERLIN && HAS_IOMEM && OF |
| @@ -22,6 +29,12 @@ config PHY_BERLIN_SATA | |||
| 22 | help | 29 | help |
| 23 | Enable this to support the SATA PHY on Marvell Berlin SoCs. | 30 | Enable this to support the SATA PHY on Marvell Berlin SoCs. |
| 24 | 31 | ||
| 32 | config ARMADA375_USBCLUSTER_PHY | ||
| 33 | def_bool y | ||
| 34 | depends on MACH_ARMADA_375 || COMPILE_TEST | ||
| 35 | depends on OF | ||
| 36 | select GENERIC_PHY | ||
| 37 | |||
| 25 | config PHY_EXYNOS_MIPI_VIDEO | 38 | config PHY_EXYNOS_MIPI_VIDEO |
| 26 | tristate "S5P/EXYNOS SoC series MIPI CSI-2/DSI PHY driver" | 39 | tristate "S5P/EXYNOS SoC series MIPI CSI-2/DSI PHY driver" |
| 27 | depends on HAS_IOMEM | 40 | depends on HAS_IOMEM |
| @@ -38,6 +51,14 @@ config PHY_MVEBU_SATA | |||
| 38 | depends on OF | 51 | depends on OF |
| 39 | select GENERIC_PHY | 52 | select GENERIC_PHY |
| 40 | 53 | ||
| 54 | config PHY_MIPHY28LP | ||
| 55 | tristate "STMicroelectronics MIPHY28LP PHY driver for STiH407" | ||
| 56 | depends on ARCH_STI | ||
| 57 | select GENERIC_PHY | ||
| 58 | help | ||
| 59 | Enable this to support the miphy transceiver (for SATA/PCIE/USB3) | ||
| 60 | that is part of STMicroelectronics STiH407 SoC. | ||
| 61 | |||
| 41 | config PHY_MIPHY365X | 62 | config PHY_MIPHY365X |
| 42 | tristate "STMicroelectronics MIPHY365X PHY driver for STiH41x series" | 63 | tristate "STMicroelectronics MIPHY365X PHY driver for STiH41x series" |
| 43 | depends on ARCH_STI | 64 | depends on ARCH_STI |
| @@ -193,7 +214,7 @@ config PHY_EXYNOS5250_USB2 | |||
| 193 | 214 | ||
| 194 | config PHY_EXYNOS5_USBDRD | 215 | config PHY_EXYNOS5_USBDRD |
| 195 | tristate "Exynos5 SoC series USB DRD PHY driver" | 216 | tristate "Exynos5 SoC series USB DRD PHY driver" |
| 196 | depends on ARCH_EXYNOS5 && OF | 217 | depends on ARCH_EXYNOS && OF |
| 197 | depends on HAS_IOMEM | 218 | depends on HAS_IOMEM |
| 198 | depends on USB_DWC3_EXYNOS | 219 | depends on USB_DWC3_EXYNOS |
| 199 | select GENERIC_PHY | 220 | select GENERIC_PHY |
diff --git a/drivers/phy/Makefile b/drivers/phy/Makefile index c4590fce082f..aa74f961e44e 100644 --- a/drivers/phy/Makefile +++ b/drivers/phy/Makefile | |||
| @@ -3,11 +3,14 @@ | |||
| 3 | # | 3 | # |
| 4 | 4 | ||
| 5 | obj-$(CONFIG_GENERIC_PHY) += phy-core.o | 5 | obj-$(CONFIG_GENERIC_PHY) += phy-core.o |
| 6 | obj-$(CONFIG_PHY_BERLIN_USB) += phy-berlin-usb.o | ||
| 6 | obj-$(CONFIG_PHY_BERLIN_SATA) += phy-berlin-sata.o | 7 | obj-$(CONFIG_PHY_BERLIN_SATA) += phy-berlin-sata.o |
| 8 | obj-$(CONFIG_ARMADA375_USBCLUSTER_PHY) += phy-armada375-usb2.o | ||
| 7 | obj-$(CONFIG_BCM_KONA_USB2_PHY) += phy-bcm-kona-usb2.o | 9 | obj-$(CONFIG_BCM_KONA_USB2_PHY) += phy-bcm-kona-usb2.o |
| 8 | obj-$(CONFIG_PHY_EXYNOS_DP_VIDEO) += phy-exynos-dp-video.o | 10 | obj-$(CONFIG_PHY_EXYNOS_DP_VIDEO) += phy-exynos-dp-video.o |
| 9 | obj-$(CONFIG_PHY_EXYNOS_MIPI_VIDEO) += phy-exynos-mipi-video.o | 11 | obj-$(CONFIG_PHY_EXYNOS_MIPI_VIDEO) += phy-exynos-mipi-video.o |
| 10 | obj-$(CONFIG_PHY_MVEBU_SATA) += phy-mvebu-sata.o | 12 | obj-$(CONFIG_PHY_MVEBU_SATA) += phy-mvebu-sata.o |
| 13 | obj-$(CONFIG_PHY_MIPHY28LP) += phy-miphy28lp.o | ||
| 11 | obj-$(CONFIG_PHY_MIPHY365X) += phy-miphy365x.o | 14 | obj-$(CONFIG_PHY_MIPHY365X) += phy-miphy365x.o |
| 12 | obj-$(CONFIG_PHY_RCAR_GEN2) += phy-rcar-gen2.o | 15 | obj-$(CONFIG_PHY_RCAR_GEN2) += phy-rcar-gen2.o |
| 13 | obj-$(CONFIG_OMAP_CONTROL_PHY) += phy-omap-control.o | 16 | obj-$(CONFIG_OMAP_CONTROL_PHY) += phy-omap-control.o |
diff --git a/drivers/phy/phy-armada375-usb2.c b/drivers/phy/phy-armada375-usb2.c new file mode 100644 index 000000000000..ac7d99d01cb3 --- /dev/null +++ b/drivers/phy/phy-armada375-usb2.c | |||
| @@ -0,0 +1,158 @@ | |||
| 1 | /* | ||
| 2 | * USB cluster support for Armada 375 platform. | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Marvell | ||
| 5 | * | ||
| 6 | * Gregory CLEMENT <gregory.clement@free-electrons.com> | ||
| 7 | * | ||
| 8 | * This file is licensed under the terms of the GNU General Public | ||
| 9 | * License version 2 or later. This program is licensed "as is" | ||
| 10 | * without any warranty of any kind, whether express or implied. | ||
| 11 | * | ||
| 12 | * Armada 375 comes with an USB2 host and device controller and an | ||
| 13 | * USB3 controller. The USB cluster control register allows to manage | ||
| 14 | * common features of both USB controllers. | ||
| 15 | */ | ||
| 16 | |||
| 17 | #include <dt-bindings/phy/phy.h> | ||
| 18 | #include <linux/init.h> | ||
| 19 | #include <linux/io.h> | ||
| 20 | #include <linux/kernel.h> | ||
| 21 | #include <linux/module.h> | ||
| 22 | #include <linux/of_address.h> | ||
| 23 | #include <linux/phy/phy.h> | ||
| 24 | #include <linux/platform_device.h> | ||
| 25 | |||
| 26 | #define USB2_PHY_CONFIG_DISABLE BIT(0) | ||
| 27 | |||
| 28 | struct armada375_cluster_phy { | ||
| 29 | struct phy *phy; | ||
| 30 | void __iomem *reg; | ||
| 31 | bool use_usb3; | ||
| 32 | int phy_provided; | ||
| 33 | }; | ||
| 34 | |||
| 35 | static int armada375_usb_phy_init(struct phy *phy) | ||
| 36 | { | ||
| 37 | struct armada375_cluster_phy *cluster_phy; | ||
| 38 | u32 reg; | ||
| 39 | |||
| 40 | cluster_phy = dev_get_drvdata(phy->dev.parent); | ||
| 41 | if (!cluster_phy) | ||
| 42 | return -ENODEV; | ||
| 43 | |||
| 44 | reg = readl(cluster_phy->reg); | ||
| 45 | if (cluster_phy->use_usb3) | ||
| 46 | reg |= USB2_PHY_CONFIG_DISABLE; | ||
| 47 | else | ||
| 48 | reg &= ~USB2_PHY_CONFIG_DISABLE; | ||
| 49 | writel(reg, cluster_phy->reg); | ||
| 50 | |||
| 51 | return 0; | ||
| 52 | } | ||
| 53 | |||
| 54 | static struct phy_ops armada375_usb_phy_ops = { | ||
| 55 | .init = armada375_usb_phy_init, | ||
| 56 | .owner = THIS_MODULE, | ||
| 57 | }; | ||
| 58 | |||
| 59 | /* | ||
| 60 | * Only one controller can use this PHY. We shouldn't have the case | ||
| 61 | * when two controllers want to use this PHY. But if this case occurs | ||
| 62 | * then we provide a phy to the first one and return an error for the | ||
| 63 | * next one. This error has also to be an error returned by | ||
| 64 | * devm_phy_optional_get() so different from ENODEV for USB2. In the | ||
| 65 | * USB3 case it still optional and we use ENODEV. | ||
| 66 | */ | ||
| 67 | static struct phy *armada375_usb_phy_xlate(struct device *dev, | ||
| 68 | struct of_phandle_args *args) | ||
| 69 | { | ||
| 70 | struct armada375_cluster_phy *cluster_phy = dev_get_drvdata(dev); | ||
| 71 | |||
| 72 | if (!cluster_phy) | ||
| 73 | return ERR_PTR(-ENODEV); | ||
| 74 | |||
| 75 | /* | ||
| 76 | * Either the phy had never been requested and then the first | ||
| 77 | * usb claiming it can get it, or it had already been | ||
| 78 | * requested in this case, we only allow to use it with the | ||
| 79 | * same configuration. | ||
| 80 | */ | ||
| 81 | if (WARN_ON((cluster_phy->phy_provided != PHY_NONE) && | ||
| 82 | (cluster_phy->phy_provided != args->args[0]))) { | ||
| 83 | dev_err(dev, "This PHY has already been provided!\n"); | ||
| 84 | dev_err(dev, "Check your device tree, only one controller can use it\n."); | ||
| 85 | if (args->args[0] == PHY_TYPE_USB2) | ||
| 86 | return ERR_PTR(-EBUSY); | ||
| 87 | else | ||
| 88 | return ERR_PTR(-ENODEV); | ||
| 89 | } | ||
| 90 | |||
| 91 | if (args->args[0] == PHY_TYPE_USB2) | ||
| 92 | cluster_phy->use_usb3 = false; | ||
| 93 | else if (args->args[0] == PHY_TYPE_USB3) | ||
| 94 | cluster_phy->use_usb3 = true; | ||
| 95 | else { | ||
| 96 | dev_err(dev, "Invalid PHY mode\n"); | ||
| 97 | return ERR_PTR(-ENODEV); | ||
| 98 | } | ||
| 99 | |||
| 100 | /* Store which phy mode is used for next test */ | ||
| 101 | cluster_phy->phy_provided = args->args[0]; | ||
| 102 | |||
| 103 | return cluster_phy->phy; | ||
| 104 | } | ||
| 105 | |||
| 106 | static int armada375_usb_phy_probe(struct platform_device *pdev) | ||
| 107 | { | ||
| 108 | struct device *dev = &pdev->dev; | ||
| 109 | struct phy *phy; | ||
| 110 | struct phy_provider *phy_provider; | ||
| 111 | void __iomem *usb_cluster_base; | ||
| 112 | struct resource *res; | ||
| 113 | struct armada375_cluster_phy *cluster_phy; | ||
| 114 | |||
| 115 | cluster_phy = devm_kzalloc(dev, sizeof(*cluster_phy), GFP_KERNEL); | ||
| 116 | if (!cluster_phy) | ||
| 117 | return -ENOMEM; | ||
| 118 | |||
| 119 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 120 | usb_cluster_base = devm_ioremap_resource(&pdev->dev, res); | ||
| 121 | if (!usb_cluster_base) | ||
| 122 | return -ENOMEM; | ||
| 123 | |||
| 124 | phy = devm_phy_create(dev, NULL, &armada375_usb_phy_ops); | ||
| 125 | if (IS_ERR(phy)) { | ||
| 126 | dev_err(dev, "failed to create PHY\n"); | ||
| 127 | return PTR_ERR(phy); | ||
| 128 | } | ||
| 129 | |||
| 130 | cluster_phy->phy = phy; | ||
| 131 | cluster_phy->reg = usb_cluster_base; | ||
| 132 | |||
| 133 | dev_set_drvdata(dev, cluster_phy); | ||
| 134 | |||
| 135 | phy_provider = devm_of_phy_provider_register(&pdev->dev, | ||
| 136 | armada375_usb_phy_xlate); | ||
| 137 | return PTR_ERR_OR_ZERO(phy_provider); | ||
| 138 | } | ||
| 139 | |||
| 140 | static const struct of_device_id of_usb_cluster_table[] = { | ||
| 141 | { .compatible = "marvell,armada-375-usb-cluster", }, | ||
| 142 | { /* end of list */ }, | ||
| 143 | }; | ||
| 144 | MODULE_DEVICE_TABLE(of, of_usb_cluster_table); | ||
| 145 | |||
| 146 | static struct platform_driver armada375_usb_phy_driver = { | ||
| 147 | .probe = armada375_usb_phy_probe, | ||
| 148 | .driver = { | ||
| 149 | .of_match_table = of_usb_cluster_table, | ||
| 150 | .name = "armada-375-usb-cluster", | ||
| 151 | .owner = THIS_MODULE, | ||
| 152 | } | ||
| 153 | }; | ||
| 154 | module_platform_driver(armada375_usb_phy_driver); | ||
| 155 | |||
| 156 | MODULE_DESCRIPTION("Armada 375 USB cluster driver"); | ||
| 157 | MODULE_AUTHOR("Gregory CLEMENT <gregory.clement@free-electrons.com>"); | ||
| 158 | MODULE_LICENSE("GPL"); | ||
diff --git a/drivers/phy/phy-bcm-kona-usb2.c b/drivers/phy/phy-bcm-kona-usb2.c index c1e0ca335c0e..ef2dc1aab2b9 100644 --- a/drivers/phy/phy-bcm-kona-usb2.c +++ b/drivers/phy/phy-bcm-kona-usb2.c | |||
| @@ -117,7 +117,7 @@ static int bcm_kona_usb2_probe(struct platform_device *pdev) | |||
| 117 | 117 | ||
| 118 | platform_set_drvdata(pdev, phy); | 118 | platform_set_drvdata(pdev, phy); |
| 119 | 119 | ||
| 120 | gphy = devm_phy_create(dev, NULL, &ops, NULL); | 120 | gphy = devm_phy_create(dev, NULL, &ops); |
| 121 | if (IS_ERR(gphy)) | 121 | if (IS_ERR(gphy)) |
| 122 | return PTR_ERR(gphy); | 122 | return PTR_ERR(gphy); |
| 123 | 123 | ||
diff --git a/drivers/phy/phy-berlin-sata.c b/drivers/phy/phy-berlin-sata.c index 69ced52d72aa..099eee8851e5 100644 --- a/drivers/phy/phy-berlin-sata.c +++ b/drivers/phy/phy-berlin-sata.c | |||
| @@ -30,7 +30,8 @@ | |||
| 30 | #define MBUS_WRITE_REQUEST_SIZE_128 (BIT(2) << 16) | 30 | #define MBUS_WRITE_REQUEST_SIZE_128 (BIT(2) << 16) |
| 31 | #define MBUS_READ_REQUEST_SIZE_128 (BIT(2) << 19) | 31 | #define MBUS_READ_REQUEST_SIZE_128 (BIT(2) << 19) |
| 32 | 32 | ||
| 33 | #define PHY_BASE 0x200 | 33 | #define BG2_PHY_BASE 0x080 |
| 34 | #define BG2Q_PHY_BASE 0x200 | ||
| 34 | 35 | ||
| 35 | /* register 0x01 */ | 36 | /* register 0x01 */ |
| 36 | #define REF_FREF_SEL_25 BIT(0) | 37 | #define REF_FREF_SEL_25 BIT(0) |
| @@ -61,15 +62,16 @@ struct phy_berlin_priv { | |||
| 61 | struct clk *clk; | 62 | struct clk *clk; |
| 62 | struct phy_berlin_desc **phys; | 63 | struct phy_berlin_desc **phys; |
| 63 | unsigned nphys; | 64 | unsigned nphys; |
| 65 | u32 phy_base; | ||
| 64 | }; | 66 | }; |
| 65 | 67 | ||
| 66 | static inline void phy_berlin_sata_reg_setbits(void __iomem *ctrl_reg, u32 reg, | 68 | static inline void phy_berlin_sata_reg_setbits(void __iomem *ctrl_reg, |
| 67 | u32 mask, u32 val) | 69 | u32 phy_base, u32 reg, u32 mask, u32 val) |
| 68 | { | 70 | { |
| 69 | u32 regval; | 71 | u32 regval; |
| 70 | 72 | ||
| 71 | /* select register */ | 73 | /* select register */ |
| 72 | writel(PHY_BASE + reg, ctrl_reg + PORT_VSR_ADDR); | 74 | writel(phy_base + reg, ctrl_reg + PORT_VSR_ADDR); |
| 73 | 75 | ||
| 74 | /* set bits */ | 76 | /* set bits */ |
| 75 | regval = readl(ctrl_reg + PORT_VSR_DATA); | 77 | regval = readl(ctrl_reg + PORT_VSR_DATA); |
| @@ -103,17 +105,20 @@ static int phy_berlin_sata_power_on(struct phy *phy) | |||
| 103 | writel(regval, priv->base + HOST_VSA_DATA); | 105 | writel(regval, priv->base + HOST_VSA_DATA); |
| 104 | 106 | ||
| 105 | /* set PHY mode and ref freq to 25 MHz */ | 107 | /* set PHY mode and ref freq to 25 MHz */ |
| 106 | phy_berlin_sata_reg_setbits(ctrl_reg, 0x1, 0xff, | 108 | phy_berlin_sata_reg_setbits(ctrl_reg, priv->phy_base, 0x01, |
| 107 | REF_FREF_SEL_25 | PHY_MODE_SATA); | 109 | 0x00ff, REF_FREF_SEL_25 | PHY_MODE_SATA); |
| 108 | 110 | ||
| 109 | /* set PHY up to 6 Gbps */ | 111 | /* set PHY up to 6 Gbps */ |
| 110 | phy_berlin_sata_reg_setbits(ctrl_reg, 0x25, 0xc00, PHY_GEN_MAX_6_0); | 112 | phy_berlin_sata_reg_setbits(ctrl_reg, priv->phy_base, 0x25, |
| 113 | 0x0c00, PHY_GEN_MAX_6_0); | ||
| 111 | 114 | ||
| 112 | /* set 40 bits width */ | 115 | /* set 40 bits width */ |
| 113 | phy_berlin_sata_reg_setbits(ctrl_reg, 0x23, 0xc00, DATA_BIT_WIDTH_40); | 116 | phy_berlin_sata_reg_setbits(ctrl_reg, priv->phy_base, 0x23, |
| 117 | 0x0c00, DATA_BIT_WIDTH_40); | ||
| 114 | 118 | ||
| 115 | /* use max pll rate */ | 119 | /* use max pll rate */ |
| 116 | phy_berlin_sata_reg_setbits(ctrl_reg, 0x2, 0x0, USE_MAX_PLL_RATE); | 120 | phy_berlin_sata_reg_setbits(ctrl_reg, priv->phy_base, 0x02, |
| 121 | 0x0000, USE_MAX_PLL_RATE); | ||
| 117 | 122 | ||
| 118 | /* set Gen3 controller speed */ | 123 | /* set Gen3 controller speed */ |
| 119 | regval = readl(ctrl_reg + PORT_SCR_CTL); | 124 | regval = readl(ctrl_reg + PORT_SCR_CTL); |
| @@ -218,6 +223,11 @@ static int phy_berlin_sata_probe(struct platform_device *pdev) | |||
| 218 | if (!priv->phys) | 223 | if (!priv->phys) |
| 219 | return -ENOMEM; | 224 | return -ENOMEM; |
| 220 | 225 | ||
| 226 | if (of_device_is_compatible(dev->of_node, "marvell,berlin2-sata-phy")) | ||
| 227 | priv->phy_base = BG2_PHY_BASE; | ||
| 228 | else | ||
| 229 | priv->phy_base = BG2Q_PHY_BASE; | ||
| 230 | |||
| 221 | dev_set_drvdata(dev, priv); | 231 | dev_set_drvdata(dev, priv); |
| 222 | spin_lock_init(&priv->lock); | 232 | spin_lock_init(&priv->lock); |
| 223 | 233 | ||
| @@ -239,7 +249,7 @@ static int phy_berlin_sata_probe(struct platform_device *pdev) | |||
| 239 | if (!phy_desc) | 249 | if (!phy_desc) |
| 240 | return -ENOMEM; | 250 | return -ENOMEM; |
| 241 | 251 | ||
| 242 | phy = devm_phy_create(dev, NULL, &phy_berlin_sata_ops, NULL); | 252 | phy = devm_phy_create(dev, NULL, &phy_berlin_sata_ops); |
| 243 | if (IS_ERR(phy)) { | 253 | if (IS_ERR(phy)) { |
| 244 | dev_err(dev, "failed to create PHY %d\n", phy_id); | 254 | dev_err(dev, "failed to create PHY %d\n", phy_id); |
| 245 | return PTR_ERR(phy); | 255 | return PTR_ERR(phy); |
| @@ -258,13 +268,11 @@ static int phy_berlin_sata_probe(struct platform_device *pdev) | |||
| 258 | 268 | ||
| 259 | phy_provider = | 269 | phy_provider = |
| 260 | devm_of_phy_provider_register(dev, phy_berlin_sata_phy_xlate); | 270 | devm_of_phy_provider_register(dev, phy_berlin_sata_phy_xlate); |
| 261 | if (IS_ERR(phy_provider)) | 271 | return PTR_ERR_OR_ZERO(phy_provider); |
| 262 | return PTR_ERR(phy_provider); | ||
| 263 | |||
| 264 | return 0; | ||
| 265 | } | 272 | } |
| 266 | 273 | ||
| 267 | static const struct of_device_id phy_berlin_sata_of_match[] = { | 274 | static const struct of_device_id phy_berlin_sata_of_match[] = { |
| 275 | { .compatible = "marvell,berlin2-sata-phy" }, | ||
| 268 | { .compatible = "marvell,berlin2q-sata-phy" }, | 276 | { .compatible = "marvell,berlin2q-sata-phy" }, |
| 269 | { }, | 277 | { }, |
| 270 | }; | 278 | }; |
diff --git a/drivers/phy/phy-berlin-usb.c b/drivers/phy/phy-berlin-usb.c new file mode 100644 index 000000000000..c8a8d53a6ece --- /dev/null +++ b/drivers/phy/phy-berlin-usb.c | |||
| @@ -0,0 +1,223 @@ | |||
| 1 | /* | ||
| 2 | * Copyright (C) 2014 Marvell Technology Group Ltd. | ||
| 3 | * | ||
| 4 | * Antoine Tenart <antoine.tenart@free-electrons.com> | ||
| 5 | * Jisheng Zhang <jszhang@marvell.com> | ||
| 6 | * | ||
| 7 | * This file is licensed under the terms of the GNU General Public | ||
| 8 | * License version 2. This program is licensed "as is" without any | ||
| 9 | * warranty of any kind, whether express or implied. | ||
| 10 | */ | ||
| 11 | |||
| 12 | #include <linux/gpio.h> | ||
| 13 | #include <linux/io.h> | ||
| 14 | #include <linux/module.h> | ||
| 15 | #include <linux/of_device.h> | ||
| 16 | #include <linux/of_gpio.h> | ||
| 17 | #include <linux/phy/phy.h> | ||
| 18 | #include <linux/platform_device.h> | ||
| 19 | #include <linux/reset.h> | ||
| 20 | |||
| 21 | #define USB_PHY_PLL 0x04 | ||
| 22 | #define USB_PHY_PLL_CONTROL 0x08 | ||
| 23 | #define USB_PHY_TX_CTRL0 0x10 | ||
| 24 | #define USB_PHY_TX_CTRL1 0x14 | ||
| 25 | #define USB_PHY_TX_CTRL2 0x18 | ||
| 26 | #define USB_PHY_RX_CTRL 0x20 | ||
| 27 | #define USB_PHY_ANALOG 0x34 | ||
| 28 | |||
| 29 | /* USB_PHY_PLL */ | ||
| 30 | #define CLK_REF_DIV(x) ((x) << 4) | ||
| 31 | #define FEEDBACK_CLK_DIV(x) ((x) << 8) | ||
| 32 | |||
| 33 | /* USB_PHY_PLL_CONTROL */ | ||
| 34 | #define CLK_STABLE BIT(0) | ||
| 35 | #define PLL_CTRL_PIN BIT(1) | ||
| 36 | #define PLL_CTRL_REG BIT(2) | ||
| 37 | #define PLL_ON BIT(3) | ||
| 38 | #define PHASE_OFF_TOL_125 (0x0 << 5) | ||
| 39 | #define PHASE_OFF_TOL_250 BIT(5) | ||
| 40 | #define KVC0_CALIB (0x0 << 9) | ||
| 41 | #define KVC0_REG_CTRL BIT(9) | ||
| 42 | #define KVC0_HIGH (0x0 << 10) | ||
| 43 | #define KVC0_LOW (0x3 << 10) | ||
| 44 | #define CLK_BLK_EN BIT(13) | ||
| 45 | |||
| 46 | /* USB_PHY_TX_CTRL0 */ | ||
| 47 | #define EXT_HS_RCAL_EN BIT(3) | ||
| 48 | #define EXT_FS_RCAL_EN BIT(4) | ||
| 49 | #define IMPCAL_VTH_DIV(x) ((x) << 5) | ||
| 50 | #define EXT_RS_RCAL_DIV(x) ((x) << 8) | ||
| 51 | #define EXT_FS_RCAL_DIV(x) ((x) << 12) | ||
| 52 | |||
| 53 | /* USB_PHY_TX_CTRL1 */ | ||
| 54 | #define TX_VDD15_14 (0x0 << 4) | ||
| 55 | #define TX_VDD15_15 BIT(4) | ||
| 56 | #define TX_VDD15_16 (0x2 << 4) | ||
| 57 | #define TX_VDD15_17 (0x3 << 4) | ||
| 58 | #define TX_VDD12_VDD (0x0 << 6) | ||
| 59 | #define TX_VDD12_11 BIT(6) | ||
| 60 | #define TX_VDD12_12 (0x2 << 6) | ||
| 61 | #define TX_VDD12_13 (0x3 << 6) | ||
| 62 | #define LOW_VDD_EN BIT(8) | ||
| 63 | #define TX_OUT_AMP(x) ((x) << 9) | ||
| 64 | |||
| 65 | /* USB_PHY_TX_CTRL2 */ | ||
| 66 | #define TX_CHAN_CTRL_REG(x) ((x) << 0) | ||
| 67 | #define DRV_SLEWRATE(x) ((x) << 4) | ||
| 68 | #define IMP_CAL_FS_HS_DLY_0 (0x0 << 6) | ||
| 69 | #define IMP_CAL_FS_HS_DLY_1 BIT(6) | ||
| 70 | #define IMP_CAL_FS_HS_DLY_2 (0x2 << 6) | ||
| 71 | #define IMP_CAL_FS_HS_DLY_3 (0x3 << 6) | ||
| 72 | #define FS_DRV_EN_MASK(x) ((x) << 8) | ||
| 73 | #define HS_DRV_EN_MASK(x) ((x) << 12) | ||
| 74 | |||
| 75 | /* USB_PHY_RX_CTRL */ | ||
| 76 | #define PHASE_FREEZE_DLY_2_CL (0x0 << 0) | ||
| 77 | #define PHASE_FREEZE_DLY_4_CL BIT(0) | ||
| 78 | #define ACK_LENGTH_8_CL (0x0 << 2) | ||
| 79 | #define ACK_LENGTH_12_CL BIT(2) | ||
| 80 | #define ACK_LENGTH_16_CL (0x2 << 2) | ||
| 81 | #define ACK_LENGTH_20_CL (0x3 << 2) | ||
| 82 | #define SQ_LENGTH_3 (0x0 << 4) | ||
| 83 | #define SQ_LENGTH_6 BIT(4) | ||
| 84 | #define SQ_LENGTH_9 (0x2 << 4) | ||
| 85 | #define SQ_LENGTH_12 (0x3 << 4) | ||
| 86 | #define DISCON_THRESHOLD_260 (0x0 << 6) | ||
| 87 | #define DISCON_THRESHOLD_270 BIT(6) | ||
| 88 | #define DISCON_THRESHOLD_280 (0x2 << 6) | ||
| 89 | #define DISCON_THRESHOLD_290 (0x3 << 6) | ||
| 90 | #define SQ_THRESHOLD(x) ((x) << 8) | ||
| 91 | #define LPF_COEF(x) ((x) << 12) | ||
| 92 | #define INTPL_CUR_10 (0x0 << 14) | ||
| 93 | #define INTPL_CUR_20 BIT(14) | ||
| 94 | #define INTPL_CUR_30 (0x2 << 14) | ||
| 95 | #define INTPL_CUR_40 (0x3 << 14) | ||
| 96 | |||
| 97 | /* USB_PHY_ANALOG */ | ||
| 98 | #define ANA_PWR_UP BIT(1) | ||
| 99 | #define ANA_PWR_DOWN BIT(2) | ||
| 100 | #define V2I_VCO_RATIO(x) ((x) << 7) | ||
| 101 | #define R_ROTATE_90 (0x0 << 10) | ||
| 102 | #define R_ROTATE_0 BIT(10) | ||
| 103 | #define MODE_TEST_EN BIT(11) | ||
| 104 | #define ANA_TEST_DC_CTRL(x) ((x) << 12) | ||
| 105 | |||
| 106 | #define to_phy_berlin_usb_priv(p) \ | ||
| 107 | container_of((p), struct phy_berlin_usb_priv, phy) | ||
| 108 | |||
| 109 | static const u32 phy_berlin_pll_dividers[] = { | ||
| 110 | /* Berlin 2 */ | ||
| 111 | CLK_REF_DIV(0xc) | FEEDBACK_CLK_DIV(0x54), | ||
| 112 | /* Berlin 2CD */ | ||
| 113 | CLK_REF_DIV(0x6) | FEEDBACK_CLK_DIV(0x55), | ||
| 114 | }; | ||
| 115 | |||
| 116 | struct phy_berlin_usb_priv { | ||
| 117 | void __iomem *base; | ||
| 118 | struct phy *phy; | ||
| 119 | struct reset_control *rst_ctrl; | ||
| 120 | u32 pll_divider; | ||
| 121 | }; | ||
| 122 | |||
| 123 | static int phy_berlin_usb_power_on(struct phy *phy) | ||
| 124 | { | ||
| 125 | struct phy_berlin_usb_priv *priv = dev_get_drvdata(phy->dev.parent); | ||
| 126 | |||
| 127 | reset_control_reset(priv->rst_ctrl); | ||
| 128 | |||
| 129 | writel(priv->pll_divider, | ||
| 130 | priv->base + USB_PHY_PLL); | ||
| 131 | writel(CLK_STABLE | PLL_CTRL_REG | PHASE_OFF_TOL_250 | KVC0_REG_CTRL | | ||
| 132 | CLK_BLK_EN, priv->base + USB_PHY_PLL_CONTROL); | ||
| 133 | writel(V2I_VCO_RATIO(0x5) | R_ROTATE_0 | ANA_TEST_DC_CTRL(0x5), | ||
| 134 | priv->base + USB_PHY_ANALOG); | ||
| 135 | writel(PHASE_FREEZE_DLY_4_CL | ACK_LENGTH_16_CL | SQ_LENGTH_12 | | ||
| 136 | DISCON_THRESHOLD_260 | SQ_THRESHOLD(0xa) | LPF_COEF(0x2) | | ||
| 137 | INTPL_CUR_30, priv->base + USB_PHY_RX_CTRL); | ||
| 138 | |||
| 139 | writel(TX_VDD12_13 | TX_OUT_AMP(0x3), priv->base + USB_PHY_TX_CTRL1); | ||
| 140 | writel(EXT_HS_RCAL_EN | IMPCAL_VTH_DIV(0x3) | EXT_RS_RCAL_DIV(0x4), | ||
| 141 | priv->base + USB_PHY_TX_CTRL0); | ||
| 142 | |||
| 143 | writel(EXT_HS_RCAL_EN | IMPCAL_VTH_DIV(0x3) | EXT_RS_RCAL_DIV(0x4) | | ||
| 144 | EXT_FS_RCAL_DIV(0x2), priv->base + USB_PHY_TX_CTRL0); | ||
| 145 | |||
| 146 | writel(EXT_HS_RCAL_EN | IMPCAL_VTH_DIV(0x3) | EXT_RS_RCAL_DIV(0x4), | ||
| 147 | priv->base + USB_PHY_TX_CTRL0); | ||
| 148 | writel(TX_CHAN_CTRL_REG(0xf) | DRV_SLEWRATE(0x3) | IMP_CAL_FS_HS_DLY_3 | | ||
| 149 | FS_DRV_EN_MASK(0xd), priv->base + USB_PHY_TX_CTRL2); | ||
| 150 | |||
| 151 | return 0; | ||
| 152 | } | ||
| 153 | |||
| 154 | static struct phy_ops phy_berlin_usb_ops = { | ||
| 155 | .power_on = phy_berlin_usb_power_on, | ||
| 156 | .owner = THIS_MODULE, | ||
| 157 | }; | ||
| 158 | |||
| 159 | static const struct of_device_id phy_berlin_sata_of_match[] = { | ||
| 160 | { | ||
| 161 | .compatible = "marvell,berlin2-usb-phy", | ||
| 162 | .data = &phy_berlin_pll_dividers[0], | ||
| 163 | }, | ||
| 164 | { | ||
| 165 | .compatible = "marvell,berlin2cd-usb-phy", | ||
| 166 | .data = &phy_berlin_pll_dividers[1], | ||
| 167 | }, | ||
| 168 | { }, | ||
| 169 | }; | ||
| 170 | MODULE_DEVICE_TABLE(of, phy_berlin_sata_of_match); | ||
| 171 | |||
| 172 | static int phy_berlin_usb_probe(struct platform_device *pdev) | ||
| 173 | { | ||
| 174 | const struct of_device_id *match = | ||
| 175 | of_match_device(phy_berlin_sata_of_match, &pdev->dev); | ||
| 176 | struct phy_berlin_usb_priv *priv; | ||
| 177 | struct resource *res; | ||
| 178 | struct phy_provider *phy_provider; | ||
| 179 | |||
| 180 | priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL); | ||
| 181 | if (!priv) | ||
| 182 | return -ENOMEM; | ||
| 183 | |||
| 184 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 185 | priv->base = devm_ioremap_resource(&pdev->dev, res); | ||
| 186 | if (IS_ERR(priv->base)) | ||
| 187 | return PTR_ERR(priv->base); | ||
| 188 | |||
| 189 | priv->rst_ctrl = devm_reset_control_get(&pdev->dev, NULL); | ||
| 190 | if (IS_ERR(priv->rst_ctrl)) | ||
| 191 | return PTR_ERR(priv->rst_ctrl); | ||
| 192 | |||
| 193 | priv->pll_divider = *((u32 *)match->data); | ||
| 194 | |||
| 195 | priv->phy = devm_phy_create(&pdev->dev, NULL, &phy_berlin_usb_ops); | ||
| 196 | if (IS_ERR(priv->phy)) { | ||
| 197 | dev_err(&pdev->dev, "failed to create PHY\n"); | ||
| 198 | return PTR_ERR(priv->phy); | ||
| 199 | } | ||
| 200 | |||
| 201 | platform_set_drvdata(pdev, priv); | ||
| 202 | |||
| 203 | phy_provider = | ||
| 204 | devm_of_phy_provider_register(&pdev->dev, of_phy_simple_xlate); | ||
| 205 | if (IS_ERR(phy_provider)) | ||
| 206 | return PTR_ERR(phy_provider); | ||
| 207 | |||
| 208 | return 0; | ||
| 209 | } | ||
| 210 | |||
| 211 | static struct platform_driver phy_berlin_usb_driver = { | ||
| 212 | .probe = phy_berlin_usb_probe, | ||
| 213 | .driver = { | ||
| 214 | .name = "phy-berlin-usb", | ||
| 215 | .owner = THIS_MODULE, | ||
| 216 | .of_match_table = phy_berlin_sata_of_match, | ||
| 217 | }, | ||
| 218 | }; | ||
| 219 | module_platform_driver(phy_berlin_usb_driver); | ||
| 220 | |||
| 221 | MODULE_AUTHOR("Antoine Tenart <antoine.tenart@free-electrons.com>"); | ||
| 222 | MODULE_DESCRIPTION("Marvell Berlin PHY driver for USB"); | ||
| 223 | MODULE_LICENSE("GPL"); | ||
diff --git a/drivers/phy/phy-core.c b/drivers/phy/phy-core.c index ff5eec5af817..a12d35338313 100644 --- a/drivers/phy/phy-core.c +++ b/drivers/phy/phy-core.c | |||
| @@ -26,6 +26,7 @@ | |||
| 26 | static struct class *phy_class; | 26 | static struct class *phy_class; |
| 27 | static DEFINE_MUTEX(phy_provider_mutex); | 27 | static DEFINE_MUTEX(phy_provider_mutex); |
| 28 | static LIST_HEAD(phy_provider_list); | 28 | static LIST_HEAD(phy_provider_list); |
| 29 | static LIST_HEAD(phys); | ||
| 29 | static DEFINE_IDA(phy_ida); | 30 | static DEFINE_IDA(phy_ida); |
| 30 | 31 | ||
| 31 | static void devm_phy_release(struct device *dev, void *res) | 32 | static void devm_phy_release(struct device *dev, void *res) |
| @@ -54,34 +55,79 @@ static int devm_phy_match(struct device *dev, void *res, void *match_data) | |||
| 54 | return res == match_data; | 55 | return res == match_data; |
| 55 | } | 56 | } |
| 56 | 57 | ||
| 57 | static struct phy *phy_lookup(struct device *device, const char *port) | 58 | /** |
| 59 | * phy_create_lookup() - allocate and register PHY/device association | ||
| 60 | * @phy: the phy of the association | ||
| 61 | * @con_id: connection ID string on device | ||
| 62 | * @dev_id: the device of the association | ||
| 63 | * | ||
| 64 | * Creates and registers phy_lookup entry. | ||
| 65 | */ | ||
| 66 | int phy_create_lookup(struct phy *phy, const char *con_id, const char *dev_id) | ||
| 58 | { | 67 | { |
| 59 | unsigned int count; | 68 | struct phy_lookup *pl; |
| 60 | struct phy *phy; | ||
| 61 | struct device *dev; | ||
| 62 | struct phy_consumer *consumers; | ||
| 63 | struct class_dev_iter iter; | ||
| 64 | 69 | ||
| 65 | class_dev_iter_init(&iter, phy_class, NULL, NULL); | 70 | if (!phy || !dev_id || !con_id) |
| 66 | while ((dev = class_dev_iter_next(&iter))) { | 71 | return -EINVAL; |
| 67 | phy = to_phy(dev); | ||
| 68 | 72 | ||
| 69 | if (!phy->init_data) | 73 | pl = kzalloc(sizeof(*pl), GFP_KERNEL); |
| 70 | continue; | 74 | if (!pl) |
| 71 | count = phy->init_data->num_consumers; | 75 | return -ENOMEM; |
| 72 | consumers = phy->init_data->consumers; | 76 | |
| 73 | while (count--) { | 77 | pl->dev_id = dev_id; |
| 74 | if (!strcmp(consumers->dev_name, dev_name(device)) && | 78 | pl->con_id = con_id; |
| 75 | !strcmp(consumers->port, port)) { | 79 | pl->phy = phy; |
| 76 | class_dev_iter_exit(&iter); | 80 | |
| 77 | return phy; | 81 | mutex_lock(&phy_provider_mutex); |
| 78 | } | 82 | list_add_tail(&pl->node, &phys); |
| 79 | consumers++; | 83 | mutex_unlock(&phy_provider_mutex); |
| 84 | |||
| 85 | return 0; | ||
| 86 | } | ||
| 87 | EXPORT_SYMBOL_GPL(phy_create_lookup); | ||
| 88 | |||
| 89 | /** | ||
| 90 | * phy_remove_lookup() - find and remove PHY/device association | ||
| 91 | * @phy: the phy of the association | ||
| 92 | * @con_id: connection ID string on device | ||
| 93 | * @dev_id: the device of the association | ||
| 94 | * | ||
| 95 | * Finds and unregisters phy_lookup entry that was created with | ||
| 96 | * phy_create_lookup(). | ||
| 97 | */ | ||
| 98 | void phy_remove_lookup(struct phy *phy, const char *con_id, const char *dev_id) | ||
| 99 | { | ||
| 100 | struct phy_lookup *pl; | ||
| 101 | |||
| 102 | if (!phy || !dev_id || !con_id) | ||
| 103 | return; | ||
| 104 | |||
| 105 | mutex_lock(&phy_provider_mutex); | ||
| 106 | list_for_each_entry(pl, &phys, node) | ||
| 107 | if (pl->phy == phy && !strcmp(pl->dev_id, dev_id) && | ||
| 108 | !strcmp(pl->con_id, con_id)) { | ||
| 109 | list_del(&pl->node); | ||
| 110 | kfree(pl); | ||
| 111 | break; | ||
| 80 | } | 112 | } |
| 81 | } | 113 | mutex_unlock(&phy_provider_mutex); |
| 114 | } | ||
| 115 | EXPORT_SYMBOL_GPL(phy_remove_lookup); | ||
| 82 | 116 | ||
| 83 | class_dev_iter_exit(&iter); | 117 | static struct phy *phy_find(struct device *dev, const char *con_id) |
| 84 | return ERR_PTR(-ENODEV); | 118 | { |
| 119 | const char *dev_id = dev_name(dev); | ||
| 120 | struct phy_lookup *p, *pl = NULL; | ||
| 121 | |||
| 122 | mutex_lock(&phy_provider_mutex); | ||
| 123 | list_for_each_entry(p, &phys, node) | ||
| 124 | if (!strcmp(p->dev_id, dev_id) && !strcmp(p->con_id, con_id)) { | ||
| 125 | pl = p; | ||
| 126 | break; | ||
| 127 | } | ||
| 128 | mutex_unlock(&phy_provider_mutex); | ||
| 129 | |||
| 130 | return pl ? pl->phy : ERR_PTR(-ENODEV); | ||
| 85 | } | 131 | } |
| 86 | 132 | ||
| 87 | static struct phy_provider *of_phy_provider_lookup(struct device_node *node) | 133 | static struct phy_provider *of_phy_provider_lookup(struct device_node *node) |
| @@ -414,21 +460,13 @@ struct phy *of_phy_simple_xlate(struct device *dev, struct of_phandle_args | |||
| 414 | { | 460 | { |
| 415 | struct phy *phy; | 461 | struct phy *phy; |
| 416 | struct class_dev_iter iter; | 462 | struct class_dev_iter iter; |
| 417 | struct device_node *node = dev->of_node; | ||
| 418 | struct device_node *child; | ||
| 419 | 463 | ||
| 420 | class_dev_iter_init(&iter, phy_class, NULL, NULL); | 464 | class_dev_iter_init(&iter, phy_class, NULL, NULL); |
| 421 | while ((dev = class_dev_iter_next(&iter))) { | 465 | while ((dev = class_dev_iter_next(&iter))) { |
| 422 | phy = to_phy(dev); | 466 | phy = to_phy(dev); |
| 423 | if (node != phy->dev.of_node) { | 467 | if (args->np != phy->dev.of_node) |
| 424 | for_each_child_of_node(node, child) { | ||
| 425 | if (child == phy->dev.of_node) | ||
| 426 | goto phy_found; | ||
| 427 | } | ||
| 428 | continue; | 468 | continue; |
| 429 | } | ||
| 430 | 469 | ||
| 431 | phy_found: | ||
| 432 | class_dev_iter_exit(&iter); | 470 | class_dev_iter_exit(&iter); |
| 433 | return phy; | 471 | return phy; |
| 434 | } | 472 | } |
| @@ -463,7 +501,7 @@ struct phy *phy_get(struct device *dev, const char *string) | |||
| 463 | string); | 501 | string); |
| 464 | phy = _of_phy_get(dev->of_node, index); | 502 | phy = _of_phy_get(dev->of_node, index); |
| 465 | } else { | 503 | } else { |
| 466 | phy = phy_lookup(dev, string); | 504 | phy = phy_find(dev, string); |
| 467 | } | 505 | } |
| 468 | if (IS_ERR(phy)) | 506 | if (IS_ERR(phy)) |
| 469 | return phy; | 507 | return phy; |
| @@ -588,13 +626,11 @@ EXPORT_SYMBOL_GPL(devm_of_phy_get); | |||
| 588 | * @dev: device that is creating the new phy | 626 | * @dev: device that is creating the new phy |
| 589 | * @node: device node of the phy | 627 | * @node: device node of the phy |
| 590 | * @ops: function pointers for performing phy operations | 628 | * @ops: function pointers for performing phy operations |
| 591 | * @init_data: contains the list of PHY consumers or NULL | ||
| 592 | * | 629 | * |
| 593 | * Called to create a phy using phy framework. | 630 | * Called to create a phy using phy framework. |
| 594 | */ | 631 | */ |
| 595 | struct phy *phy_create(struct device *dev, struct device_node *node, | 632 | struct phy *phy_create(struct device *dev, struct device_node *node, |
| 596 | const struct phy_ops *ops, | 633 | const struct phy_ops *ops) |
| 597 | struct phy_init_data *init_data) | ||
| 598 | { | 634 | { |
| 599 | int ret; | 635 | int ret; |
| 600 | int id; | 636 | int id; |
| @@ -632,7 +668,6 @@ struct phy *phy_create(struct device *dev, struct device_node *node, | |||
| 632 | phy->dev.of_node = node ?: dev->of_node; | 668 | phy->dev.of_node = node ?: dev->of_node; |
| 633 | phy->id = id; | 669 | phy->id = id; |
| 634 | phy->ops = ops; | 670 | phy->ops = ops; |
| 635 | phy->init_data = init_data; | ||
| 636 | 671 | ||
| 637 | ret = dev_set_name(&phy->dev, "phy-%s.%d", dev_name(dev), id); | 672 | ret = dev_set_name(&phy->dev, "phy-%s.%d", dev_name(dev), id); |
| 638 | if (ret) | 673 | if (ret) |
| @@ -667,7 +702,6 @@ EXPORT_SYMBOL_GPL(phy_create); | |||
| 667 | * @dev: device that is creating the new phy | 702 | * @dev: device that is creating the new phy |
| 668 | * @node: device node of the phy | 703 | * @node: device node of the phy |
| 669 | * @ops: function pointers for performing phy operations | 704 | * @ops: function pointers for performing phy operations |
| 670 | * @init_data: contains the list of PHY consumers or NULL | ||
| 671 | * | 705 | * |
| 672 | * Creates a new PHY device adding it to the PHY class. | 706 | * Creates a new PHY device adding it to the PHY class. |
| 673 | * While at that, it also associates the device with the phy using devres. | 707 | * While at that, it also associates the device with the phy using devres. |
| @@ -675,8 +709,7 @@ EXPORT_SYMBOL_GPL(phy_create); | |||
| 675 | * then, devres data is freed. | 709 | * then, devres data is freed. |
| 676 | */ | 710 | */ |
| 677 | struct phy *devm_phy_create(struct device *dev, struct device_node *node, | 711 | struct phy *devm_phy_create(struct device *dev, struct device_node *node, |
| 678 | const struct phy_ops *ops, | 712 | const struct phy_ops *ops) |
| 679 | struct phy_init_data *init_data) | ||
| 680 | { | 713 | { |
| 681 | struct phy **ptr, *phy; | 714 | struct phy **ptr, *phy; |
| 682 | 715 | ||
| @@ -684,7 +717,7 @@ struct phy *devm_phy_create(struct device *dev, struct device_node *node, | |||
| 684 | if (!ptr) | 717 | if (!ptr) |
| 685 | return ERR_PTR(-ENOMEM); | 718 | return ERR_PTR(-ENOMEM); |
| 686 | 719 | ||
| 687 | phy = phy_create(dev, node, ops, init_data); | 720 | phy = phy_create(dev, node, ops); |
| 688 | if (!IS_ERR(phy)) { | 721 | if (!IS_ERR(phy)) { |
| 689 | *ptr = phy; | 722 | *ptr = phy; |
| 690 | devres_add(dev, ptr); | 723 | devres_add(dev, ptr); |
diff --git a/drivers/phy/phy-exynos-dp-video.c b/drivers/phy/phy-exynos-dp-video.c index 84f49e5a3f24..f86cbe68ddaf 100644 --- a/drivers/phy/phy-exynos-dp-video.c +++ b/drivers/phy/phy-exynos-dp-video.c | |||
| @@ -112,7 +112,7 @@ static int exynos_dp_video_phy_probe(struct platform_device *pdev) | |||
| 112 | match = of_match_node(exynos_dp_video_phy_of_match, dev->of_node); | 112 | match = of_match_node(exynos_dp_video_phy_of_match, dev->of_node); |
| 113 | state->drvdata = match->data; | 113 | state->drvdata = match->data; |
| 114 | 114 | ||
| 115 | phy = devm_phy_create(dev, NULL, &exynos_dp_video_phy_ops, NULL); | 115 | phy = devm_phy_create(dev, NULL, &exynos_dp_video_phy_ops); |
| 116 | if (IS_ERR(phy)) { | 116 | if (IS_ERR(phy)) { |
| 117 | dev_err(dev, "failed to create Display Port PHY\n"); | 117 | dev_err(dev, "failed to create Display Port PHY\n"); |
| 118 | return PTR_ERR(phy); | 118 | return PTR_ERR(phy); |
diff --git a/drivers/phy/phy-exynos-mipi-video.c b/drivers/phy/phy-exynos-mipi-video.c index 6a9bef138617..943e0f88a120 100644 --- a/drivers/phy/phy-exynos-mipi-video.c +++ b/drivers/phy/phy-exynos-mipi-video.c | |||
| @@ -137,7 +137,7 @@ static int exynos_mipi_video_phy_probe(struct platform_device *pdev) | |||
| 137 | 137 | ||
| 138 | for (i = 0; i < EXYNOS_MIPI_PHYS_NUM; i++) { | 138 | for (i = 0; i < EXYNOS_MIPI_PHYS_NUM; i++) { |
| 139 | struct phy *phy = devm_phy_create(dev, NULL, | 139 | struct phy *phy = devm_phy_create(dev, NULL, |
| 140 | &exynos_mipi_video_phy_ops, NULL); | 140 | &exynos_mipi_video_phy_ops); |
| 141 | if (IS_ERR(phy)) { | 141 | if (IS_ERR(phy)) { |
| 142 | dev_err(dev, "failed to create PHY %d\n", i); | 142 | dev_err(dev, "failed to create PHY %d\n", i); |
| 143 | return PTR_ERR(phy); | 143 | return PTR_ERR(phy); |
diff --git a/drivers/phy/phy-exynos5-usbdrd.c b/drivers/phy/phy-exynos5-usbdrd.c index f756aca871db..04374018425f 100644 --- a/drivers/phy/phy-exynos5-usbdrd.c +++ b/drivers/phy/phy-exynos5-usbdrd.c | |||
| @@ -141,6 +141,7 @@ struct exynos5_usbdrd_phy_drvdata { | |||
| 141 | const struct exynos5_usbdrd_phy_config *phy_cfg; | 141 | const struct exynos5_usbdrd_phy_config *phy_cfg; |
| 142 | u32 pmu_offset_usbdrd0_phy; | 142 | u32 pmu_offset_usbdrd0_phy; |
| 143 | u32 pmu_offset_usbdrd1_phy; | 143 | u32 pmu_offset_usbdrd1_phy; |
| 144 | bool has_common_clk_gate; | ||
| 144 | }; | 145 | }; |
| 145 | 146 | ||
| 146 | /** | 147 | /** |
| @@ -148,6 +149,9 @@ struct exynos5_usbdrd_phy_drvdata { | |||
| 148 | * @dev: pointer to device instance of this platform device | 149 | * @dev: pointer to device instance of this platform device |
| 149 | * @reg_phy: usb phy controller register memory base | 150 | * @reg_phy: usb phy controller register memory base |
| 150 | * @clk: phy clock for register access | 151 | * @clk: phy clock for register access |
| 152 | * @pipeclk: clock for pipe3 phy | ||
| 153 | * @utmiclk: clock for utmi+ phy | ||
| 154 | * @itpclk: clock for ITP generation | ||
| 151 | * @drv_data: pointer to SoC level driver data structure | 155 | * @drv_data: pointer to SoC level driver data structure |
| 152 | * @phys[]: array for 'EXYNOS5_DRDPHYS_NUM' number of PHY | 156 | * @phys[]: array for 'EXYNOS5_DRDPHYS_NUM' number of PHY |
| 153 | * instances each with its 'phy' and 'phy_cfg'. | 157 | * instances each with its 'phy' and 'phy_cfg'. |
| @@ -155,12 +159,16 @@ struct exynos5_usbdrd_phy_drvdata { | |||
| 155 | * reference clocks' for SS and HS operations | 159 | * reference clocks' for SS and HS operations |
| 156 | * @ref_clk: reference clock to PHY block from which PHY's | 160 | * @ref_clk: reference clock to PHY block from which PHY's |
| 157 | * operational clocks are derived | 161 | * operational clocks are derived |
| 158 | * @ref_rate: rate of above reference clock | 162 | * vbus: VBUS regulator for phy |
| 163 | * vbus_boost: Boost regulator for VBUS present on few Exynos boards | ||
| 159 | */ | 164 | */ |
| 160 | struct exynos5_usbdrd_phy { | 165 | struct exynos5_usbdrd_phy { |
| 161 | struct device *dev; | 166 | struct device *dev; |
| 162 | void __iomem *reg_phy; | 167 | void __iomem *reg_phy; |
| 163 | struct clk *clk; | 168 | struct clk *clk; |
| 169 | struct clk *pipeclk; | ||
| 170 | struct clk *utmiclk; | ||
| 171 | struct clk *itpclk; | ||
| 164 | const struct exynos5_usbdrd_phy_drvdata *drv_data; | 172 | const struct exynos5_usbdrd_phy_drvdata *drv_data; |
| 165 | struct phy_usb_instance { | 173 | struct phy_usb_instance { |
| 166 | struct phy *phy; | 174 | struct phy *phy; |
| @@ -172,6 +180,7 @@ struct exynos5_usbdrd_phy { | |||
| 172 | u32 extrefclk; | 180 | u32 extrefclk; |
| 173 | struct clk *ref_clk; | 181 | struct clk *ref_clk; |
| 174 | struct regulator *vbus; | 182 | struct regulator *vbus; |
| 183 | struct regulator *vbus_boost; | ||
| 175 | }; | 184 | }; |
| 176 | 185 | ||
| 177 | static inline | 186 | static inline |
| @@ -447,13 +456,27 @@ static int exynos5_usbdrd_phy_power_on(struct phy *phy) | |||
| 447 | dev_dbg(phy_drd->dev, "Request to power_on usbdrd_phy phy\n"); | 456 | dev_dbg(phy_drd->dev, "Request to power_on usbdrd_phy phy\n"); |
| 448 | 457 | ||
| 449 | clk_prepare_enable(phy_drd->ref_clk); | 458 | clk_prepare_enable(phy_drd->ref_clk); |
| 459 | if (!phy_drd->drv_data->has_common_clk_gate) { | ||
| 460 | clk_prepare_enable(phy_drd->pipeclk); | ||
| 461 | clk_prepare_enable(phy_drd->utmiclk); | ||
| 462 | clk_prepare_enable(phy_drd->itpclk); | ||
| 463 | } | ||
| 450 | 464 | ||
| 451 | /* Enable VBUS supply */ | 465 | /* Enable VBUS supply */ |
| 466 | if (phy_drd->vbus_boost) { | ||
| 467 | ret = regulator_enable(phy_drd->vbus_boost); | ||
| 468 | if (ret) { | ||
| 469 | dev_err(phy_drd->dev, | ||
| 470 | "Failed to enable VBUS boost supply\n"); | ||
| 471 | goto fail_vbus; | ||
| 472 | } | ||
| 473 | } | ||
| 474 | |||
| 452 | if (phy_drd->vbus) { | 475 | if (phy_drd->vbus) { |
| 453 | ret = regulator_enable(phy_drd->vbus); | 476 | ret = regulator_enable(phy_drd->vbus); |
| 454 | if (ret) { | 477 | if (ret) { |
| 455 | dev_err(phy_drd->dev, "Failed to enable VBUS supply\n"); | 478 | dev_err(phy_drd->dev, "Failed to enable VBUS supply\n"); |
| 456 | goto fail_vbus; | 479 | goto fail_vbus_boost; |
| 457 | } | 480 | } |
| 458 | } | 481 | } |
| 459 | 482 | ||
| @@ -462,8 +485,17 @@ static int exynos5_usbdrd_phy_power_on(struct phy *phy) | |||
| 462 | 485 | ||
| 463 | return 0; | 486 | return 0; |
| 464 | 487 | ||
| 488 | fail_vbus_boost: | ||
| 489 | if (phy_drd->vbus_boost) | ||
| 490 | regulator_disable(phy_drd->vbus_boost); | ||
| 491 | |||
| 465 | fail_vbus: | 492 | fail_vbus: |
| 466 | clk_disable_unprepare(phy_drd->ref_clk); | 493 | clk_disable_unprepare(phy_drd->ref_clk); |
| 494 | if (!phy_drd->drv_data->has_common_clk_gate) { | ||
| 495 | clk_disable_unprepare(phy_drd->itpclk); | ||
| 496 | clk_disable_unprepare(phy_drd->utmiclk); | ||
| 497 | clk_disable_unprepare(phy_drd->pipeclk); | ||
| 498 | } | ||
| 467 | 499 | ||
| 468 | return ret; | 500 | return ret; |
| 469 | } | 501 | } |
| @@ -481,8 +513,15 @@ static int exynos5_usbdrd_phy_power_off(struct phy *phy) | |||
| 481 | /* Disable VBUS supply */ | 513 | /* Disable VBUS supply */ |
| 482 | if (phy_drd->vbus) | 514 | if (phy_drd->vbus) |
| 483 | regulator_disable(phy_drd->vbus); | 515 | regulator_disable(phy_drd->vbus); |
| 516 | if (phy_drd->vbus_boost) | ||
| 517 | regulator_disable(phy_drd->vbus_boost); | ||
| 484 | 518 | ||
| 485 | clk_disable_unprepare(phy_drd->ref_clk); | 519 | clk_disable_unprepare(phy_drd->ref_clk); |
| 520 | if (!phy_drd->drv_data->has_common_clk_gate) { | ||
| 521 | clk_disable_unprepare(phy_drd->itpclk); | ||
| 522 | clk_disable_unprepare(phy_drd->pipeclk); | ||
| 523 | clk_disable_unprepare(phy_drd->utmiclk); | ||
| 524 | } | ||
| 486 | 525 | ||
| 487 | return 0; | 526 | return 0; |
| 488 | } | 527 | } |
| @@ -506,6 +545,57 @@ static struct phy_ops exynos5_usbdrd_phy_ops = { | |||
| 506 | .owner = THIS_MODULE, | 545 | .owner = THIS_MODULE, |
| 507 | }; | 546 | }; |
| 508 | 547 | ||
| 548 | static int exynos5_usbdrd_phy_clk_handle(struct exynos5_usbdrd_phy *phy_drd) | ||
| 549 | { | ||
| 550 | unsigned long ref_rate; | ||
| 551 | int ret; | ||
| 552 | |||
| 553 | phy_drd->clk = devm_clk_get(phy_drd->dev, "phy"); | ||
| 554 | if (IS_ERR(phy_drd->clk)) { | ||
| 555 | dev_err(phy_drd->dev, "Failed to get phy clock\n"); | ||
| 556 | return PTR_ERR(phy_drd->clk); | ||
| 557 | } | ||
| 558 | |||
| 559 | phy_drd->ref_clk = devm_clk_get(phy_drd->dev, "ref"); | ||
| 560 | if (IS_ERR(phy_drd->ref_clk)) { | ||
| 561 | dev_err(phy_drd->dev, "Failed to get phy reference clock\n"); | ||
| 562 | return PTR_ERR(phy_drd->ref_clk); | ||
| 563 | } | ||
| 564 | ref_rate = clk_get_rate(phy_drd->ref_clk); | ||
| 565 | |||
| 566 | ret = exynos5_rate_to_clk(ref_rate, &phy_drd->extrefclk); | ||
| 567 | if (ret) { | ||
| 568 | dev_err(phy_drd->dev, "Clock rate (%ld) not supported\n", | ||
| 569 | ref_rate); | ||
| 570 | return ret; | ||
| 571 | } | ||
| 572 | |||
| 573 | if (!phy_drd->drv_data->has_common_clk_gate) { | ||
| 574 | phy_drd->pipeclk = devm_clk_get(phy_drd->dev, "phy_pipe"); | ||
| 575 | if (IS_ERR(phy_drd->pipeclk)) { | ||
| 576 | dev_info(phy_drd->dev, | ||
| 577 | "PIPE3 phy operational clock not specified\n"); | ||
| 578 | phy_drd->pipeclk = NULL; | ||
| 579 | } | ||
| 580 | |||
| 581 | phy_drd->utmiclk = devm_clk_get(phy_drd->dev, "phy_utmi"); | ||
| 582 | if (IS_ERR(phy_drd->utmiclk)) { | ||
| 583 | dev_info(phy_drd->dev, | ||
| 584 | "UTMI phy operational clock not specified\n"); | ||
| 585 | phy_drd->utmiclk = NULL; | ||
| 586 | } | ||
| 587 | |||
| 588 | phy_drd->itpclk = devm_clk_get(phy_drd->dev, "itp"); | ||
| 589 | if (IS_ERR(phy_drd->itpclk)) { | ||
| 590 | dev_info(phy_drd->dev, | ||
| 591 | "ITP clock from main OSC not specified\n"); | ||
| 592 | phy_drd->itpclk = NULL; | ||
| 593 | } | ||
| 594 | } | ||
| 595 | |||
| 596 | return 0; | ||
| 597 | } | ||
| 598 | |||
| 509 | static const struct exynos5_usbdrd_phy_config phy_cfg_exynos5[] = { | 599 | static const struct exynos5_usbdrd_phy_config phy_cfg_exynos5[] = { |
| 510 | { | 600 | { |
| 511 | .id = EXYNOS5_DRDPHY_UTMI, | 601 | .id = EXYNOS5_DRDPHY_UTMI, |
| @@ -525,11 +615,19 @@ static const struct exynos5_usbdrd_phy_drvdata exynos5420_usbdrd_phy = { | |||
| 525 | .phy_cfg = phy_cfg_exynos5, | 615 | .phy_cfg = phy_cfg_exynos5, |
| 526 | .pmu_offset_usbdrd0_phy = EXYNOS5_USBDRD_PHY_CONTROL, | 616 | .pmu_offset_usbdrd0_phy = EXYNOS5_USBDRD_PHY_CONTROL, |
| 527 | .pmu_offset_usbdrd1_phy = EXYNOS5420_USBDRD1_PHY_CONTROL, | 617 | .pmu_offset_usbdrd1_phy = EXYNOS5420_USBDRD1_PHY_CONTROL, |
| 618 | .has_common_clk_gate = true, | ||
| 528 | }; | 619 | }; |
| 529 | 620 | ||
| 530 | static const struct exynos5_usbdrd_phy_drvdata exynos5250_usbdrd_phy = { | 621 | static const struct exynos5_usbdrd_phy_drvdata exynos5250_usbdrd_phy = { |
| 531 | .phy_cfg = phy_cfg_exynos5, | 622 | .phy_cfg = phy_cfg_exynos5, |
| 532 | .pmu_offset_usbdrd0_phy = EXYNOS5_USBDRD_PHY_CONTROL, | 623 | .pmu_offset_usbdrd0_phy = EXYNOS5_USBDRD_PHY_CONTROL, |
| 624 | .has_common_clk_gate = true, | ||
| 625 | }; | ||
| 626 | |||
| 627 | static const struct exynos5_usbdrd_phy_drvdata exynos7_usbdrd_phy = { | ||
| 628 | .phy_cfg = phy_cfg_exynos5, | ||
| 629 | .pmu_offset_usbdrd0_phy = EXYNOS5_USBDRD_PHY_CONTROL, | ||
| 630 | .has_common_clk_gate = false, | ||
| 533 | }; | 631 | }; |
| 534 | 632 | ||
| 535 | static const struct of_device_id exynos5_usbdrd_phy_of_match[] = { | 633 | static const struct of_device_id exynos5_usbdrd_phy_of_match[] = { |
| @@ -539,6 +637,9 @@ static const struct of_device_id exynos5_usbdrd_phy_of_match[] = { | |||
| 539 | }, { | 637 | }, { |
| 540 | .compatible = "samsung,exynos5420-usbdrd-phy", | 638 | .compatible = "samsung,exynos5420-usbdrd-phy", |
| 541 | .data = &exynos5420_usbdrd_phy | 639 | .data = &exynos5420_usbdrd_phy |
| 640 | }, { | ||
| 641 | .compatible = "samsung,exynos7-usbdrd-phy", | ||
| 642 | .data = &exynos7_usbdrd_phy | ||
| 542 | }, | 643 | }, |
| 543 | { }, | 644 | { }, |
| 544 | }; | 645 | }; |
| @@ -555,7 +656,6 @@ static int exynos5_usbdrd_phy_probe(struct platform_device *pdev) | |||
| 555 | const struct exynos5_usbdrd_phy_drvdata *drv_data; | 656 | const struct exynos5_usbdrd_phy_drvdata *drv_data; |
| 556 | struct regmap *reg_pmu; | 657 | struct regmap *reg_pmu; |
| 557 | u32 pmu_offset; | 658 | u32 pmu_offset; |
| 558 | unsigned long ref_rate; | ||
| 559 | int i, ret; | 659 | int i, ret; |
| 560 | int channel; | 660 | int channel; |
| 561 | 661 | ||
| @@ -576,23 +676,9 @@ static int exynos5_usbdrd_phy_probe(struct platform_device *pdev) | |||
| 576 | drv_data = match->data; | 676 | drv_data = match->data; |
| 577 | phy_drd->drv_data = drv_data; | 677 | phy_drd->drv_data = drv_data; |
| 578 | 678 | ||
| 579 | phy_drd->clk = devm_clk_get(dev, "phy"); | 679 | ret = exynos5_usbdrd_phy_clk_handle(phy_drd); |
| 580 | if (IS_ERR(phy_drd->clk)) { | ||
| 581 | dev_err(dev, "Failed to get clock of phy controller\n"); | ||
| 582 | return PTR_ERR(phy_drd->clk); | ||
| 583 | } | ||
| 584 | |||
| 585 | phy_drd->ref_clk = devm_clk_get(dev, "ref"); | ||
| 586 | if (IS_ERR(phy_drd->ref_clk)) { | ||
| 587 | dev_err(dev, "Failed to get reference clock of usbdrd phy\n"); | ||
| 588 | return PTR_ERR(phy_drd->ref_clk); | ||
| 589 | } | ||
| 590 | ref_rate = clk_get_rate(phy_drd->ref_clk); | ||
| 591 | |||
| 592 | ret = exynos5_rate_to_clk(ref_rate, &phy_drd->extrefclk); | ||
| 593 | if (ret) { | 680 | if (ret) { |
| 594 | dev_err(phy_drd->dev, "Clock rate (%ld) not supported\n", | 681 | dev_err(dev, "Failed to initialize clocks\n"); |
| 595 | ref_rate); | ||
| 596 | return ret; | 682 | return ret; |
| 597 | } | 683 | } |
| 598 | 684 | ||
| @@ -622,7 +708,7 @@ static int exynos5_usbdrd_phy_probe(struct platform_device *pdev) | |||
| 622 | break; | 708 | break; |
| 623 | } | 709 | } |
| 624 | 710 | ||
| 625 | /* Get Vbus regulator */ | 711 | /* Get Vbus regulators */ |
| 626 | phy_drd->vbus = devm_regulator_get(dev, "vbus"); | 712 | phy_drd->vbus = devm_regulator_get(dev, "vbus"); |
| 627 | if (IS_ERR(phy_drd->vbus)) { | 713 | if (IS_ERR(phy_drd->vbus)) { |
| 628 | ret = PTR_ERR(phy_drd->vbus); | 714 | ret = PTR_ERR(phy_drd->vbus); |
| @@ -633,12 +719,21 @@ static int exynos5_usbdrd_phy_probe(struct platform_device *pdev) | |||
| 633 | phy_drd->vbus = NULL; | 719 | phy_drd->vbus = NULL; |
| 634 | } | 720 | } |
| 635 | 721 | ||
| 722 | phy_drd->vbus_boost = devm_regulator_get(dev, "vbus-boost"); | ||
| 723 | if (IS_ERR(phy_drd->vbus_boost)) { | ||
| 724 | ret = PTR_ERR(phy_drd->vbus_boost); | ||
| 725 | if (ret == -EPROBE_DEFER) | ||
| 726 | return ret; | ||
| 727 | |||
| 728 | dev_warn(dev, "Failed to get VBUS boost supply regulator\n"); | ||
| 729 | phy_drd->vbus_boost = NULL; | ||
| 730 | } | ||
| 731 | |||
| 636 | dev_vdbg(dev, "Creating usbdrd_phy phy\n"); | 732 | dev_vdbg(dev, "Creating usbdrd_phy phy\n"); |
| 637 | 733 | ||
| 638 | for (i = 0; i < EXYNOS5_DRDPHYS_NUM; i++) { | 734 | for (i = 0; i < EXYNOS5_DRDPHYS_NUM; i++) { |
| 639 | struct phy *phy = devm_phy_create(dev, NULL, | 735 | struct phy *phy = devm_phy_create(dev, NULL, |
| 640 | &exynos5_usbdrd_phy_ops, | 736 | &exynos5_usbdrd_phy_ops); |
| 641 | NULL); | ||
| 642 | if (IS_ERR(phy)) { | 737 | if (IS_ERR(phy)) { |
| 643 | dev_err(dev, "Failed to create usbdrd_phy phy\n"); | 738 | dev_err(dev, "Failed to create usbdrd_phy phy\n"); |
| 644 | return PTR_ERR(phy); | 739 | return PTR_ERR(phy); |
diff --git a/drivers/phy/phy-exynos5250-sata.c b/drivers/phy/phy-exynos5250-sata.c index 54cf4ae60d29..bc858cc800a1 100644 --- a/drivers/phy/phy-exynos5250-sata.c +++ b/drivers/phy/phy-exynos5250-sata.c | |||
| @@ -210,7 +210,7 @@ static int exynos_sata_phy_probe(struct platform_device *pdev) | |||
| 210 | return ret; | 210 | return ret; |
| 211 | } | 211 | } |
| 212 | 212 | ||
| 213 | sata_phy->phy = devm_phy_create(dev, NULL, &exynos_sata_phy_ops, NULL); | 213 | sata_phy->phy = devm_phy_create(dev, NULL, &exynos_sata_phy_ops); |
| 214 | if (IS_ERR(sata_phy->phy)) { | 214 | if (IS_ERR(sata_phy->phy)) { |
| 215 | clk_disable_unprepare(sata_phy->phyclk); | 215 | clk_disable_unprepare(sata_phy->phyclk); |
| 216 | dev_err(dev, "failed to create PHY\n"); | 216 | dev_err(dev, "failed to create PHY\n"); |
diff --git a/drivers/phy/phy-hix5hd2-sata.c b/drivers/phy/phy-hix5hd2-sata.c index d5d978085c6d..34915b4202f1 100644 --- a/drivers/phy/phy-hix5hd2-sata.c +++ b/drivers/phy/phy-hix5hd2-sata.c | |||
| @@ -156,7 +156,7 @@ static int hix5hd2_sata_phy_probe(struct platform_device *pdev) | |||
| 156 | if (IS_ERR(priv->peri_ctrl)) | 156 | if (IS_ERR(priv->peri_ctrl)) |
| 157 | priv->peri_ctrl = NULL; | 157 | priv->peri_ctrl = NULL; |
| 158 | 158 | ||
| 159 | phy = devm_phy_create(dev, NULL, &hix5hd2_sata_phy_ops, NULL); | 159 | phy = devm_phy_create(dev, NULL, &hix5hd2_sata_phy_ops); |
| 160 | if (IS_ERR(phy)) { | 160 | if (IS_ERR(phy)) { |
| 161 | dev_err(dev, "failed to create PHY\n"); | 161 | dev_err(dev, "failed to create PHY\n"); |
| 162 | return PTR_ERR(phy); | 162 | return PTR_ERR(phy); |
| @@ -164,10 +164,7 @@ static int hix5hd2_sata_phy_probe(struct platform_device *pdev) | |||
| 164 | 164 | ||
| 165 | phy_set_drvdata(phy, priv); | 165 | phy_set_drvdata(phy, priv); |
| 166 | phy_provider = devm_of_phy_provider_register(dev, of_phy_simple_xlate); | 166 | phy_provider = devm_of_phy_provider_register(dev, of_phy_simple_xlate); |
| 167 | if (IS_ERR(phy_provider)) | 167 | return PTR_ERR_OR_ZERO(phy_provider); |
| 168 | return PTR_ERR(phy_provider); | ||
| 169 | |||
| 170 | return 0; | ||
| 171 | } | 168 | } |
| 172 | 169 | ||
| 173 | static const struct of_device_id hix5hd2_sata_phy_of_match[] = { | 170 | static const struct of_device_id hix5hd2_sata_phy_of_match[] = { |
diff --git a/drivers/phy/phy-miphy28lp.c b/drivers/phy/phy-miphy28lp.c new file mode 100644 index 000000000000..e34da13885e8 --- /dev/null +++ b/drivers/phy/phy-miphy28lp.c | |||
| @@ -0,0 +1,1283 @@ | |||
| 1 | /* | ||
| 2 | * Copyright (C) 2014 STMicroelectronics | ||
| 3 | * | ||
| 4 | * STMicroelectronics PHY driver MiPHY28lp (for SoC STiH407). | ||
| 5 | * | ||
| 6 | * Author: Alexandre Torgue <alexandre.torgue@st.com> | ||
| 7 | * | ||
| 8 | * This program is free software; you can redistribute it and/or modify | ||
| 9 | * it under the terms of the GNU General Public License version 2, as | ||
| 10 | * published by the Free Software Foundation. | ||
| 11 | * | ||
| 12 | */ | ||
| 13 | |||
| 14 | #include <linux/platform_device.h> | ||
| 15 | #include <linux/io.h> | ||
| 16 | #include <linux/kernel.h> | ||
| 17 | #include <linux/module.h> | ||
| 18 | #include <linux/of.h> | ||
| 19 | #include <linux/of_platform.h> | ||
| 20 | #include <linux/of_address.h> | ||
| 21 | #include <linux/clk.h> | ||
| 22 | #include <linux/phy/phy.h> | ||
| 23 | #include <linux/delay.h> | ||
| 24 | #include <linux/mfd/syscon.h> | ||
| 25 | #include <linux/regmap.h> | ||
| 26 | #include <linux/reset.h> | ||
| 27 | |||
| 28 | #include <dt-bindings/phy/phy.h> | ||
| 29 | |||
| 30 | /* MiPHY registers */ | ||
| 31 | #define MIPHY_CONF_RESET 0x00 | ||
| 32 | #define RST_APPLI_SW BIT(0) | ||
| 33 | #define RST_CONF_SW BIT(1) | ||
| 34 | #define RST_MACRO_SW BIT(2) | ||
| 35 | |||
| 36 | #define MIPHY_RESET 0x01 | ||
| 37 | #define RST_PLL_SW BIT(0) | ||
| 38 | #define RST_COMP_SW BIT(2) | ||
| 39 | |||
| 40 | #define MIPHY_STATUS_1 0x02 | ||
| 41 | #define PHY_RDY BIT(0) | ||
| 42 | #define HFC_RDY BIT(1) | ||
| 43 | #define HFC_PLL BIT(2) | ||
| 44 | |||
| 45 | #define MIPHY_CONTROL 0x04 | ||
| 46 | #define TERM_EN_SW BIT(2) | ||
| 47 | #define DIS_LINK_RST BIT(3) | ||
| 48 | #define AUTO_RST_RX BIT(4) | ||
| 49 | #define PX_RX_POL BIT(5) | ||
| 50 | |||
| 51 | #define MIPHY_BOUNDARY_SEL 0x0a | ||
| 52 | #define TX_SEL BIT(6) | ||
| 53 | #define SSC_SEL BIT(4) | ||
| 54 | #define GENSEL_SEL BIT(0) | ||
| 55 | |||
| 56 | #define MIPHY_BOUNDARY_1 0x0b | ||
| 57 | #define MIPHY_BOUNDARY_2 0x0c | ||
| 58 | #define SSC_EN_SW BIT(2) | ||
| 59 | |||
| 60 | #define MIPHY_PLL_CLKREF_FREQ 0x0d | ||
| 61 | #define MIPHY_SPEED 0x0e | ||
| 62 | #define TX_SPDSEL_80DEC 0 | ||
| 63 | #define TX_SPDSEL_40DEC 1 | ||
| 64 | #define TX_SPDSEL_20DEC 2 | ||
| 65 | #define RX_SPDSEL_80DEC 0 | ||
| 66 | #define RX_SPDSEL_40DEC (1 << 2) | ||
| 67 | #define RX_SPDSEL_20DEC (2 << 2) | ||
| 68 | |||
| 69 | #define MIPHY_CONF 0x0f | ||
| 70 | #define MIPHY_CTRL_TEST_SEL 0x20 | ||
| 71 | #define MIPHY_CTRL_TEST_1 0x21 | ||
| 72 | #define MIPHY_CTRL_TEST_2 0x22 | ||
| 73 | #define MIPHY_CTRL_TEST_3 0x23 | ||
| 74 | #define MIPHY_CTRL_TEST_4 0x24 | ||
| 75 | #define MIPHY_FEEDBACK_TEST 0x25 | ||
| 76 | #define MIPHY_DEBUG_BUS 0x26 | ||
| 77 | #define MIPHY_DEBUG_STATUS_MSB 0x27 | ||
| 78 | #define MIPHY_DEBUG_STATUS_LSB 0x28 | ||
| 79 | #define MIPHY_PWR_RAIL_1 0x29 | ||
| 80 | #define MIPHY_PWR_RAIL_2 0x2a | ||
| 81 | #define MIPHY_SYNCHAR_CONTROL 0x30 | ||
| 82 | |||
| 83 | #define MIPHY_COMP_FSM_1 0x3a | ||
| 84 | #define COMP_START BIT(6) | ||
| 85 | |||
| 86 | #define MIPHY_COMP_FSM_6 0x3f | ||
| 87 | #define COMP_DONE BIT(7) | ||
| 88 | |||
| 89 | #define MIPHY_COMP_POSTP 0x42 | ||
| 90 | #define MIPHY_TX_CTRL_1 0x49 | ||
| 91 | #define TX_REG_STEP_0V 0 | ||
| 92 | #define TX_REG_STEP_P_25MV 1 | ||
| 93 | #define TX_REG_STEP_P_50MV 2 | ||
| 94 | #define TX_REG_STEP_N_25MV 7 | ||
| 95 | #define TX_REG_STEP_N_50MV 6 | ||
| 96 | #define TX_REG_STEP_N_75MV 5 | ||
| 97 | |||
| 98 | #define MIPHY_TX_CTRL_2 0x4a | ||
| 99 | #define TX_SLEW_SW_40_PS 0 | ||
| 100 | #define TX_SLEW_SW_80_PS 1 | ||
| 101 | #define TX_SLEW_SW_120_PS 2 | ||
| 102 | |||
| 103 | #define MIPHY_TX_CTRL_3 0x4b | ||
| 104 | #define MIPHY_TX_CAL_MAN 0x4e | ||
| 105 | #define TX_SLEW_CAL_MAN_EN BIT(0) | ||
| 106 | |||
| 107 | #define MIPHY_TST_BIAS_BOOST_2 0x62 | ||
| 108 | #define MIPHY_BIAS_BOOST_1 0x63 | ||
| 109 | #define MIPHY_BIAS_BOOST_2 0x64 | ||
| 110 | #define MIPHY_RX_DESBUFF_FDB_2 0x67 | ||
| 111 | #define MIPHY_RX_DESBUFF_FDB_3 0x68 | ||
| 112 | #define MIPHY_SIGDET_COMPENS1 0x69 | ||
| 113 | #define MIPHY_SIGDET_COMPENS2 0x6a | ||
| 114 | #define MIPHY_JITTER_PERIOD 0x6b | ||
| 115 | #define MIPHY_JITTER_AMPLITUDE_1 0x6c | ||
| 116 | #define MIPHY_JITTER_AMPLITUDE_2 0x6d | ||
| 117 | #define MIPHY_JITTER_AMPLITUDE_3 0x6e | ||
| 118 | #define MIPHY_RX_K_GAIN 0x78 | ||
| 119 | #define MIPHY_RX_BUFFER_CTRL 0x7a | ||
| 120 | #define VGA_GAIN BIT(0) | ||
| 121 | #define EQ_DC_GAIN BIT(2) | ||
| 122 | #define EQ_BOOST_GAIN BIT(3) | ||
| 123 | |||
| 124 | #define MIPHY_RX_VGA_GAIN 0x7b | ||
| 125 | #define MIPHY_RX_EQU_GAIN_1 0x7f | ||
| 126 | #define MIPHY_RX_EQU_GAIN_2 0x80 | ||
| 127 | #define MIPHY_RX_EQU_GAIN_3 0x81 | ||
| 128 | #define MIPHY_RX_CAL_CTRL_1 0x97 | ||
| 129 | #define MIPHY_RX_CAL_CTRL_2 0x98 | ||
| 130 | |||
| 131 | #define MIPHY_RX_CAL_OFFSET_CTRL 0x99 | ||
| 132 | #define CAL_OFFSET_VGA_64 (0x03 << 0) | ||
| 133 | #define CAL_OFFSET_THRESHOLD_64 (0x03 << 2) | ||
| 134 | #define VGA_OFFSET_POLARITY BIT(4) | ||
| 135 | #define OFFSET_COMPENSATION_EN BIT(6) | ||
| 136 | |||
| 137 | #define MIPHY_RX_CAL_VGA_STEP 0x9a | ||
| 138 | #define MIPHY_RX_CAL_EYE_MIN 0x9d | ||
| 139 | #define MIPHY_RX_CAL_OPT_LENGTH 0x9f | ||
| 140 | #define MIPHY_RX_LOCK_CTRL_1 0xc1 | ||
| 141 | #define MIPHY_RX_LOCK_SETTINGS_OPT 0xc2 | ||
| 142 | #define MIPHY_RX_LOCK_STEP 0xc4 | ||
| 143 | |||
| 144 | #define MIPHY_RX_SIGDET_SLEEP_OA 0xc9 | ||
| 145 | #define MIPHY_RX_SIGDET_SLEEP_SEL 0xca | ||
| 146 | #define MIPHY_RX_SIGDET_WAIT_SEL 0xcb | ||
| 147 | #define MIPHY_RX_SIGDET_DATA_SEL 0xcc | ||
| 148 | #define EN_ULTRA_LOW_POWER BIT(0) | ||
| 149 | #define EN_FIRST_HALF BIT(1) | ||
| 150 | #define EN_SECOND_HALF BIT(2) | ||
| 151 | #define EN_DIGIT_SIGNAL_CHECK BIT(3) | ||
| 152 | |||
| 153 | #define MIPHY_RX_POWER_CTRL_1 0xcd | ||
| 154 | #define MIPHY_RX_POWER_CTRL_2 0xce | ||
| 155 | #define MIPHY_PLL_CALSET_CTRL 0xd3 | ||
| 156 | #define MIPHY_PLL_CALSET_1 0xd4 | ||
| 157 | #define MIPHY_PLL_CALSET_2 0xd5 | ||
| 158 | #define MIPHY_PLL_CALSET_3 0xd6 | ||
| 159 | #define MIPHY_PLL_CALSET_4 0xd7 | ||
| 160 | #define MIPHY_PLL_SBR_1 0xe3 | ||
| 161 | #define SET_NEW_CHANGE BIT(1) | ||
| 162 | |||
| 163 | #define MIPHY_PLL_SBR_2 0xe4 | ||
| 164 | #define MIPHY_PLL_SBR_3 0xe5 | ||
| 165 | #define MIPHY_PLL_SBR_4 0xe6 | ||
| 166 | #define MIPHY_PLL_COMMON_MISC_2 0xe9 | ||
| 167 | #define START_ACT_FILT BIT(6) | ||
| 168 | |||
| 169 | #define MIPHY_PLL_SPAREIN 0xeb | ||
| 170 | |||
| 171 | /* | ||
| 172 | * On STiH407 the glue logic can be different among MiPHY devices; for example: | ||
| 173 | * MiPHY0: OSC_FORCE_EXT means: | ||
| 174 | * 0: 30MHz crystal clk - 1: 100MHz ext clk routed through MiPHY1 | ||
| 175 | * MiPHY1: OSC_FORCE_EXT means: | ||
| 176 | * 1: 30MHz crystal clk - 0: 100MHz ext clk routed through MiPHY1 | ||
| 177 | * Some devices have not the possibility to check if the osc is ready. | ||
| 178 | */ | ||
| 179 | #define MIPHY_OSC_FORCE_EXT BIT(3) | ||
| 180 | #define MIPHY_OSC_RDY BIT(5) | ||
| 181 | |||
| 182 | #define MIPHY_CTRL_MASK 0x0f | ||
| 183 | #define MIPHY_CTRL_DEFAULT 0 | ||
| 184 | #define MIPHY_CTRL_SYNC_D_EN BIT(2) | ||
| 185 | |||
| 186 | /* SATA / PCIe defines */ | ||
| 187 | #define SATA_CTRL_MASK 0x07 | ||
| 188 | #define PCIE_CTRL_MASK 0xff | ||
| 189 | #define SATA_CTRL_SELECT_SATA 1 | ||
| 190 | #define SATA_CTRL_SELECT_PCIE 0 | ||
| 191 | #define SYSCFG_PCIE_PCIE_VAL 0x80 | ||
| 192 | #define SATA_SPDMODE 1 | ||
| 193 | |||
| 194 | #define MIPHY_SATA_BANK_NB 3 | ||
| 195 | #define MIPHY_PCIE_BANK_NB 2 | ||
| 196 | |||
| 197 | struct miphy28lp_phy { | ||
| 198 | struct phy *phy; | ||
| 199 | struct miphy28lp_dev *phydev; | ||
| 200 | void __iomem *base; | ||
| 201 | void __iomem *pipebase; | ||
| 202 | |||
| 203 | bool osc_force_ext; | ||
| 204 | bool osc_rdy; | ||
| 205 | bool px_rx_pol_inv; | ||
| 206 | bool ssc; | ||
| 207 | bool tx_impedance; | ||
| 208 | |||
| 209 | struct reset_control *miphy_rst; | ||
| 210 | |||
| 211 | u32 sata_gen; | ||
| 212 | |||
| 213 | /* Sysconfig registers offsets needed to configure the device */ | ||
| 214 | u32 syscfg_miphy_ctrl; | ||
| 215 | u32 syscfg_miphy_status; | ||
| 216 | u32 syscfg_pci; | ||
| 217 | u32 syscfg_sata; | ||
| 218 | u8 type; | ||
| 219 | }; | ||
| 220 | |||
| 221 | struct miphy28lp_dev { | ||
| 222 | struct device *dev; | ||
| 223 | struct regmap *regmap; | ||
| 224 | struct mutex miphy_mutex; | ||
| 225 | struct miphy28lp_phy **phys; | ||
| 226 | }; | ||
| 227 | |||
| 228 | struct miphy_initval { | ||
| 229 | u16 reg; | ||
| 230 | u16 val; | ||
| 231 | }; | ||
| 232 | |||
| 233 | enum miphy_sata_gen { SATA_GEN1, SATA_GEN2, SATA_GEN3 }; | ||
| 234 | |||
| 235 | static char *PHY_TYPE_name[] = { "sata-up", "pcie-up", "", "usb3-up" }; | ||
| 236 | |||
| 237 | struct pll_ratio { | ||
| 238 | int clk_ref; | ||
| 239 | int calset_1; | ||
| 240 | int calset_2; | ||
| 241 | int calset_3; | ||
| 242 | int calset_4; | ||
| 243 | int cal_ctrl; | ||
| 244 | }; | ||
| 245 | |||
| 246 | static struct pll_ratio sata_pll_ratio = { | ||
| 247 | .clk_ref = 0x1e, | ||
| 248 | .calset_1 = 0xc8, | ||
| 249 | .calset_2 = 0x00, | ||
| 250 | .calset_3 = 0x00, | ||
| 251 | .calset_4 = 0x00, | ||
| 252 | .cal_ctrl = 0x00, | ||
| 253 | }; | ||
| 254 | |||
| 255 | static struct pll_ratio pcie_pll_ratio = { | ||
| 256 | .clk_ref = 0x1e, | ||
| 257 | .calset_1 = 0xa6, | ||
| 258 | .calset_2 = 0xaa, | ||
| 259 | .calset_3 = 0xaa, | ||
| 260 | .calset_4 = 0x00, | ||
| 261 | .cal_ctrl = 0x00, | ||
| 262 | }; | ||
| 263 | |||
| 264 | static struct pll_ratio usb3_pll_ratio = { | ||
| 265 | .clk_ref = 0x1e, | ||
| 266 | .calset_1 = 0xa6, | ||
| 267 | .calset_2 = 0xaa, | ||
| 268 | .calset_3 = 0xaa, | ||
| 269 | .calset_4 = 0x04, | ||
| 270 | .cal_ctrl = 0x00, | ||
| 271 | }; | ||
| 272 | |||
| 273 | struct miphy28lp_pll_gen { | ||
| 274 | int bank; | ||
| 275 | int speed; | ||
| 276 | int bias_boost_1; | ||
| 277 | int bias_boost_2; | ||
| 278 | int tx_ctrl_1; | ||
| 279 | int tx_ctrl_2; | ||
| 280 | int tx_ctrl_3; | ||
| 281 | int rx_k_gain; | ||
| 282 | int rx_vga_gain; | ||
| 283 | int rx_equ_gain_1; | ||
| 284 | int rx_equ_gain_2; | ||
| 285 | int rx_equ_gain_3; | ||
| 286 | int rx_buff_ctrl; | ||
| 287 | }; | ||
| 288 | |||
| 289 | static struct miphy28lp_pll_gen sata_pll_gen[] = { | ||
| 290 | { | ||
| 291 | .bank = 0x00, | ||
| 292 | .speed = TX_SPDSEL_80DEC | RX_SPDSEL_80DEC, | ||
| 293 | .bias_boost_1 = 0x00, | ||
| 294 | .bias_boost_2 = 0xae, | ||
| 295 | .tx_ctrl_2 = 0x53, | ||
| 296 | .tx_ctrl_3 = 0x00, | ||
| 297 | .rx_buff_ctrl = EQ_BOOST_GAIN | EQ_DC_GAIN | VGA_GAIN, | ||
| 298 | .rx_vga_gain = 0x00, | ||
| 299 | .rx_equ_gain_1 = 0x7d, | ||
| 300 | .rx_equ_gain_2 = 0x56, | ||
| 301 | .rx_equ_gain_3 = 0x00, | ||
| 302 | }, | ||
| 303 | { | ||
| 304 | .bank = 0x01, | ||
| 305 | .speed = TX_SPDSEL_40DEC | RX_SPDSEL_40DEC, | ||
| 306 | .bias_boost_1 = 0x00, | ||
| 307 | .bias_boost_2 = 0xae, | ||
| 308 | .tx_ctrl_2 = 0x72, | ||
| 309 | .tx_ctrl_3 = 0x20, | ||
| 310 | .rx_buff_ctrl = EQ_BOOST_GAIN | EQ_DC_GAIN | VGA_GAIN, | ||
| 311 | .rx_vga_gain = 0x00, | ||
| 312 | .rx_equ_gain_1 = 0x7d, | ||
| 313 | .rx_equ_gain_2 = 0x56, | ||
| 314 | .rx_equ_gain_3 = 0x00, | ||
| 315 | }, | ||
| 316 | { | ||
| 317 | .bank = 0x02, | ||
| 318 | .speed = TX_SPDSEL_20DEC | RX_SPDSEL_20DEC, | ||
| 319 | .bias_boost_1 = 0x00, | ||
| 320 | .bias_boost_2 = 0xae, | ||
| 321 | .tx_ctrl_2 = 0xc0, | ||
| 322 | .tx_ctrl_3 = 0x20, | ||
| 323 | .rx_buff_ctrl = EQ_BOOST_GAIN | EQ_DC_GAIN | VGA_GAIN, | ||
| 324 | .rx_vga_gain = 0x00, | ||
| 325 | .rx_equ_gain_1 = 0x7d, | ||
| 326 | .rx_equ_gain_2 = 0x56, | ||
| 327 | .rx_equ_gain_3 = 0x00, | ||
| 328 | }, | ||
| 329 | }; | ||
| 330 | |||
| 331 | static struct miphy28lp_pll_gen pcie_pll_gen[] = { | ||
| 332 | { | ||
| 333 | .bank = 0x00, | ||
| 334 | .speed = TX_SPDSEL_40DEC | RX_SPDSEL_40DEC, | ||
| 335 | .bias_boost_1 = 0x00, | ||
| 336 | .bias_boost_2 = 0xa5, | ||
| 337 | .tx_ctrl_1 = TX_REG_STEP_N_25MV, | ||
| 338 | .tx_ctrl_2 = 0x71, | ||
| 339 | .tx_ctrl_3 = 0x60, | ||
| 340 | .rx_k_gain = 0x98, | ||
| 341 | .rx_buff_ctrl = EQ_BOOST_GAIN | EQ_DC_GAIN | VGA_GAIN, | ||
| 342 | .rx_vga_gain = 0x00, | ||
| 343 | .rx_equ_gain_1 = 0x79, | ||
| 344 | .rx_equ_gain_2 = 0x56, | ||
| 345 | }, | ||
| 346 | { | ||
| 347 | .bank = 0x01, | ||
| 348 | .speed = TX_SPDSEL_20DEC | RX_SPDSEL_20DEC, | ||
| 349 | .bias_boost_1 = 0x00, | ||
| 350 | .bias_boost_2 = 0xa5, | ||
| 351 | .tx_ctrl_1 = TX_REG_STEP_N_25MV, | ||
| 352 | .tx_ctrl_2 = 0x70, | ||
| 353 | .tx_ctrl_3 = 0x60, | ||
| 354 | .rx_k_gain = 0xcc, | ||
| 355 | .rx_buff_ctrl = EQ_BOOST_GAIN | EQ_DC_GAIN | VGA_GAIN, | ||
| 356 | .rx_vga_gain = 0x00, | ||
| 357 | .rx_equ_gain_1 = 0x78, | ||
| 358 | .rx_equ_gain_2 = 0x07, | ||
| 359 | }, | ||
| 360 | }; | ||
| 361 | |||
| 362 | static inline void miphy28lp_set_reset(struct miphy28lp_phy *miphy_phy) | ||
| 363 | { | ||
| 364 | void *base = miphy_phy->base; | ||
| 365 | u8 val; | ||
| 366 | |||
| 367 | /* Putting Macro in reset */ | ||
| 368 | writeb_relaxed(RST_APPLI_SW, base + MIPHY_CONF_RESET); | ||
| 369 | |||
| 370 | val = RST_APPLI_SW | RST_CONF_SW; | ||
| 371 | writeb_relaxed(val, base + MIPHY_CONF_RESET); | ||
| 372 | |||
| 373 | writeb_relaxed(RST_APPLI_SW, base + MIPHY_CONF_RESET); | ||
| 374 | |||
| 375 | /* Bringing the MIPHY-CPU registers out of reset */ | ||
| 376 | if (miphy_phy->type == PHY_TYPE_PCIE) { | ||
| 377 | val = AUTO_RST_RX | TERM_EN_SW; | ||
| 378 | writeb_relaxed(val, base + MIPHY_CONTROL); | ||
| 379 | } else { | ||
| 380 | val = AUTO_RST_RX | TERM_EN_SW | DIS_LINK_RST; | ||
| 381 | writeb_relaxed(val, base + MIPHY_CONTROL); | ||
| 382 | } | ||
| 383 | } | ||
| 384 | |||
| 385 | static inline void miphy28lp_pll_calibration(struct miphy28lp_phy *miphy_phy, | ||
| 386 | struct pll_ratio *pll_ratio) | ||
| 387 | { | ||
| 388 | void *base = miphy_phy->base; | ||
| 389 | u8 val; | ||
| 390 | |||
| 391 | /* Applying PLL Settings */ | ||
| 392 | writeb_relaxed(0x1d, base + MIPHY_PLL_SPAREIN); | ||
| 393 | writeb_relaxed(pll_ratio->clk_ref, base + MIPHY_PLL_CLKREF_FREQ); | ||
| 394 | |||
| 395 | /* PLL Ratio */ | ||
| 396 | writeb_relaxed(pll_ratio->calset_1, base + MIPHY_PLL_CALSET_1); | ||
| 397 | writeb_relaxed(pll_ratio->calset_2, base + MIPHY_PLL_CALSET_2); | ||
| 398 | writeb_relaxed(pll_ratio->calset_3, base + MIPHY_PLL_CALSET_3); | ||
| 399 | writeb_relaxed(pll_ratio->calset_4, base + MIPHY_PLL_CALSET_4); | ||
| 400 | writeb_relaxed(pll_ratio->cal_ctrl, base + MIPHY_PLL_CALSET_CTRL); | ||
| 401 | |||
| 402 | writeb_relaxed(TX_SEL, base + MIPHY_BOUNDARY_SEL); | ||
| 403 | |||
| 404 | val = (0x68 << 1) | TX_SLEW_CAL_MAN_EN; | ||
| 405 | writeb_relaxed(val, base + MIPHY_TX_CAL_MAN); | ||
| 406 | |||
| 407 | val = VGA_OFFSET_POLARITY | CAL_OFFSET_THRESHOLD_64 | CAL_OFFSET_VGA_64; | ||
| 408 | |||
| 409 | if (miphy_phy->type != PHY_TYPE_SATA) | ||
| 410 | val |= OFFSET_COMPENSATION_EN; | ||
| 411 | |||
| 412 | writeb_relaxed(val, base + MIPHY_RX_CAL_OFFSET_CTRL); | ||
| 413 | |||
| 414 | if (miphy_phy->type == PHY_TYPE_USB3) { | ||
| 415 | writeb_relaxed(0x00, base + MIPHY_CONF); | ||
| 416 | writeb_relaxed(0x70, base + MIPHY_RX_LOCK_STEP); | ||
| 417 | writeb_relaxed(EN_FIRST_HALF, base + MIPHY_RX_SIGDET_SLEEP_OA); | ||
| 418 | writeb_relaxed(EN_FIRST_HALF, base + MIPHY_RX_SIGDET_SLEEP_SEL); | ||
| 419 | writeb_relaxed(EN_FIRST_HALF, base + MIPHY_RX_SIGDET_WAIT_SEL); | ||
| 420 | |||
| 421 | val = EN_DIGIT_SIGNAL_CHECK | EN_FIRST_HALF; | ||
| 422 | writeb_relaxed(val, base + MIPHY_RX_SIGDET_DATA_SEL); | ||
| 423 | } | ||
| 424 | |||
| 425 | } | ||
| 426 | |||
| 427 | static inline void miphy28lp_sata_config_gen(struct miphy28lp_phy *miphy_phy) | ||
| 428 | { | ||
| 429 | void __iomem *base = miphy_phy->base; | ||
| 430 | int i; | ||
| 431 | |||
| 432 | for (i = 0; i < ARRAY_SIZE(sata_pll_gen); i++) { | ||
| 433 | struct miphy28lp_pll_gen *gen = &sata_pll_gen[i]; | ||
| 434 | |||
| 435 | /* Banked settings */ | ||
| 436 | writeb_relaxed(gen->bank, base + MIPHY_CONF); | ||
| 437 | writeb_relaxed(gen->speed, base + MIPHY_SPEED); | ||
| 438 | writeb_relaxed(gen->bias_boost_1, base + MIPHY_BIAS_BOOST_1); | ||
| 439 | writeb_relaxed(gen->bias_boost_2, base + MIPHY_BIAS_BOOST_2); | ||
| 440 | |||
| 441 | /* TX buffer Settings */ | ||
| 442 | writeb_relaxed(gen->tx_ctrl_2, base + MIPHY_TX_CTRL_2); | ||
| 443 | writeb_relaxed(gen->tx_ctrl_3, base + MIPHY_TX_CTRL_3); | ||
| 444 | |||
| 445 | /* RX Buffer Settings */ | ||
| 446 | writeb_relaxed(gen->rx_buff_ctrl, base + MIPHY_RX_BUFFER_CTRL); | ||
| 447 | writeb_relaxed(gen->rx_vga_gain, base + MIPHY_RX_VGA_GAIN); | ||
| 448 | writeb_relaxed(gen->rx_equ_gain_1, base + MIPHY_RX_EQU_GAIN_1); | ||
| 449 | writeb_relaxed(gen->rx_equ_gain_2, base + MIPHY_RX_EQU_GAIN_2); | ||
| 450 | writeb_relaxed(gen->rx_equ_gain_3, base + MIPHY_RX_EQU_GAIN_3); | ||
| 451 | } | ||
| 452 | } | ||
| 453 | |||
| 454 | static inline void miphy28lp_pcie_config_gen(struct miphy28lp_phy *miphy_phy) | ||
| 455 | { | ||
| 456 | void __iomem *base = miphy_phy->base; | ||
| 457 | int i; | ||
| 458 | |||
| 459 | for (i = 0; i < ARRAY_SIZE(pcie_pll_gen); i++) { | ||
| 460 | struct miphy28lp_pll_gen *gen = &pcie_pll_gen[i]; | ||
| 461 | |||
| 462 | /* Banked settings */ | ||
| 463 | writeb_relaxed(gen->bank, base + MIPHY_CONF); | ||
| 464 | writeb_relaxed(gen->speed, base + MIPHY_SPEED); | ||
| 465 | writeb_relaxed(gen->bias_boost_1, base + MIPHY_BIAS_BOOST_1); | ||
| 466 | writeb_relaxed(gen->bias_boost_2, base + MIPHY_BIAS_BOOST_2); | ||
| 467 | |||
| 468 | /* TX buffer Settings */ | ||
| 469 | writeb_relaxed(gen->tx_ctrl_1, base + MIPHY_TX_CTRL_1); | ||
| 470 | writeb_relaxed(gen->tx_ctrl_2, base + MIPHY_TX_CTRL_2); | ||
| 471 | writeb_relaxed(gen->tx_ctrl_3, base + MIPHY_TX_CTRL_3); | ||
| 472 | |||
| 473 | writeb_relaxed(gen->rx_k_gain, base + MIPHY_RX_K_GAIN); | ||
| 474 | |||
| 475 | /* RX Buffer Settings */ | ||
| 476 | writeb_relaxed(gen->rx_buff_ctrl, base + MIPHY_RX_BUFFER_CTRL); | ||
| 477 | writeb_relaxed(gen->rx_vga_gain, base + MIPHY_RX_VGA_GAIN); | ||
| 478 | writeb_relaxed(gen->rx_equ_gain_1, base + MIPHY_RX_EQU_GAIN_1); | ||
| 479 | writeb_relaxed(gen->rx_equ_gain_2, base + MIPHY_RX_EQU_GAIN_2); | ||
| 480 | } | ||
| 481 | } | ||
| 482 | |||
| 483 | static inline int miphy28lp_wait_compensation(struct miphy28lp_phy *miphy_phy) | ||
| 484 | { | ||
| 485 | unsigned long finish = jiffies + 5 * HZ; | ||
| 486 | u8 val; | ||
| 487 | |||
| 488 | /* Waiting for Compensation to complete */ | ||
| 489 | do { | ||
| 490 | val = readb_relaxed(miphy_phy->base + MIPHY_COMP_FSM_6); | ||
| 491 | |||
| 492 | if (time_after_eq(jiffies, finish)) | ||
| 493 | return -EBUSY; | ||
| 494 | cpu_relax(); | ||
| 495 | } while (!(val & COMP_DONE)); | ||
| 496 | |||
| 497 | return 0; | ||
| 498 | } | ||
| 499 | |||
| 500 | |||
| 501 | static inline int miphy28lp_compensation(struct miphy28lp_phy *miphy_phy, | ||
| 502 | struct pll_ratio *pll_ratio) | ||
| 503 | { | ||
| 504 | void __iomem *base = miphy_phy->base; | ||
| 505 | |||
| 506 | /* Poll for HFC ready after reset release */ | ||
| 507 | /* Compensation measurement */ | ||
| 508 | writeb_relaxed(RST_PLL_SW | RST_COMP_SW, base + MIPHY_RESET); | ||
| 509 | |||
| 510 | writeb_relaxed(0x00, base + MIPHY_PLL_COMMON_MISC_2); | ||
| 511 | writeb_relaxed(pll_ratio->clk_ref, base + MIPHY_PLL_CLKREF_FREQ); | ||
| 512 | writeb_relaxed(COMP_START, base + MIPHY_COMP_FSM_1); | ||
| 513 | |||
| 514 | if (miphy_phy->type == PHY_TYPE_PCIE) | ||
| 515 | writeb_relaxed(RST_PLL_SW, base + MIPHY_RESET); | ||
| 516 | |||
| 517 | writeb_relaxed(0x00, base + MIPHY_RESET); | ||
| 518 | writeb_relaxed(START_ACT_FILT, base + MIPHY_PLL_COMMON_MISC_2); | ||
| 519 | writeb_relaxed(SET_NEW_CHANGE, base + MIPHY_PLL_SBR_1); | ||
| 520 | |||
| 521 | /* TX compensation offset to re-center TX impedance */ | ||
| 522 | writeb_relaxed(0x00, base + MIPHY_COMP_POSTP); | ||
| 523 | |||
| 524 | if (miphy_phy->type == PHY_TYPE_PCIE) | ||
| 525 | return miphy28lp_wait_compensation(miphy_phy); | ||
| 526 | |||
| 527 | return 0; | ||
| 528 | } | ||
| 529 | |||
| 530 | static inline void miphy28_usb3_miphy_reset(struct miphy28lp_phy *miphy_phy) | ||
| 531 | { | ||
| 532 | void __iomem *base = miphy_phy->base; | ||
| 533 | u8 val; | ||
| 534 | |||
| 535 | /* MIPHY Reset */ | ||
| 536 | writeb_relaxed(RST_APPLI_SW, base + MIPHY_CONF_RESET); | ||
| 537 | writeb_relaxed(0x00, base + MIPHY_CONF_RESET); | ||
| 538 | writeb_relaxed(RST_COMP_SW, base + MIPHY_RESET); | ||
| 539 | |||
| 540 | val = RST_COMP_SW | RST_PLL_SW; | ||
| 541 | writeb_relaxed(val, base + MIPHY_RESET); | ||
| 542 | |||
| 543 | writeb_relaxed(0x00, base + MIPHY_PLL_COMMON_MISC_2); | ||
| 544 | writeb_relaxed(0x1e, base + MIPHY_PLL_CLKREF_FREQ); | ||
| 545 | writeb_relaxed(COMP_START, base + MIPHY_COMP_FSM_1); | ||
| 546 | writeb_relaxed(RST_PLL_SW, base + MIPHY_RESET); | ||
| 547 | writeb_relaxed(0x00, base + MIPHY_RESET); | ||
| 548 | writeb_relaxed(START_ACT_FILT, base + MIPHY_PLL_COMMON_MISC_2); | ||
| 549 | writeb_relaxed(0x00, base + MIPHY_CONF); | ||
| 550 | writeb_relaxed(0x00, base + MIPHY_BOUNDARY_1); | ||
| 551 | writeb_relaxed(0x00, base + MIPHY_TST_BIAS_BOOST_2); | ||
| 552 | writeb_relaxed(0x00, base + MIPHY_CONF); | ||
| 553 | writeb_relaxed(SET_NEW_CHANGE, base + MIPHY_PLL_SBR_1); | ||
| 554 | writeb_relaxed(0xa5, base + MIPHY_DEBUG_BUS); | ||
| 555 | writeb_relaxed(0x00, base + MIPHY_CONF); | ||
| 556 | } | ||
| 557 | |||
| 558 | static void miphy_sata_tune_ssc(struct miphy28lp_phy *miphy_phy) | ||
| 559 | { | ||
| 560 | void __iomem *base = miphy_phy->base; | ||
| 561 | u8 val; | ||
| 562 | |||
| 563 | /* Compensate Tx impedance to avoid out of range values */ | ||
| 564 | /* | ||
| 565 | * Enable the SSC on PLL for all banks | ||
| 566 | * SSC Modulation @ 31 KHz and 4000 ppm modulation amp | ||
| 567 | */ | ||
| 568 | val = readb_relaxed(base + MIPHY_BOUNDARY_2); | ||
| 569 | val |= SSC_EN_SW; | ||
| 570 | writeb_relaxed(val, base + MIPHY_BOUNDARY_2); | ||
| 571 | |||
| 572 | val = readb_relaxed(base + MIPHY_BOUNDARY_SEL); | ||
| 573 | val |= SSC_SEL; | ||
| 574 | writeb_relaxed(val, base + MIPHY_BOUNDARY_SEL); | ||
| 575 | |||
| 576 | for (val = 0; val < MIPHY_SATA_BANK_NB; val++) { | ||
| 577 | writeb_relaxed(val, base + MIPHY_CONF); | ||
| 578 | |||
| 579 | /* Add value to each reference clock cycle */ | ||
| 580 | /* and define the period length of the SSC */ | ||
| 581 | writeb_relaxed(0x3c, base + MIPHY_PLL_SBR_2); | ||
| 582 | writeb_relaxed(0x6c, base + MIPHY_PLL_SBR_3); | ||
| 583 | writeb_relaxed(0x81, base + MIPHY_PLL_SBR_4); | ||
| 584 | |||
| 585 | /* Clear any previous request */ | ||
| 586 | writeb_relaxed(0x00, base + MIPHY_PLL_SBR_1); | ||
| 587 | |||
| 588 | /* requests the PLL to take in account new parameters */ | ||
| 589 | writeb_relaxed(SET_NEW_CHANGE, base + MIPHY_PLL_SBR_1); | ||
| 590 | |||
| 591 | /* To be sure there is no other pending requests */ | ||
| 592 | writeb_relaxed(0x00, base + MIPHY_PLL_SBR_1); | ||
| 593 | } | ||
| 594 | } | ||
| 595 | |||
| 596 | static void miphy_pcie_tune_ssc(struct miphy28lp_phy *miphy_phy) | ||
| 597 | { | ||
| 598 | void __iomem *base = miphy_phy->base; | ||
| 599 | u8 val; | ||
| 600 | |||
| 601 | /* Compensate Tx impedance to avoid out of range values */ | ||
| 602 | /* | ||
| 603 | * Enable the SSC on PLL for all banks | ||
| 604 | * SSC Modulation @ 31 KHz and 4000 ppm modulation amp | ||
| 605 | */ | ||
| 606 | val = readb_relaxed(base + MIPHY_BOUNDARY_2); | ||
| 607 | val |= SSC_EN_SW; | ||
| 608 | writeb_relaxed(val, base + MIPHY_BOUNDARY_2); | ||
| 609 | |||
| 610 | val = readb_relaxed(base + MIPHY_BOUNDARY_SEL); | ||
| 611 | val |= SSC_SEL; | ||
| 612 | writeb_relaxed(val, base + MIPHY_BOUNDARY_SEL); | ||
| 613 | |||
| 614 | for (val = 0; val < MIPHY_PCIE_BANK_NB; val++) { | ||
| 615 | writeb_relaxed(val, base + MIPHY_CONF); | ||
| 616 | |||
| 617 | /* Validate Step component */ | ||
| 618 | writeb_relaxed(0x69, base + MIPHY_PLL_SBR_3); | ||
| 619 | writeb_relaxed(0x21, base + MIPHY_PLL_SBR_4); | ||
| 620 | |||
| 621 | /* Validate Period component */ | ||
| 622 | writeb_relaxed(0x3c, base + MIPHY_PLL_SBR_2); | ||
| 623 | writeb_relaxed(0x21, base + MIPHY_PLL_SBR_4); | ||
| 624 | |||
| 625 | /* Clear any previous request */ | ||
| 626 | writeb_relaxed(0x00, base + MIPHY_PLL_SBR_1); | ||
| 627 | |||
| 628 | /* requests the PLL to take in account new parameters */ | ||
| 629 | writeb_relaxed(SET_NEW_CHANGE, base + MIPHY_PLL_SBR_1); | ||
| 630 | |||
| 631 | /* To be sure there is no other pending requests */ | ||
| 632 | writeb_relaxed(0x00, base + MIPHY_PLL_SBR_1); | ||
| 633 | } | ||
| 634 | } | ||
| 635 | |||
| 636 | static inline void miphy_tune_tx_impedance(struct miphy28lp_phy *miphy_phy) | ||
| 637 | { | ||
| 638 | /* Compensate Tx impedance to avoid out of range values */ | ||
| 639 | writeb_relaxed(0x02, miphy_phy->base + MIPHY_COMP_POSTP); | ||
| 640 | } | ||
| 641 | |||
| 642 | static inline int miphy28lp_configure_sata(struct miphy28lp_phy *miphy_phy) | ||
| 643 | { | ||
| 644 | void __iomem *base = miphy_phy->base; | ||
| 645 | int err; | ||
| 646 | u8 val; | ||
| 647 | |||
| 648 | /* Putting Macro in reset */ | ||
| 649 | miphy28lp_set_reset(miphy_phy); | ||
| 650 | |||
| 651 | /* PLL calibration */ | ||
| 652 | miphy28lp_pll_calibration(miphy_phy, &sata_pll_ratio); | ||
| 653 | |||
| 654 | /* Banked settings Gen1/Gen2/Gen3 */ | ||
| 655 | miphy28lp_sata_config_gen(miphy_phy); | ||
| 656 | |||
| 657 | /* Power control */ | ||
| 658 | /* Input bridge enable, manual input bridge control */ | ||
| 659 | writeb_relaxed(0x21, base + MIPHY_RX_POWER_CTRL_1); | ||
| 660 | |||
| 661 | /* Macro out of reset */ | ||
| 662 | writeb_relaxed(0x00, base + MIPHY_CONF_RESET); | ||
| 663 | |||
| 664 | /* Poll for HFC ready after reset release */ | ||
| 665 | /* Compensation measurement */ | ||
| 666 | err = miphy28lp_compensation(miphy_phy, &sata_pll_ratio); | ||
| 667 | if (err) | ||
| 668 | return err; | ||
| 669 | |||
| 670 | if (miphy_phy->px_rx_pol_inv) { | ||
| 671 | /* Invert Rx polarity */ | ||
| 672 | val = readb_relaxed(miphy_phy->base + MIPHY_CONTROL); | ||
| 673 | val |= PX_RX_POL; | ||
| 674 | writeb_relaxed(val, miphy_phy->base + MIPHY_CONTROL); | ||
| 675 | } | ||
| 676 | |||
| 677 | if (miphy_phy->ssc) | ||
| 678 | miphy_sata_tune_ssc(miphy_phy); | ||
| 679 | |||
| 680 | if (miphy_phy->tx_impedance) | ||
| 681 | miphy_tune_tx_impedance(miphy_phy); | ||
| 682 | |||
| 683 | return 0; | ||
| 684 | } | ||
| 685 | |||
| 686 | static inline int miphy28lp_configure_pcie(struct miphy28lp_phy *miphy_phy) | ||
| 687 | { | ||
| 688 | void __iomem *base = miphy_phy->base; | ||
| 689 | int err; | ||
| 690 | |||
| 691 | /* Putting Macro in reset */ | ||
| 692 | miphy28lp_set_reset(miphy_phy); | ||
| 693 | |||
| 694 | /* PLL calibration */ | ||
| 695 | miphy28lp_pll_calibration(miphy_phy, &pcie_pll_ratio); | ||
| 696 | |||
| 697 | /* Banked settings Gen1/Gen2 */ | ||
| 698 | miphy28lp_pcie_config_gen(miphy_phy); | ||
| 699 | |||
| 700 | /* Power control */ | ||
| 701 | /* Input bridge enable, manual input bridge control */ | ||
| 702 | writeb_relaxed(0x21, base + MIPHY_RX_POWER_CTRL_1); | ||
| 703 | |||
| 704 | /* Macro out of reset */ | ||
| 705 | writeb_relaxed(0x00, base + MIPHY_CONF_RESET); | ||
| 706 | |||
| 707 | /* Poll for HFC ready after reset release */ | ||
| 708 | /* Compensation measurement */ | ||
| 709 | err = miphy28lp_compensation(miphy_phy, &pcie_pll_ratio); | ||
| 710 | if (err) | ||
| 711 | return err; | ||
| 712 | |||
| 713 | if (miphy_phy->ssc) | ||
| 714 | miphy_pcie_tune_ssc(miphy_phy); | ||
| 715 | |||
| 716 | if (miphy_phy->tx_impedance) | ||
| 717 | miphy_tune_tx_impedance(miphy_phy); | ||
| 718 | |||
| 719 | return 0; | ||
| 720 | } | ||
| 721 | |||
| 722 | |||
| 723 | static inline void miphy28lp_configure_usb3(struct miphy28lp_phy *miphy_phy) | ||
| 724 | { | ||
| 725 | void __iomem *base = miphy_phy->base; | ||
| 726 | u8 val; | ||
| 727 | |||
| 728 | /* Putting Macro in reset */ | ||
| 729 | miphy28lp_set_reset(miphy_phy); | ||
| 730 | |||
| 731 | /* PLL calibration */ | ||
| 732 | miphy28lp_pll_calibration(miphy_phy, &usb3_pll_ratio); | ||
| 733 | |||
| 734 | /* Writing The Speed Rate */ | ||
| 735 | writeb_relaxed(0x00, base + MIPHY_CONF); | ||
| 736 | |||
| 737 | val = RX_SPDSEL_20DEC | TX_SPDSEL_20DEC; | ||
| 738 | writeb_relaxed(val, base + MIPHY_SPEED); | ||
| 739 | |||
| 740 | /* RX Channel compensation and calibration */ | ||
| 741 | writeb_relaxed(0x1c, base + MIPHY_RX_LOCK_SETTINGS_OPT); | ||
| 742 | writeb_relaxed(0x51, base + MIPHY_RX_CAL_CTRL_1); | ||
| 743 | writeb_relaxed(0x70, base + MIPHY_RX_CAL_CTRL_2); | ||
| 744 | |||
| 745 | val = OFFSET_COMPENSATION_EN | VGA_OFFSET_POLARITY | | ||
| 746 | CAL_OFFSET_THRESHOLD_64 | CAL_OFFSET_VGA_64; | ||
| 747 | writeb_relaxed(val, base + MIPHY_RX_CAL_OFFSET_CTRL); | ||
| 748 | writeb_relaxed(0x22, base + MIPHY_RX_CAL_VGA_STEP); | ||
| 749 | writeb_relaxed(0x0e, base + MIPHY_RX_CAL_OPT_LENGTH); | ||
| 750 | |||
| 751 | val = EQ_DC_GAIN | VGA_GAIN; | ||
| 752 | writeb_relaxed(val, base + MIPHY_RX_BUFFER_CTRL); | ||
| 753 | writeb_relaxed(0x78, base + MIPHY_RX_EQU_GAIN_1); | ||
| 754 | writeb_relaxed(0x1b, base + MIPHY_SYNCHAR_CONTROL); | ||
| 755 | |||
| 756 | /* TX compensation offset to re-center TX impedance */ | ||
| 757 | writeb_relaxed(0x02, base + MIPHY_COMP_POSTP); | ||
| 758 | |||
| 759 | /* Enable GENSEL_SEL and SSC */ | ||
| 760 | /* TX_SEL=0 swing preemp forced by pipe registres */ | ||
| 761 | val = SSC_SEL | GENSEL_SEL; | ||
| 762 | writeb_relaxed(val, base + MIPHY_BOUNDARY_SEL); | ||
| 763 | |||
| 764 | /* MIPHY Bias boost */ | ||
| 765 | writeb_relaxed(0x00, base + MIPHY_BIAS_BOOST_1); | ||
| 766 | writeb_relaxed(0xa7, base + MIPHY_BIAS_BOOST_2); | ||
| 767 | |||
| 768 | /* SSC modulation */ | ||
| 769 | writeb_relaxed(SSC_EN_SW, base + MIPHY_BOUNDARY_2); | ||
| 770 | |||
| 771 | /* MIPHY TX control */ | ||
| 772 | writeb_relaxed(0x00, base + MIPHY_CONF); | ||
| 773 | |||
| 774 | /* Validate Step component */ | ||
| 775 | writeb_relaxed(0x5a, base + MIPHY_PLL_SBR_3); | ||
| 776 | writeb_relaxed(0xa0, base + MIPHY_PLL_SBR_4); | ||
| 777 | |||
| 778 | /* Validate Period component */ | ||
| 779 | writeb_relaxed(0x3c, base + MIPHY_PLL_SBR_2); | ||
| 780 | writeb_relaxed(0xa1, base + MIPHY_PLL_SBR_4); | ||
| 781 | |||
| 782 | /* Clear any previous request */ | ||
| 783 | writeb_relaxed(0x00, base + MIPHY_PLL_SBR_1); | ||
| 784 | |||
| 785 | /* requests the PLL to take in account new parameters */ | ||
| 786 | writeb_relaxed(0x02, base + MIPHY_PLL_SBR_1); | ||
| 787 | |||
| 788 | /* To be sure there is no other pending requests */ | ||
| 789 | writeb_relaxed(0x00, base + MIPHY_PLL_SBR_1); | ||
| 790 | |||
| 791 | /* Rx PI controller settings */ | ||
| 792 | writeb_relaxed(0xca, base + MIPHY_RX_K_GAIN); | ||
| 793 | |||
| 794 | /* MIPHY RX input bridge control */ | ||
| 795 | /* INPUT_BRIDGE_EN_SW=1, manual input bridge control[0]=1 */ | ||
| 796 | writeb_relaxed(0x21, base + MIPHY_RX_POWER_CTRL_1); | ||
| 797 | writeb_relaxed(0x29, base + MIPHY_RX_POWER_CTRL_1); | ||
| 798 | writeb_relaxed(0x1a, base + MIPHY_RX_POWER_CTRL_2); | ||
| 799 | |||
| 800 | /* MIPHY Reset for usb3 */ | ||
| 801 | miphy28_usb3_miphy_reset(miphy_phy); | ||
| 802 | } | ||
| 803 | |||
| 804 | static inline int miphy_is_ready(struct miphy28lp_phy *miphy_phy) | ||
| 805 | { | ||
| 806 | unsigned long finish = jiffies + 5 * HZ; | ||
| 807 | u8 mask = HFC_PLL | HFC_RDY; | ||
| 808 | u8 val; | ||
| 809 | |||
| 810 | /* | ||
| 811 | * For PCIe and USB3 check only that PLL and HFC are ready | ||
| 812 | * For SATA check also that phy is ready! | ||
| 813 | */ | ||
| 814 | if (miphy_phy->type == PHY_TYPE_SATA) | ||
| 815 | mask |= PHY_RDY; | ||
| 816 | |||
| 817 | do { | ||
| 818 | val = readb_relaxed(miphy_phy->base + MIPHY_STATUS_1); | ||
| 819 | if ((val & mask) != mask) | ||
| 820 | cpu_relax(); | ||
| 821 | else | ||
| 822 | return 0; | ||
| 823 | } while (!time_after_eq(jiffies, finish)); | ||
| 824 | |||
| 825 | return -EBUSY; | ||
| 826 | } | ||
| 827 | |||
| 828 | static int miphy_osc_is_ready(struct miphy28lp_phy *miphy_phy) | ||
| 829 | { | ||
| 830 | struct miphy28lp_dev *miphy_dev = miphy_phy->phydev; | ||
| 831 | unsigned long finish = jiffies + 5 * HZ; | ||
| 832 | u32 val; | ||
| 833 | |||
| 834 | if (!miphy_phy->osc_rdy) | ||
| 835 | return 0; | ||
| 836 | |||
| 837 | if (!miphy_phy->syscfg_miphy_status) | ||
| 838 | return -EINVAL; | ||
| 839 | |||
| 840 | do { | ||
| 841 | regmap_read(miphy_dev->regmap, miphy_phy->syscfg_miphy_status, | ||
| 842 | &val); | ||
| 843 | |||
| 844 | if ((val & MIPHY_OSC_RDY) != MIPHY_OSC_RDY) | ||
| 845 | cpu_relax(); | ||
| 846 | else | ||
| 847 | return 0; | ||
| 848 | } while (!time_after_eq(jiffies, finish)); | ||
| 849 | |||
| 850 | return -EBUSY; | ||
| 851 | } | ||
| 852 | |||
| 853 | static int miphy28lp_get_resource_byname(struct device_node *child, | ||
| 854 | char *rname, struct resource *res) | ||
| 855 | { | ||
| 856 | int index; | ||
| 857 | |||
| 858 | index = of_property_match_string(child, "reg-names", rname); | ||
| 859 | if (index < 0) | ||
| 860 | return -ENODEV; | ||
| 861 | |||
| 862 | return of_address_to_resource(child, index, res); | ||
| 863 | } | ||
| 864 | |||
| 865 | static int miphy28lp_get_one_addr(struct device *dev, | ||
| 866 | struct device_node *child, char *rname, | ||
| 867 | void __iomem **base) | ||
| 868 | { | ||
| 869 | struct resource res; | ||
| 870 | int ret; | ||
| 871 | |||
| 872 | ret = miphy28lp_get_resource_byname(child, rname, &res); | ||
| 873 | if (!ret) { | ||
| 874 | *base = devm_ioremap(dev, res.start, resource_size(&res)); | ||
| 875 | if (!*base) { | ||
| 876 | dev_err(dev, "failed to ioremap %s address region\n" | ||
| 877 | , rname); | ||
| 878 | return -ENOENT; | ||
| 879 | } | ||
| 880 | } | ||
| 881 | |||
| 882 | return 0; | ||
| 883 | } | ||
| 884 | |||
| 885 | /* MiPHY reset and sysconf setup */ | ||
| 886 | static int miphy28lp_setup(struct miphy28lp_phy *miphy_phy, u32 miphy_val) | ||
| 887 | { | ||
| 888 | int err; | ||
| 889 | struct miphy28lp_dev *miphy_dev = miphy_phy->phydev; | ||
| 890 | |||
| 891 | if (!miphy_phy->syscfg_miphy_ctrl) | ||
| 892 | return -EINVAL; | ||
| 893 | |||
| 894 | err = reset_control_assert(miphy_phy->miphy_rst); | ||
| 895 | if (err) { | ||
| 896 | dev_err(miphy_dev->dev, "unable to bring out of miphy reset\n"); | ||
| 897 | return err; | ||
| 898 | } | ||
| 899 | |||
| 900 | if (miphy_phy->osc_force_ext) | ||
| 901 | miphy_val |= MIPHY_OSC_FORCE_EXT; | ||
| 902 | |||
| 903 | regmap_update_bits(miphy_dev->regmap, miphy_phy->syscfg_miphy_ctrl, | ||
| 904 | MIPHY_CTRL_MASK, miphy_val); | ||
| 905 | |||
| 906 | err = reset_control_deassert(miphy_phy->miphy_rst); | ||
| 907 | if (err) { | ||
| 908 | dev_err(miphy_dev->dev, "unable to bring out of miphy reset\n"); | ||
| 909 | return err; | ||
| 910 | } | ||
| 911 | |||
| 912 | return miphy_osc_is_ready(miphy_phy); | ||
| 913 | } | ||
| 914 | |||
| 915 | static int miphy28lp_init_sata(struct miphy28lp_phy *miphy_phy) | ||
| 916 | { | ||
| 917 | struct miphy28lp_dev *miphy_dev = miphy_phy->phydev; | ||
| 918 | int err, sata_conf = SATA_CTRL_SELECT_SATA; | ||
| 919 | |||
| 920 | if ((!miphy_phy->syscfg_sata) || (!miphy_phy->syscfg_pci) | ||
| 921 | || (!miphy_phy->base)) | ||
| 922 | return -EINVAL; | ||
| 923 | |||
| 924 | dev_info(miphy_dev->dev, "sata-up mode, addr 0x%p\n", miphy_phy->base); | ||
| 925 | |||
| 926 | /* Configure the glue-logic */ | ||
| 927 | sata_conf |= ((miphy_phy->sata_gen - SATA_GEN1) << SATA_SPDMODE); | ||
| 928 | |||
| 929 | regmap_update_bits(miphy_dev->regmap, miphy_phy->syscfg_sata, | ||
| 930 | SATA_CTRL_MASK, sata_conf); | ||
| 931 | |||
| 932 | regmap_update_bits(miphy_dev->regmap, miphy_phy->syscfg_pci, | ||
| 933 | PCIE_CTRL_MASK, SATA_CTRL_SELECT_PCIE); | ||
| 934 | |||
| 935 | /* MiPHY path and clocking init */ | ||
| 936 | err = miphy28lp_setup(miphy_phy, MIPHY_CTRL_DEFAULT); | ||
| 937 | |||
| 938 | if (err) { | ||
| 939 | dev_err(miphy_dev->dev, "SATA phy setup failed\n"); | ||
| 940 | return err; | ||
| 941 | } | ||
| 942 | |||
| 943 | /* initialize miphy */ | ||
| 944 | miphy28lp_configure_sata(miphy_phy); | ||
| 945 | |||
| 946 | return miphy_is_ready(miphy_phy); | ||
| 947 | } | ||
| 948 | |||
| 949 | static int miphy28lp_init_pcie(struct miphy28lp_phy *miphy_phy) | ||
| 950 | { | ||
| 951 | struct miphy28lp_dev *miphy_dev = miphy_phy->phydev; | ||
| 952 | int err; | ||
| 953 | |||
| 954 | if ((!miphy_phy->syscfg_sata) || (!miphy_phy->syscfg_pci) | ||
| 955 | || (!miphy_phy->base) || (!miphy_phy->pipebase)) | ||
| 956 | return -EINVAL; | ||
| 957 | |||
| 958 | dev_info(miphy_dev->dev, "pcie-up mode, addr 0x%p\n", miphy_phy->base); | ||
| 959 | |||
| 960 | /* Configure the glue-logic */ | ||
| 961 | regmap_update_bits(miphy_dev->regmap, miphy_phy->syscfg_sata, | ||
| 962 | SATA_CTRL_MASK, SATA_CTRL_SELECT_PCIE); | ||
| 963 | |||
| 964 | regmap_update_bits(miphy_dev->regmap, miphy_phy->syscfg_pci, | ||
| 965 | PCIE_CTRL_MASK, SYSCFG_PCIE_PCIE_VAL); | ||
| 966 | |||
| 967 | /* MiPHY path and clocking init */ | ||
| 968 | err = miphy28lp_setup(miphy_phy, MIPHY_CTRL_DEFAULT); | ||
| 969 | |||
| 970 | if (err) { | ||
| 971 | dev_err(miphy_dev->dev, "PCIe phy setup failed\n"); | ||
| 972 | return err; | ||
| 973 | } | ||
| 974 | |||
| 975 | /* initialize miphy */ | ||
| 976 | err = miphy28lp_configure_pcie(miphy_phy); | ||
| 977 | if (err) | ||
| 978 | return err; | ||
| 979 | |||
| 980 | /* PIPE Wrapper Configuration */ | ||
| 981 | writeb_relaxed(0x68, miphy_phy->pipebase + 0x104); /* Rise_0 */ | ||
| 982 | writeb_relaxed(0x61, miphy_phy->pipebase + 0x105); /* Rise_1 */ | ||
| 983 | writeb_relaxed(0x68, miphy_phy->pipebase + 0x108); /* Fall_0 */ | ||
| 984 | writeb_relaxed(0x61, miphy_phy->pipebase + 0x109); /* Fall-1 */ | ||
| 985 | writeb_relaxed(0x68, miphy_phy->pipebase + 0x10c); /* Threshold_0 */ | ||
| 986 | writeb_relaxed(0x60, miphy_phy->pipebase + 0x10d); /* Threshold_1 */ | ||
| 987 | |||
| 988 | /* Wait for phy_ready */ | ||
| 989 | return miphy_is_ready(miphy_phy); | ||
| 990 | } | ||
| 991 | |||
| 992 | static int miphy28lp_init_usb3(struct miphy28lp_phy *miphy_phy) | ||
| 993 | { | ||
| 994 | struct miphy28lp_dev *miphy_dev = miphy_phy->phydev; | ||
| 995 | int err; | ||
| 996 | |||
| 997 | if ((!miphy_phy->base) || (!miphy_phy->pipebase)) | ||
| 998 | return -EINVAL; | ||
| 999 | |||
| 1000 | dev_info(miphy_dev->dev, "usb3-up mode, addr 0x%p\n", miphy_phy->base); | ||
| 1001 | |||
| 1002 | /* MiPHY path and clocking init */ | ||
| 1003 | err = miphy28lp_setup(miphy_phy, MIPHY_CTRL_SYNC_D_EN); | ||
| 1004 | if (err) { | ||
| 1005 | dev_err(miphy_dev->dev, "USB3 phy setup failed\n"); | ||
| 1006 | return err; | ||
| 1007 | } | ||
| 1008 | |||
| 1009 | /* initialize miphy */ | ||
| 1010 | miphy28lp_configure_usb3(miphy_phy); | ||
| 1011 | |||
| 1012 | /* PIPE Wrapper Configuration */ | ||
| 1013 | writeb_relaxed(0x68, miphy_phy->pipebase + 0x23); | ||
| 1014 | writeb_relaxed(0x61, miphy_phy->pipebase + 0x24); | ||
| 1015 | writeb_relaxed(0x68, miphy_phy->pipebase + 0x26); | ||
| 1016 | writeb_relaxed(0x61, miphy_phy->pipebase + 0x27); | ||
| 1017 | writeb_relaxed(0x18, miphy_phy->pipebase + 0x29); | ||
| 1018 | writeb_relaxed(0x61, miphy_phy->pipebase + 0x2a); | ||
| 1019 | |||
| 1020 | /* pipe Wrapper usb3 TX swing de-emph margin PREEMPH[7:4], SWING[3:0] */ | ||
| 1021 | writeb_relaxed(0X67, miphy_phy->pipebase + 0x68); | ||
| 1022 | writeb_relaxed(0x0d, miphy_phy->pipebase + 0x69); | ||
| 1023 | writeb_relaxed(0X67, miphy_phy->pipebase + 0x6a); | ||
| 1024 | writeb_relaxed(0X0d, miphy_phy->pipebase + 0x6b); | ||
| 1025 | writeb_relaxed(0X67, miphy_phy->pipebase + 0x6c); | ||
| 1026 | writeb_relaxed(0X0d, miphy_phy->pipebase + 0x6d); | ||
| 1027 | writeb_relaxed(0X67, miphy_phy->pipebase + 0x6e); | ||
| 1028 | writeb_relaxed(0X0d, miphy_phy->pipebase + 0x6f); | ||
| 1029 | |||
| 1030 | return miphy_is_ready(miphy_phy); | ||
| 1031 | } | ||
| 1032 | |||
| 1033 | static int miphy28lp_init(struct phy *phy) | ||
| 1034 | { | ||
| 1035 | struct miphy28lp_phy *miphy_phy = phy_get_drvdata(phy); | ||
| 1036 | struct miphy28lp_dev *miphy_dev = miphy_phy->phydev; | ||
| 1037 | int ret; | ||
| 1038 | |||
| 1039 | mutex_lock(&miphy_dev->miphy_mutex); | ||
| 1040 | |||
| 1041 | switch (miphy_phy->type) { | ||
| 1042 | |||
| 1043 | case PHY_TYPE_SATA: | ||
| 1044 | ret = miphy28lp_init_sata(miphy_phy); | ||
| 1045 | break; | ||
| 1046 | case PHY_TYPE_PCIE: | ||
| 1047 | ret = miphy28lp_init_pcie(miphy_phy); | ||
| 1048 | break; | ||
| 1049 | case PHY_TYPE_USB3: | ||
| 1050 | ret = miphy28lp_init_usb3(miphy_phy); | ||
| 1051 | break; | ||
| 1052 | default: | ||
| 1053 | return -EINVAL; | ||
| 1054 | } | ||
| 1055 | |||
| 1056 | mutex_unlock(&miphy_dev->miphy_mutex); | ||
| 1057 | |||
| 1058 | return ret; | ||
| 1059 | } | ||
| 1060 | |||
| 1061 | static int miphy28lp_get_addr(struct miphy28lp_phy *miphy_phy) | ||
| 1062 | { | ||
| 1063 | struct miphy28lp_dev *miphy_dev = miphy_phy->phydev; | ||
| 1064 | struct device_node *phynode = miphy_phy->phy->dev.of_node; | ||
| 1065 | int err; | ||
| 1066 | |||
| 1067 | if ((miphy_phy->type != PHY_TYPE_SATA) && | ||
| 1068 | (miphy_phy->type != PHY_TYPE_PCIE) && | ||
| 1069 | (miphy_phy->type != PHY_TYPE_USB3)) { | ||
| 1070 | return -EINVAL; | ||
| 1071 | } | ||
| 1072 | |||
| 1073 | err = miphy28lp_get_one_addr(miphy_dev->dev, phynode, | ||
| 1074 | PHY_TYPE_name[miphy_phy->type - PHY_TYPE_SATA], | ||
| 1075 | &miphy_phy->base); | ||
| 1076 | if (err) | ||
| 1077 | return err; | ||
| 1078 | |||
| 1079 | if ((miphy_phy->type == PHY_TYPE_PCIE) || | ||
| 1080 | (miphy_phy->type == PHY_TYPE_USB3)) { | ||
| 1081 | err = miphy28lp_get_one_addr(miphy_dev->dev, phynode, "pipew", | ||
| 1082 | &miphy_phy->pipebase); | ||
| 1083 | if (err) | ||
| 1084 | return err; | ||
| 1085 | } | ||
| 1086 | |||
| 1087 | return 0; | ||
| 1088 | } | ||
| 1089 | |||
| 1090 | static struct phy *miphy28lp_xlate(struct device *dev, | ||
| 1091 | struct of_phandle_args *args) | ||
| 1092 | { | ||
| 1093 | struct miphy28lp_dev *miphy_dev = dev_get_drvdata(dev); | ||
| 1094 | struct miphy28lp_phy *miphy_phy = NULL; | ||
| 1095 | struct device_node *phynode = args->np; | ||
| 1096 | int ret, index = 0; | ||
| 1097 | |||
| 1098 | if (!of_device_is_available(phynode)) { | ||
| 1099 | dev_warn(dev, "Requested PHY is disabled\n"); | ||
| 1100 | return ERR_PTR(-ENODEV); | ||
| 1101 | } | ||
| 1102 | |||
| 1103 | if (args->args_count != 1) { | ||
| 1104 | dev_err(dev, "Invalid number of cells in 'phy' property\n"); | ||
| 1105 | return ERR_PTR(-EINVAL); | ||
| 1106 | } | ||
| 1107 | |||
| 1108 | for (index = 0; index < of_get_child_count(dev->of_node); index++) | ||
| 1109 | if (phynode == miphy_dev->phys[index]->phy->dev.of_node) { | ||
| 1110 | miphy_phy = miphy_dev->phys[index]; | ||
| 1111 | break; | ||
| 1112 | } | ||
| 1113 | |||
| 1114 | if (!miphy_phy) { | ||
| 1115 | dev_err(dev, "Failed to find appropriate phy\n"); | ||
| 1116 | return ERR_PTR(-EINVAL); | ||
| 1117 | } | ||
| 1118 | |||
| 1119 | miphy_phy->type = args->args[0]; | ||
| 1120 | |||
| 1121 | ret = miphy28lp_get_addr(miphy_phy); | ||
| 1122 | if (ret < 0) | ||
| 1123 | return ERR_PTR(ret); | ||
| 1124 | |||
| 1125 | return miphy_phy->phy; | ||
| 1126 | } | ||
| 1127 | |||
| 1128 | static struct phy_ops miphy28lp_ops = { | ||
| 1129 | .init = miphy28lp_init, | ||
| 1130 | }; | ||
| 1131 | |||
| 1132 | static int miphy28lp_probe_resets(struct device_node *node, | ||
| 1133 | struct miphy28lp_phy *miphy_phy) | ||
| 1134 | { | ||
| 1135 | struct miphy28lp_dev *miphy_dev = miphy_phy->phydev; | ||
| 1136 | int err; | ||
| 1137 | |||
| 1138 | miphy_phy->miphy_rst = of_reset_control_get(node, "miphy-sw-rst"); | ||
| 1139 | |||
| 1140 | if (IS_ERR(miphy_phy->miphy_rst)) { | ||
| 1141 | dev_err(miphy_dev->dev, | ||
| 1142 | "miphy soft reset control not defined\n"); | ||
| 1143 | return PTR_ERR(miphy_phy->miphy_rst); | ||
| 1144 | } | ||
| 1145 | |||
| 1146 | err = reset_control_deassert(miphy_phy->miphy_rst); | ||
| 1147 | if (err) { | ||
| 1148 | dev_err(miphy_dev->dev, "unable to bring out of miphy reset\n"); | ||
| 1149 | return err; | ||
| 1150 | } | ||
| 1151 | |||
| 1152 | return 0; | ||
| 1153 | } | ||
| 1154 | |||
| 1155 | static int miphy28lp_of_probe(struct device_node *np, | ||
| 1156 | struct miphy28lp_phy *miphy_phy) | ||
| 1157 | { | ||
| 1158 | struct resource res; | ||
| 1159 | |||
| 1160 | miphy_phy->osc_force_ext = | ||
| 1161 | of_property_read_bool(np, "st,osc-force-ext"); | ||
| 1162 | |||
| 1163 | miphy_phy->osc_rdy = of_property_read_bool(np, "st,osc-rdy"); | ||
| 1164 | |||
| 1165 | miphy_phy->px_rx_pol_inv = | ||
| 1166 | of_property_read_bool(np, "st,px_rx_pol_inv"); | ||
| 1167 | |||
| 1168 | miphy_phy->ssc = of_property_read_bool(np, "st,ssc-on"); | ||
| 1169 | |||
| 1170 | miphy_phy->tx_impedance = | ||
| 1171 | of_property_read_bool(np, "st,tx-impedance-comp"); | ||
| 1172 | |||
| 1173 | of_property_read_u32(np, "st,sata-gen", &miphy_phy->sata_gen); | ||
| 1174 | if (!miphy_phy->sata_gen) | ||
| 1175 | miphy_phy->sata_gen = SATA_GEN1; | ||
| 1176 | |||
| 1177 | if (!miphy28lp_get_resource_byname(np, "miphy-ctrl-glue", &res)) | ||
| 1178 | miphy_phy->syscfg_miphy_ctrl = res.start; | ||
| 1179 | |||
| 1180 | if (!miphy28lp_get_resource_byname(np, "miphy-status-glue", &res)) | ||
| 1181 | miphy_phy->syscfg_miphy_status = res.start; | ||
| 1182 | |||
| 1183 | if (!miphy28lp_get_resource_byname(np, "pcie-glue", &res)) | ||
| 1184 | miphy_phy->syscfg_pci = res.start; | ||
| 1185 | |||
| 1186 | if (!miphy28lp_get_resource_byname(np, "sata-glue", &res)) | ||
| 1187 | miphy_phy->syscfg_sata = res.start; | ||
| 1188 | |||
| 1189 | |||
| 1190 | return 0; | ||
| 1191 | } | ||
| 1192 | |||
| 1193 | static int miphy28lp_probe(struct platform_device *pdev) | ||
| 1194 | { | ||
| 1195 | struct device_node *child, *np = pdev->dev.of_node; | ||
| 1196 | struct miphy28lp_dev *miphy_dev; | ||
| 1197 | struct phy_provider *provider; | ||
| 1198 | struct phy *phy; | ||
| 1199 | int chancount, port = 0; | ||
| 1200 | int ret; | ||
| 1201 | |||
| 1202 | miphy_dev = devm_kzalloc(&pdev->dev, sizeof(*miphy_dev), GFP_KERNEL); | ||
| 1203 | if (!miphy_dev) | ||
| 1204 | return -ENOMEM; | ||
| 1205 | |||
| 1206 | chancount = of_get_child_count(np); | ||
| 1207 | miphy_dev->phys = devm_kzalloc(&pdev->dev, sizeof(phy) * chancount, | ||
| 1208 | GFP_KERNEL); | ||
| 1209 | if (!miphy_dev->phys) | ||
| 1210 | return -ENOMEM; | ||
| 1211 | |||
| 1212 | miphy_dev->regmap = syscon_regmap_lookup_by_phandle(np, "st,syscfg"); | ||
| 1213 | if (IS_ERR(miphy_dev->regmap)) { | ||
| 1214 | dev_err(miphy_dev->dev, "No syscfg phandle specified\n"); | ||
| 1215 | return PTR_ERR(miphy_dev->regmap); | ||
| 1216 | } | ||
| 1217 | |||
| 1218 | miphy_dev->dev = &pdev->dev; | ||
| 1219 | |||
| 1220 | dev_set_drvdata(&pdev->dev, miphy_dev); | ||
| 1221 | |||
| 1222 | mutex_init(&miphy_dev->miphy_mutex); | ||
| 1223 | |||
| 1224 | for_each_child_of_node(np, child) { | ||
| 1225 | struct miphy28lp_phy *miphy_phy; | ||
| 1226 | |||
| 1227 | miphy_phy = devm_kzalloc(&pdev->dev, sizeof(*miphy_phy), | ||
| 1228 | GFP_KERNEL); | ||
| 1229 | if (!miphy_phy) | ||
| 1230 | return -ENOMEM; | ||
| 1231 | |||
| 1232 | miphy_dev->phys[port] = miphy_phy; | ||
| 1233 | |||
| 1234 | phy = devm_phy_create(&pdev->dev, child, &miphy28lp_ops); | ||
| 1235 | if (IS_ERR(phy)) { | ||
| 1236 | dev_err(&pdev->dev, "failed to create PHY\n"); | ||
| 1237 | return PTR_ERR(phy); | ||
| 1238 | } | ||
| 1239 | |||
| 1240 | miphy_dev->phys[port]->phy = phy; | ||
| 1241 | miphy_dev->phys[port]->phydev = miphy_dev; | ||
| 1242 | |||
| 1243 | ret = miphy28lp_of_probe(child, miphy_phy); | ||
| 1244 | if (ret) | ||
| 1245 | return ret; | ||
| 1246 | |||
| 1247 | ret = miphy28lp_probe_resets(child, miphy_dev->phys[port]); | ||
| 1248 | if (ret) | ||
| 1249 | return ret; | ||
| 1250 | |||
| 1251 | phy_set_drvdata(phy, miphy_dev->phys[port]); | ||
| 1252 | port++; | ||
| 1253 | |||
| 1254 | } | ||
| 1255 | |||
| 1256 | provider = devm_of_phy_provider_register(&pdev->dev, miphy28lp_xlate); | ||
| 1257 | if (IS_ERR(provider)) | ||
| 1258 | return PTR_ERR(provider); | ||
| 1259 | |||
| 1260 | return 0; | ||
| 1261 | } | ||
| 1262 | |||
| 1263 | static const struct of_device_id miphy28lp_of_match[] = { | ||
| 1264 | {.compatible = "st,miphy28lp-phy", }, | ||
| 1265 | {}, | ||
| 1266 | }; | ||
| 1267 | |||
| 1268 | MODULE_DEVICE_TABLE(of, miphy28lp_of_match); | ||
| 1269 | |||
| 1270 | static struct platform_driver miphy28lp_driver = { | ||
| 1271 | .probe = miphy28lp_probe, | ||
| 1272 | .driver = { | ||
| 1273 | .name = "miphy28lp-phy", | ||
| 1274 | .owner = THIS_MODULE, | ||
| 1275 | .of_match_table = miphy28lp_of_match, | ||
| 1276 | } | ||
| 1277 | }; | ||
| 1278 | |||
| 1279 | module_platform_driver(miphy28lp_driver); | ||
| 1280 | |||
| 1281 | MODULE_AUTHOR("Alexandre Torgue <alexandre.torgue@st.com>"); | ||
| 1282 | MODULE_DESCRIPTION("STMicroelectronics miphy28lp driver"); | ||
| 1283 | MODULE_LICENSE("GPL v2"); | ||
diff --git a/drivers/phy/phy-miphy365x.c b/drivers/phy/phy-miphy365x.c index 801afaf2d449..6ab43a814ad2 100644 --- a/drivers/phy/phy-miphy365x.c +++ b/drivers/phy/phy-miphy365x.c | |||
| @@ -593,7 +593,7 @@ static int miphy365x_probe(struct platform_device *pdev) | |||
| 593 | 593 | ||
| 594 | miphy_dev->phys[port] = miphy_phy; | 594 | miphy_dev->phys[port] = miphy_phy; |
| 595 | 595 | ||
| 596 | phy = devm_phy_create(&pdev->dev, child, &miphy365x_ops, NULL); | 596 | phy = devm_phy_create(&pdev->dev, child, &miphy365x_ops); |
| 597 | if (IS_ERR(phy)) { | 597 | if (IS_ERR(phy)) { |
| 598 | dev_err(&pdev->dev, "failed to create PHY\n"); | 598 | dev_err(&pdev->dev, "failed to create PHY\n"); |
| 599 | return PTR_ERR(phy); | 599 | return PTR_ERR(phy); |
| @@ -610,10 +610,7 @@ static int miphy365x_probe(struct platform_device *pdev) | |||
| 610 | } | 610 | } |
| 611 | 611 | ||
| 612 | provider = devm_of_phy_provider_register(&pdev->dev, miphy365x_xlate); | 612 | provider = devm_of_phy_provider_register(&pdev->dev, miphy365x_xlate); |
| 613 | if (IS_ERR(provider)) | 613 | return PTR_ERR_OR_ZERO(provider); |
| 614 | return PTR_ERR(provider); | ||
| 615 | |||
| 616 | return 0; | ||
| 617 | } | 614 | } |
| 618 | 615 | ||
| 619 | static const struct of_device_id miphy365x_of_match[] = { | 616 | static const struct of_device_id miphy365x_of_match[] = { |
diff --git a/drivers/phy/phy-mvebu-sata.c b/drivers/phy/phy-mvebu-sata.c index d395558cb12e..03b94f92e6f1 100644 --- a/drivers/phy/phy-mvebu-sata.c +++ b/drivers/phy/phy-mvebu-sata.c | |||
| @@ -101,7 +101,7 @@ static int phy_mvebu_sata_probe(struct platform_device *pdev) | |||
| 101 | if (IS_ERR(priv->clk)) | 101 | if (IS_ERR(priv->clk)) |
| 102 | return PTR_ERR(priv->clk); | 102 | return PTR_ERR(priv->clk); |
| 103 | 103 | ||
| 104 | phy = devm_phy_create(&pdev->dev, NULL, &phy_mvebu_sata_ops, NULL); | 104 | phy = devm_phy_create(&pdev->dev, NULL, &phy_mvebu_sata_ops); |
| 105 | if (IS_ERR(phy)) | 105 | if (IS_ERR(phy)) |
| 106 | return PTR_ERR(phy); | 106 | return PTR_ERR(phy); |
| 107 | 107 | ||
diff --git a/drivers/phy/phy-omap-usb2.c b/drivers/phy/phy-omap-usb2.c index f091576b6449..4e489a8850e5 100644 --- a/drivers/phy/phy-omap-usb2.c +++ b/drivers/phy/phy-omap-usb2.c | |||
| @@ -60,7 +60,7 @@ EXPORT_SYMBOL_GPL(omap_usb2_set_comparator); | |||
| 60 | 60 | ||
| 61 | static int omap_usb_set_vbus(struct usb_otg *otg, bool enabled) | 61 | static int omap_usb_set_vbus(struct usb_otg *otg, bool enabled) |
| 62 | { | 62 | { |
| 63 | struct omap_usb *phy = phy_to_omapusb(otg->phy); | 63 | struct omap_usb *phy = phy_to_omapusb(otg->usb_phy); |
| 64 | 64 | ||
| 65 | if (!phy->comparator) | 65 | if (!phy->comparator) |
| 66 | return -ENODEV; | 66 | return -ENODEV; |
| @@ -70,7 +70,7 @@ static int omap_usb_set_vbus(struct usb_otg *otg, bool enabled) | |||
| 70 | 70 | ||
| 71 | static int omap_usb_start_srp(struct usb_otg *otg) | 71 | static int omap_usb_start_srp(struct usb_otg *otg) |
| 72 | { | 72 | { |
| 73 | struct omap_usb *phy = phy_to_omapusb(otg->phy); | 73 | struct omap_usb *phy = phy_to_omapusb(otg->usb_phy); |
| 74 | 74 | ||
| 75 | if (!phy->comparator) | 75 | if (!phy->comparator) |
| 76 | return -ENODEV; | 76 | return -ENODEV; |
| @@ -80,11 +80,9 @@ static int omap_usb_start_srp(struct usb_otg *otg) | |||
| 80 | 80 | ||
| 81 | static int omap_usb_set_host(struct usb_otg *otg, struct usb_bus *host) | 81 | static int omap_usb_set_host(struct usb_otg *otg, struct usb_bus *host) |
| 82 | { | 82 | { |
| 83 | struct usb_phy *phy = otg->phy; | ||
| 84 | |||
| 85 | otg->host = host; | 83 | otg->host = host; |
| 86 | if (!host) | 84 | if (!host) |
| 87 | phy->state = OTG_STATE_UNDEFINED; | 85 | otg->state = OTG_STATE_UNDEFINED; |
| 88 | 86 | ||
| 89 | return 0; | 87 | return 0; |
| 90 | } | 88 | } |
| @@ -92,11 +90,9 @@ static int omap_usb_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
| 92 | static int omap_usb_set_peripheral(struct usb_otg *otg, | 90 | static int omap_usb_set_peripheral(struct usb_otg *otg, |
| 93 | struct usb_gadget *gadget) | 91 | struct usb_gadget *gadget) |
| 94 | { | 92 | { |
| 95 | struct usb_phy *phy = otg->phy; | ||
| 96 | |||
| 97 | otg->gadget = gadget; | 93 | otg->gadget = gadget; |
| 98 | if (!gadget) | 94 | if (!gadget) |
| 99 | phy->state = OTG_STATE_UNDEFINED; | 95 | otg->state = OTG_STATE_UNDEFINED; |
| 100 | 96 | ||
| 101 | return 0; | 97 | return 0; |
| 102 | } | 98 | } |
| @@ -255,12 +251,12 @@ static int omap_usb2_probe(struct platform_device *pdev) | |||
| 255 | otg->set_vbus = omap_usb_set_vbus; | 251 | otg->set_vbus = omap_usb_set_vbus; |
| 256 | if (phy_data->flags & OMAP_USB2_HAS_START_SRP) | 252 | if (phy_data->flags & OMAP_USB2_HAS_START_SRP) |
| 257 | otg->start_srp = omap_usb_start_srp; | 253 | otg->start_srp = omap_usb_start_srp; |
| 258 | otg->phy = &phy->phy; | 254 | otg->usb_phy = &phy->phy; |
| 259 | 255 | ||
| 260 | platform_set_drvdata(pdev, phy); | 256 | platform_set_drvdata(pdev, phy); |
| 261 | pm_runtime_enable(phy->dev); | 257 | pm_runtime_enable(phy->dev); |
| 262 | 258 | ||
| 263 | generic_phy = devm_phy_create(phy->dev, NULL, &ops, NULL); | 259 | generic_phy = devm_phy_create(phy->dev, NULL, &ops); |
| 264 | if (IS_ERR(generic_phy)) { | 260 | if (IS_ERR(generic_phy)) { |
| 265 | pm_runtime_disable(phy->dev); | 261 | pm_runtime_disable(phy->dev); |
| 266 | return PTR_ERR(generic_phy); | 262 | return PTR_ERR(generic_phy); |
diff --git a/drivers/phy/phy-qcom-apq8064-sata.c b/drivers/phy/phy-qcom-apq8064-sata.c index 7b3ddfb65898..4b243f7a10e4 100644 --- a/drivers/phy/phy-qcom-apq8064-sata.c +++ b/drivers/phy/phy-qcom-apq8064-sata.c | |||
| @@ -228,8 +228,7 @@ static int qcom_apq8064_sata_phy_probe(struct platform_device *pdev) | |||
| 228 | if (IS_ERR(phy->mmio)) | 228 | if (IS_ERR(phy->mmio)) |
| 229 | return PTR_ERR(phy->mmio); | 229 | return PTR_ERR(phy->mmio); |
| 230 | 230 | ||
| 231 | generic_phy = devm_phy_create(dev, NULL, &qcom_apq8064_sata_phy_ops, | 231 | generic_phy = devm_phy_create(dev, NULL, &qcom_apq8064_sata_phy_ops); |
| 232 | NULL); | ||
| 233 | if (IS_ERR(generic_phy)) { | 232 | if (IS_ERR(generic_phy)) { |
| 234 | dev_err(dev, "%s: failed to create phy\n", __func__); | 233 | dev_err(dev, "%s: failed to create phy\n", __func__); |
| 235 | return PTR_ERR(generic_phy); | 234 | return PTR_ERR(generic_phy); |
diff --git a/drivers/phy/phy-qcom-ipq806x-sata.c b/drivers/phy/phy-qcom-ipq806x-sata.c index 759b0bf5b6b3..6f2fe2627916 100644 --- a/drivers/phy/phy-qcom-ipq806x-sata.c +++ b/drivers/phy/phy-qcom-ipq806x-sata.c | |||
| @@ -150,8 +150,7 @@ static int qcom_ipq806x_sata_phy_probe(struct platform_device *pdev) | |||
| 150 | if (IS_ERR(phy->mmio)) | 150 | if (IS_ERR(phy->mmio)) |
| 151 | return PTR_ERR(phy->mmio); | 151 | return PTR_ERR(phy->mmio); |
| 152 | 152 | ||
| 153 | generic_phy = devm_phy_create(dev, NULL, &qcom_ipq806x_sata_phy_ops, | 153 | generic_phy = devm_phy_create(dev, NULL, &qcom_ipq806x_sata_phy_ops); |
| 154 | NULL); | ||
| 155 | if (IS_ERR(generic_phy)) { | 154 | if (IS_ERR(generic_phy)) { |
| 156 | dev_err(dev, "%s: failed to create phy\n", __func__); | 155 | dev_err(dev, "%s: failed to create phy\n", __func__); |
| 157 | return PTR_ERR(generic_phy); | 156 | return PTR_ERR(generic_phy); |
diff --git a/drivers/phy/phy-rcar-gen2.c b/drivers/phy/phy-rcar-gen2.c index 2793af17799f..778276aba3aa 100644 --- a/drivers/phy/phy-rcar-gen2.c +++ b/drivers/phy/phy-rcar-gen2.c | |||
| @@ -304,7 +304,7 @@ static int rcar_gen2_phy_probe(struct platform_device *pdev) | |||
| 304 | phy->select_value = select_value[channel_num][n]; | 304 | phy->select_value = select_value[channel_num][n]; |
| 305 | 305 | ||
| 306 | phy->phy = devm_phy_create(dev, NULL, | 306 | phy->phy = devm_phy_create(dev, NULL, |
| 307 | &rcar_gen2_phy_ops, NULL); | 307 | &rcar_gen2_phy_ops); |
| 308 | if (IS_ERR(phy->phy)) { | 308 | if (IS_ERR(phy->phy)) { |
| 309 | dev_err(dev, "Failed to create PHY\n"); | 309 | dev_err(dev, "Failed to create PHY\n"); |
| 310 | return PTR_ERR(phy->phy); | 310 | return PTR_ERR(phy->phy); |
diff --git a/drivers/phy/phy-samsung-usb2.c b/drivers/phy/phy-samsung-usb2.c index 908949dfb4db..4a12f66b7fb5 100644 --- a/drivers/phy/phy-samsung-usb2.c +++ b/drivers/phy/phy-samsung-usb2.c | |||
| @@ -202,8 +202,7 @@ static int samsung_usb2_phy_probe(struct platform_device *pdev) | |||
| 202 | struct samsung_usb2_phy_instance *p = &drv->instances[i]; | 202 | struct samsung_usb2_phy_instance *p = &drv->instances[i]; |
| 203 | 203 | ||
| 204 | dev_dbg(dev, "Creating phy \"%s\"\n", label); | 204 | dev_dbg(dev, "Creating phy \"%s\"\n", label); |
| 205 | p->phy = devm_phy_create(dev, NULL, &samsung_usb2_phy_ops, | 205 | p->phy = devm_phy_create(dev, NULL, &samsung_usb2_phy_ops); |
| 206 | NULL); | ||
| 207 | if (IS_ERR(p->phy)) { | 206 | if (IS_ERR(p->phy)) { |
| 208 | dev_err(drv->dev, "Failed to create usb2_phy \"%s\"\n", | 207 | dev_err(drv->dev, "Failed to create usb2_phy \"%s\"\n", |
| 209 | label); | 208 | label); |
diff --git a/drivers/phy/phy-spear1310-miphy.c b/drivers/phy/phy-spear1310-miphy.c index 5f4c586ee951..9f47fae7eecb 100644 --- a/drivers/phy/phy-spear1310-miphy.c +++ b/drivers/phy/phy-spear1310-miphy.c | |||
| @@ -227,7 +227,7 @@ static int spear1310_miphy_probe(struct platform_device *pdev) | |||
| 227 | return -EINVAL; | 227 | return -EINVAL; |
| 228 | } | 228 | } |
| 229 | 229 | ||
| 230 | priv->phy = devm_phy_create(dev, NULL, &spear1310_miphy_ops, NULL); | 230 | priv->phy = devm_phy_create(dev, NULL, &spear1310_miphy_ops); |
| 231 | if (IS_ERR(priv->phy)) { | 231 | if (IS_ERR(priv->phy)) { |
| 232 | dev_err(dev, "failed to create SATA PCIe PHY\n"); | 232 | dev_err(dev, "failed to create SATA PCIe PHY\n"); |
| 233 | return PTR_ERR(priv->phy); | 233 | return PTR_ERR(priv->phy); |
diff --git a/drivers/phy/phy-spear1340-miphy.c b/drivers/phy/phy-spear1340-miphy.c index 1ecd0945bad3..e42bc200275f 100644 --- a/drivers/phy/phy-spear1340-miphy.c +++ b/drivers/phy/phy-spear1340-miphy.c | |||
| @@ -259,7 +259,7 @@ static int spear1340_miphy_probe(struct platform_device *pdev) | |||
| 259 | return PTR_ERR(priv->misc); | 259 | return PTR_ERR(priv->misc); |
| 260 | } | 260 | } |
| 261 | 261 | ||
| 262 | priv->phy = devm_phy_create(dev, NULL, &spear1340_miphy_ops, NULL); | 262 | priv->phy = devm_phy_create(dev, NULL, &spear1340_miphy_ops); |
| 263 | if (IS_ERR(priv->phy)) { | 263 | if (IS_ERR(priv->phy)) { |
| 264 | dev_err(dev, "failed to create SATA PCIe PHY\n"); | 264 | dev_err(dev, "failed to create SATA PCIe PHY\n"); |
| 265 | return PTR_ERR(priv->phy); | 265 | return PTR_ERR(priv->phy); |
diff --git a/drivers/phy/phy-stih407-usb.c b/drivers/phy/phy-stih407-usb.c index 42428d4181ea..74f0fab3cd8a 100644 --- a/drivers/phy/phy-stih407-usb.c +++ b/drivers/phy/phy-stih407-usb.c | |||
| @@ -137,7 +137,7 @@ static int stih407_usb2_picophy_probe(struct platform_device *pdev) | |||
| 137 | } | 137 | } |
| 138 | phy_dev->param = res->start; | 138 | phy_dev->param = res->start; |
| 139 | 139 | ||
| 140 | phy = devm_phy_create(dev, NULL, &stih407_usb2_picophy_data, NULL); | 140 | phy = devm_phy_create(dev, NULL, &stih407_usb2_picophy_data); |
| 141 | if (IS_ERR(phy)) { | 141 | if (IS_ERR(phy)) { |
| 142 | dev_err(dev, "failed to create Display Port PHY\n"); | 142 | dev_err(dev, "failed to create Display Port PHY\n"); |
| 143 | return PTR_ERR(phy); | 143 | return PTR_ERR(phy); |
diff --git a/drivers/phy/phy-stih41x-usb.c b/drivers/phy/phy-stih41x-usb.c index 9f16cb8e01f4..a603801293ff 100644 --- a/drivers/phy/phy-stih41x-usb.c +++ b/drivers/phy/phy-stih41x-usb.c | |||
| @@ -148,7 +148,7 @@ static int stih41x_usb_phy_probe(struct platform_device *pdev) | |||
| 148 | return PTR_ERR(phy_dev->clk); | 148 | return PTR_ERR(phy_dev->clk); |
| 149 | } | 149 | } |
| 150 | 150 | ||
| 151 | phy = devm_phy_create(dev, NULL, &stih41x_usb_phy_ops, NULL); | 151 | phy = devm_phy_create(dev, NULL, &stih41x_usb_phy_ops); |
| 152 | 152 | ||
| 153 | if (IS_ERR(phy)) { | 153 | if (IS_ERR(phy)) { |
| 154 | dev_err(dev, "failed to create phy\n"); | 154 | dev_err(dev, "failed to create phy\n"); |
| @@ -160,10 +160,7 @@ static int stih41x_usb_phy_probe(struct platform_device *pdev) | |||
| 160 | phy_set_drvdata(phy, phy_dev); | 160 | phy_set_drvdata(phy, phy_dev); |
| 161 | 161 | ||
| 162 | phy_provider = devm_of_phy_provider_register(dev, of_phy_simple_xlate); | 162 | phy_provider = devm_of_phy_provider_register(dev, of_phy_simple_xlate); |
| 163 | if (IS_ERR(phy_provider)) | 163 | return PTR_ERR_OR_ZERO(phy_provider); |
| 164 | return PTR_ERR(phy_provider); | ||
| 165 | |||
| 166 | return 0; | ||
| 167 | } | 164 | } |
| 168 | 165 | ||
| 169 | static const struct of_device_id stih41x_usb_phy_of_match[] = { | 166 | static const struct of_device_id stih41x_usb_phy_of_match[] = { |
diff --git a/drivers/phy/phy-sun4i-usb.c b/drivers/phy/phy-sun4i-usb.c index 0baf5efc8a40..fb02a67c9181 100644 --- a/drivers/phy/phy-sun4i-usb.c +++ b/drivers/phy/phy-sun4i-usb.c | |||
| @@ -157,6 +157,10 @@ static int sun4i_usb_phy_init(struct phy *_phy) | |||
| 157 | return ret; | 157 | return ret; |
| 158 | } | 158 | } |
| 159 | 159 | ||
| 160 | /* Enable USB 45 Ohm resistor calibration */ | ||
| 161 | if (phy->index == 0) | ||
| 162 | sun4i_usb_phy_write(phy, PHY_RES45_CAL_EN, 0x01, 1); | ||
| 163 | |||
| 160 | /* Adjust PHY's magnitude and rate */ | 164 | /* Adjust PHY's magnitude and rate */ |
| 161 | sun4i_usb_phy_write(phy, PHY_TX_AMPLITUDE_TUNE, 0x14, 5); | 165 | sun4i_usb_phy_write(phy, PHY_TX_AMPLITUDE_TUNE, 0x14, 5); |
| 162 | 166 | ||
| @@ -213,7 +217,7 @@ static struct phy *sun4i_usb_phy_xlate(struct device *dev, | |||
| 213 | { | 217 | { |
| 214 | struct sun4i_usb_phy_data *data = dev_get_drvdata(dev); | 218 | struct sun4i_usb_phy_data *data = dev_get_drvdata(dev); |
| 215 | 219 | ||
| 216 | if (WARN_ON(args->args[0] == 0 || args->args[0] >= data->num_phys)) | 220 | if (args->args[0] >= data->num_phys) |
| 217 | return ERR_PTR(-ENODEV); | 221 | return ERR_PTR(-ENODEV); |
| 218 | 222 | ||
| 219 | return data->phys[args->args[0]].phy; | 223 | return data->phys[args->args[0]].phy; |
| @@ -255,8 +259,7 @@ static int sun4i_usb_phy_probe(struct platform_device *pdev) | |||
| 255 | if (IS_ERR(data->base)) | 259 | if (IS_ERR(data->base)) |
| 256 | return PTR_ERR(data->base); | 260 | return PTR_ERR(data->base); |
| 257 | 261 | ||
| 258 | /* Skip 0, 0 is the phy for otg which is not yet supported. */ | 262 | for (i = 0; i < data->num_phys; i++) { |
| 259 | for (i = 1; i < data->num_phys; i++) { | ||
| 260 | struct sun4i_usb_phy *phy = data->phys + i; | 263 | struct sun4i_usb_phy *phy = data->phys + i; |
| 261 | char name[16]; | 264 | char name[16]; |
| 262 | 265 | ||
| @@ -295,7 +298,7 @@ static int sun4i_usb_phy_probe(struct platform_device *pdev) | |||
| 295 | return PTR_ERR(phy->pmu); | 298 | return PTR_ERR(phy->pmu); |
| 296 | } | 299 | } |
| 297 | 300 | ||
| 298 | phy->phy = devm_phy_create(dev, NULL, &sun4i_usb_phy_ops, NULL); | 301 | phy->phy = devm_phy_create(dev, NULL, &sun4i_usb_phy_ops); |
| 299 | if (IS_ERR(phy->phy)) { | 302 | if (IS_ERR(phy->phy)) { |
| 300 | dev_err(dev, "failed to create PHY %d\n", i); | 303 | dev_err(dev, "failed to create PHY %d\n", i); |
| 301 | return PTR_ERR(phy->phy); | 304 | return PTR_ERR(phy->phy); |
diff --git a/drivers/phy/phy-ti-pipe3.c b/drivers/phy/phy-ti-pipe3.c index ab1e22d9a1e8..c297b7a10d30 100644 --- a/drivers/phy/phy-ti-pipe3.c +++ b/drivers/phy/phy-ti-pipe3.c | |||
| @@ -399,7 +399,7 @@ static int ti_pipe3_probe(struct platform_device *pdev) | |||
| 399 | platform_set_drvdata(pdev, phy); | 399 | platform_set_drvdata(pdev, phy); |
| 400 | pm_runtime_enable(phy->dev); | 400 | pm_runtime_enable(phy->dev); |
| 401 | 401 | ||
| 402 | generic_phy = devm_phy_create(phy->dev, NULL, &ops, NULL); | 402 | generic_phy = devm_phy_create(phy->dev, NULL, &ops); |
| 403 | if (IS_ERR(generic_phy)) | 403 | if (IS_ERR(generic_phy)) |
| 404 | return PTR_ERR(generic_phy); | 404 | return PTR_ERR(generic_phy); |
| 405 | 405 | ||
diff --git a/drivers/phy/phy-twl4030-usb.c b/drivers/phy/phy-twl4030-usb.c index 7b04befd5271..8e87f54671f3 100644 --- a/drivers/phy/phy-twl4030-usb.c +++ b/drivers/phy/phy-twl4030-usb.c | |||
| @@ -606,7 +606,7 @@ static int twl4030_set_peripheral(struct usb_otg *otg, | |||
| 606 | 606 | ||
| 607 | otg->gadget = gadget; | 607 | otg->gadget = gadget; |
| 608 | if (!gadget) | 608 | if (!gadget) |
| 609 | otg->phy->state = OTG_STATE_UNDEFINED; | 609 | otg->state = OTG_STATE_UNDEFINED; |
| 610 | 610 | ||
| 611 | return 0; | 611 | return 0; |
| 612 | } | 612 | } |
| @@ -618,7 +618,7 @@ static int twl4030_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
| 618 | 618 | ||
| 619 | otg->host = host; | 619 | otg->host = host; |
| 620 | if (!host) | 620 | if (!host) |
| 621 | otg->phy->state = OTG_STATE_UNDEFINED; | 621 | otg->state = OTG_STATE_UNDEFINED; |
| 622 | 622 | ||
| 623 | return 0; | 623 | return 0; |
| 624 | } | 624 | } |
| @@ -644,7 +644,6 @@ static int twl4030_usb_probe(struct platform_device *pdev) | |||
| 644 | struct usb_otg *otg; | 644 | struct usb_otg *otg; |
| 645 | struct device_node *np = pdev->dev.of_node; | 645 | struct device_node *np = pdev->dev.of_node; |
| 646 | struct phy_provider *phy_provider; | 646 | struct phy_provider *phy_provider; |
| 647 | struct phy_init_data *init_data = NULL; | ||
| 648 | 647 | ||
| 649 | twl = devm_kzalloc(&pdev->dev, sizeof(*twl), GFP_KERNEL); | 648 | twl = devm_kzalloc(&pdev->dev, sizeof(*twl), GFP_KERNEL); |
| 650 | if (!twl) | 649 | if (!twl) |
| @@ -655,7 +654,6 @@ static int twl4030_usb_probe(struct platform_device *pdev) | |||
| 655 | (enum twl4030_usb_mode *)&twl->usb_mode); | 654 | (enum twl4030_usb_mode *)&twl->usb_mode); |
| 656 | else if (pdata) { | 655 | else if (pdata) { |
| 657 | twl->usb_mode = pdata->usb_mode; | 656 | twl->usb_mode = pdata->usb_mode; |
| 658 | init_data = pdata->init_data; | ||
| 659 | } else { | 657 | } else { |
| 660 | dev_err(&pdev->dev, "twl4030 initialized without pdata\n"); | 658 | dev_err(&pdev->dev, "twl4030 initialized without pdata\n"); |
| 661 | return -EINVAL; | 659 | return -EINVAL; |
| @@ -676,11 +674,11 @@ static int twl4030_usb_probe(struct platform_device *pdev) | |||
| 676 | twl->phy.otg = otg; | 674 | twl->phy.otg = otg; |
| 677 | twl->phy.type = USB_PHY_TYPE_USB2; | 675 | twl->phy.type = USB_PHY_TYPE_USB2; |
| 678 | 676 | ||
| 679 | otg->phy = &twl->phy; | 677 | otg->usb_phy = &twl->phy; |
| 680 | otg->set_host = twl4030_set_host; | 678 | otg->set_host = twl4030_set_host; |
| 681 | otg->set_peripheral = twl4030_set_peripheral; | 679 | otg->set_peripheral = twl4030_set_peripheral; |
| 682 | 680 | ||
| 683 | phy = devm_phy_create(twl->dev, NULL, &ops, init_data); | 681 | phy = devm_phy_create(twl->dev, NULL, &ops); |
| 684 | if (IS_ERR(phy)) { | 682 | if (IS_ERR(phy)) { |
| 685 | dev_dbg(&pdev->dev, "Failed to create PHY\n"); | 683 | dev_dbg(&pdev->dev, "Failed to create PHY\n"); |
| 686 | return PTR_ERR(phy); | 684 | return PTR_ERR(phy); |
| @@ -733,6 +731,11 @@ static int twl4030_usb_probe(struct platform_device *pdev) | |||
| 733 | return status; | 731 | return status; |
| 734 | } | 732 | } |
| 735 | 733 | ||
| 734 | if (pdata) | ||
| 735 | err = phy_create_lookup(phy, "usb", "musb-hdrc.0"); | ||
| 736 | if (err) | ||
| 737 | return err; | ||
| 738 | |||
| 736 | pm_runtime_mark_last_busy(&pdev->dev); | 739 | pm_runtime_mark_last_busy(&pdev->dev); |
| 737 | pm_runtime_put_autosuspend(twl->dev); | 740 | pm_runtime_put_autosuspend(twl->dev); |
| 738 | 741 | ||
diff --git a/drivers/phy/phy-xgene.c b/drivers/phy/phy-xgene.c index f8a51b16ade8..29214a36ea28 100644 --- a/drivers/phy/phy-xgene.c +++ b/drivers/phy/phy-xgene.c | |||
| @@ -1707,7 +1707,7 @@ static int xgene_phy_probe(struct platform_device *pdev) | |||
| 1707 | ctx->dev = &pdev->dev; | 1707 | ctx->dev = &pdev->dev; |
| 1708 | platform_set_drvdata(pdev, ctx); | 1708 | platform_set_drvdata(pdev, ctx); |
| 1709 | 1709 | ||
| 1710 | ctx->phy = devm_phy_create(ctx->dev, NULL, &xgene_phy_ops, NULL); | 1710 | ctx->phy = devm_phy_create(ctx->dev, NULL, &xgene_phy_ops); |
| 1711 | if (IS_ERR(ctx->phy)) { | 1711 | if (IS_ERR(ctx->phy)) { |
| 1712 | dev_dbg(&pdev->dev, "Failed to create PHY\n"); | 1712 | dev_dbg(&pdev->dev, "Failed to create PHY\n"); |
| 1713 | rc = PTR_ERR(ctx->phy); | 1713 | rc = PTR_ERR(ctx->phy); |
diff --git a/drivers/pinctrl/pinctrl-tegra-xusb.c b/drivers/pinctrl/pinctrl-tegra-xusb.c index 080ec7723ef2..753d747d4261 100644 --- a/drivers/pinctrl/pinctrl-tegra-xusb.c +++ b/drivers/pinctrl/pinctrl-tegra-xusb.c | |||
| @@ -915,7 +915,7 @@ static int tegra_xusb_padctl_probe(struct platform_device *pdev) | |||
| 915 | goto reset; | 915 | goto reset; |
| 916 | } | 916 | } |
| 917 | 917 | ||
| 918 | phy = devm_phy_create(&pdev->dev, NULL, &pcie_phy_ops, NULL); | 918 | phy = devm_phy_create(&pdev->dev, NULL, &pcie_phy_ops); |
| 919 | if (IS_ERR(phy)) { | 919 | if (IS_ERR(phy)) { |
| 920 | err = PTR_ERR(phy); | 920 | err = PTR_ERR(phy); |
| 921 | goto unregister; | 921 | goto unregister; |
| @@ -924,7 +924,7 @@ static int tegra_xusb_padctl_probe(struct platform_device *pdev) | |||
| 924 | padctl->phys[TEGRA_XUSB_PADCTL_PCIE] = phy; | 924 | padctl->phys[TEGRA_XUSB_PADCTL_PCIE] = phy; |
| 925 | phy_set_drvdata(phy, padctl); | 925 | phy_set_drvdata(phy, padctl); |
| 926 | 926 | ||
| 927 | phy = devm_phy_create(&pdev->dev, NULL, &sata_phy_ops, NULL); | 927 | phy = devm_phy_create(&pdev->dev, NULL, &sata_phy_ops); |
| 928 | if (IS_ERR(phy)) { | 928 | if (IS_ERR(phy)) { |
| 929 | err = PTR_ERR(phy); | 929 | err = PTR_ERR(phy); |
| 930 | goto unregister; | 930 | goto unregister; |
diff --git a/drivers/usb/chipidea/Makefile b/drivers/usb/chipidea/Makefile index 2f099c7df7b5..1fc86a2ca22d 100644 --- a/drivers/usb/chipidea/Makefile +++ b/drivers/usb/chipidea/Makefile | |||
| @@ -10,6 +10,7 @@ ci_hdrc-$(CONFIG_USB_OTG_FSM) += otg_fsm.o | |||
| 10 | 10 | ||
| 11 | # Glue/Bridge layers go here | 11 | # Glue/Bridge layers go here |
| 12 | 12 | ||
| 13 | obj-$(CONFIG_USB_CHIPIDEA) += ci_hdrc_usb2.o | ||
| 13 | obj-$(CONFIG_USB_CHIPIDEA) += ci_hdrc_msm.o | 14 | obj-$(CONFIG_USB_CHIPIDEA) += ci_hdrc_msm.o |
| 14 | obj-$(CONFIG_USB_CHIPIDEA) += ci_hdrc_zevio.o | 15 | obj-$(CONFIG_USB_CHIPIDEA) += ci_hdrc_zevio.o |
| 15 | 16 | ||
diff --git a/drivers/usb/chipidea/ci.h b/drivers/usb/chipidea/ci.h index ea40626e0246..65913d48f0c8 100644 --- a/drivers/usb/chipidea/ci.h +++ b/drivers/usb/chipidea/ci.h | |||
| @@ -161,7 +161,8 @@ struct hw_bank { | |||
| 161 | * @test_mode: the selected test mode | 161 | * @test_mode: the selected test mode |
| 162 | * @platdata: platform specific information supplied by parent device | 162 | * @platdata: platform specific information supplied by parent device |
| 163 | * @vbus_active: is VBUS active | 163 | * @vbus_active: is VBUS active |
| 164 | * @transceiver: pointer to USB PHY, if any | 164 | * @phy: pointer to PHY, if any |
| 165 | * @usb_phy: pointer to USB PHY, if any and if using the USB PHY framework | ||
| 165 | * @hcd: pointer to usb_hcd for ehci host driver | 166 | * @hcd: pointer to usb_hcd for ehci host driver |
| 166 | * @debugfs: root dentry for this controller in debugfs | 167 | * @debugfs: root dentry for this controller in debugfs |
| 167 | * @id_event: indicates there is an id event, and handled at ci_otg_work | 168 | * @id_event: indicates there is an id event, and handled at ci_otg_work |
| @@ -177,6 +178,7 @@ struct ci_hdrc { | |||
| 177 | struct ci_role_driver *roles[CI_ROLE_END]; | 178 | struct ci_role_driver *roles[CI_ROLE_END]; |
| 178 | enum ci_role role; | 179 | enum ci_role role; |
| 179 | bool is_otg; | 180 | bool is_otg; |
| 181 | struct usb_otg otg; | ||
| 180 | struct otg_fsm fsm; | 182 | struct otg_fsm fsm; |
| 181 | struct ci_otg_fsm_timer_list *fsm_timer; | 183 | struct ci_otg_fsm_timer_list *fsm_timer; |
| 182 | struct work_struct work; | 184 | struct work_struct work; |
| @@ -201,7 +203,9 @@ struct ci_hdrc { | |||
| 201 | 203 | ||
| 202 | struct ci_hdrc_platform_data *platdata; | 204 | struct ci_hdrc_platform_data *platdata; |
| 203 | int vbus_active; | 205 | int vbus_active; |
| 204 | struct usb_phy *transceiver; | 206 | struct phy *phy; |
| 207 | /* old usb_phy interface */ | ||
| 208 | struct usb_phy *usb_phy; | ||
| 205 | struct usb_hcd *hcd; | 209 | struct usb_hcd *hcd; |
| 206 | struct dentry *debugfs; | 210 | struct dentry *debugfs; |
| 207 | bool id_event; | 211 | bool id_event; |
| @@ -348,7 +352,7 @@ u32 hw_read_intr_enable(struct ci_hdrc *ci); | |||
| 348 | 352 | ||
| 349 | u32 hw_read_intr_status(struct ci_hdrc *ci); | 353 | u32 hw_read_intr_status(struct ci_hdrc *ci); |
| 350 | 354 | ||
| 351 | int hw_device_reset(struct ci_hdrc *ci, u32 mode); | 355 | int hw_device_reset(struct ci_hdrc *ci); |
| 352 | 356 | ||
| 353 | int hw_port_test_set(struct ci_hdrc *ci, u8 mode); | 357 | int hw_port_test_set(struct ci_hdrc *ci, u8 mode); |
| 354 | 358 | ||
diff --git a/drivers/usb/chipidea/ci_hdrc_imx.c b/drivers/usb/chipidea/ci_hdrc_imx.c index a7ab0f15926e..450a168974d5 100644 --- a/drivers/usb/chipidea/ci_hdrc_imx.c +++ b/drivers/usb/chipidea/ci_hdrc_imx.c | |||
| @@ -106,8 +106,7 @@ static int ci_hdrc_imx_probe(struct platform_device *pdev) | |||
| 106 | struct ci_hdrc_platform_data pdata = { | 106 | struct ci_hdrc_platform_data pdata = { |
| 107 | .name = dev_name(&pdev->dev), | 107 | .name = dev_name(&pdev->dev), |
| 108 | .capoffset = DEF_CAPOFFSET, | 108 | .capoffset = DEF_CAPOFFSET, |
| 109 | .flags = CI_HDRC_REQUIRE_TRANSCEIVER | | 109 | .flags = CI_HDRC_DISABLE_STREAMING, |
| 110 | CI_HDRC_DISABLE_STREAMING, | ||
| 111 | }; | 110 | }; |
| 112 | int ret; | 111 | int ret; |
| 113 | const struct of_device_id *of_id = | 112 | const struct of_device_id *of_id = |
| @@ -115,10 +114,8 @@ static int ci_hdrc_imx_probe(struct platform_device *pdev) | |||
| 115 | const struct ci_hdrc_imx_platform_flag *imx_platform_flag = of_id->data; | 114 | const struct ci_hdrc_imx_platform_flag *imx_platform_flag = of_id->data; |
| 116 | 115 | ||
| 117 | data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL); | 116 | data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL); |
| 118 | if (!data) { | 117 | if (!data) |
| 119 | dev_err(&pdev->dev, "Failed to allocate ci_hdrc-imx data!\n"); | ||
| 120 | return -ENOMEM; | 118 | return -ENOMEM; |
| 121 | } | ||
| 122 | 119 | ||
| 123 | data->usbmisc_data = usbmisc_get_init_data(&pdev->dev); | 120 | data->usbmisc_data = usbmisc_get_init_data(&pdev->dev); |
| 124 | if (IS_ERR(data->usbmisc_data)) | 121 | if (IS_ERR(data->usbmisc_data)) |
| @@ -147,7 +144,7 @@ static int ci_hdrc_imx_probe(struct platform_device *pdev) | |||
| 147 | goto err_clk; | 144 | goto err_clk; |
| 148 | } | 145 | } |
| 149 | 146 | ||
| 150 | pdata.phy = data->phy; | 147 | pdata.usb_phy = data->phy; |
| 151 | 148 | ||
| 152 | if (imx_platform_flag->flags & CI_HDRC_IMX_IMX28_WRITE_FIX) | 149 | if (imx_platform_flag->flags & CI_HDRC_IMX_IMX28_WRITE_FIX) |
| 153 | pdata.flags |= CI_HDRC_IMX28_WRITE_FIX; | 150 | pdata.flags |= CI_HDRC_IMX28_WRITE_FIX; |
| @@ -210,6 +207,41 @@ static int ci_hdrc_imx_remove(struct platform_device *pdev) | |||
| 210 | return 0; | 207 | return 0; |
| 211 | } | 208 | } |
| 212 | 209 | ||
| 210 | #ifdef CONFIG_PM_SLEEP | ||
| 211 | static int imx_controller_suspend(struct device *dev) | ||
| 212 | { | ||
| 213 | struct ci_hdrc_imx_data *data = dev_get_drvdata(dev); | ||
| 214 | |||
| 215 | dev_dbg(dev, "at %s\n", __func__); | ||
| 216 | |||
| 217 | clk_disable_unprepare(data->clk); | ||
| 218 | |||
| 219 | return 0; | ||
| 220 | } | ||
| 221 | |||
| 222 | static int imx_controller_resume(struct device *dev) | ||
| 223 | { | ||
| 224 | struct ci_hdrc_imx_data *data = dev_get_drvdata(dev); | ||
| 225 | |||
| 226 | dev_dbg(dev, "at %s\n", __func__); | ||
| 227 | |||
| 228 | return clk_prepare_enable(data->clk); | ||
| 229 | } | ||
| 230 | |||
| 231 | static int ci_hdrc_imx_suspend(struct device *dev) | ||
| 232 | { | ||
| 233 | return imx_controller_suspend(dev); | ||
| 234 | } | ||
| 235 | |||
| 236 | static int ci_hdrc_imx_resume(struct device *dev) | ||
| 237 | { | ||
| 238 | return imx_controller_resume(dev); | ||
| 239 | } | ||
| 240 | #endif /* CONFIG_PM_SLEEP */ | ||
| 241 | |||
| 242 | static const struct dev_pm_ops ci_hdrc_imx_pm_ops = { | ||
| 243 | SET_SYSTEM_SLEEP_PM_OPS(ci_hdrc_imx_suspend, ci_hdrc_imx_resume) | ||
| 244 | }; | ||
| 213 | static struct platform_driver ci_hdrc_imx_driver = { | 245 | static struct platform_driver ci_hdrc_imx_driver = { |
| 214 | .probe = ci_hdrc_imx_probe, | 246 | .probe = ci_hdrc_imx_probe, |
| 215 | .remove = ci_hdrc_imx_remove, | 247 | .remove = ci_hdrc_imx_remove, |
| @@ -217,6 +249,7 @@ static struct platform_driver ci_hdrc_imx_driver = { | |||
| 217 | .name = "imx_usb", | 249 | .name = "imx_usb", |
| 218 | .owner = THIS_MODULE, | 250 | .owner = THIS_MODULE, |
| 219 | .of_match_table = ci_hdrc_imx_dt_ids, | 251 | .of_match_table = ci_hdrc_imx_dt_ids, |
| 252 | .pm = &ci_hdrc_imx_pm_ops, | ||
| 220 | }, | 253 | }, |
| 221 | }; | 254 | }; |
| 222 | 255 | ||
diff --git a/drivers/usb/chipidea/ci_hdrc_msm.c b/drivers/usb/chipidea/ci_hdrc_msm.c index 4935ac38fd00..d79ecc08a1be 100644 --- a/drivers/usb/chipidea/ci_hdrc_msm.c +++ b/drivers/usb/chipidea/ci_hdrc_msm.c | |||
| @@ -26,15 +26,15 @@ static void ci_hdrc_msm_notify_event(struct ci_hdrc *ci, unsigned event) | |||
| 26 | dev_dbg(dev, "CI_HDRC_CONTROLLER_RESET_EVENT received\n"); | 26 | dev_dbg(dev, "CI_HDRC_CONTROLLER_RESET_EVENT received\n"); |
| 27 | writel(0, USB_AHBBURST); | 27 | writel(0, USB_AHBBURST); |
| 28 | writel(0, USB_AHBMODE); | 28 | writel(0, USB_AHBMODE); |
| 29 | usb_phy_init(ci->transceiver); | 29 | usb_phy_init(ci->usb_phy); |
| 30 | break; | 30 | break; |
| 31 | case CI_HDRC_CONTROLLER_STOPPED_EVENT: | 31 | case CI_HDRC_CONTROLLER_STOPPED_EVENT: |
| 32 | dev_dbg(dev, "CI_HDRC_CONTROLLER_STOPPED_EVENT received\n"); | 32 | dev_dbg(dev, "CI_HDRC_CONTROLLER_STOPPED_EVENT received\n"); |
| 33 | /* | 33 | /* |
| 34 | * Put the transceiver in non-driving mode. Otherwise host | 34 | * Put the phy in non-driving mode. Otherwise host |
| 35 | * may not detect soft-disconnection. | 35 | * may not detect soft-disconnection. |
| 36 | */ | 36 | */ |
| 37 | usb_phy_notify_disconnect(ci->transceiver, USB_SPEED_UNKNOWN); | 37 | usb_phy_notify_disconnect(ci->usb_phy, USB_SPEED_UNKNOWN); |
| 38 | break; | 38 | break; |
| 39 | default: | 39 | default: |
| 40 | dev_dbg(dev, "unknown ci_hdrc event\n"); | 40 | dev_dbg(dev, "unknown ci_hdrc event\n"); |
| @@ -46,7 +46,6 @@ static struct ci_hdrc_platform_data ci_hdrc_msm_platdata = { | |||
| 46 | .name = "ci_hdrc_msm", | 46 | .name = "ci_hdrc_msm", |
| 47 | .capoffset = DEF_CAPOFFSET, | 47 | .capoffset = DEF_CAPOFFSET, |
| 48 | .flags = CI_HDRC_REGS_SHARED | | 48 | .flags = CI_HDRC_REGS_SHARED | |
| 49 | CI_HDRC_REQUIRE_TRANSCEIVER | | ||
| 50 | CI_HDRC_DISABLE_STREAMING, | 49 | CI_HDRC_DISABLE_STREAMING, |
| 51 | 50 | ||
| 52 | .notify_event = ci_hdrc_msm_notify_event, | 51 | .notify_event = ci_hdrc_msm_notify_event, |
| @@ -68,7 +67,7 @@ static int ci_hdrc_msm_probe(struct platform_device *pdev) | |||
| 68 | if (IS_ERR(phy)) | 67 | if (IS_ERR(phy)) |
| 69 | return PTR_ERR(phy); | 68 | return PTR_ERR(phy); |
| 70 | 69 | ||
| 71 | ci_hdrc_msm_platdata.phy = phy; | 70 | ci_hdrc_msm_platdata.usb_phy = phy; |
| 72 | 71 | ||
| 73 | plat_ci = ci_hdrc_add_device(&pdev->dev, | 72 | plat_ci = ci_hdrc_add_device(&pdev->dev, |
| 74 | pdev->resource, pdev->num_resources, | 73 | pdev->resource, pdev->num_resources, |
diff --git a/drivers/usb/chipidea/ci_hdrc_usb2.c b/drivers/usb/chipidea/ci_hdrc_usb2.c new file mode 100644 index 000000000000..45844c951788 --- /dev/null +++ b/drivers/usb/chipidea/ci_hdrc_usb2.c | |||
| @@ -0,0 +1,115 @@ | |||
| 1 | /* | ||
| 2 | * Copyright (C) 2014 Marvell Technology Group Ltd. | ||
| 3 | * | ||
| 4 | * Antoine Tenart <antoine.tenart@free-electrons.com> | ||
| 5 | * | ||
| 6 | * This file is licensed under the terms of the GNU General Public | ||
| 7 | * License version 2. This program is licensed "as is" without any | ||
| 8 | * warranty of any kind, whether express or implied. | ||
| 9 | */ | ||
| 10 | |||
| 11 | #include <linux/clk.h> | ||
| 12 | #include <linux/dma-mapping.h> | ||
| 13 | #include <linux/module.h> | ||
| 14 | #include <linux/of.h> | ||
| 15 | #include <linux/phy/phy.h> | ||
| 16 | #include <linux/platform_device.h> | ||
| 17 | #include <linux/usb/chipidea.h> | ||
| 18 | #include <linux/usb/hcd.h> | ||
| 19 | #include <linux/usb/ulpi.h> | ||
| 20 | |||
| 21 | #include "ci.h" | ||
| 22 | |||
| 23 | struct ci_hdrc_usb2_priv { | ||
| 24 | struct platform_device *ci_pdev; | ||
| 25 | struct clk *clk; | ||
| 26 | }; | ||
| 27 | |||
| 28 | static struct ci_hdrc_platform_data ci_default_pdata = { | ||
| 29 | .capoffset = DEF_CAPOFFSET, | ||
| 30 | .flags = CI_HDRC_DISABLE_STREAMING, | ||
| 31 | }; | ||
| 32 | |||
| 33 | static int ci_hdrc_usb2_probe(struct platform_device *pdev) | ||
| 34 | { | ||
| 35 | struct device *dev = &pdev->dev; | ||
| 36 | struct ci_hdrc_usb2_priv *priv; | ||
| 37 | struct ci_hdrc_platform_data *ci_pdata = dev_get_platdata(dev); | ||
| 38 | int ret; | ||
| 39 | |||
| 40 | if (!ci_pdata) | ||
| 41 | ci_pdata = &ci_default_pdata; | ||
| 42 | |||
| 43 | priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); | ||
| 44 | if (!priv) | ||
| 45 | return -ENOMEM; | ||
| 46 | |||
| 47 | priv->clk = devm_clk_get(dev, NULL); | ||
| 48 | if (!IS_ERR(priv->clk)) { | ||
| 49 | ret = clk_prepare_enable(priv->clk); | ||
| 50 | if (ret) { | ||
| 51 | dev_err(dev, "failed to enable the clock: %d\n", ret); | ||
| 52 | return ret; | ||
| 53 | } | ||
| 54 | } | ||
| 55 | |||
| 56 | ret = dma_set_mask_and_coherent(dev, DMA_BIT_MASK(32)); | ||
| 57 | if (ret) | ||
| 58 | goto clk_err; | ||
| 59 | |||
| 60 | ci_pdata->name = dev_name(dev); | ||
| 61 | |||
| 62 | priv->ci_pdev = ci_hdrc_add_device(dev, pdev->resource, | ||
| 63 | pdev->num_resources, ci_pdata); | ||
| 64 | if (IS_ERR(priv->ci_pdev)) { | ||
| 65 | ret = PTR_ERR(priv->ci_pdev); | ||
| 66 | if (ret != -EPROBE_DEFER) | ||
| 67 | dev_err(dev, | ||
| 68 | "failed to register ci_hdrc platform device: %d\n", | ||
| 69 | ret); | ||
| 70 | goto clk_err; | ||
| 71 | } | ||
| 72 | |||
| 73 | platform_set_drvdata(pdev, priv); | ||
| 74 | |||
| 75 | pm_runtime_no_callbacks(dev); | ||
| 76 | pm_runtime_enable(dev); | ||
| 77 | |||
| 78 | return 0; | ||
| 79 | |||
| 80 | clk_err: | ||
| 81 | if (!IS_ERR(priv->clk)) | ||
| 82 | clk_disable_unprepare(priv->clk); | ||
| 83 | return ret; | ||
| 84 | } | ||
| 85 | |||
| 86 | static int ci_hdrc_usb2_remove(struct platform_device *pdev) | ||
| 87 | { | ||
| 88 | struct ci_hdrc_usb2_priv *priv = platform_get_drvdata(pdev); | ||
| 89 | |||
| 90 | pm_runtime_disable(&pdev->dev); | ||
| 91 | ci_hdrc_remove_device(priv->ci_pdev); | ||
| 92 | clk_disable_unprepare(priv->clk); | ||
| 93 | |||
| 94 | return 0; | ||
| 95 | } | ||
| 96 | |||
| 97 | static const struct of_device_id ci_hdrc_usb2_of_match[] = { | ||
| 98 | { .compatible = "chipidea,usb2" }, | ||
| 99 | { } | ||
| 100 | }; | ||
| 101 | MODULE_DEVICE_TABLE(of, ci_hdrc_usb2_of_match); | ||
| 102 | |||
| 103 | static struct platform_driver ci_hdrc_usb2_driver = { | ||
| 104 | .probe = ci_hdrc_usb2_probe, | ||
| 105 | .remove = ci_hdrc_usb2_remove, | ||
| 106 | .driver = { | ||
| 107 | .name = "chipidea-usb2", | ||
| 108 | .of_match_table = of_match_ptr(ci_hdrc_usb2_of_match), | ||
| 109 | }, | ||
| 110 | }; | ||
| 111 | module_platform_driver(ci_hdrc_usb2_driver); | ||
| 112 | |||
| 113 | MODULE_DESCRIPTION("ChipIdea HDRC USB2 binding for ci13xxx"); | ||
| 114 | MODULE_AUTHOR("Antoine Tenart <antoine.tenart@free-electrons.com>"); | ||
| 115 | MODULE_LICENSE("GPL"); | ||
diff --git a/drivers/usb/chipidea/core.c b/drivers/usb/chipidea/core.c index 9bdc6bd73432..e14eafb2a05e 100644 --- a/drivers/usb/chipidea/core.c +++ b/drivers/usb/chipidea/core.c | |||
| @@ -47,6 +47,7 @@ | |||
| 47 | #include <linux/delay.h> | 47 | #include <linux/delay.h> |
| 48 | #include <linux/device.h> | 48 | #include <linux/device.h> |
| 49 | #include <linux/dma-mapping.h> | 49 | #include <linux/dma-mapping.h> |
| 50 | #include <linux/phy/phy.h> | ||
| 50 | #include <linux/platform_device.h> | 51 | #include <linux/platform_device.h> |
| 51 | #include <linux/module.h> | 52 | #include <linux/module.h> |
| 52 | #include <linux/idr.h> | 53 | #include <linux/idr.h> |
| @@ -189,24 +190,29 @@ u8 hw_port_test_get(struct ci_hdrc *ci) | |||
| 189 | return hw_read(ci, OP_PORTSC, PORTSC_PTC) >> __ffs(PORTSC_PTC); | 190 | return hw_read(ci, OP_PORTSC, PORTSC_PTC) >> __ffs(PORTSC_PTC); |
| 190 | } | 191 | } |
| 191 | 192 | ||
| 193 | static void hw_wait_phy_stable(void) | ||
| 194 | { | ||
| 195 | /* | ||
| 196 | * The phy needs some delay to output the stable status from low | ||
| 197 | * power mode. And for OTGSC, the status inputs are debounced | ||
| 198 | * using a 1 ms time constant, so, delay 2ms for controller to get | ||
| 199 | * the stable status, like vbus and id when the phy leaves low power. | ||
| 200 | */ | ||
| 201 | usleep_range(2000, 2500); | ||
| 202 | } | ||
| 203 | |||
| 192 | /* The PHY enters/leaves low power mode */ | 204 | /* The PHY enters/leaves low power mode */ |
| 193 | static void ci_hdrc_enter_lpm(struct ci_hdrc *ci, bool enable) | 205 | static void ci_hdrc_enter_lpm(struct ci_hdrc *ci, bool enable) |
| 194 | { | 206 | { |
| 195 | enum ci_hw_regs reg = ci->hw_bank.lpm ? OP_DEVLC : OP_PORTSC; | 207 | enum ci_hw_regs reg = ci->hw_bank.lpm ? OP_DEVLC : OP_PORTSC; |
| 196 | bool lpm = !!(hw_read(ci, reg, PORTSC_PHCD(ci->hw_bank.lpm))); | 208 | bool lpm = !!(hw_read(ci, reg, PORTSC_PHCD(ci->hw_bank.lpm))); |
| 197 | 209 | ||
| 198 | if (enable && !lpm) { | 210 | if (enable && !lpm) |
| 199 | hw_write(ci, reg, PORTSC_PHCD(ci->hw_bank.lpm), | 211 | hw_write(ci, reg, PORTSC_PHCD(ci->hw_bank.lpm), |
| 200 | PORTSC_PHCD(ci->hw_bank.lpm)); | 212 | PORTSC_PHCD(ci->hw_bank.lpm)); |
| 201 | } else if (!enable && lpm) { | 213 | else if (!enable && lpm) |
| 202 | hw_write(ci, reg, PORTSC_PHCD(ci->hw_bank.lpm), | 214 | hw_write(ci, reg, PORTSC_PHCD(ci->hw_bank.lpm), |
| 203 | 0); | 215 | 0); |
| 204 | /* | ||
| 205 | * the PHY needs some time (less | ||
| 206 | * than 1ms) to leave low power mode. | ||
| 207 | */ | ||
| 208 | usleep_range(1000, 1100); | ||
| 209 | } | ||
| 210 | } | 216 | } |
| 211 | 217 | ||
| 212 | static int hw_device_init(struct ci_hdrc *ci, void __iomem *base) | 218 | static int hw_device_init(struct ci_hdrc *ci, void __iomem *base) |
| @@ -299,6 +305,49 @@ static void hw_phymode_configure(struct ci_hdrc *ci) | |||
| 299 | } | 305 | } |
| 300 | 306 | ||
| 301 | /** | 307 | /** |
| 308 | * _ci_usb_phy_init: initialize phy taking in account both phy and usb_phy | ||
| 309 | * interfaces | ||
| 310 | * @ci: the controller | ||
| 311 | * | ||
| 312 | * This function returns an error code if the phy failed to init | ||
| 313 | */ | ||
| 314 | static int _ci_usb_phy_init(struct ci_hdrc *ci) | ||
| 315 | { | ||
| 316 | int ret; | ||
| 317 | |||
| 318 | if (ci->phy) { | ||
| 319 | ret = phy_init(ci->phy); | ||
| 320 | if (ret) | ||
| 321 | return ret; | ||
| 322 | |||
| 323 | ret = phy_power_on(ci->phy); | ||
| 324 | if (ret) { | ||
| 325 | phy_exit(ci->phy); | ||
| 326 | return ret; | ||
| 327 | } | ||
| 328 | } else { | ||
| 329 | ret = usb_phy_init(ci->usb_phy); | ||
| 330 | } | ||
| 331 | |||
| 332 | return ret; | ||
| 333 | } | ||
| 334 | |||
| 335 | /** | ||
| 336 | * _ci_usb_phy_exit: deinitialize phy taking in account both phy and usb_phy | ||
| 337 | * interfaces | ||
| 338 | * @ci: the controller | ||
| 339 | */ | ||
| 340 | static void ci_usb_phy_exit(struct ci_hdrc *ci) | ||
| 341 | { | ||
| 342 | if (ci->phy) { | ||
| 343 | phy_power_off(ci->phy); | ||
| 344 | phy_exit(ci->phy); | ||
| 345 | } else { | ||
| 346 | usb_phy_shutdown(ci->usb_phy); | ||
| 347 | } | ||
| 348 | } | ||
| 349 | |||
| 350 | /** | ||
| 302 | * ci_usb_phy_init: initialize phy according to different phy type | 351 | * ci_usb_phy_init: initialize phy according to different phy type |
| 303 | * @ci: the controller | 352 | * @ci: the controller |
| 304 | * | 353 | * |
| @@ -312,40 +361,68 @@ static int ci_usb_phy_init(struct ci_hdrc *ci) | |||
| 312 | case USBPHY_INTERFACE_MODE_UTMI: | 361 | case USBPHY_INTERFACE_MODE_UTMI: |
| 313 | case USBPHY_INTERFACE_MODE_UTMIW: | 362 | case USBPHY_INTERFACE_MODE_UTMIW: |
| 314 | case USBPHY_INTERFACE_MODE_HSIC: | 363 | case USBPHY_INTERFACE_MODE_HSIC: |
| 315 | ret = usb_phy_init(ci->transceiver); | 364 | ret = _ci_usb_phy_init(ci); |
| 316 | if (ret) | 365 | if (!ret) |
| 366 | hw_wait_phy_stable(); | ||
| 367 | else | ||
| 317 | return ret; | 368 | return ret; |
| 318 | hw_phymode_configure(ci); | 369 | hw_phymode_configure(ci); |
| 319 | break; | 370 | break; |
| 320 | case USBPHY_INTERFACE_MODE_ULPI: | 371 | case USBPHY_INTERFACE_MODE_ULPI: |
| 321 | case USBPHY_INTERFACE_MODE_SERIAL: | 372 | case USBPHY_INTERFACE_MODE_SERIAL: |
| 322 | hw_phymode_configure(ci); | 373 | hw_phymode_configure(ci); |
| 323 | ret = usb_phy_init(ci->transceiver); | 374 | ret = _ci_usb_phy_init(ci); |
| 324 | if (ret) | 375 | if (ret) |
| 325 | return ret; | 376 | return ret; |
| 326 | break; | 377 | break; |
| 327 | default: | 378 | default: |
| 328 | ret = usb_phy_init(ci->transceiver); | 379 | ret = _ci_usb_phy_init(ci); |
| 380 | if (!ret) | ||
| 381 | hw_wait_phy_stable(); | ||
| 329 | } | 382 | } |
| 330 | 383 | ||
| 331 | return ret; | 384 | return ret; |
| 332 | } | 385 | } |
| 333 | 386 | ||
| 334 | /** | 387 | /** |
| 335 | * hw_device_reset: resets chip (execute without interruption) | 388 | * hw_controller_reset: do controller reset |
| 336 | * @ci: the controller | 389 | * @ci: the controller |
| 337 | * | 390 | * |
| 338 | * This function returns an error code | 391 | * This function returns an error code |
| 339 | */ | 392 | */ |
| 340 | int hw_device_reset(struct ci_hdrc *ci, u32 mode) | 393 | static int hw_controller_reset(struct ci_hdrc *ci) |
| 341 | { | 394 | { |
| 395 | int count = 0; | ||
| 396 | |||
| 397 | hw_write(ci, OP_USBCMD, USBCMD_RST, USBCMD_RST); | ||
| 398 | while (hw_read(ci, OP_USBCMD, USBCMD_RST)) { | ||
| 399 | udelay(10); | ||
| 400 | if (count++ > 1000) | ||
| 401 | return -ETIMEDOUT; | ||
| 402 | } | ||
| 403 | |||
| 404 | return 0; | ||
| 405 | } | ||
| 406 | |||
| 407 | /** | ||
| 408 | * hw_device_reset: resets chip (execute without interruption) | ||
| 409 | * @ci: the controller | ||
| 410 | * | ||
| 411 | * This function returns an error code | ||
| 412 | */ | ||
| 413 | int hw_device_reset(struct ci_hdrc *ci) | ||
| 414 | { | ||
| 415 | int ret; | ||
| 416 | |||
| 342 | /* should flush & stop before reset */ | 417 | /* should flush & stop before reset */ |
| 343 | hw_write(ci, OP_ENDPTFLUSH, ~0, ~0); | 418 | hw_write(ci, OP_ENDPTFLUSH, ~0, ~0); |
| 344 | hw_write(ci, OP_USBCMD, USBCMD_RS, 0); | 419 | hw_write(ci, OP_USBCMD, USBCMD_RS, 0); |
| 345 | 420 | ||
| 346 | hw_write(ci, OP_USBCMD, USBCMD_RST, USBCMD_RST); | 421 | ret = hw_controller_reset(ci); |
| 347 | while (hw_read(ci, OP_USBCMD, USBCMD_RST)) | 422 | if (ret) { |
| 348 | udelay(10); /* not RTOS friendly */ | 423 | dev_err(ci->dev, "error resetting controller, ret=%d\n", ret); |
| 424 | return ret; | ||
| 425 | } | ||
| 349 | 426 | ||
| 350 | if (ci->platdata->notify_event) | 427 | if (ci->platdata->notify_event) |
| 351 | ci->platdata->notify_event(ci, | 428 | ci->platdata->notify_event(ci, |
| @@ -363,12 +440,12 @@ int hw_device_reset(struct ci_hdrc *ci, u32 mode) | |||
| 363 | 440 | ||
| 364 | /* USBMODE should be configured step by step */ | 441 | /* USBMODE should be configured step by step */ |
| 365 | hw_write(ci, OP_USBMODE, USBMODE_CM, USBMODE_CM_IDLE); | 442 | hw_write(ci, OP_USBMODE, USBMODE_CM, USBMODE_CM_IDLE); |
| 366 | hw_write(ci, OP_USBMODE, USBMODE_CM, mode); | 443 | hw_write(ci, OP_USBMODE, USBMODE_CM, USBMODE_CM_DC); |
| 367 | /* HW >= 2.3 */ | 444 | /* HW >= 2.3 */ |
| 368 | hw_write(ci, OP_USBMODE, USBMODE_SLOM, USBMODE_SLOM); | 445 | hw_write(ci, OP_USBMODE, USBMODE_SLOM, USBMODE_SLOM); |
| 369 | 446 | ||
| 370 | if (hw_read(ci, OP_USBMODE, USBMODE_CM) != mode) { | 447 | if (hw_read(ci, OP_USBMODE, USBMODE_CM) != USBMODE_CM_DC) { |
| 371 | pr_err("cannot enter in %s mode", ci_role(ci)->name); | 448 | pr_err("cannot enter in %s device mode", ci_role(ci)->name); |
| 372 | pr_err("lpm = %i", ci->hw_bank.lpm); | 449 | pr_err("lpm = %i", ci->hw_bank.lpm); |
| 373 | return -ENODEV; | 450 | return -ENODEV; |
| 374 | } | 451 | } |
| @@ -472,7 +549,7 @@ static int ci_get_platdata(struct device *dev, | |||
| 472 | if (PTR_ERR(platdata->reg_vbus) == -EPROBE_DEFER) { | 549 | if (PTR_ERR(platdata->reg_vbus) == -EPROBE_DEFER) { |
| 473 | return -EPROBE_DEFER; | 550 | return -EPROBE_DEFER; |
| 474 | } else if (PTR_ERR(platdata->reg_vbus) == -ENODEV) { | 551 | } else if (PTR_ERR(platdata->reg_vbus) == -ENODEV) { |
| 475 | /* no vbus regualator is needed */ | 552 | /* no vbus regulator is needed */ |
| 476 | platdata->reg_vbus = NULL; | 553 | platdata->reg_vbus = NULL; |
| 477 | } else if (IS_ERR(platdata->reg_vbus)) { | 554 | } else if (IS_ERR(platdata->reg_vbus)) { |
| 478 | dev_err(dev, "Getting regulator error: %ld\n", | 555 | dev_err(dev, "Getting regulator error: %ld\n", |
| @@ -589,11 +666,10 @@ static int ci_hdrc_probe(struct platform_device *pdev) | |||
| 589 | return PTR_ERR(base); | 666 | return PTR_ERR(base); |
| 590 | 667 | ||
| 591 | ci = devm_kzalloc(dev, sizeof(*ci), GFP_KERNEL); | 668 | ci = devm_kzalloc(dev, sizeof(*ci), GFP_KERNEL); |
| 592 | if (!ci) { | 669 | if (!ci) |
| 593 | dev_err(dev, "can't allocate device\n"); | ||
| 594 | return -ENOMEM; | 670 | return -ENOMEM; |
| 595 | } | ||
| 596 | 671 | ||
| 672 | platform_set_drvdata(pdev, ci); | ||
| 597 | ci->dev = dev; | 673 | ci->dev = dev; |
| 598 | ci->platdata = dev_get_platdata(dev); | 674 | ci->platdata = dev_get_platdata(dev); |
| 599 | ci->imx28_write_fix = !!(ci->platdata->flags & | 675 | ci->imx28_write_fix = !!(ci->platdata->flags & |
| @@ -605,36 +681,32 @@ static int ci_hdrc_probe(struct platform_device *pdev) | |||
| 605 | return -ENODEV; | 681 | return -ENODEV; |
| 606 | } | 682 | } |
| 607 | 683 | ||
| 608 | if (ci->platdata->phy) | 684 | if (ci->platdata->phy) { |
| 609 | ci->transceiver = ci->platdata->phy; | 685 | ci->phy = ci->platdata->phy; |
| 610 | else | 686 | } else if (ci->platdata->usb_phy) { |
| 611 | ci->transceiver = devm_usb_get_phy(dev, USB_PHY_TYPE_USB2); | 687 | ci->usb_phy = ci->platdata->usb_phy; |
| 612 | 688 | } else { | |
| 613 | if (IS_ERR(ci->transceiver)) { | 689 | ci->phy = devm_phy_get(dev->parent, "usb-phy"); |
| 614 | ret = PTR_ERR(ci->transceiver); | 690 | ci->usb_phy = devm_usb_get_phy(dev->parent, USB_PHY_TYPE_USB2); |
| 615 | /* | 691 | |
| 616 | * if -ENXIO is returned, it means PHY layer wasn't | 692 | /* if both generic PHY and USB PHY layers aren't enabled */ |
| 617 | * enabled, so it makes no sense to return -EPROBE_DEFER | 693 | if (PTR_ERR(ci->phy) == -ENOSYS && |
| 618 | * in that case, since no PHY driver will ever probe. | 694 | PTR_ERR(ci->usb_phy) == -ENXIO) |
| 619 | */ | 695 | return -ENXIO; |
| 620 | if (ret == -ENXIO) | 696 | |
| 621 | return ret; | 697 | if (IS_ERR(ci->phy) && IS_ERR(ci->usb_phy)) |
| 698 | return -EPROBE_DEFER; | ||
| 622 | 699 | ||
| 623 | dev_err(dev, "no usb2 phy configured\n"); | 700 | if (IS_ERR(ci->phy)) |
| 624 | return -EPROBE_DEFER; | 701 | ci->phy = NULL; |
| 702 | else if (IS_ERR(ci->usb_phy)) | ||
| 703 | ci->usb_phy = NULL; | ||
| 625 | } | 704 | } |
| 626 | 705 | ||
| 627 | ret = ci_usb_phy_init(ci); | 706 | ret = ci_usb_phy_init(ci); |
| 628 | if (ret) { | 707 | if (ret) { |
| 629 | dev_err(dev, "unable to init phy: %d\n", ret); | 708 | dev_err(dev, "unable to init phy: %d\n", ret); |
| 630 | return ret; | 709 | return ret; |
| 631 | } else { | ||
| 632 | /* | ||
| 633 | * The delay to sync PHY's status, the maximum delay is | ||
| 634 | * 2ms since the otgsc uses 1ms timer to debounce the | ||
| 635 | * PHY's input | ||
| 636 | */ | ||
| 637 | usleep_range(2000, 2500); | ||
| 638 | } | 710 | } |
| 639 | 711 | ||
| 640 | ci->hw_bank.phys = res->start; | 712 | ci->hw_bank.phys = res->start; |
| @@ -711,9 +783,8 @@ static int ci_hdrc_probe(struct platform_device *pdev) | |||
| 711 | } | 783 | } |
| 712 | } | 784 | } |
| 713 | 785 | ||
| 714 | platform_set_drvdata(pdev, ci); | 786 | ret = devm_request_irq(dev, ci->irq, ci_irq, IRQF_SHARED, |
| 715 | ret = request_irq(ci->irq, ci_irq, IRQF_SHARED, ci->platdata->name, | 787 | ci->platdata->name, ci); |
| 716 | ci); | ||
| 717 | if (ret) | 788 | if (ret) |
| 718 | goto stop; | 789 | goto stop; |
| 719 | 790 | ||
| @@ -724,11 +795,10 @@ static int ci_hdrc_probe(struct platform_device *pdev) | |||
| 724 | if (!ret) | 795 | if (!ret) |
| 725 | return 0; | 796 | return 0; |
| 726 | 797 | ||
| 727 | free_irq(ci->irq, ci); | ||
| 728 | stop: | 798 | stop: |
| 729 | ci_role_destroy(ci); | 799 | ci_role_destroy(ci); |
| 730 | deinit_phy: | 800 | deinit_phy: |
| 731 | usb_phy_shutdown(ci->transceiver); | 801 | ci_usb_phy_exit(ci); |
| 732 | 802 | ||
| 733 | return ret; | 803 | return ret; |
| 734 | } | 804 | } |
| @@ -738,19 +808,66 @@ static int ci_hdrc_remove(struct platform_device *pdev) | |||
| 738 | struct ci_hdrc *ci = platform_get_drvdata(pdev); | 808 | struct ci_hdrc *ci = platform_get_drvdata(pdev); |
| 739 | 809 | ||
| 740 | dbg_remove_files(ci); | 810 | dbg_remove_files(ci); |
| 741 | free_irq(ci->irq, ci); | ||
| 742 | ci_role_destroy(ci); | 811 | ci_role_destroy(ci); |
| 743 | ci_hdrc_enter_lpm(ci, true); | 812 | ci_hdrc_enter_lpm(ci, true); |
| 744 | usb_phy_shutdown(ci->transceiver); | 813 | ci_usb_phy_exit(ci); |
| 814 | |||
| 815 | return 0; | ||
| 816 | } | ||
| 817 | |||
| 818 | #ifdef CONFIG_PM_SLEEP | ||
| 819 | static void ci_controller_suspend(struct ci_hdrc *ci) | ||
| 820 | { | ||
| 821 | ci_hdrc_enter_lpm(ci, true); | ||
| 822 | |||
| 823 | if (ci->usb_phy) | ||
| 824 | usb_phy_set_suspend(ci->usb_phy, 1); | ||
| 825 | } | ||
| 826 | |||
| 827 | static int ci_controller_resume(struct device *dev) | ||
| 828 | { | ||
| 829 | struct ci_hdrc *ci = dev_get_drvdata(dev); | ||
| 830 | |||
| 831 | dev_dbg(dev, "at %s\n", __func__); | ||
| 832 | |||
| 833 | ci_hdrc_enter_lpm(ci, false); | ||
| 834 | |||
| 835 | if (ci->usb_phy) { | ||
| 836 | usb_phy_set_suspend(ci->usb_phy, 0); | ||
| 837 | usb_phy_set_wakeup(ci->usb_phy, false); | ||
| 838 | hw_wait_phy_stable(); | ||
| 839 | } | ||
| 745 | 840 | ||
| 746 | return 0; | 841 | return 0; |
| 747 | } | 842 | } |
| 748 | 843 | ||
| 844 | static int ci_suspend(struct device *dev) | ||
| 845 | { | ||
| 846 | struct ci_hdrc *ci = dev_get_drvdata(dev); | ||
| 847 | |||
| 848 | if (ci->wq) | ||
| 849 | flush_workqueue(ci->wq); | ||
| 850 | |||
| 851 | ci_controller_suspend(ci); | ||
| 852 | |||
| 853 | return 0; | ||
| 854 | } | ||
| 855 | |||
| 856 | static int ci_resume(struct device *dev) | ||
| 857 | { | ||
| 858 | return ci_controller_resume(dev); | ||
| 859 | } | ||
| 860 | #endif /* CONFIG_PM_SLEEP */ | ||
| 861 | |||
| 862 | static const struct dev_pm_ops ci_pm_ops = { | ||
| 863 | SET_SYSTEM_SLEEP_PM_OPS(ci_suspend, ci_resume) | ||
| 864 | }; | ||
| 749 | static struct platform_driver ci_hdrc_driver = { | 865 | static struct platform_driver ci_hdrc_driver = { |
| 750 | .probe = ci_hdrc_probe, | 866 | .probe = ci_hdrc_probe, |
| 751 | .remove = ci_hdrc_remove, | 867 | .remove = ci_hdrc_remove, |
| 752 | .driver = { | 868 | .driver = { |
| 753 | .name = "ci_hdrc", | 869 | .name = "ci_hdrc", |
| 870 | .pm = &ci_pm_ops, | ||
| 754 | .owner = THIS_MODULE, | 871 | .owner = THIS_MODULE, |
| 755 | }, | 872 | }, |
| 756 | }; | 873 | }; |
diff --git a/drivers/usb/chipidea/debug.c b/drivers/usb/chipidea/debug.c index 795d6538d630..268e4236e84c 100644 --- a/drivers/usb/chipidea/debug.c +++ b/drivers/usb/chipidea/debug.c | |||
| @@ -220,7 +220,7 @@ static int ci_otg_show(struct seq_file *s, void *unused) | |||
| 220 | 220 | ||
| 221 | /* ------ State ----- */ | 221 | /* ------ State ----- */ |
| 222 | seq_printf(s, "OTG state: %s\n\n", | 222 | seq_printf(s, "OTG state: %s\n\n", |
| 223 | usb_otg_state_string(ci->transceiver->state)); | 223 | usb_otg_state_string(ci->otg.state)); |
| 224 | 224 | ||
| 225 | /* ------ State Machine Variables ----- */ | 225 | /* ------ State Machine Variables ----- */ |
| 226 | seq_printf(s, "a_bus_drop: %d\n", fsm->a_bus_drop); | 226 | seq_printf(s, "a_bus_drop: %d\n", fsm->a_bus_drop); |
diff --git a/drivers/usb/chipidea/host.c b/drivers/usb/chipidea/host.c index ebde7b6ce687..c1694cff1eaf 100644 --- a/drivers/usb/chipidea/host.c +++ b/drivers/usb/chipidea/host.c | |||
| @@ -34,6 +34,44 @@ | |||
| 34 | 34 | ||
| 35 | static struct hc_driver __read_mostly ci_ehci_hc_driver; | 35 | static struct hc_driver __read_mostly ci_ehci_hc_driver; |
| 36 | 36 | ||
| 37 | struct ehci_ci_priv { | ||
| 38 | struct regulator *reg_vbus; | ||
| 39 | }; | ||
| 40 | |||
| 41 | static int ehci_ci_portpower(struct usb_hcd *hcd, int portnum, bool enable) | ||
| 42 | { | ||
| 43 | struct ehci_hcd *ehci = hcd_to_ehci(hcd); | ||
| 44 | struct ehci_ci_priv *priv = (struct ehci_ci_priv *)ehci->priv; | ||
| 45 | struct device *dev = hcd->self.controller; | ||
| 46 | struct ci_hdrc *ci = dev_get_drvdata(dev); | ||
| 47 | int ret = 0; | ||
| 48 | int port = HCS_N_PORTS(ehci->hcs_params); | ||
| 49 | |||
| 50 | if (priv->reg_vbus && !ci_otg_is_fsm_mode(ci)) { | ||
| 51 | if (port > 1) { | ||
| 52 | dev_warn(dev, | ||
| 53 | "Not support multi-port regulator control\n"); | ||
| 54 | return 0; | ||
| 55 | } | ||
| 56 | if (enable) | ||
| 57 | ret = regulator_enable(priv->reg_vbus); | ||
| 58 | else | ||
| 59 | ret = regulator_disable(priv->reg_vbus); | ||
| 60 | if (ret) { | ||
| 61 | dev_err(dev, | ||
| 62 | "Failed to %s vbus regulator, ret=%d\n", | ||
| 63 | enable ? "enable" : "disable", ret); | ||
| 64 | return ret; | ||
| 65 | } | ||
| 66 | } | ||
| 67 | return 0; | ||
| 68 | }; | ||
| 69 | |||
| 70 | static const struct ehci_driver_overrides ehci_ci_overrides = { | ||
| 71 | .extra_priv_size = sizeof(struct ehci_ci_priv), | ||
| 72 | .port_power = ehci_ci_portpower, | ||
| 73 | }; | ||
| 74 | |||
| 37 | static irqreturn_t host_irq(struct ci_hdrc *ci) | 75 | static irqreturn_t host_irq(struct ci_hdrc *ci) |
| 38 | { | 76 | { |
| 39 | return usb_hcd_irq(ci->irq, ci->hcd); | 77 | return usb_hcd_irq(ci->irq, ci->hcd); |
| @@ -43,6 +81,7 @@ static int host_start(struct ci_hdrc *ci) | |||
| 43 | { | 81 | { |
| 44 | struct usb_hcd *hcd; | 82 | struct usb_hcd *hcd; |
| 45 | struct ehci_hcd *ehci; | 83 | struct ehci_hcd *ehci; |
| 84 | struct ehci_ci_priv *priv; | ||
| 46 | int ret; | 85 | int ret; |
| 47 | 86 | ||
| 48 | if (usb_disabled()) | 87 | if (usb_disabled()) |
| @@ -52,15 +91,17 @@ static int host_start(struct ci_hdrc *ci) | |||
| 52 | if (!hcd) | 91 | if (!hcd) |
| 53 | return -ENOMEM; | 92 | return -ENOMEM; |
| 54 | 93 | ||
| 55 | dev_set_drvdata(ci->dev, ci); | ||
| 56 | hcd->rsrc_start = ci->hw_bank.phys; | 94 | hcd->rsrc_start = ci->hw_bank.phys; |
| 57 | hcd->rsrc_len = ci->hw_bank.size; | 95 | hcd->rsrc_len = ci->hw_bank.size; |
| 58 | hcd->regs = ci->hw_bank.abs; | 96 | hcd->regs = ci->hw_bank.abs; |
| 59 | hcd->has_tt = 1; | 97 | hcd->has_tt = 1; |
| 60 | 98 | ||
| 61 | hcd->power_budget = ci->platdata->power_budget; | 99 | hcd->power_budget = ci->platdata->power_budget; |
| 62 | hcd->usb_phy = ci->transceiver; | ||
| 63 | hcd->tpl_support = ci->platdata->tpl_support; | 100 | hcd->tpl_support = ci->platdata->tpl_support; |
| 101 | if (ci->phy) | ||
| 102 | hcd->phy = ci->phy; | ||
| 103 | else | ||
| 104 | hcd->usb_phy = ci->usb_phy; | ||
| 64 | 105 | ||
| 65 | ehci = hcd_to_ehci(hcd); | 106 | ehci = hcd_to_ehci(hcd); |
| 66 | ehci->caps = ci->hw_bank.cap; | 107 | ehci->caps = ci->hw_bank.cap; |
| @@ -68,28 +109,21 @@ static int host_start(struct ci_hdrc *ci) | |||
| 68 | ehci->has_tdi_phy_lpm = ci->hw_bank.lpm; | 109 | ehci->has_tdi_phy_lpm = ci->hw_bank.lpm; |
| 69 | ehci->imx28_write_fix = ci->imx28_write_fix; | 110 | ehci->imx28_write_fix = ci->imx28_write_fix; |
| 70 | 111 | ||
| 71 | /* | 112 | priv = (struct ehci_ci_priv *)ehci->priv; |
| 72 | * vbus is always on if host is not in OTG FSM mode, | 113 | priv->reg_vbus = NULL; |
| 73 | * otherwise should be controlled by OTG FSM | 114 | |
| 74 | */ | 115 | if (ci->platdata->reg_vbus) |
| 75 | if (ci->platdata->reg_vbus && !ci_otg_is_fsm_mode(ci)) { | 116 | priv->reg_vbus = ci->platdata->reg_vbus; |
| 76 | ret = regulator_enable(ci->platdata->reg_vbus); | ||
| 77 | if (ret) { | ||
| 78 | dev_err(ci->dev, | ||
| 79 | "Failed to enable vbus regulator, ret=%d\n", | ||
| 80 | ret); | ||
| 81 | goto put_hcd; | ||
| 82 | } | ||
| 83 | } | ||
| 84 | 117 | ||
| 85 | ret = usb_add_hcd(hcd, 0, 0); | 118 | ret = usb_add_hcd(hcd, 0, 0); |
| 86 | if (ret) { | 119 | if (ret) { |
| 87 | goto disable_reg; | 120 | goto put_hcd; |
| 88 | } else { | 121 | } else { |
| 89 | struct usb_otg *otg = ci->transceiver->otg; | 122 | struct usb_otg *otg = &ci->otg; |
| 90 | 123 | ||
| 91 | ci->hcd = hcd; | 124 | ci->hcd = hcd; |
| 92 | if (otg) { | 125 | |
| 126 | if (ci_otg_is_fsm_mode(ci)) { | ||
| 93 | otg->host = &hcd->self; | 127 | otg->host = &hcd->self; |
| 94 | hcd->self.otg_port = 1; | 128 | hcd->self.otg_port = 1; |
| 95 | } | 129 | } |
| @@ -100,10 +134,6 @@ static int host_start(struct ci_hdrc *ci) | |||
| 100 | 134 | ||
| 101 | return ret; | 135 | return ret; |
| 102 | 136 | ||
| 103 | disable_reg: | ||
| 104 | if (ci->platdata->reg_vbus && !ci_otg_is_fsm_mode(ci)) | ||
| 105 | regulator_disable(ci->platdata->reg_vbus); | ||
| 106 | |||
| 107 | put_hcd: | 137 | put_hcd: |
| 108 | usb_put_hcd(hcd); | 138 | usb_put_hcd(hcd); |
| 109 | 139 | ||
| @@ -117,8 +147,6 @@ static void host_stop(struct ci_hdrc *ci) | |||
| 117 | if (hcd) { | 147 | if (hcd) { |
| 118 | usb_remove_hcd(hcd); | 148 | usb_remove_hcd(hcd); |
| 119 | usb_put_hcd(hcd); | 149 | usb_put_hcd(hcd); |
| 120 | if (ci->platdata->reg_vbus && !ci_otg_is_fsm_mode(ci)) | ||
| 121 | regulator_disable(ci->platdata->reg_vbus); | ||
| 122 | } | 150 | } |
| 123 | } | 151 | } |
| 124 | 152 | ||
| @@ -146,7 +174,7 @@ int ci_hdrc_host_init(struct ci_hdrc *ci) | |||
| 146 | rdrv->name = "host"; | 174 | rdrv->name = "host"; |
| 147 | ci->roles[CI_ROLE_HOST] = rdrv; | 175 | ci->roles[CI_ROLE_HOST] = rdrv; |
| 148 | 176 | ||
| 149 | ehci_init_driver(&ci_ehci_hc_driver, NULL); | 177 | ehci_init_driver(&ci_ehci_hc_driver, &ehci_ci_overrides); |
| 150 | 178 | ||
| 151 | return 0; | 179 | return 0; |
| 152 | } | 180 | } |
diff --git a/drivers/usb/chipidea/otg_fsm.c b/drivers/usb/chipidea/otg_fsm.c index caaabc58021e..562e581f6765 100644 --- a/drivers/usb/chipidea/otg_fsm.c +++ b/drivers/usb/chipidea/otg_fsm.c | |||
| @@ -303,7 +303,7 @@ static void a_wait_vfall_tmout_func(void *ptr, unsigned long indicator) | |||
| 303 | set_tmout(ci, indicator); | 303 | set_tmout(ci, indicator); |
| 304 | /* Disable port power */ | 304 | /* Disable port power */ |
| 305 | hw_write(ci, OP_PORTSC, PORTSC_W1C_BITS | PORTSC_PP, 0); | 305 | hw_write(ci, OP_PORTSC, PORTSC_W1C_BITS | PORTSC_PP, 0); |
| 306 | /* Clear exsiting DP irq */ | 306 | /* Clear existing DP irq */ |
| 307 | hw_write_otgsc(ci, OTGSC_DPIS, OTGSC_DPIS); | 307 | hw_write_otgsc(ci, OTGSC_DPIS, OTGSC_DPIS); |
| 308 | /* Enable data pulse irq */ | 308 | /* Enable data pulse irq */ |
| 309 | hw_write_otgsc(ci, OTGSC_DPIE, OTGSC_DPIE); | 309 | hw_write_otgsc(ci, OTGSC_DPIE, OTGSC_DPIE); |
| @@ -328,7 +328,7 @@ static void b_ssend_srp_tmout_func(void *ptr, unsigned long indicator) | |||
| 328 | set_tmout(ci, indicator); | 328 | set_tmout(ci, indicator); |
| 329 | 329 | ||
| 330 | /* only vbus fall below B_sess_vld in b_idle state */ | 330 | /* only vbus fall below B_sess_vld in b_idle state */ |
| 331 | if (ci->transceiver->state == OTG_STATE_B_IDLE) | 331 | if (ci->fsm.otg->state == OTG_STATE_B_IDLE) |
| 332 | ci_otg_queue_work(ci); | 332 | ci_otg_queue_work(ci); |
| 333 | } | 333 | } |
| 334 | 334 | ||
| @@ -543,7 +543,7 @@ static int ci_otg_start_host(struct otg_fsm *fsm, int on) | |||
| 543 | ci_role_start(ci, CI_ROLE_HOST); | 543 | ci_role_start(ci, CI_ROLE_HOST); |
| 544 | } else { | 544 | } else { |
| 545 | ci_role_stop(ci); | 545 | ci_role_stop(ci); |
| 546 | hw_device_reset(ci, USBMODE_CM_DC); | 546 | hw_device_reset(ci); |
| 547 | ci_role_start(ci, CI_ROLE_GADGET); | 547 | ci_role_start(ci, CI_ROLE_GADGET); |
| 548 | } | 548 | } |
| 549 | mutex_lock(&fsm->lock); | 549 | mutex_lock(&fsm->lock); |
| @@ -582,11 +582,11 @@ int ci_otg_fsm_work(struct ci_hdrc *ci) | |||
| 582 | * when there is no gadget class driver | 582 | * when there is no gadget class driver |
| 583 | */ | 583 | */ |
| 584 | if (ci->fsm.id && !(ci->driver) && | 584 | if (ci->fsm.id && !(ci->driver) && |
| 585 | ci->transceiver->state < OTG_STATE_A_IDLE) | 585 | ci->fsm.otg->state < OTG_STATE_A_IDLE) |
| 586 | return 0; | 586 | return 0; |
| 587 | 587 | ||
| 588 | if (otg_statemachine(&ci->fsm)) { | 588 | if (otg_statemachine(&ci->fsm)) { |
| 589 | if (ci->transceiver->state == OTG_STATE_A_IDLE) { | 589 | if (ci->fsm.otg->state == OTG_STATE_A_IDLE) { |
| 590 | /* | 590 | /* |
| 591 | * Further state change for cases: | 591 | * Further state change for cases: |
| 592 | * a_idle to b_idle; or | 592 | * a_idle to b_idle; or |
| @@ -600,7 +600,7 @@ int ci_otg_fsm_work(struct ci_hdrc *ci) | |||
| 600 | ci_otg_queue_work(ci); | 600 | ci_otg_queue_work(ci); |
| 601 | if (ci->id_event) | 601 | if (ci->id_event) |
| 602 | ci->id_event = false; | 602 | ci->id_event = false; |
| 603 | } else if (ci->transceiver->state == OTG_STATE_B_IDLE) { | 603 | } else if (ci->fsm.otg->state == OTG_STATE_B_IDLE) { |
| 604 | if (ci->fsm.b_sess_vld) { | 604 | if (ci->fsm.b_sess_vld) { |
| 605 | ci->fsm.power_up = 0; | 605 | ci->fsm.power_up = 0; |
| 606 | /* | 606 | /* |
| @@ -627,7 +627,7 @@ static void ci_otg_fsm_event(struct ci_hdrc *ci) | |||
| 627 | otg_bsess_vld = hw_read_otgsc(ci, OTGSC_BSV); | 627 | otg_bsess_vld = hw_read_otgsc(ci, OTGSC_BSV); |
| 628 | port_conn = hw_read(ci, OP_PORTSC, PORTSC_CCS); | 628 | port_conn = hw_read(ci, OP_PORTSC, PORTSC_CCS); |
| 629 | 629 | ||
| 630 | switch (ci->transceiver->state) { | 630 | switch (ci->fsm.otg->state) { |
| 631 | case OTG_STATE_A_WAIT_BCON: | 631 | case OTG_STATE_A_WAIT_BCON: |
| 632 | if (port_conn) { | 632 | if (port_conn) { |
| 633 | fsm->b_conn = 1; | 633 | fsm->b_conn = 1; |
| @@ -663,7 +663,7 @@ static void ci_otg_fsm_event(struct ci_hdrc *ci) | |||
| 663 | fsm->b_bus_suspend = 1; | 663 | fsm->b_bus_suspend = 1; |
| 664 | /* | 664 | /* |
| 665 | * Init a timer to know how long this suspend | 665 | * Init a timer to know how long this suspend |
| 666 | * will contine, if time out, indicates B no longer | 666 | * will continue, if time out, indicates B no longer |
| 667 | * wants to be host role | 667 | * wants to be host role |
| 668 | */ | 668 | */ |
| 669 | ci_otg_add_timer(ci, A_BIDL_ADIS); | 669 | ci_otg_add_timer(ci, A_BIDL_ADIS); |
| @@ -778,34 +778,25 @@ void ci_hdrc_otg_fsm_start(struct ci_hdrc *ci) | |||
| 778 | int ci_hdrc_otg_fsm_init(struct ci_hdrc *ci) | 778 | int ci_hdrc_otg_fsm_init(struct ci_hdrc *ci) |
| 779 | { | 779 | { |
| 780 | int retval = 0; | 780 | int retval = 0; |
| 781 | struct usb_otg *otg; | ||
| 782 | 781 | ||
| 783 | otg = devm_kzalloc(ci->dev, | 782 | if (ci->phy) |
| 784 | sizeof(struct usb_otg), GFP_KERNEL); | 783 | ci->otg.phy = ci->phy; |
| 785 | if (!otg) { | 784 | else |
| 786 | dev_err(ci->dev, | 785 | ci->otg.usb_phy = ci->usb_phy; |
| 787 | "Failed to allocate usb_otg structure for ci hdrc otg!\n"); | ||
| 788 | return -ENOMEM; | ||
| 789 | } | ||
| 790 | 786 | ||
| 791 | otg->phy = ci->transceiver; | 787 | ci->otg.gadget = &ci->gadget; |
| 792 | otg->gadget = &ci->gadget; | 788 | ci->fsm.otg = &ci->otg; |
| 793 | ci->fsm.otg = otg; | ||
| 794 | ci->transceiver->otg = ci->fsm.otg; | ||
| 795 | ci->fsm.power_up = 1; | 789 | ci->fsm.power_up = 1; |
| 796 | ci->fsm.id = hw_read_otgsc(ci, OTGSC_ID) ? 1 : 0; | 790 | ci->fsm.id = hw_read_otgsc(ci, OTGSC_ID) ? 1 : 0; |
| 797 | ci->transceiver->state = OTG_STATE_UNDEFINED; | 791 | ci->fsm.otg->state = OTG_STATE_UNDEFINED; |
| 798 | ci->fsm.ops = &ci_otg_ops; | 792 | ci->fsm.ops = &ci_otg_ops; |
| 799 | 793 | ||
| 800 | mutex_init(&ci->fsm.lock); | 794 | mutex_init(&ci->fsm.lock); |
| 801 | 795 | ||
| 802 | ci->fsm_timer = devm_kzalloc(ci->dev, | 796 | ci->fsm_timer = devm_kzalloc(ci->dev, |
| 803 | sizeof(struct ci_otg_fsm_timer_list), GFP_KERNEL); | 797 | sizeof(struct ci_otg_fsm_timer_list), GFP_KERNEL); |
| 804 | if (!ci->fsm_timer) { | 798 | if (!ci->fsm_timer) |
| 805 | dev_err(ci->dev, | ||
| 806 | "Failed to allocate timer structure for ci hdrc otg!\n"); | ||
| 807 | return -ENOMEM; | 799 | return -ENOMEM; |
| 808 | } | ||
| 809 | 800 | ||
| 810 | INIT_LIST_HEAD(&ci->fsm_timer->active_timers); | 801 | INIT_LIST_HEAD(&ci->fsm_timer->active_timers); |
| 811 | retval = ci_otg_init_timers(ci); | 802 | retval = ci_otg_init_timers(ci); |
diff --git a/drivers/usb/chipidea/udc.c b/drivers/usb/chipidea/udc.c index 0444d3f8971a..4fe18ce3bd5a 100644 --- a/drivers/usb/chipidea/udc.c +++ b/drivers/usb/chipidea/udc.c | |||
| @@ -692,10 +692,8 @@ __acquires(ci->lock) | |||
| 692 | int retval; | 692 | int retval; |
| 693 | 693 | ||
| 694 | spin_unlock(&ci->lock); | 694 | spin_unlock(&ci->lock); |
| 695 | if (ci->gadget.speed != USB_SPEED_UNKNOWN) { | 695 | if (ci->gadget.speed != USB_SPEED_UNKNOWN) |
| 696 | if (ci->driver) | 696 | usb_gadget_udc_reset(&ci->gadget, ci->driver); |
| 697 | ci->driver->disconnect(&ci->gadget); | ||
| 698 | } | ||
| 699 | 697 | ||
| 700 | retval = _gadget_stop_activity(&ci->gadget); | 698 | retval = _gadget_stop_activity(&ci->gadget); |
| 701 | if (retval) | 699 | if (retval) |
| @@ -709,8 +707,6 @@ __acquires(ci->lock) | |||
| 709 | if (ci->status == NULL) | 707 | if (ci->status == NULL) |
| 710 | retval = -ENOMEM; | 708 | retval = -ENOMEM; |
| 711 | 709 | ||
| 712 | usb_gadget_set_state(&ci->gadget, USB_STATE_DEFAULT); | ||
| 713 | |||
| 714 | done: | 710 | done: |
| 715 | spin_lock(&ci->lock); | 711 | spin_lock(&ci->lock); |
| 716 | 712 | ||
| @@ -1475,7 +1471,7 @@ static int ci_udc_vbus_session(struct usb_gadget *_gadget, int is_active) | |||
| 1475 | if (gadget_ready) { | 1471 | if (gadget_ready) { |
| 1476 | if (is_active) { | 1472 | if (is_active) { |
| 1477 | pm_runtime_get_sync(&_gadget->dev); | 1473 | pm_runtime_get_sync(&_gadget->dev); |
| 1478 | hw_device_reset(ci, USBMODE_CM_DC); | 1474 | hw_device_reset(ci); |
| 1479 | hw_device_state(ci, ci->ep0out->qh.dma); | 1475 | hw_device_state(ci, ci->ep0out->qh.dma); |
| 1480 | usb_gadget_set_state(_gadget, USB_STATE_POWERED); | 1476 | usb_gadget_set_state(_gadget, USB_STATE_POWERED); |
| 1481 | } else { | 1477 | } else { |
| @@ -1519,8 +1515,8 @@ static int ci_udc_vbus_draw(struct usb_gadget *_gadget, unsigned ma) | |||
| 1519 | { | 1515 | { |
| 1520 | struct ci_hdrc *ci = container_of(_gadget, struct ci_hdrc, gadget); | 1516 | struct ci_hdrc *ci = container_of(_gadget, struct ci_hdrc, gadget); |
| 1521 | 1517 | ||
| 1522 | if (ci->transceiver) | 1518 | if (ci->usb_phy) |
| 1523 | return usb_phy_set_power(ci->transceiver, ma); | 1519 | return usb_phy_set_power(ci->usb_phy, ma); |
| 1524 | return -ENOTSUPP; | 1520 | return -ENOTSUPP; |
| 1525 | } | 1521 | } |
| 1526 | 1522 | ||
| @@ -1544,8 +1540,7 @@ static int ci_udc_pullup(struct usb_gadget *_gadget, int is_on) | |||
| 1544 | 1540 | ||
| 1545 | static int ci_udc_start(struct usb_gadget *gadget, | 1541 | static int ci_udc_start(struct usb_gadget *gadget, |
| 1546 | struct usb_gadget_driver *driver); | 1542 | struct usb_gadget_driver *driver); |
| 1547 | static int ci_udc_stop(struct usb_gadget *gadget, | 1543 | static int ci_udc_stop(struct usb_gadget *gadget); |
| 1548 | struct usb_gadget_driver *driver); | ||
| 1549 | /** | 1544 | /** |
| 1550 | * Device operations part of the API to the USB controller hardware, | 1545 | * Device operations part of the API to the USB controller hardware, |
| 1551 | * which don't involve endpoints (or i/o) | 1546 | * which don't involve endpoints (or i/o) |
| @@ -1665,7 +1660,7 @@ static int ci_udc_start(struct usb_gadget *gadget, | |||
| 1665 | pm_runtime_get_sync(&ci->gadget.dev); | 1660 | pm_runtime_get_sync(&ci->gadget.dev); |
| 1666 | if (ci->vbus_active) { | 1661 | if (ci->vbus_active) { |
| 1667 | spin_lock_irqsave(&ci->lock, flags); | 1662 | spin_lock_irqsave(&ci->lock, flags); |
| 1668 | hw_device_reset(ci, USBMODE_CM_DC); | 1663 | hw_device_reset(ci); |
| 1669 | } else { | 1664 | } else { |
| 1670 | pm_runtime_put_sync(&ci->gadget.dev); | 1665 | pm_runtime_put_sync(&ci->gadget.dev); |
| 1671 | return retval; | 1666 | return retval; |
| @@ -1682,8 +1677,7 @@ static int ci_udc_start(struct usb_gadget *gadget, | |||
| 1682 | /** | 1677 | /** |
| 1683 | * ci_udc_stop: unregister a gadget driver | 1678 | * ci_udc_stop: unregister a gadget driver |
| 1684 | */ | 1679 | */ |
| 1685 | static int ci_udc_stop(struct usb_gadget *gadget, | 1680 | static int ci_udc_stop(struct usb_gadget *gadget) |
| 1686 | struct usb_gadget_driver *driver) | ||
| 1687 | { | 1681 | { |
| 1688 | struct ci_hdrc *ci = container_of(gadget, struct ci_hdrc, gadget); | 1682 | struct ci_hdrc *ci = container_of(gadget, struct ci_hdrc, gadget); |
| 1689 | unsigned long flags; | 1683 | unsigned long flags; |
diff --git a/drivers/usb/chipidea/usbmisc_imx.c b/drivers/usb/chipidea/usbmisc_imx.c index 926c997ef310..58591e9dcede 100644 --- a/drivers/usb/chipidea/usbmisc_imx.c +++ b/drivers/usb/chipidea/usbmisc_imx.c | |||
| @@ -117,10 +117,9 @@ static int usbmisc_imx25_post(struct imx_usbmisc_data *data) | |||
| 117 | if (data->index > 2) | 117 | if (data->index > 2) |
| 118 | return -EINVAL; | 118 | return -EINVAL; |
| 119 | 119 | ||
| 120 | reg = usbmisc->base + MX25_USB_PHY_CTRL_OFFSET; | ||
| 121 | |||
| 122 | if (data->evdo) { | 120 | if (data->evdo) { |
| 123 | spin_lock_irqsave(&usbmisc->lock, flags); | 121 | spin_lock_irqsave(&usbmisc->lock, flags); |
| 122 | reg = usbmisc->base + MX25_USB_PHY_CTRL_OFFSET; | ||
| 124 | val = readl(reg); | 123 | val = readl(reg); |
| 125 | writel(val | MX25_BM_EXTERNAL_VBUS_DIVIDER, reg); | 124 | writel(val | MX25_BM_EXTERNAL_VBUS_DIVIDER, reg); |
| 126 | spin_unlock_irqrestore(&usbmisc->lock, flags); | 125 | spin_unlock_irqrestore(&usbmisc->lock, flags); |
| @@ -172,8 +171,7 @@ static int usbmisc_imx53_init(struct imx_usbmisc_data *data) | |||
| 172 | return -EINVAL; | 171 | return -EINVAL; |
| 173 | 172 | ||
| 174 | /* Select a 24 MHz reference clock for the PHY */ | 173 | /* Select a 24 MHz reference clock for the PHY */ |
| 175 | reg = usbmisc->base + MX53_USB_OTG_PHY_CTRL_1_OFFSET; | 174 | val = readl(usbmisc->base + MX53_USB_OTG_PHY_CTRL_1_OFFSET); |
| 176 | val = readl(reg); | ||
| 177 | val &= ~MX53_USB_PHYCTRL1_PLLDIV_MASK; | 175 | val &= ~MX53_USB_PHYCTRL1_PLLDIV_MASK; |
| 178 | val |= MX53_USB_PLL_DIV_24_MHZ; | 176 | val |= MX53_USB_PLL_DIV_24_MHZ; |
| 179 | writel(val, usbmisc->base + MX53_USB_OTG_PHY_CTRL_1_OFFSET); | 177 | writel(val, usbmisc->base + MX53_USB_OTG_PHY_CTRL_1_OFFSET); |
diff --git a/drivers/usb/class/cdc-acm.c b/drivers/usb/class/cdc-acm.c index 077d58ac3dcb..546a17e8ad5b 100644 --- a/drivers/usb/class/cdc-acm.c +++ b/drivers/usb/class/cdc-acm.c | |||
| @@ -1157,8 +1157,6 @@ static int acm_probe(struct usb_interface *intf, | |||
| 1157 | case USB_CDC_CALL_MANAGEMENT_TYPE: | 1157 | case USB_CDC_CALL_MANAGEMENT_TYPE: |
| 1158 | call_management_function = buffer[3]; | 1158 | call_management_function = buffer[3]; |
| 1159 | call_interface_num = buffer[4]; | 1159 | call_interface_num = buffer[4]; |
| 1160 | if ((quirks & NOT_A_MODEM) == 0 && (call_management_function & 3) != 3) | ||
| 1161 | dev_err(&intf->dev, "This device cannot do calls on its own. It is not a modem.\n"); | ||
| 1162 | break; | 1160 | break; |
| 1163 | default: | 1161 | default: |
| 1164 | /* there are LOTS more CDC descriptors that | 1162 | /* there are LOTS more CDC descriptors that |
| @@ -1197,10 +1195,11 @@ next_desc: | |||
| 1197 | } else { | 1195 | } else { |
| 1198 | control_interface = usb_ifnum_to_if(usb_dev, union_header->bMasterInterface0); | 1196 | control_interface = usb_ifnum_to_if(usb_dev, union_header->bMasterInterface0); |
| 1199 | data_interface = usb_ifnum_to_if(usb_dev, (data_interface_num = union_header->bSlaveInterface0)); | 1197 | data_interface = usb_ifnum_to_if(usb_dev, (data_interface_num = union_header->bSlaveInterface0)); |
| 1200 | if (!control_interface || !data_interface) { | 1198 | } |
| 1201 | dev_dbg(&intf->dev, "no interfaces\n"); | 1199 | |
| 1202 | return -ENODEV; | 1200 | if (!control_interface || !data_interface) { |
| 1203 | } | 1201 | dev_dbg(&intf->dev, "no interfaces\n"); |
| 1202 | return -ENODEV; | ||
| 1204 | } | 1203 | } |
| 1205 | 1204 | ||
| 1206 | if (data_interface_num != call_interface_num) | 1205 | if (data_interface_num != call_interface_num) |
| @@ -1475,6 +1474,7 @@ alloc_fail8: | |||
| 1475 | &dev_attr_wCountryCodes); | 1474 | &dev_attr_wCountryCodes); |
| 1476 | device_remove_file(&acm->control->dev, | 1475 | device_remove_file(&acm->control->dev, |
| 1477 | &dev_attr_iCountryCodeRelDate); | 1476 | &dev_attr_iCountryCodeRelDate); |
| 1477 | kfree(acm->country_codes); | ||
| 1478 | } | 1478 | } |
| 1479 | device_remove_file(&acm->control->dev, &dev_attr_bmCapabilities); | 1479 | device_remove_file(&acm->control->dev, &dev_attr_bmCapabilities); |
| 1480 | alloc_fail7: | 1480 | alloc_fail7: |
| @@ -1813,11 +1813,6 @@ static const struct usb_device_id acm_ids[] = { | |||
| 1813 | 1813 | ||
| 1814 | /* NOTE: non-Nokia COMM/ACM/0xff is likely MSFT RNDIS... NOT a modem! */ | 1814 | /* NOTE: non-Nokia COMM/ACM/0xff is likely MSFT RNDIS... NOT a modem! */ |
| 1815 | 1815 | ||
| 1816 | /* Support Lego NXT using pbLua firmware */ | ||
| 1817 | { USB_DEVICE(0x0694, 0xff00), | ||
| 1818 | .driver_info = NOT_A_MODEM, | ||
| 1819 | }, | ||
| 1820 | |||
| 1821 | /* Support for Droids MuIn LCD */ | 1816 | /* Support for Droids MuIn LCD */ |
| 1822 | { USB_DEVICE(0x04d8, 0x000b), | 1817 | { USB_DEVICE(0x04d8, 0x000b), |
| 1823 | .driver_info = NO_DATA_INTERFACE, | 1818 | .driver_info = NO_DATA_INTERFACE, |
diff --git a/drivers/usb/class/cdc-acm.h b/drivers/usb/class/cdc-acm.h index d3251ebd09e2..ffeb3c83941f 100644 --- a/drivers/usb/class/cdc-acm.h +++ b/drivers/usb/class/cdc-acm.h | |||
| @@ -130,7 +130,6 @@ struct acm { | |||
| 130 | #define NO_UNION_NORMAL BIT(0) | 130 | #define NO_UNION_NORMAL BIT(0) |
| 131 | #define SINGLE_RX_URB BIT(1) | 131 | #define SINGLE_RX_URB BIT(1) |
| 132 | #define NO_CAP_LINE BIT(2) | 132 | #define NO_CAP_LINE BIT(2) |
| 133 | #define NOT_A_MODEM BIT(3) | ||
| 134 | #define NO_DATA_INTERFACE BIT(4) | 133 | #define NO_DATA_INTERFACE BIT(4) |
| 135 | #define IGNORE_DEVICE BIT(5) | 134 | #define IGNORE_DEVICE BIT(5) |
| 136 | #define QUIRK_CONTROL_LINE_STATE BIT(6) | 135 | #define QUIRK_CONTROL_LINE_STATE BIT(6) |
diff --git a/drivers/usb/class/usbtmc.c b/drivers/usb/class/usbtmc.c index ec978408a2ee..960bc089111b 100644 --- a/drivers/usb/class/usbtmc.c +++ b/drivers/usb/class/usbtmc.c | |||
| @@ -1104,10 +1104,8 @@ static int usbtmc_probe(struct usb_interface *intf, | |||
| 1104 | dev_dbg(&intf->dev, "%s called\n", __func__); | 1104 | dev_dbg(&intf->dev, "%s called\n", __func__); |
| 1105 | 1105 | ||
| 1106 | data = devm_kzalloc(&intf->dev, sizeof(*data), GFP_KERNEL); | 1106 | data = devm_kzalloc(&intf->dev, sizeof(*data), GFP_KERNEL); |
| 1107 | if (!data) { | 1107 | if (!data) |
| 1108 | dev_err(&intf->dev, "Unable to allocate kernel memory\n"); | ||
| 1109 | return -ENOMEM; | 1108 | return -ENOMEM; |
| 1110 | } | ||
| 1111 | 1109 | ||
| 1112 | data->intf = intf; | 1110 | data->intf = intf; |
| 1113 | data->id = id; | 1111 | data->id = id; |
diff --git a/drivers/usb/common/usb-otg-fsm.c b/drivers/usb/common/usb-otg-fsm.c index 98e8340a5bb1..c6b35b77dab7 100644 --- a/drivers/usb/common/usb-otg-fsm.c +++ b/drivers/usb/common/usb-otg-fsm.c | |||
| @@ -124,10 +124,10 @@ static void otg_leave_state(struct otg_fsm *fsm, enum usb_otg_state old_state) | |||
| 124 | static int otg_set_state(struct otg_fsm *fsm, enum usb_otg_state new_state) | 124 | static int otg_set_state(struct otg_fsm *fsm, enum usb_otg_state new_state) |
| 125 | { | 125 | { |
| 126 | state_changed = 1; | 126 | state_changed = 1; |
| 127 | if (fsm->otg->phy->state == new_state) | 127 | if (fsm->otg->state == new_state) |
| 128 | return 0; | 128 | return 0; |
| 129 | VDBG("Set state: %s\n", usb_otg_state_string(new_state)); | 129 | VDBG("Set state: %s\n", usb_otg_state_string(new_state)); |
| 130 | otg_leave_state(fsm, fsm->otg->phy->state); | 130 | otg_leave_state(fsm, fsm->otg->state); |
| 131 | switch (new_state) { | 131 | switch (new_state) { |
| 132 | case OTG_STATE_B_IDLE: | 132 | case OTG_STATE_B_IDLE: |
| 133 | otg_drv_vbus(fsm, 0); | 133 | otg_drv_vbus(fsm, 0); |
| @@ -236,7 +236,7 @@ static int otg_set_state(struct otg_fsm *fsm, enum usb_otg_state new_state) | |||
| 236 | break; | 236 | break; |
| 237 | } | 237 | } |
| 238 | 238 | ||
| 239 | fsm->otg->phy->state = new_state; | 239 | fsm->otg->state = new_state; |
| 240 | return 0; | 240 | return 0; |
| 241 | } | 241 | } |
| 242 | 242 | ||
| @@ -247,7 +247,7 @@ int otg_statemachine(struct otg_fsm *fsm) | |||
| 247 | 247 | ||
| 248 | mutex_lock(&fsm->lock); | 248 | mutex_lock(&fsm->lock); |
| 249 | 249 | ||
| 250 | state = fsm->otg->phy->state; | 250 | state = fsm->otg->state; |
| 251 | state_changed = 0; | 251 | state_changed = 0; |
| 252 | /* State machine state change judgement */ | 252 | /* State machine state change judgement */ |
| 253 | 253 | ||
diff --git a/drivers/usb/core/hcd.c b/drivers/usb/core/hcd.c index 278be0515e8e..11cee55ae397 100644 --- a/drivers/usb/core/hcd.c +++ b/drivers/usb/core/hcd.c | |||
| @@ -2646,7 +2646,7 @@ int usb_add_hcd(struct usb_hcd *hcd, | |||
| 2646 | } | 2646 | } |
| 2647 | } | 2647 | } |
| 2648 | 2648 | ||
| 2649 | if (IS_ENABLED(CONFIG_GENERIC_PHY)) { | 2649 | if (IS_ENABLED(CONFIG_GENERIC_PHY) && !hcd->phy) { |
| 2650 | struct phy *phy = phy_get(hcd->self.controller, "usb"); | 2650 | struct phy *phy = phy_get(hcd->self.controller, "usb"); |
| 2651 | 2651 | ||
| 2652 | if (IS_ERR(phy)) { | 2652 | if (IS_ERR(phy)) { |
| @@ -2666,6 +2666,7 @@ int usb_add_hcd(struct usb_hcd *hcd, | |||
| 2666 | goto err_phy; | 2666 | goto err_phy; |
| 2667 | } | 2667 | } |
| 2668 | hcd->phy = phy; | 2668 | hcd->phy = phy; |
| 2669 | hcd->remove_phy = 1; | ||
| 2669 | } | 2670 | } |
| 2670 | } | 2671 | } |
| 2671 | 2672 | ||
| @@ -2812,7 +2813,7 @@ err_allocate_root_hub: | |||
| 2812 | err_register_bus: | 2813 | err_register_bus: |
| 2813 | hcd_buffer_destroy(hcd); | 2814 | hcd_buffer_destroy(hcd); |
| 2814 | err_create_buf: | 2815 | err_create_buf: |
| 2815 | if (IS_ENABLED(CONFIG_GENERIC_PHY) && hcd->phy) { | 2816 | if (IS_ENABLED(CONFIG_GENERIC_PHY) && hcd->remove_phy && hcd->phy) { |
| 2816 | phy_power_off(hcd->phy); | 2817 | phy_power_off(hcd->phy); |
| 2817 | phy_exit(hcd->phy); | 2818 | phy_exit(hcd->phy); |
| 2818 | phy_put(hcd->phy); | 2819 | phy_put(hcd->phy); |
| @@ -2896,7 +2897,7 @@ void usb_remove_hcd(struct usb_hcd *hcd) | |||
| 2896 | usb_deregister_bus(&hcd->self); | 2897 | usb_deregister_bus(&hcd->self); |
| 2897 | hcd_buffer_destroy(hcd); | 2898 | hcd_buffer_destroy(hcd); |
| 2898 | 2899 | ||
| 2899 | if (IS_ENABLED(CONFIG_GENERIC_PHY) && hcd->phy) { | 2900 | if (IS_ENABLED(CONFIG_GENERIC_PHY) && hcd->remove_phy && hcd->phy) { |
| 2900 | phy_power_off(hcd->phy); | 2901 | phy_power_off(hcd->phy); |
| 2901 | phy_exit(hcd->phy); | 2902 | phy_exit(hcd->phy); |
| 2902 | phy_put(hcd->phy); | 2903 | phy_put(hcd->phy); |
diff --git a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c index c9596525ba8c..aeb50bb6ba9c 100644 --- a/drivers/usb/core/hub.c +++ b/drivers/usb/core/hub.c | |||
| @@ -2543,11 +2543,14 @@ int usb_authorize_device(struct usb_device *usb_dev) | |||
| 2543 | "can't autoresume for authorization: %d\n", result); | 2543 | "can't autoresume for authorization: %d\n", result); |
| 2544 | goto error_autoresume; | 2544 | goto error_autoresume; |
| 2545 | } | 2545 | } |
| 2546 | result = usb_get_device_descriptor(usb_dev, sizeof(usb_dev->descriptor)); | 2546 | |
| 2547 | if (result < 0) { | 2547 | if (usb_dev->wusb) { |
| 2548 | dev_err(&usb_dev->dev, "can't re-read device descriptor for " | 2548 | result = usb_get_device_descriptor(usb_dev, sizeof(usb_dev->descriptor)); |
| 2549 | "authorization: %d\n", result); | 2549 | if (result < 0) { |
| 2550 | goto error_device_descriptor; | 2550 | dev_err(&usb_dev->dev, "can't re-read device descriptor for " |
| 2551 | "authorization: %d\n", result); | ||
| 2552 | goto error_device_descriptor; | ||
| 2553 | } | ||
| 2551 | } | 2554 | } |
| 2552 | 2555 | ||
| 2553 | usb_dev->authorized = 1; | 2556 | usb_dev->authorized = 1; |
| @@ -3907,14 +3910,9 @@ static void usb_enable_link_state(struct usb_hcd *hcd, struct usb_device *udev, | |||
| 3907 | static int usb_disable_link_state(struct usb_hcd *hcd, struct usb_device *udev, | 3910 | static int usb_disable_link_state(struct usb_hcd *hcd, struct usb_device *udev, |
| 3908 | enum usb3_link_state state) | 3911 | enum usb3_link_state state) |
| 3909 | { | 3912 | { |
| 3910 | int feature; | ||
| 3911 | |||
| 3912 | switch (state) { | 3913 | switch (state) { |
| 3913 | case USB3_LPM_U1: | 3914 | case USB3_LPM_U1: |
| 3914 | feature = USB_PORT_FEAT_U1_TIMEOUT; | ||
| 3915 | break; | ||
| 3916 | case USB3_LPM_U2: | 3915 | case USB3_LPM_U2: |
| 3917 | feature = USB_PORT_FEAT_U2_TIMEOUT; | ||
| 3918 | break; | 3916 | break; |
| 3919 | default: | 3917 | default: |
| 3920 | dev_warn(&udev->dev, "%s: Can't disable non-U1 or U2 state.\n", | 3918 | dev_warn(&udev->dev, "%s: Can't disable non-U1 or U2 state.\n", |
diff --git a/drivers/usb/dwc2/Kconfig b/drivers/usb/dwc2/Kconfig index f93807b3631a..b323c4c11b0a 100644 --- a/drivers/usb/dwc2/Kconfig +++ b/drivers/usb/dwc2/Kconfig | |||
| @@ -1,6 +1,6 @@ | |||
| 1 | config USB_DWC2 | 1 | config USB_DWC2 |
| 2 | bool "DesignWare USB2 DRD Core Support" | 2 | tristate "DesignWare USB2 DRD Core Support" |
| 3 | depends on USB | 3 | depends on USB || USB_GADGET |
| 4 | help | 4 | help |
| 5 | Say Y here if your system has a Dual Role Hi-Speed USB | 5 | Say Y here if your system has a Dual Role Hi-Speed USB |
| 6 | controller based on the DesignWare HSOTG IP Core. | 6 | controller based on the DesignWare HSOTG IP Core. |
| @@ -10,49 +10,61 @@ config USB_DWC2 | |||
| 10 | bus interface module (if you have a PCI bus system) will be | 10 | bus interface module (if you have a PCI bus system) will be |
| 11 | called dwc2_pci.ko, and the platform interface module (for | 11 | called dwc2_pci.ko, and the platform interface module (for |
| 12 | controllers directly connected to the CPU) will be called | 12 | controllers directly connected to the CPU) will be called |
| 13 | dwc2_platform.ko. For gadget mode, there will be a single | 13 | dwc2_platform.ko. For all modes(host, gadget and dual-role), there |
| 14 | module called dwc2_gadget.ko. | 14 | will be an additional module named dwc2.ko. |
| 15 | |||
| 16 | NOTE: The s3c-hsotg driver is now renamed to dwc2_gadget. The | ||
| 17 | host and gadget drivers are still currently separate drivers. | ||
| 18 | There are plans to merge the dwc2_gadget driver with the dwc2 | ||
| 19 | host driver in the near future to create a dual-role driver. | ||
| 20 | 15 | ||
| 21 | if USB_DWC2 | 16 | if USB_DWC2 |
| 22 | 17 | ||
| 18 | choice | ||
| 19 | bool "DWC2 Mode Selection" | ||
| 20 | default USB_DWC2_DUAL_ROLE if (USB && USB_GADGET) | ||
| 21 | default USB_DWC2_HOST if (USB && !USB_GADGET) | ||
| 22 | default USB_DWC2_PERIPHERAL if (!USB && USB_GADGET) | ||
| 23 | |||
| 23 | config USB_DWC2_HOST | 24 | config USB_DWC2_HOST |
| 24 | tristate "Host only mode" | 25 | bool "Host only mode" |
| 25 | depends on USB | 26 | depends on USB |
| 26 | help | 27 | help |
| 27 | The Designware USB2.0 high-speed host controller | 28 | The Designware USB2.0 high-speed host controller |
| 28 | integrated into many SoCs. | 29 | integrated into many SoCs. Select this option if you want the |
| 30 | driver to operate in Host-only mode. | ||
| 29 | 31 | ||
| 30 | config USB_DWC2_PLATFORM | 32 | comment "Gadget/Dual-role mode requires USB Gadget support to be enabled" |
| 31 | bool "DWC2 Platform" | 33 | |
| 32 | depends on USB_DWC2_HOST | 34 | config USB_DWC2_PERIPHERAL |
| 33 | default USB_DWC2_HOST | 35 | bool "Gadget only mode" |
| 36 | depends on USB_GADGET=y || USB_GADGET=USB_DWC2 | ||
| 34 | help | 37 | help |
| 35 | The Designware USB2.0 platform interface module for | 38 | The Designware USB2.0 high-speed gadget controller |
| 36 | controllers directly connected to the CPU. This is only | 39 | integrated into many SoCs. Select this option if you want the |
| 37 | used for host mode. | 40 | driver to operate in Peripheral-only mode. This option requires |
| 41 | USB_GADGET to be enabled. | ||
| 42 | |||
| 43 | config USB_DWC2_DUAL_ROLE | ||
| 44 | bool "Dual Role mode" | ||
| 45 | depends on (USB=y || USB=USB_DWC2) && (USB_GADGET=y || USB_GADGET=USB_DWC2) | ||
| 46 | help | ||
| 47 | Select this option if you want the driver to work in a dual-role | ||
| 48 | mode. In this mode both host and gadget features are enabled, and | ||
| 49 | the role will be determined by the cable that gets plugged-in. This | ||
| 50 | option requires USB_GADGET to be enabled. | ||
| 51 | endchoice | ||
| 52 | |||
| 53 | config USB_DWC2_PLATFORM | ||
| 54 | tristate "DWC2 Platform" | ||
| 55 | default USB_DWC2_HOST || USB_DWC2_PERIPHERAL | ||
| 56 | help | ||
| 57 | The Designware USB2.0 platform interface module for | ||
| 58 | controllers directly connected to the CPU. | ||
| 38 | 59 | ||
| 39 | config USB_DWC2_PCI | 60 | config USB_DWC2_PCI |
| 40 | bool "DWC2 PCI" | 61 | tristate "DWC2 PCI" |
| 41 | depends on USB_DWC2_HOST && PCI | 62 | depends on USB_DWC2_HOST && PCI |
| 42 | default USB_DWC2_HOST | 63 | default USB_DWC2_HOST |
| 43 | help | 64 | help |
| 44 | The Designware USB2.0 PCI interface module for controllers | 65 | The Designware USB2.0 PCI interface module for controllers |
| 45 | connected to a PCI bus. This is only used for host mode. | 66 | connected to a PCI bus. This is only used for host mode. |
| 46 | 67 | ||
| 47 | comment "Gadget mode requires USB Gadget support to be enabled" | ||
| 48 | |||
| 49 | config USB_DWC2_PERIPHERAL | ||
| 50 | tristate "Gadget only mode" | ||
| 51 | depends on USB_GADGET | ||
| 52 | help | ||
| 53 | The Designware USB2.0 high-speed gadget controller | ||
| 54 | integrated into many SoCs. | ||
| 55 | |||
| 56 | config USB_DWC2_DEBUG | 68 | config USB_DWC2_DEBUG |
| 57 | bool "Enable Debugging Messages" | 69 | bool "Enable Debugging Messages" |
| 58 | help | 70 | help |
diff --git a/drivers/usb/dwc2/Makefile b/drivers/usb/dwc2/Makefile index b73d2a527970..8f752679752a 100644 --- a/drivers/usb/dwc2/Makefile +++ b/drivers/usb/dwc2/Makefile | |||
| @@ -1,28 +1,28 @@ | |||
| 1 | ccflags-$(CONFIG_USB_DWC2_DEBUG) += -DDEBUG | 1 | ccflags-$(CONFIG_USB_DWC2_DEBUG) += -DDEBUG |
| 2 | ccflags-$(CONFIG_USB_DWC2_VERBOSE) += -DVERBOSE_DEBUG | 2 | ccflags-$(CONFIG_USB_DWC2_VERBOSE) += -DVERBOSE_DEBUG |
| 3 | 3 | ||
| 4 | obj-$(CONFIG_USB_DWC2_HOST) += dwc2.o | 4 | obj-$(CONFIG_USB_DWC2) += dwc2.o |
| 5 | dwc2-y := core.o core_intr.o | 5 | dwc2-y := core.o core_intr.o |
| 6 | dwc2-y += hcd.o hcd_intr.o | 6 | |
| 7 | dwc2-y += hcd_queue.o hcd_ddma.o | 7 | ifneq ($(filter y,$(CONFIG_USB_DWC2_HOST) $(CONFIG_USB_DWC2_DUAL_ROLE)),) |
| 8 | dwc2-y += hcd.o hcd_intr.o | ||
| 9 | dwc2-y += hcd_queue.o hcd_ddma.o | ||
| 10 | endif | ||
| 11 | |||
| 12 | ifneq ($(filter y,$(CONFIG_USB_DWC2_PERIPHERAL) $(CONFIG_USB_DWC2_DUAL_ROLE)),) | ||
| 13 | dwc2-y += gadget.o | ||
| 14 | endif | ||
| 8 | 15 | ||
| 9 | # NOTE: The previous s3c-hsotg peripheral mode only driver has been moved to | 16 | # NOTE: The previous s3c-hsotg peripheral mode only driver has been moved to |
| 10 | # this location and renamed gadget.c. When building for dynamically linked | 17 | # this location and renamed gadget.c. When building for dynamically linked |
| 11 | # modules, dwc2_gadget.ko will get built for peripheral mode. For host mode, | 18 | # modules, dwc2.ko will get built for host mode, peripheral mode, and dual-role |
| 12 | # the core module will be dwc2.ko, the PCI bus interface module will called | 19 | # mode. The PCI bus interface module will called dwc2_pci.ko and the platform |
| 13 | # dwc2_pci.ko and the platform interface module will be called dwc2_platform.ko. | 20 | # interface module will be called dwc2_platform.ko. |
| 14 | # At present the host and gadget driver will be separate drivers, but there | ||
| 15 | # are plans in the near future to create a dual-role driver. | ||
| 16 | 21 | ||
| 17 | ifneq ($(CONFIG_USB_DWC2_PCI),) | 22 | ifneq ($(CONFIG_USB_DWC2_PCI),) |
| 18 | obj-$(CONFIG_USB_DWC2_HOST) += dwc2_pci.o | 23 | obj-$(CONFIG_USB_DWC2) += dwc2_pci.o |
| 19 | dwc2_pci-y := pci.o | 24 | dwc2_pci-y := pci.o |
| 20 | endif | 25 | endif |
| 21 | 26 | ||
| 22 | ifneq ($(CONFIG_USB_DWC2_PLATFORM),) | 27 | obj-$(CONFIG_USB_DWC2_PLATFORM) += dwc2_platform.o |
| 23 | obj-$(CONFIG_USB_DWC2_HOST) += dwc2_platform.o | 28 | dwc2_platform-y := platform.o |
| 24 | dwc2_platform-y := platform.o | ||
| 25 | endif | ||
| 26 | |||
| 27 | obj-$(CONFIG_USB_DWC2_PERIPHERAL) += dwc2_gadget.o | ||
| 28 | dwc2_gadget-y := gadget.o | ||
diff --git a/drivers/usb/dwc2/core.c b/drivers/usb/dwc2/core.c index d9269459d481..7605850b7a9c 100644 --- a/drivers/usb/dwc2/core.c +++ b/drivers/usb/dwc2/core.c | |||
| @@ -458,16 +458,6 @@ int dwc2_core_init(struct dwc2_hsotg *hsotg, bool select_phy, int irq) | |||
| 458 | /* Clear the SRP success bit for FS-I2c */ | 458 | /* Clear the SRP success bit for FS-I2c */ |
| 459 | hsotg->srp_success = 0; | 459 | hsotg->srp_success = 0; |
| 460 | 460 | ||
| 461 | if (irq >= 0) { | ||
| 462 | dev_dbg(hsotg->dev, "registering common handler for irq%d\n", | ||
| 463 | irq); | ||
| 464 | retval = devm_request_irq(hsotg->dev, irq, | ||
| 465 | dwc2_handle_common_intr, IRQF_SHARED, | ||
| 466 | dev_name(hsotg->dev), hsotg); | ||
| 467 | if (retval) | ||
| 468 | return retval; | ||
| 469 | } | ||
| 470 | |||
| 471 | /* Enable common interrupts */ | 461 | /* Enable common interrupts */ |
| 472 | dwc2_enable_common_interrupts(hsotg); | 462 | dwc2_enable_common_interrupts(hsotg); |
| 473 | 463 | ||
diff --git a/drivers/usb/dwc2/core.h b/drivers/usb/dwc2/core.h index 55c90c53f2d6..7a70a1349334 100644 --- a/drivers/usb/dwc2/core.h +++ b/drivers/usb/dwc2/core.h | |||
| @@ -84,7 +84,7 @@ static const char * const s3c_hsotg_supply_names[] = { | |||
| 84 | */ | 84 | */ |
| 85 | #define EP0_MPS_LIMIT 64 | 85 | #define EP0_MPS_LIMIT 64 |
| 86 | 86 | ||
| 87 | struct s3c_hsotg; | 87 | struct dwc2_hsotg; |
| 88 | struct s3c_hsotg_req; | 88 | struct s3c_hsotg_req; |
| 89 | 89 | ||
| 90 | /** | 90 | /** |
| @@ -130,7 +130,7 @@ struct s3c_hsotg_req; | |||
| 130 | struct s3c_hsotg_ep { | 130 | struct s3c_hsotg_ep { |
| 131 | struct usb_ep ep; | 131 | struct usb_ep ep; |
| 132 | struct list_head queue; | 132 | struct list_head queue; |
| 133 | struct s3c_hsotg *parent; | 133 | struct dwc2_hsotg *parent; |
| 134 | struct s3c_hsotg_req *req; | 134 | struct s3c_hsotg_req *req; |
| 135 | struct dentry *debugfs; | 135 | struct dentry *debugfs; |
| 136 | 136 | ||
| @@ -155,67 +155,6 @@ struct s3c_hsotg_ep { | |||
| 155 | }; | 155 | }; |
| 156 | 156 | ||
| 157 | /** | 157 | /** |
| 158 | * struct s3c_hsotg - driver state. | ||
| 159 | * @dev: The parent device supplied to the probe function | ||
| 160 | * @driver: USB gadget driver | ||
| 161 | * @phy: The otg phy transceiver structure for phy control. | ||
| 162 | * @uphy: The otg phy transceiver structure for old USB phy control. | ||
| 163 | * @plat: The platform specific configuration data. This can be removed once | ||
| 164 | * all SoCs support usb transceiver. | ||
| 165 | * @regs: The memory area mapped for accessing registers. | ||
| 166 | * @irq: The IRQ number we are using | ||
| 167 | * @supplies: Definition of USB power supplies | ||
| 168 | * @phyif: PHY interface width | ||
| 169 | * @dedicated_fifos: Set if the hardware has dedicated IN-EP fifos. | ||
| 170 | * @num_of_eps: Number of available EPs (excluding EP0) | ||
| 171 | * @debug_root: root directrory for debugfs. | ||
| 172 | * @debug_file: main status file for debugfs. | ||
| 173 | * @debug_fifo: FIFO status file for debugfs. | ||
| 174 | * @ep0_reply: Request used for ep0 reply. | ||
| 175 | * @ep0_buff: Buffer for EP0 reply data, if needed. | ||
| 176 | * @ctrl_buff: Buffer for EP0 control requests. | ||
| 177 | * @ctrl_req: Request for EP0 control packets. | ||
| 178 | * @setup: NAK management for EP0 SETUP | ||
| 179 | * @last_rst: Time of last reset | ||
| 180 | * @eps: The endpoints being supplied to the gadget framework | ||
| 181 | */ | ||
| 182 | struct s3c_hsotg { | ||
| 183 | struct device *dev; | ||
| 184 | struct usb_gadget_driver *driver; | ||
| 185 | struct phy *phy; | ||
| 186 | struct usb_phy *uphy; | ||
| 187 | struct s3c_hsotg_plat *plat; | ||
| 188 | |||
| 189 | spinlock_t lock; | ||
| 190 | |||
| 191 | void __iomem *regs; | ||
| 192 | int irq; | ||
| 193 | struct clk *clk; | ||
| 194 | |||
| 195 | struct regulator_bulk_data supplies[ARRAY_SIZE(s3c_hsotg_supply_names)]; | ||
| 196 | |||
| 197 | u32 phyif; | ||
| 198 | int fifo_mem; | ||
| 199 | unsigned int dedicated_fifos:1; | ||
| 200 | unsigned char num_of_eps; | ||
| 201 | u32 fifo_map; | ||
| 202 | |||
| 203 | struct dentry *debug_root; | ||
| 204 | struct dentry *debug_file; | ||
| 205 | struct dentry *debug_fifo; | ||
| 206 | |||
| 207 | struct usb_request *ep0_reply; | ||
| 208 | struct usb_request *ctrl_req; | ||
| 209 | u8 ep0_buff[8]; | ||
| 210 | u8 ctrl_buff[8]; | ||
| 211 | |||
| 212 | struct usb_gadget gadget; | ||
| 213 | unsigned int setup; | ||
| 214 | unsigned long last_rst; | ||
| 215 | struct s3c_hsotg_ep *eps; | ||
| 216 | }; | ||
| 217 | |||
| 218 | /** | ||
| 219 | * struct s3c_hsotg_req - data transfer request | 158 | * struct s3c_hsotg_req - data transfer request |
| 220 | * @req: The USB gadget request | 159 | * @req: The USB gadget request |
| 221 | * @queue: The list of requests for the endpoint this is queued for. | 160 | * @queue: The list of requests for the endpoint this is queued for. |
| @@ -229,6 +168,7 @@ struct s3c_hsotg_req { | |||
| 229 | unsigned char mapped; | 168 | unsigned char mapped; |
| 230 | }; | 169 | }; |
| 231 | 170 | ||
| 171 | #if IS_ENABLED(CONFIG_USB_DWC2_PERIPHERAL) || IS_ENABLED(CONFIG_USB_DWC2_DUAL_ROLE) | ||
| 232 | #define call_gadget(_hs, _entry) \ | 172 | #define call_gadget(_hs, _entry) \ |
| 233 | do { \ | 173 | do { \ |
| 234 | if ((_hs)->gadget.speed != USB_SPEED_UNKNOWN && \ | 174 | if ((_hs)->gadget.speed != USB_SPEED_UNKNOWN && \ |
| @@ -238,6 +178,9 @@ do { \ | |||
| 238 | spin_lock(&_hs->lock); \ | 178 | spin_lock(&_hs->lock); \ |
| 239 | } \ | 179 | } \ |
| 240 | } while (0) | 180 | } while (0) |
| 181 | #else | ||
| 182 | #define call_gadget(_hs, _entry) do {} while (0) | ||
| 183 | #endif | ||
| 241 | 184 | ||
| 242 | struct dwc2_hsotg; | 185 | struct dwc2_hsotg; |
| 243 | struct dwc2_host_chan; | 186 | struct dwc2_host_chan; |
| @@ -495,11 +438,13 @@ struct dwc2_hw_params { | |||
| 495 | * struct dwc2_hsotg - Holds the state of the driver, including the non-periodic | 438 | * struct dwc2_hsotg - Holds the state of the driver, including the non-periodic |
| 496 | * and periodic schedules | 439 | * and periodic schedules |
| 497 | * | 440 | * |
| 441 | * These are common for both host and peripheral modes: | ||
| 442 | * | ||
| 498 | * @dev: The struct device pointer | 443 | * @dev: The struct device pointer |
| 499 | * @regs: Pointer to controller regs | 444 | * @regs: Pointer to controller regs |
| 500 | * @core_params: Parameters that define how the core should be configured | ||
| 501 | * @hw_params: Parameters that were autodetected from the | 445 | * @hw_params: Parameters that were autodetected from the |
| 502 | * hardware registers | 446 | * hardware registers |
| 447 | * @core_params: Parameters that define how the core should be configured | ||
| 503 | * @op_state: The operational State, during transitions (a_host=> | 448 | * @op_state: The operational State, during transitions (a_host=> |
| 504 | * a_peripheral and b_device=>b_host) this may not match | 449 | * a_peripheral and b_device=>b_host) this may not match |
| 505 | * the core, but allows the software to determine | 450 | * the core, but allows the software to determine |
| @@ -508,6 +453,8 @@ struct dwc2_hw_params { | |||
| 508 | * - USB_DR_MODE_PERIPHERAL | 453 | * - USB_DR_MODE_PERIPHERAL |
| 509 | * - USB_DR_MODE_HOST | 454 | * - USB_DR_MODE_HOST |
| 510 | * - USB_DR_MODE_OTG | 455 | * - USB_DR_MODE_OTG |
| 456 | * @lock: Spinlock that protects all the driver data structures | ||
| 457 | * @priv: Stores a pointer to the struct usb_hcd | ||
| 511 | * @queuing_high_bandwidth: True if multiple packets of a high-bandwidth | 458 | * @queuing_high_bandwidth: True if multiple packets of a high-bandwidth |
| 512 | * transfer are in process of being queued | 459 | * transfer are in process of being queued |
| 513 | * @srp_success: Stores status of SRP request in the case of a FS PHY | 460 | * @srp_success: Stores status of SRP request in the case of a FS PHY |
| @@ -517,6 +464,9 @@ struct dwc2_hw_params { | |||
| 517 | * interrupt | 464 | * interrupt |
| 518 | * @wkp_timer: Timer object for handling Wakeup Detected interrupt | 465 | * @wkp_timer: Timer object for handling Wakeup Detected interrupt |
| 519 | * @lx_state: Lx state of connected device | 466 | * @lx_state: Lx state of connected device |
| 467 | * | ||
| 468 | * These are for host mode: | ||
| 469 | * | ||
| 520 | * @flags: Flags for handling root port state changes | 470 | * @flags: Flags for handling root port state changes |
| 521 | * @non_periodic_sched_inactive: Inactive QHs in the non-periodic schedule. | 471 | * @non_periodic_sched_inactive: Inactive QHs in the non-periodic schedule. |
| 522 | * Transfers associated with these QHs are not currently | 472 | * Transfers associated with these QHs are not currently |
| @@ -585,11 +535,31 @@ struct dwc2_hw_params { | |||
| 585 | * @status_buf_dma: DMA address for status_buf | 535 | * @status_buf_dma: DMA address for status_buf |
| 586 | * @start_work: Delayed work for handling host A-cable connection | 536 | * @start_work: Delayed work for handling host A-cable connection |
| 587 | * @reset_work: Delayed work for handling a port reset | 537 | * @reset_work: Delayed work for handling a port reset |
| 588 | * @lock: Spinlock that protects all the driver data structures | ||
| 589 | * @priv: Stores a pointer to the struct usb_hcd | ||
| 590 | * @otg_port: OTG port number | 538 | * @otg_port: OTG port number |
| 591 | * @frame_list: Frame list | 539 | * @frame_list: Frame list |
| 592 | * @frame_list_dma: Frame list DMA address | 540 | * @frame_list_dma: Frame list DMA address |
| 541 | * | ||
| 542 | * These are for peripheral mode: | ||
| 543 | * | ||
| 544 | * @driver: USB gadget driver | ||
| 545 | * @phy: The otg phy transceiver structure for phy control. | ||
| 546 | * @uphy: The otg phy transceiver structure for old USB phy control. | ||
| 547 | * @plat: The platform specific configuration data. This can be removed once | ||
| 548 | * all SoCs support usb transceiver. | ||
| 549 | * @supplies: Definition of USB power supplies | ||
| 550 | * @phyif: PHY interface width | ||
| 551 | * @dedicated_fifos: Set if the hardware has dedicated IN-EP fifos. | ||
| 552 | * @num_of_eps: Number of available EPs (excluding EP0) | ||
| 553 | * @debug_root: Root directrory for debugfs. | ||
| 554 | * @debug_file: Main status file for debugfs. | ||
| 555 | * @debug_fifo: FIFO status file for debugfs. | ||
| 556 | * @ep0_reply: Request used for ep0 reply. | ||
| 557 | * @ep0_buff: Buffer for EP0 reply data, if needed. | ||
| 558 | * @ctrl_buff: Buffer for EP0 control requests. | ||
| 559 | * @ctrl_req: Request for EP0 control packets. | ||
| 560 | * @setup: NAK management for EP0 SETUP | ||
| 561 | * @last_rst: Time of last reset | ||
| 562 | * @eps: The endpoints being supplied to the gadget framework | ||
| 593 | */ | 563 | */ |
| 594 | struct dwc2_hsotg { | 564 | struct dwc2_hsotg { |
| 595 | struct device *dev; | 565 | struct device *dev; |
| @@ -601,6 +571,16 @@ struct dwc2_hsotg { | |||
| 601 | enum usb_otg_state op_state; | 571 | enum usb_otg_state op_state; |
| 602 | enum usb_dr_mode dr_mode; | 572 | enum usb_dr_mode dr_mode; |
| 603 | 573 | ||
| 574 | struct phy *phy; | ||
| 575 | struct usb_phy *uphy; | ||
| 576 | struct regulator_bulk_data supplies[ARRAY_SIZE(s3c_hsotg_supply_names)]; | ||
| 577 | |||
| 578 | spinlock_t lock; | ||
| 579 | struct mutex init_mutex; | ||
| 580 | void *priv; | ||
| 581 | int irq; | ||
| 582 | struct clk *clk; | ||
| 583 | |||
| 604 | unsigned int queuing_high_bandwidth:1; | 584 | unsigned int queuing_high_bandwidth:1; |
| 605 | unsigned int srp_success:1; | 585 | unsigned int srp_success:1; |
| 606 | 586 | ||
| @@ -609,6 +589,18 @@ struct dwc2_hsotg { | |||
| 609 | struct timer_list wkp_timer; | 589 | struct timer_list wkp_timer; |
| 610 | enum dwc2_lx_state lx_state; | 590 | enum dwc2_lx_state lx_state; |
| 611 | 591 | ||
| 592 | struct dentry *debug_root; | ||
| 593 | struct dentry *debug_file; | ||
| 594 | struct dentry *debug_fifo; | ||
| 595 | |||
| 596 | /* DWC OTG HW Release versions */ | ||
| 597 | #define DWC2_CORE_REV_2_71a 0x4f54271a | ||
| 598 | #define DWC2_CORE_REV_2_90a 0x4f54290a | ||
| 599 | #define DWC2_CORE_REV_2_92a 0x4f54292a | ||
| 600 | #define DWC2_CORE_REV_2_94a 0x4f54294a | ||
| 601 | #define DWC2_CORE_REV_3_00a 0x4f54300a | ||
| 602 | |||
| 603 | #if IS_ENABLED(CONFIG_USB_DWC2_HOST) || IS_ENABLED(CONFIG_USB_DWC2_DUAL_ROLE) | ||
| 612 | union dwc2_hcd_internal_flags { | 604 | union dwc2_hcd_internal_flags { |
| 613 | u32 d32; | 605 | u32 d32; |
| 614 | struct { | 606 | struct { |
| @@ -655,19 +647,10 @@ struct dwc2_hsotg { | |||
| 655 | 647 | ||
| 656 | struct delayed_work start_work; | 648 | struct delayed_work start_work; |
| 657 | struct delayed_work reset_work; | 649 | struct delayed_work reset_work; |
| 658 | spinlock_t lock; | ||
| 659 | void *priv; | ||
| 660 | u8 otg_port; | 650 | u8 otg_port; |
| 661 | u32 *frame_list; | 651 | u32 *frame_list; |
| 662 | dma_addr_t frame_list_dma; | 652 | dma_addr_t frame_list_dma; |
| 663 | 653 | ||
| 664 | /* DWC OTG HW Release versions */ | ||
| 665 | #define DWC2_CORE_REV_2_71a 0x4f54271a | ||
| 666 | #define DWC2_CORE_REV_2_90a 0x4f54290a | ||
| 667 | #define DWC2_CORE_REV_2_92a 0x4f54292a | ||
| 668 | #define DWC2_CORE_REV_2_94a 0x4f54294a | ||
| 669 | #define DWC2_CORE_REV_3_00a 0x4f54300a | ||
| 670 | |||
| 671 | #ifdef DEBUG | 654 | #ifdef DEBUG |
| 672 | u32 frrem_samples; | 655 | u32 frrem_samples; |
| 673 | u64 frrem_accum; | 656 | u64 frrem_accum; |
| @@ -686,6 +669,31 @@ struct dwc2_hsotg { | |||
| 686 | u32 hfnum_other_samples_b; | 669 | u32 hfnum_other_samples_b; |
| 687 | u64 hfnum_other_frrem_accum_b; | 670 | u64 hfnum_other_frrem_accum_b; |
| 688 | #endif | 671 | #endif |
| 672 | #endif /* CONFIG_USB_DWC2_HOST || CONFIG_USB_DWC2_DUAL_ROLE */ | ||
| 673 | |||
| 674 | #if IS_ENABLED(CONFIG_USB_DWC2_PERIPHERAL) || IS_ENABLED(CONFIG_USB_DWC2_DUAL_ROLE) | ||
| 675 | /* Gadget structures */ | ||
| 676 | struct usb_gadget_driver *driver; | ||
| 677 | struct s3c_hsotg_plat *plat; | ||
| 678 | |||
| 679 | u32 phyif; | ||
| 680 | int fifo_mem; | ||
| 681 | unsigned int dedicated_fifos:1; | ||
| 682 | unsigned char num_of_eps; | ||
| 683 | u32 fifo_map; | ||
| 684 | |||
| 685 | struct usb_request *ep0_reply; | ||
| 686 | struct usb_request *ctrl_req; | ||
| 687 | u8 ep0_buff[8]; | ||
| 688 | u8 ctrl_buff[8]; | ||
| 689 | |||
| 690 | struct usb_gadget gadget; | ||
| 691 | unsigned int enabled:1; | ||
| 692 | unsigned int connected:1; | ||
| 693 | unsigned int setup:1; | ||
| 694 | unsigned long last_rst; | ||
| 695 | struct s3c_hsotg_ep *eps; | ||
| 696 | #endif /* CONFIG_USB_DWC2_PERIPHERAL || CONFIG_USB_DWC2_DUAL_ROLE */ | ||
| 689 | }; | 697 | }; |
| 690 | 698 | ||
| 691 | /* Reasons for halting a host channel */ | 699 | /* Reasons for halting a host channel */ |
| @@ -955,4 +963,43 @@ extern void dwc2_dump_global_registers(struct dwc2_hsotg *hsotg); | |||
| 955 | */ | 963 | */ |
| 956 | extern u16 dwc2_get_otg_version(struct dwc2_hsotg *hsotg); | 964 | extern u16 dwc2_get_otg_version(struct dwc2_hsotg *hsotg); |
| 957 | 965 | ||
| 966 | /* Gadget defines */ | ||
| 967 | #if IS_ENABLED(CONFIG_USB_DWC2_PERIPHERAL) || IS_ENABLED(CONFIG_USB_DWC2_DUAL_ROLE) | ||
| 968 | extern int s3c_hsotg_remove(struct dwc2_hsotg *hsotg); | ||
| 969 | extern int s3c_hsotg_suspend(struct dwc2_hsotg *dwc2); | ||
| 970 | extern int s3c_hsotg_resume(struct dwc2_hsotg *dwc2); | ||
| 971 | extern int dwc2_gadget_init(struct dwc2_hsotg *hsotg, int irq); | ||
| 972 | extern void s3c_hsotg_core_init_disconnected(struct dwc2_hsotg *dwc2); | ||
| 973 | extern void s3c_hsotg_core_connect(struct dwc2_hsotg *hsotg); | ||
| 974 | extern void s3c_hsotg_disconnect(struct dwc2_hsotg *dwc2); | ||
| 975 | #else | ||
| 976 | static inline int s3c_hsotg_remove(struct dwc2_hsotg *dwc2) | ||
| 977 | { return 0; } | ||
| 978 | static inline int s3c_hsotg_suspend(struct dwc2_hsotg *dwc2) | ||
| 979 | { return 0; } | ||
| 980 | static inline int s3c_hsotg_resume(struct dwc2_hsotg *dwc2) | ||
| 981 | { return 0; } | ||
| 982 | static inline int dwc2_gadget_init(struct dwc2_hsotg *hsotg, int irq) | ||
| 983 | { return 0; } | ||
| 984 | static inline void s3c_hsotg_core_init_disconnected(struct dwc2_hsotg *dwc2) {} | ||
| 985 | static inline void s3c_hsotg_core_connect(struct dwc2_hsotg *hsotg) {} | ||
| 986 | static inline void s3c_hsotg_disconnect(struct dwc2_hsotg *dwc2) {} | ||
| 987 | #endif | ||
| 988 | |||
| 989 | #if IS_ENABLED(CONFIG_USB_DWC2_HOST) || IS_ENABLED(CONFIG_USB_DWC2_DUAL_ROLE) | ||
| 990 | extern int dwc2_hcd_get_frame_number(struct dwc2_hsotg *hsotg); | ||
| 991 | extern void dwc2_hcd_disconnect(struct dwc2_hsotg *hsotg); | ||
| 992 | extern void dwc2_hcd_start(struct dwc2_hsotg *hsotg); | ||
| 993 | #else | ||
| 994 | static inline void dwc2_set_all_params(struct dwc2_core_params *params, int value) {} | ||
| 995 | static inline int dwc2_hcd_get_frame_number(struct dwc2_hsotg *hsotg) | ||
| 996 | { return 0; } | ||
| 997 | static inline void dwc2_hcd_disconnect(struct dwc2_hsotg *hsotg) {} | ||
| 998 | static inline void dwc2_hcd_start(struct dwc2_hsotg *hsotg) {} | ||
| 999 | static inline void dwc2_hcd_remove(struct dwc2_hsotg *hsotg) {} | ||
| 1000 | static inline int dwc2_hcd_init(struct dwc2_hsotg *hsotg, int irq, | ||
| 1001 | const struct dwc2_core_params *params) | ||
| 1002 | { return 0; } | ||
| 1003 | #endif | ||
| 1004 | |||
| 958 | #endif /* __DWC2_CORE_H__ */ | 1005 | #endif /* __DWC2_CORE_H__ */ |
diff --git a/drivers/usb/dwc2/core_intr.c b/drivers/usb/dwc2/core_intr.c index c93918b70d03..ad43c5bc1ef1 100644 --- a/drivers/usb/dwc2/core_intr.c +++ b/drivers/usb/dwc2/core_intr.c | |||
| @@ -128,6 +128,9 @@ static void dwc2_handle_otg_intr(struct dwc2_hsotg *hsotg) | |||
| 128 | dwc2_op_state_str(hsotg)); | 128 | dwc2_op_state_str(hsotg)); |
| 129 | gotgctl = readl(hsotg->regs + GOTGCTL); | 129 | gotgctl = readl(hsotg->regs + GOTGCTL); |
| 130 | 130 | ||
| 131 | if (dwc2_is_device_mode(hsotg)) | ||
| 132 | s3c_hsotg_disconnect(hsotg); | ||
| 133 | |||
| 131 | if (hsotg->op_state == OTG_STATE_B_HOST) { | 134 | if (hsotg->op_state == OTG_STATE_B_HOST) { |
| 132 | hsotg->op_state = OTG_STATE_B_PERIPHERAL; | 135 | hsotg->op_state = OTG_STATE_B_PERIPHERAL; |
| 133 | } else { | 136 | } else { |
| @@ -287,9 +290,11 @@ static void dwc2_handle_conn_id_status_change_intr(struct dwc2_hsotg *hsotg) | |||
| 287 | * Release lock before scheduling workq as it holds spinlock during | 290 | * Release lock before scheduling workq as it holds spinlock during |
| 288 | * scheduling. | 291 | * scheduling. |
| 289 | */ | 292 | */ |
| 290 | spin_unlock(&hsotg->lock); | 293 | if (hsotg->wq_otg) { |
| 291 | queue_work(hsotg->wq_otg, &hsotg->wf_otg); | 294 | spin_unlock(&hsotg->lock); |
| 292 | spin_lock(&hsotg->lock); | 295 | queue_work(hsotg->wq_otg, &hsotg->wf_otg); |
| 296 | spin_lock(&hsotg->lock); | ||
| 297 | } | ||
| 293 | 298 | ||
| 294 | /* Clear interrupt */ | 299 | /* Clear interrupt */ |
| 295 | writel(GINTSTS_CONIDSTSCHNG, hsotg->regs + GINTSTS); | 300 | writel(GINTSTS_CONIDSTSCHNG, hsotg->regs + GINTSTS); |
| @@ -312,6 +317,12 @@ static void dwc2_handle_session_req_intr(struct dwc2_hsotg *hsotg) | |||
| 312 | 317 | ||
| 313 | /* Clear interrupt */ | 318 | /* Clear interrupt */ |
| 314 | writel(GINTSTS_SESSREQINT, hsotg->regs + GINTSTS); | 319 | writel(GINTSTS_SESSREQINT, hsotg->regs + GINTSTS); |
| 320 | |||
| 321 | /* | ||
| 322 | * Report disconnect if there is any previous session established | ||
| 323 | */ | ||
| 324 | if (dwc2_is_device_mode(hsotg)) | ||
| 325 | s3c_hsotg_disconnect(hsotg); | ||
| 315 | } | 326 | } |
| 316 | 327 | ||
| 317 | /* | 328 | /* |
diff --git a/drivers/usb/dwc2/gadget.c b/drivers/usb/dwc2/gadget.c index 8b5c079c7b7d..200168ec2d75 100644 --- a/drivers/usb/dwc2/gadget.c +++ b/drivers/usb/dwc2/gadget.c | |||
| @@ -21,6 +21,7 @@ | |||
| 21 | #include <linux/platform_device.h> | 21 | #include <linux/platform_device.h> |
| 22 | #include <linux/dma-mapping.h> | 22 | #include <linux/dma-mapping.h> |
| 23 | #include <linux/debugfs.h> | 23 | #include <linux/debugfs.h> |
| 24 | #include <linux/mutex.h> | ||
| 24 | #include <linux/seq_file.h> | 25 | #include <linux/seq_file.h> |
| 25 | #include <linux/delay.h> | 26 | #include <linux/delay.h> |
| 26 | #include <linux/io.h> | 27 | #include <linux/io.h> |
| @@ -36,6 +37,7 @@ | |||
| 36 | #include <linux/platform_data/s3c-hsotg.h> | 37 | #include <linux/platform_data/s3c-hsotg.h> |
| 37 | 38 | ||
| 38 | #include "core.h" | 39 | #include "core.h" |
| 40 | #include "hw.h" | ||
| 39 | 41 | ||
| 40 | /* conversion functions */ | 42 | /* conversion functions */ |
| 41 | static inline struct s3c_hsotg_req *our_req(struct usb_request *req) | 43 | static inline struct s3c_hsotg_req *our_req(struct usb_request *req) |
| @@ -48,9 +50,9 @@ static inline struct s3c_hsotg_ep *our_ep(struct usb_ep *ep) | |||
| 48 | return container_of(ep, struct s3c_hsotg_ep, ep); | 50 | return container_of(ep, struct s3c_hsotg_ep, ep); |
| 49 | } | 51 | } |
| 50 | 52 | ||
| 51 | static inline struct s3c_hsotg *to_hsotg(struct usb_gadget *gadget) | 53 | static inline struct dwc2_hsotg *to_hsotg(struct usb_gadget *gadget) |
| 52 | { | 54 | { |
| 53 | return container_of(gadget, struct s3c_hsotg, gadget); | 55 | return container_of(gadget, struct dwc2_hsotg, gadget); |
| 54 | } | 56 | } |
| 55 | 57 | ||
| 56 | static inline void __orr32(void __iomem *ptr, u32 val) | 58 | static inline void __orr32(void __iomem *ptr, u32 val) |
| @@ -64,7 +66,7 @@ static inline void __bic32(void __iomem *ptr, u32 val) | |||
| 64 | } | 66 | } |
| 65 | 67 | ||
| 66 | /* forward decleration of functions */ | 68 | /* forward decleration of functions */ |
| 67 | static void s3c_hsotg_dump(struct s3c_hsotg *hsotg); | 69 | static void s3c_hsotg_dump(struct dwc2_hsotg *hsotg); |
| 68 | 70 | ||
| 69 | /** | 71 | /** |
| 70 | * using_dma - return the DMA status of the driver. | 72 | * using_dma - return the DMA status of the driver. |
| @@ -85,7 +87,7 @@ static void s3c_hsotg_dump(struct s3c_hsotg *hsotg); | |||
| 85 | * | 87 | * |
| 86 | * Until this issue is sorted out, we always return 'false'. | 88 | * Until this issue is sorted out, we always return 'false'. |
| 87 | */ | 89 | */ |
| 88 | static inline bool using_dma(struct s3c_hsotg *hsotg) | 90 | static inline bool using_dma(struct dwc2_hsotg *hsotg) |
| 89 | { | 91 | { |
| 90 | return false; /* support is not complete */ | 92 | return false; /* support is not complete */ |
| 91 | } | 93 | } |
| @@ -95,7 +97,7 @@ static inline bool using_dma(struct s3c_hsotg *hsotg) | |||
| 95 | * @hsotg: The device state | 97 | * @hsotg: The device state |
| 96 | * @ints: A bitmask of the interrupts to enable | 98 | * @ints: A bitmask of the interrupts to enable |
| 97 | */ | 99 | */ |
| 98 | static void s3c_hsotg_en_gsint(struct s3c_hsotg *hsotg, u32 ints) | 100 | static void s3c_hsotg_en_gsint(struct dwc2_hsotg *hsotg, u32 ints) |
| 99 | { | 101 | { |
| 100 | u32 gsintmsk = readl(hsotg->regs + GINTMSK); | 102 | u32 gsintmsk = readl(hsotg->regs + GINTMSK); |
| 101 | u32 new_gsintmsk; | 103 | u32 new_gsintmsk; |
| @@ -113,7 +115,7 @@ static void s3c_hsotg_en_gsint(struct s3c_hsotg *hsotg, u32 ints) | |||
| 113 | * @hsotg: The device state | 115 | * @hsotg: The device state |
| 114 | * @ints: A bitmask of the interrupts to enable | 116 | * @ints: A bitmask of the interrupts to enable |
| 115 | */ | 117 | */ |
| 116 | static void s3c_hsotg_disable_gsint(struct s3c_hsotg *hsotg, u32 ints) | 118 | static void s3c_hsotg_disable_gsint(struct dwc2_hsotg *hsotg, u32 ints) |
| 117 | { | 119 | { |
| 118 | u32 gsintmsk = readl(hsotg->regs + GINTMSK); | 120 | u32 gsintmsk = readl(hsotg->regs + GINTMSK); |
| 119 | u32 new_gsintmsk; | 121 | u32 new_gsintmsk; |
| @@ -134,7 +136,7 @@ static void s3c_hsotg_disable_gsint(struct s3c_hsotg *hsotg, u32 ints) | |||
| 134 | * Set or clear the mask for an individual endpoint's interrupt | 136 | * Set or clear the mask for an individual endpoint's interrupt |
| 135 | * request. | 137 | * request. |
| 136 | */ | 138 | */ |
| 137 | static void s3c_hsotg_ctrl_epint(struct s3c_hsotg *hsotg, | 139 | static void s3c_hsotg_ctrl_epint(struct dwc2_hsotg *hsotg, |
| 138 | unsigned int ep, unsigned int dir_in, | 140 | unsigned int ep, unsigned int dir_in, |
| 139 | unsigned int en) | 141 | unsigned int en) |
| 140 | { | 142 | { |
| @@ -159,7 +161,7 @@ static void s3c_hsotg_ctrl_epint(struct s3c_hsotg *hsotg, | |||
| 159 | * s3c_hsotg_init_fifo - initialise non-periodic FIFOs | 161 | * s3c_hsotg_init_fifo - initialise non-periodic FIFOs |
| 160 | * @hsotg: The device instance. | 162 | * @hsotg: The device instance. |
| 161 | */ | 163 | */ |
| 162 | static void s3c_hsotg_init_fifo(struct s3c_hsotg *hsotg) | 164 | static void s3c_hsotg_init_fifo(struct dwc2_hsotg *hsotg) |
| 163 | { | 165 | { |
| 164 | unsigned int ep; | 166 | unsigned int ep; |
| 165 | unsigned int addr; | 167 | unsigned int addr; |
| @@ -283,7 +285,7 @@ static inline int is_ep_periodic(struct s3c_hsotg_ep *hs_ep) | |||
| 283 | * This is the reverse of s3c_hsotg_map_dma(), called for the completion | 285 | * This is the reverse of s3c_hsotg_map_dma(), called for the completion |
| 284 | * of a request to ensure the buffer is ready for access by the caller. | 286 | * of a request to ensure the buffer is ready for access by the caller. |
| 285 | */ | 287 | */ |
| 286 | static void s3c_hsotg_unmap_dma(struct s3c_hsotg *hsotg, | 288 | static void s3c_hsotg_unmap_dma(struct dwc2_hsotg *hsotg, |
| 287 | struct s3c_hsotg_ep *hs_ep, | 289 | struct s3c_hsotg_ep *hs_ep, |
| 288 | struct s3c_hsotg_req *hs_req) | 290 | struct s3c_hsotg_req *hs_req) |
| 289 | { | 291 | { |
| @@ -312,7 +314,7 @@ static void s3c_hsotg_unmap_dma(struct s3c_hsotg *hsotg, | |||
| 312 | * | 314 | * |
| 313 | * This routine is only needed for PIO | 315 | * This routine is only needed for PIO |
| 314 | */ | 316 | */ |
| 315 | static int s3c_hsotg_write_fifo(struct s3c_hsotg *hsotg, | 317 | static int s3c_hsotg_write_fifo(struct dwc2_hsotg *hsotg, |
| 316 | struct s3c_hsotg_ep *hs_ep, | 318 | struct s3c_hsotg_ep *hs_ep, |
| 317 | struct s3c_hsotg_req *hs_req) | 319 | struct s3c_hsotg_req *hs_req) |
| 318 | { | 320 | { |
| @@ -517,7 +519,7 @@ static unsigned get_ep_limit(struct s3c_hsotg_ep *hs_ep) | |||
| 517 | * Start the given request running by setting the endpoint registers | 519 | * Start the given request running by setting the endpoint registers |
| 518 | * appropriately, and writing any data to the FIFOs. | 520 | * appropriately, and writing any data to the FIFOs. |
| 519 | */ | 521 | */ |
| 520 | static void s3c_hsotg_start_req(struct s3c_hsotg *hsotg, | 522 | static void s3c_hsotg_start_req(struct dwc2_hsotg *hsotg, |
| 521 | struct s3c_hsotg_ep *hs_ep, | 523 | struct s3c_hsotg_ep *hs_ep, |
| 522 | struct s3c_hsotg_req *hs_req, | 524 | struct s3c_hsotg_req *hs_req, |
| 523 | bool continuing) | 525 | bool continuing) |
| @@ -707,7 +709,7 @@ static void s3c_hsotg_start_req(struct s3c_hsotg *hsotg, | |||
| 707 | * DMA memory, then we map the memory and mark our request to allow us to | 709 | * DMA memory, then we map the memory and mark our request to allow us to |
| 708 | * cleanup on completion. | 710 | * cleanup on completion. |
| 709 | */ | 711 | */ |
| 710 | static int s3c_hsotg_map_dma(struct s3c_hsotg *hsotg, | 712 | static int s3c_hsotg_map_dma(struct dwc2_hsotg *hsotg, |
| 711 | struct s3c_hsotg_ep *hs_ep, | 713 | struct s3c_hsotg_ep *hs_ep, |
| 712 | struct usb_request *req) | 714 | struct usb_request *req) |
| 713 | { | 715 | { |
| @@ -736,7 +738,7 @@ static int s3c_hsotg_ep_queue(struct usb_ep *ep, struct usb_request *req, | |||
| 736 | { | 738 | { |
| 737 | struct s3c_hsotg_req *hs_req = our_req(req); | 739 | struct s3c_hsotg_req *hs_req = our_req(req); |
| 738 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); | 740 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); |
| 739 | struct s3c_hsotg *hs = hs_ep->parent; | 741 | struct dwc2_hsotg *hs = hs_ep->parent; |
| 740 | bool first; | 742 | bool first; |
| 741 | 743 | ||
| 742 | dev_dbg(hs->dev, "%s: req %p: %d@%p, noi=%d, zero=%d, snok=%d\n", | 744 | dev_dbg(hs->dev, "%s: req %p: %d@%p, noi=%d, zero=%d, snok=%d\n", |
| @@ -768,7 +770,7 @@ static int s3c_hsotg_ep_queue_lock(struct usb_ep *ep, struct usb_request *req, | |||
| 768 | gfp_t gfp_flags) | 770 | gfp_t gfp_flags) |
| 769 | { | 771 | { |
| 770 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); | 772 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); |
| 771 | struct s3c_hsotg *hs = hs_ep->parent; | 773 | struct dwc2_hsotg *hs = hs_ep->parent; |
| 772 | unsigned long flags = 0; | 774 | unsigned long flags = 0; |
| 773 | int ret = 0; | 775 | int ret = 0; |
| 774 | 776 | ||
| @@ -799,7 +801,7 @@ static void s3c_hsotg_complete_oursetup(struct usb_ep *ep, | |||
| 799 | struct usb_request *req) | 801 | struct usb_request *req) |
| 800 | { | 802 | { |
| 801 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); | 803 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); |
| 802 | struct s3c_hsotg *hsotg = hs_ep->parent; | 804 | struct dwc2_hsotg *hsotg = hs_ep->parent; |
| 803 | 805 | ||
| 804 | dev_dbg(hsotg->dev, "%s: ep %p, req %p\n", __func__, ep, req); | 806 | dev_dbg(hsotg->dev, "%s: ep %p, req %p\n", __func__, ep, req); |
| 805 | 807 | ||
| @@ -814,7 +816,7 @@ static void s3c_hsotg_complete_oursetup(struct usb_ep *ep, | |||
| 814 | * Convert the given wIndex into a pointer to an driver endpoint | 816 | * Convert the given wIndex into a pointer to an driver endpoint |
| 815 | * structure, or return NULL if it is not a valid endpoint. | 817 | * structure, or return NULL if it is not a valid endpoint. |
| 816 | */ | 818 | */ |
| 817 | static struct s3c_hsotg_ep *ep_from_windex(struct s3c_hsotg *hsotg, | 819 | static struct s3c_hsotg_ep *ep_from_windex(struct dwc2_hsotg *hsotg, |
| 818 | u32 windex) | 820 | u32 windex) |
| 819 | { | 821 | { |
| 820 | struct s3c_hsotg_ep *ep = &hsotg->eps[windex & 0x7F]; | 822 | struct s3c_hsotg_ep *ep = &hsotg->eps[windex & 0x7F]; |
| @@ -843,7 +845,7 @@ static struct s3c_hsotg_ep *ep_from_windex(struct s3c_hsotg *hsotg, | |||
| 843 | * Create a request and queue it on the given endpoint. This is useful as | 845 | * Create a request and queue it on the given endpoint. This is useful as |
| 844 | * an internal method of sending replies to certain control requests, etc. | 846 | * an internal method of sending replies to certain control requests, etc. |
| 845 | */ | 847 | */ |
| 846 | static int s3c_hsotg_send_reply(struct s3c_hsotg *hsotg, | 848 | static int s3c_hsotg_send_reply(struct dwc2_hsotg *hsotg, |
| 847 | struct s3c_hsotg_ep *ep, | 849 | struct s3c_hsotg_ep *ep, |
| 848 | void *buff, | 850 | void *buff, |
| 849 | int length) | 851 | int length) |
| @@ -884,7 +886,7 @@ static int s3c_hsotg_send_reply(struct s3c_hsotg *hsotg, | |||
| 884 | * @hsotg: The device state | 886 | * @hsotg: The device state |
| 885 | * @ctrl: USB control request | 887 | * @ctrl: USB control request |
| 886 | */ | 888 | */ |
| 887 | static int s3c_hsotg_process_req_status(struct s3c_hsotg *hsotg, | 889 | static int s3c_hsotg_process_req_status(struct dwc2_hsotg *hsotg, |
| 888 | struct usb_ctrlrequest *ctrl) | 890 | struct usb_ctrlrequest *ctrl) |
| 889 | { | 891 | { |
| 890 | struct s3c_hsotg_ep *ep0 = &hsotg->eps[0]; | 892 | struct s3c_hsotg_ep *ep0 = &hsotg->eps[0]; |
| @@ -955,7 +957,7 @@ static struct s3c_hsotg_req *get_ep_head(struct s3c_hsotg_ep *hs_ep) | |||
| 955 | * @hsotg: The device state | 957 | * @hsotg: The device state |
| 956 | * @ctrl: USB control request | 958 | * @ctrl: USB control request |
| 957 | */ | 959 | */ |
| 958 | static int s3c_hsotg_process_req_feature(struct s3c_hsotg *hsotg, | 960 | static int s3c_hsotg_process_req_feature(struct dwc2_hsotg *hsotg, |
| 959 | struct usb_ctrlrequest *ctrl) | 961 | struct usb_ctrlrequest *ctrl) |
| 960 | { | 962 | { |
| 961 | struct s3c_hsotg_ep *ep0 = &hsotg->eps[0]; | 963 | struct s3c_hsotg_ep *ep0 = &hsotg->eps[0]; |
| @@ -1028,8 +1030,7 @@ static int s3c_hsotg_process_req_feature(struct s3c_hsotg *hsotg, | |||
| 1028 | return 1; | 1030 | return 1; |
| 1029 | } | 1031 | } |
| 1030 | 1032 | ||
| 1031 | static void s3c_hsotg_enqueue_setup(struct s3c_hsotg *hsotg); | 1033 | static void s3c_hsotg_enqueue_setup(struct dwc2_hsotg *hsotg); |
| 1032 | static void s3c_hsotg_disconnect(struct s3c_hsotg *hsotg); | ||
| 1033 | 1034 | ||
| 1034 | /** | 1035 | /** |
| 1035 | * s3c_hsotg_stall_ep0 - stall ep0 | 1036 | * s3c_hsotg_stall_ep0 - stall ep0 |
| @@ -1037,7 +1038,7 @@ static void s3c_hsotg_disconnect(struct s3c_hsotg *hsotg); | |||
| 1037 | * | 1038 | * |
| 1038 | * Set stall for ep0 as response for setup request. | 1039 | * Set stall for ep0 as response for setup request. |
| 1039 | */ | 1040 | */ |
| 1040 | static void s3c_hsotg_stall_ep0(struct s3c_hsotg *hsotg) | 1041 | static void s3c_hsotg_stall_ep0(struct dwc2_hsotg *hsotg) |
| 1041 | { | 1042 | { |
| 1042 | struct s3c_hsotg_ep *ep0 = &hsotg->eps[0]; | 1043 | struct s3c_hsotg_ep *ep0 = &hsotg->eps[0]; |
| 1043 | u32 reg; | 1044 | u32 reg; |
| @@ -1076,7 +1077,7 @@ static void s3c_hsotg_stall_ep0(struct s3c_hsotg *hsotg) | |||
| 1076 | * needs to work out what to do next (and whether to pass it on to the | 1077 | * needs to work out what to do next (and whether to pass it on to the |
| 1077 | * gadget driver). | 1078 | * gadget driver). |
| 1078 | */ | 1079 | */ |
| 1079 | static void s3c_hsotg_process_control(struct s3c_hsotg *hsotg, | 1080 | static void s3c_hsotg_process_control(struct dwc2_hsotg *hsotg, |
| 1080 | struct usb_ctrlrequest *ctrl) | 1081 | struct usb_ctrlrequest *ctrl) |
| 1081 | { | 1082 | { |
| 1082 | struct s3c_hsotg_ep *ep0 = &hsotg->eps[0]; | 1083 | struct s3c_hsotg_ep *ep0 = &hsotg->eps[0]; |
| @@ -1107,7 +1108,6 @@ static void s3c_hsotg_process_control(struct s3c_hsotg *hsotg, | |||
| 1107 | if ((ctrl->bRequestType & USB_TYPE_MASK) == USB_TYPE_STANDARD) { | 1108 | if ((ctrl->bRequestType & USB_TYPE_MASK) == USB_TYPE_STANDARD) { |
| 1108 | switch (ctrl->bRequest) { | 1109 | switch (ctrl->bRequest) { |
| 1109 | case USB_REQ_SET_ADDRESS: | 1110 | case USB_REQ_SET_ADDRESS: |
| 1110 | s3c_hsotg_disconnect(hsotg); | ||
| 1111 | dcfg = readl(hsotg->regs + DCFG); | 1111 | dcfg = readl(hsotg->regs + DCFG); |
| 1112 | dcfg &= ~DCFG_DEVADDR_MASK; | 1112 | dcfg &= ~DCFG_DEVADDR_MASK; |
| 1113 | dcfg |= (le16_to_cpu(ctrl->wValue) << | 1113 | dcfg |= (le16_to_cpu(ctrl->wValue) << |
| @@ -1161,7 +1161,7 @@ static void s3c_hsotg_complete_setup(struct usb_ep *ep, | |||
| 1161 | struct usb_request *req) | 1161 | struct usb_request *req) |
| 1162 | { | 1162 | { |
| 1163 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); | 1163 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); |
| 1164 | struct s3c_hsotg *hsotg = hs_ep->parent; | 1164 | struct dwc2_hsotg *hsotg = hs_ep->parent; |
| 1165 | 1165 | ||
| 1166 | if (req->status < 0) { | 1166 | if (req->status < 0) { |
| 1167 | dev_dbg(hsotg->dev, "%s: failed %d\n", __func__, req->status); | 1167 | dev_dbg(hsotg->dev, "%s: failed %d\n", __func__, req->status); |
| @@ -1183,7 +1183,7 @@ static void s3c_hsotg_complete_setup(struct usb_ep *ep, | |||
| 1183 | * Enqueue a request on EP0 if necessary to received any SETUP packets | 1183 | * Enqueue a request on EP0 if necessary to received any SETUP packets |
| 1184 | * received from the host. | 1184 | * received from the host. |
| 1185 | */ | 1185 | */ |
| 1186 | static void s3c_hsotg_enqueue_setup(struct s3c_hsotg *hsotg) | 1186 | static void s3c_hsotg_enqueue_setup(struct dwc2_hsotg *hsotg) |
| 1187 | { | 1187 | { |
| 1188 | struct usb_request *req = hsotg->ctrl_req; | 1188 | struct usb_request *req = hsotg->ctrl_req; |
| 1189 | struct s3c_hsotg_req *hs_req = our_req(req); | 1189 | struct s3c_hsotg_req *hs_req = our_req(req); |
| @@ -1226,7 +1226,7 @@ static void s3c_hsotg_enqueue_setup(struct s3c_hsotg *hsotg) | |||
| 1226 | * | 1226 | * |
| 1227 | * Note, expects the ep to already be locked as appropriate. | 1227 | * Note, expects the ep to already be locked as appropriate. |
| 1228 | */ | 1228 | */ |
| 1229 | static void s3c_hsotg_complete_request(struct s3c_hsotg *hsotg, | 1229 | static void s3c_hsotg_complete_request(struct dwc2_hsotg *hsotg, |
| 1230 | struct s3c_hsotg_ep *hs_ep, | 1230 | struct s3c_hsotg_ep *hs_ep, |
| 1231 | struct s3c_hsotg_req *hs_req, | 1231 | struct s3c_hsotg_req *hs_req, |
| 1232 | int result) | 1232 | int result) |
| @@ -1291,7 +1291,7 @@ static void s3c_hsotg_complete_request(struct s3c_hsotg *hsotg, | |||
| 1291 | * endpoint, so sort out whether we need to read the data into a request | 1291 | * endpoint, so sort out whether we need to read the data into a request |
| 1292 | * that has been made for that endpoint. | 1292 | * that has been made for that endpoint. |
| 1293 | */ | 1293 | */ |
| 1294 | static void s3c_hsotg_rx_data(struct s3c_hsotg *hsotg, int ep_idx, int size) | 1294 | static void s3c_hsotg_rx_data(struct dwc2_hsotg *hsotg, int ep_idx, int size) |
| 1295 | { | 1295 | { |
| 1296 | struct s3c_hsotg_ep *hs_ep = &hsotg->eps[ep_idx]; | 1296 | struct s3c_hsotg_ep *hs_ep = &hsotg->eps[ep_idx]; |
| 1297 | struct s3c_hsotg_req *hs_req = hs_ep->req; | 1297 | struct s3c_hsotg_req *hs_req = hs_ep->req; |
| @@ -1356,7 +1356,7 @@ static void s3c_hsotg_rx_data(struct s3c_hsotg *hsotg, int ep_idx, int size) | |||
| 1356 | * currently believed that we do not need to wait for any space in | 1356 | * currently believed that we do not need to wait for any space in |
| 1357 | * the TxFIFO. | 1357 | * the TxFIFO. |
| 1358 | */ | 1358 | */ |
| 1359 | static void s3c_hsotg_send_zlp(struct s3c_hsotg *hsotg, | 1359 | static void s3c_hsotg_send_zlp(struct dwc2_hsotg *hsotg, |
| 1360 | struct s3c_hsotg_req *req) | 1360 | struct s3c_hsotg_req *req) |
| 1361 | { | 1361 | { |
| 1362 | u32 ctrl; | 1362 | u32 ctrl; |
| @@ -1398,7 +1398,7 @@ static void s3c_hsotg_send_zlp(struct s3c_hsotg *hsotg, | |||
| 1398 | * transfer for an OUT endpoint has been completed, either by a short | 1398 | * transfer for an OUT endpoint has been completed, either by a short |
| 1399 | * packet or by the finish of a transfer. | 1399 | * packet or by the finish of a transfer. |
| 1400 | */ | 1400 | */ |
| 1401 | static void s3c_hsotg_handle_outdone(struct s3c_hsotg *hsotg, | 1401 | static void s3c_hsotg_handle_outdone(struct dwc2_hsotg *hsotg, |
| 1402 | int epnum, bool was_setup) | 1402 | int epnum, bool was_setup) |
| 1403 | { | 1403 | { |
| 1404 | u32 epsize = readl(hsotg->regs + DOEPTSIZ(epnum)); | 1404 | u32 epsize = readl(hsotg->regs + DOEPTSIZ(epnum)); |
| @@ -1471,7 +1471,7 @@ static void s3c_hsotg_handle_outdone(struct s3c_hsotg *hsotg, | |||
| 1471 | * | 1471 | * |
| 1472 | * Return the current frame number | 1472 | * Return the current frame number |
| 1473 | */ | 1473 | */ |
| 1474 | static u32 s3c_hsotg_read_frameno(struct s3c_hsotg *hsotg) | 1474 | static u32 s3c_hsotg_read_frameno(struct dwc2_hsotg *hsotg) |
| 1475 | { | 1475 | { |
| 1476 | u32 dsts; | 1476 | u32 dsts; |
| 1477 | 1477 | ||
| @@ -1498,7 +1498,7 @@ static u32 s3c_hsotg_read_frameno(struct s3c_hsotg *hsotg) | |||
| 1498 | * as the actual data should be sent to the memory directly and we turn | 1498 | * as the actual data should be sent to the memory directly and we turn |
| 1499 | * on the completion interrupts to get notifications of transfer completion. | 1499 | * on the completion interrupts to get notifications of transfer completion. |
| 1500 | */ | 1500 | */ |
| 1501 | static void s3c_hsotg_handle_rx(struct s3c_hsotg *hsotg) | 1501 | static void s3c_hsotg_handle_rx(struct dwc2_hsotg *hsotg) |
| 1502 | { | 1502 | { |
| 1503 | u32 grxstsr = readl(hsotg->regs + GRXSTSP); | 1503 | u32 grxstsr = readl(hsotg->regs + GRXSTSP); |
| 1504 | u32 epnum, status, size; | 1504 | u32 epnum, status, size; |
| @@ -1590,7 +1590,7 @@ static u32 s3c_hsotg_ep0_mps(unsigned int mps) | |||
| 1590 | * Configure the maximum packet size for the given endpoint, updating | 1590 | * Configure the maximum packet size for the given endpoint, updating |
| 1591 | * the hardware control registers to reflect this. | 1591 | * the hardware control registers to reflect this. |
| 1592 | */ | 1592 | */ |
| 1593 | static void s3c_hsotg_set_ep_maxpacket(struct s3c_hsotg *hsotg, | 1593 | static void s3c_hsotg_set_ep_maxpacket(struct dwc2_hsotg *hsotg, |
| 1594 | unsigned int ep, unsigned int mps) | 1594 | unsigned int ep, unsigned int mps) |
| 1595 | { | 1595 | { |
| 1596 | struct s3c_hsotg_ep *hs_ep = &hsotg->eps[ep]; | 1596 | struct s3c_hsotg_ep *hs_ep = &hsotg->eps[ep]; |
| @@ -1645,7 +1645,7 @@ bad_mps: | |||
| 1645 | * @hsotg: The driver state | 1645 | * @hsotg: The driver state |
| 1646 | * @idx: The index for the endpoint (0..15) | 1646 | * @idx: The index for the endpoint (0..15) |
| 1647 | */ | 1647 | */ |
| 1648 | static void s3c_hsotg_txfifo_flush(struct s3c_hsotg *hsotg, unsigned int idx) | 1648 | static void s3c_hsotg_txfifo_flush(struct dwc2_hsotg *hsotg, unsigned int idx) |
| 1649 | { | 1649 | { |
| 1650 | int timeout; | 1650 | int timeout; |
| 1651 | int val; | 1651 | int val; |
| @@ -1681,7 +1681,7 @@ static void s3c_hsotg_txfifo_flush(struct s3c_hsotg *hsotg, unsigned int idx) | |||
| 1681 | * Check to see if there is a request that has data to send, and if so | 1681 | * Check to see if there is a request that has data to send, and if so |
| 1682 | * make an attempt to write data into the FIFO. | 1682 | * make an attempt to write data into the FIFO. |
| 1683 | */ | 1683 | */ |
| 1684 | static int s3c_hsotg_trytx(struct s3c_hsotg *hsotg, | 1684 | static int s3c_hsotg_trytx(struct dwc2_hsotg *hsotg, |
| 1685 | struct s3c_hsotg_ep *hs_ep) | 1685 | struct s3c_hsotg_ep *hs_ep) |
| 1686 | { | 1686 | { |
| 1687 | struct s3c_hsotg_req *hs_req = hs_ep->req; | 1687 | struct s3c_hsotg_req *hs_req = hs_ep->req; |
| @@ -1714,7 +1714,7 @@ static int s3c_hsotg_trytx(struct s3c_hsotg *hsotg, | |||
| 1714 | * An IN transfer has been completed, update the transfer's state and then | 1714 | * An IN transfer has been completed, update the transfer's state and then |
| 1715 | * call the relevant completion routines. | 1715 | * call the relevant completion routines. |
| 1716 | */ | 1716 | */ |
| 1717 | static void s3c_hsotg_complete_in(struct s3c_hsotg *hsotg, | 1717 | static void s3c_hsotg_complete_in(struct dwc2_hsotg *hsotg, |
| 1718 | struct s3c_hsotg_ep *hs_ep) | 1718 | struct s3c_hsotg_ep *hs_ep) |
| 1719 | { | 1719 | { |
| 1720 | struct s3c_hsotg_req *hs_req = hs_ep->req; | 1720 | struct s3c_hsotg_req *hs_req = hs_ep->req; |
| @@ -1791,7 +1791,7 @@ static void s3c_hsotg_complete_in(struct s3c_hsotg *hsotg, | |||
| 1791 | * | 1791 | * |
| 1792 | * Process and clear any interrupt pending for an individual endpoint | 1792 | * Process and clear any interrupt pending for an individual endpoint |
| 1793 | */ | 1793 | */ |
| 1794 | static void s3c_hsotg_epint(struct s3c_hsotg *hsotg, unsigned int idx, | 1794 | static void s3c_hsotg_epint(struct dwc2_hsotg *hsotg, unsigned int idx, |
| 1795 | int dir_in) | 1795 | int dir_in) |
| 1796 | { | 1796 | { |
| 1797 | struct s3c_hsotg_ep *hs_ep = &hsotg->eps[idx]; | 1797 | struct s3c_hsotg_ep *hs_ep = &hsotg->eps[idx]; |
| @@ -1916,7 +1916,7 @@ static void s3c_hsotg_epint(struct s3c_hsotg *hsotg, unsigned int idx, | |||
| 1916 | * Handle updating the device settings after the enumeration phase has | 1916 | * Handle updating the device settings after the enumeration phase has |
| 1917 | * been completed. | 1917 | * been completed. |
| 1918 | */ | 1918 | */ |
| 1919 | static void s3c_hsotg_irq_enumdone(struct s3c_hsotg *hsotg) | 1919 | static void s3c_hsotg_irq_enumdone(struct dwc2_hsotg *hsotg) |
| 1920 | { | 1920 | { |
| 1921 | u32 dsts = readl(hsotg->regs + DSTS); | 1921 | u32 dsts = readl(hsotg->regs + DSTS); |
| 1922 | int ep0_mps = 0, ep_mps = 8; | 1922 | int ep0_mps = 0, ep_mps = 8; |
| @@ -1993,7 +1993,7 @@ static void s3c_hsotg_irq_enumdone(struct s3c_hsotg *hsotg) | |||
| 1993 | * Go through the requests on the given endpoint and mark them | 1993 | * Go through the requests on the given endpoint and mark them |
| 1994 | * completed with the given result code. | 1994 | * completed with the given result code. |
| 1995 | */ | 1995 | */ |
| 1996 | static void kill_all_requests(struct s3c_hsotg *hsotg, | 1996 | static void kill_all_requests(struct dwc2_hsotg *hsotg, |
| 1997 | struct s3c_hsotg_ep *ep, | 1997 | struct s3c_hsotg_ep *ep, |
| 1998 | int result, bool force) | 1998 | int result, bool force) |
| 1999 | { | 1999 | { |
| @@ -2027,22 +2027,27 @@ static void kill_all_requests(struct s3c_hsotg *hsotg, | |||
| 2027 | * transactions and signal the gadget driver that this | 2027 | * transactions and signal the gadget driver that this |
| 2028 | * has happened. | 2028 | * has happened. |
| 2029 | */ | 2029 | */ |
| 2030 | static void s3c_hsotg_disconnect(struct s3c_hsotg *hsotg) | 2030 | void s3c_hsotg_disconnect(struct dwc2_hsotg *hsotg) |
| 2031 | { | 2031 | { |
| 2032 | unsigned ep; | 2032 | unsigned ep; |
| 2033 | 2033 | ||
| 2034 | if (!hsotg->connected) | ||
| 2035 | return; | ||
| 2036 | |||
| 2037 | hsotg->connected = 0; | ||
| 2034 | for (ep = 0; ep < hsotg->num_of_eps; ep++) | 2038 | for (ep = 0; ep < hsotg->num_of_eps; ep++) |
| 2035 | kill_all_requests(hsotg, &hsotg->eps[ep], -ESHUTDOWN, true); | 2039 | kill_all_requests(hsotg, &hsotg->eps[ep], -ESHUTDOWN, true); |
| 2036 | 2040 | ||
| 2037 | call_gadget(hsotg, disconnect); | 2041 | call_gadget(hsotg, disconnect); |
| 2038 | } | 2042 | } |
| 2043 | EXPORT_SYMBOL_GPL(s3c_hsotg_disconnect); | ||
| 2039 | 2044 | ||
| 2040 | /** | 2045 | /** |
| 2041 | * s3c_hsotg_irq_fifoempty - TX FIFO empty interrupt handler | 2046 | * s3c_hsotg_irq_fifoempty - TX FIFO empty interrupt handler |
| 2042 | * @hsotg: The device state: | 2047 | * @hsotg: The device state: |
| 2043 | * @periodic: True if this is a periodic FIFO interrupt | 2048 | * @periodic: True if this is a periodic FIFO interrupt |
| 2044 | */ | 2049 | */ |
| 2045 | static void s3c_hsotg_irq_fifoempty(struct s3c_hsotg *hsotg, bool periodic) | 2050 | static void s3c_hsotg_irq_fifoempty(struct dwc2_hsotg *hsotg, bool periodic) |
| 2046 | { | 2051 | { |
| 2047 | struct s3c_hsotg_ep *ep; | 2052 | struct s3c_hsotg_ep *ep; |
| 2048 | int epno, ret; | 2053 | int epno, ret; |
| @@ -2076,7 +2081,7 @@ static void s3c_hsotg_irq_fifoempty(struct s3c_hsotg *hsotg, bool periodic) | |||
| 2076 | * | 2081 | * |
| 2077 | * Issue a soft reset to the core, and await the core finishing it. | 2082 | * Issue a soft reset to the core, and await the core finishing it. |
| 2078 | */ | 2083 | */ |
| 2079 | static int s3c_hsotg_corereset(struct s3c_hsotg *hsotg) | 2084 | static int s3c_hsotg_corereset(struct dwc2_hsotg *hsotg) |
| 2080 | { | 2085 | { |
| 2081 | int timeout; | 2086 | int timeout; |
| 2082 | u32 grstctl; | 2087 | u32 grstctl; |
| @@ -2124,7 +2129,7 @@ static int s3c_hsotg_corereset(struct s3c_hsotg *hsotg) | |||
| 2124 | * | 2129 | * |
| 2125 | * Issue a soft reset to the core, and await the core finishing it. | 2130 | * Issue a soft reset to the core, and await the core finishing it. |
| 2126 | */ | 2131 | */ |
| 2127 | static void s3c_hsotg_core_init(struct s3c_hsotg *hsotg) | 2132 | void s3c_hsotg_core_init_disconnected(struct dwc2_hsotg *hsotg) |
| 2128 | { | 2133 | { |
| 2129 | s3c_hsotg_corereset(hsotg); | 2134 | s3c_hsotg_corereset(hsotg); |
| 2130 | 2135 | ||
| @@ -2241,12 +2246,23 @@ static void s3c_hsotg_core_init(struct s3c_hsotg *hsotg) | |||
| 2241 | readl(hsotg->regs + DOEPCTL0)); | 2246 | readl(hsotg->regs + DOEPCTL0)); |
| 2242 | 2247 | ||
| 2243 | /* clear global NAKs */ | 2248 | /* clear global NAKs */ |
| 2244 | writel(DCTL_CGOUTNAK | DCTL_CGNPINNAK, | 2249 | writel(DCTL_CGOUTNAK | DCTL_CGNPINNAK | DCTL_SFTDISCON, |
| 2245 | hsotg->regs + DCTL); | 2250 | hsotg->regs + DCTL); |
| 2246 | 2251 | ||
| 2247 | /* must be at-least 3ms to allow bus to see disconnect */ | 2252 | /* must be at-least 3ms to allow bus to see disconnect */ |
| 2248 | mdelay(3); | 2253 | mdelay(3); |
| 2249 | 2254 | ||
| 2255 | hsotg->last_rst = jiffies; | ||
| 2256 | } | ||
| 2257 | |||
| 2258 | static void s3c_hsotg_core_disconnect(struct dwc2_hsotg *hsotg) | ||
| 2259 | { | ||
| 2260 | /* set the soft-disconnect bit */ | ||
| 2261 | __orr32(hsotg->regs + DCTL, DCTL_SFTDISCON); | ||
| 2262 | } | ||
| 2263 | |||
| 2264 | void s3c_hsotg_core_connect(struct dwc2_hsotg *hsotg) | ||
| 2265 | { | ||
| 2250 | /* remove the soft-disconnect and let's go */ | 2266 | /* remove the soft-disconnect and let's go */ |
| 2251 | __bic32(hsotg->regs + DCTL, DCTL_SFTDISCON); | 2267 | __bic32(hsotg->regs + DCTL, DCTL_SFTDISCON); |
| 2252 | } | 2268 | } |
| @@ -2258,7 +2274,7 @@ static void s3c_hsotg_core_init(struct s3c_hsotg *hsotg) | |||
| 2258 | */ | 2274 | */ |
| 2259 | static irqreturn_t s3c_hsotg_irq(int irq, void *pw) | 2275 | static irqreturn_t s3c_hsotg_irq(int irq, void *pw) |
| 2260 | { | 2276 | { |
| 2261 | struct s3c_hsotg *hsotg = pw; | 2277 | struct dwc2_hsotg *hsotg = pw; |
| 2262 | int retry_count = 8; | 2278 | int retry_count = 8; |
| 2263 | u32 gintsts; | 2279 | u32 gintsts; |
| 2264 | u32 gintmsk; | 2280 | u32 gintmsk; |
| @@ -2273,31 +2289,11 @@ irq_retry: | |||
| 2273 | 2289 | ||
| 2274 | gintsts &= gintmsk; | 2290 | gintsts &= gintmsk; |
| 2275 | 2291 | ||
| 2276 | if (gintsts & GINTSTS_OTGINT) { | ||
| 2277 | u32 otgint = readl(hsotg->regs + GOTGINT); | ||
| 2278 | |||
| 2279 | dev_info(hsotg->dev, "OTGInt: %08x\n", otgint); | ||
| 2280 | |||
| 2281 | writel(otgint, hsotg->regs + GOTGINT); | ||
| 2282 | } | ||
| 2283 | |||
| 2284 | if (gintsts & GINTSTS_SESSREQINT) { | ||
| 2285 | dev_dbg(hsotg->dev, "%s: SessReqInt\n", __func__); | ||
| 2286 | writel(GINTSTS_SESSREQINT, hsotg->regs + GINTSTS); | ||
| 2287 | } | ||
| 2288 | |||
| 2289 | if (gintsts & GINTSTS_ENUMDONE) { | 2292 | if (gintsts & GINTSTS_ENUMDONE) { |
| 2290 | writel(GINTSTS_ENUMDONE, hsotg->regs + GINTSTS); | 2293 | writel(GINTSTS_ENUMDONE, hsotg->regs + GINTSTS); |
| 2291 | 2294 | ||
| 2292 | s3c_hsotg_irq_enumdone(hsotg); | 2295 | s3c_hsotg_irq_enumdone(hsotg); |
| 2293 | } | 2296 | hsotg->connected = 1; |
| 2294 | |||
| 2295 | if (gintsts & GINTSTS_CONIDSTSCHNG) { | ||
| 2296 | dev_dbg(hsotg->dev, "ConIDStsChg (DSTS=0x%08x, GOTCTL=%08x)\n", | ||
| 2297 | readl(hsotg->regs + DSTS), | ||
| 2298 | readl(hsotg->regs + GOTGCTL)); | ||
| 2299 | |||
| 2300 | writel(GINTSTS_CONIDSTSCHNG, hsotg->regs + GINTSTS); | ||
| 2301 | } | 2297 | } |
| 2302 | 2298 | ||
| 2303 | if (gintsts & (GINTSTS_OEPINT | GINTSTS_IEPINT)) { | 2299 | if (gintsts & (GINTSTS_OEPINT | GINTSTS_IEPINT)) { |
| @@ -2340,8 +2336,8 @@ irq_retry: | |||
| 2340 | kill_all_requests(hsotg, &hsotg->eps[0], | 2336 | kill_all_requests(hsotg, &hsotg->eps[0], |
| 2341 | -ECONNRESET, true); | 2337 | -ECONNRESET, true); |
| 2342 | 2338 | ||
| 2343 | s3c_hsotg_core_init(hsotg); | 2339 | s3c_hsotg_core_init_disconnected(hsotg); |
| 2344 | hsotg->last_rst = jiffies; | 2340 | s3c_hsotg_core_connect(hsotg); |
| 2345 | } | 2341 | } |
| 2346 | } | 2342 | } |
| 2347 | } | 2343 | } |
| @@ -2380,25 +2376,6 @@ irq_retry: | |||
| 2380 | s3c_hsotg_handle_rx(hsotg); | 2376 | s3c_hsotg_handle_rx(hsotg); |
| 2381 | } | 2377 | } |
| 2382 | 2378 | ||
| 2383 | if (gintsts & GINTSTS_MODEMIS) { | ||
| 2384 | dev_warn(hsotg->dev, "warning, mode mismatch triggered\n"); | ||
| 2385 | writel(GINTSTS_MODEMIS, hsotg->regs + GINTSTS); | ||
| 2386 | } | ||
| 2387 | |||
| 2388 | if (gintsts & GINTSTS_USBSUSP) { | ||
| 2389 | dev_info(hsotg->dev, "GINTSTS_USBSusp\n"); | ||
| 2390 | writel(GINTSTS_USBSUSP, hsotg->regs + GINTSTS); | ||
| 2391 | |||
| 2392 | call_gadget(hsotg, suspend); | ||
| 2393 | } | ||
| 2394 | |||
| 2395 | if (gintsts & GINTSTS_WKUPINT) { | ||
| 2396 | dev_info(hsotg->dev, "GINTSTS_WkUpIn\n"); | ||
| 2397 | writel(GINTSTS_WKUPINT, hsotg->regs + GINTSTS); | ||
| 2398 | |||
| 2399 | call_gadget(hsotg, resume); | ||
| 2400 | } | ||
| 2401 | |||
| 2402 | if (gintsts & GINTSTS_ERLYSUSP) { | 2379 | if (gintsts & GINTSTS_ERLYSUSP) { |
| 2403 | dev_dbg(hsotg->dev, "GINTSTS_ErlySusp\n"); | 2380 | dev_dbg(hsotg->dev, "GINTSTS_ErlySusp\n"); |
| 2404 | writel(GINTSTS_ERLYSUSP, hsotg->regs + GINTSTS); | 2381 | writel(GINTSTS_ERLYSUSP, hsotg->regs + GINTSTS); |
| @@ -2450,7 +2427,7 @@ static int s3c_hsotg_ep_enable(struct usb_ep *ep, | |||
| 2450 | const struct usb_endpoint_descriptor *desc) | 2427 | const struct usb_endpoint_descriptor *desc) |
| 2451 | { | 2428 | { |
| 2452 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); | 2429 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); |
| 2453 | struct s3c_hsotg *hsotg = hs_ep->parent; | 2430 | struct dwc2_hsotg *hsotg = hs_ep->parent; |
| 2454 | unsigned long flags; | 2431 | unsigned long flags; |
| 2455 | int index = hs_ep->index; | 2432 | int index = hs_ep->index; |
| 2456 | u32 epctrl_reg; | 2433 | u32 epctrl_reg; |
| @@ -2593,7 +2570,7 @@ error: | |||
| 2593 | static int s3c_hsotg_ep_disable(struct usb_ep *ep) | 2570 | static int s3c_hsotg_ep_disable(struct usb_ep *ep) |
| 2594 | { | 2571 | { |
| 2595 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); | 2572 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); |
| 2596 | struct s3c_hsotg *hsotg = hs_ep->parent; | 2573 | struct dwc2_hsotg *hsotg = hs_ep->parent; |
| 2597 | int dir_in = hs_ep->dir_in; | 2574 | int dir_in = hs_ep->dir_in; |
| 2598 | int index = hs_ep->index; | 2575 | int index = hs_ep->index; |
| 2599 | unsigned long flags; | 2576 | unsigned long flags; |
| @@ -2658,7 +2635,7 @@ static int s3c_hsotg_ep_dequeue(struct usb_ep *ep, struct usb_request *req) | |||
| 2658 | { | 2635 | { |
| 2659 | struct s3c_hsotg_req *hs_req = our_req(req); | 2636 | struct s3c_hsotg_req *hs_req = our_req(req); |
| 2660 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); | 2637 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); |
| 2661 | struct s3c_hsotg *hs = hs_ep->parent; | 2638 | struct dwc2_hsotg *hs = hs_ep->parent; |
| 2662 | unsigned long flags; | 2639 | unsigned long flags; |
| 2663 | 2640 | ||
| 2664 | dev_dbg(hs->dev, "ep_dequeue(%p,%p)\n", ep, req); | 2641 | dev_dbg(hs->dev, "ep_dequeue(%p,%p)\n", ep, req); |
| @@ -2684,7 +2661,7 @@ static int s3c_hsotg_ep_dequeue(struct usb_ep *ep, struct usb_request *req) | |||
| 2684 | static int s3c_hsotg_ep_sethalt(struct usb_ep *ep, int value) | 2661 | static int s3c_hsotg_ep_sethalt(struct usb_ep *ep, int value) |
| 2685 | { | 2662 | { |
| 2686 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); | 2663 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); |
| 2687 | struct s3c_hsotg *hs = hs_ep->parent; | 2664 | struct dwc2_hsotg *hs = hs_ep->parent; |
| 2688 | int index = hs_ep->index; | 2665 | int index = hs_ep->index; |
| 2689 | u32 epreg; | 2666 | u32 epreg; |
| 2690 | u32 epctl; | 2667 | u32 epctl; |
| @@ -2748,7 +2725,7 @@ static int s3c_hsotg_ep_sethalt(struct usb_ep *ep, int value) | |||
| 2748 | static int s3c_hsotg_ep_sethalt_lock(struct usb_ep *ep, int value) | 2725 | static int s3c_hsotg_ep_sethalt_lock(struct usb_ep *ep, int value) |
| 2749 | { | 2726 | { |
| 2750 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); | 2727 | struct s3c_hsotg_ep *hs_ep = our_ep(ep); |
| 2751 | struct s3c_hsotg *hs = hs_ep->parent; | 2728 | struct dwc2_hsotg *hs = hs_ep->parent; |
| 2752 | unsigned long flags = 0; | 2729 | unsigned long flags = 0; |
| 2753 | int ret = 0; | 2730 | int ret = 0; |
| 2754 | 2731 | ||
| @@ -2777,7 +2754,7 @@ static struct usb_ep_ops s3c_hsotg_ep_ops = { | |||
| 2777 | * A wrapper for platform code responsible for controlling | 2754 | * A wrapper for platform code responsible for controlling |
| 2778 | * low-level USB code | 2755 | * low-level USB code |
| 2779 | */ | 2756 | */ |
| 2780 | static void s3c_hsotg_phy_enable(struct s3c_hsotg *hsotg) | 2757 | static void s3c_hsotg_phy_enable(struct dwc2_hsotg *hsotg) |
| 2781 | { | 2758 | { |
| 2782 | struct platform_device *pdev = to_platform_device(hsotg->dev); | 2759 | struct platform_device *pdev = to_platform_device(hsotg->dev); |
| 2783 | 2760 | ||
| @@ -2800,7 +2777,7 @@ static void s3c_hsotg_phy_enable(struct s3c_hsotg *hsotg) | |||
| 2800 | * A wrapper for platform code responsible for controlling | 2777 | * A wrapper for platform code responsible for controlling |
| 2801 | * low-level USB code | 2778 | * low-level USB code |
| 2802 | */ | 2779 | */ |
| 2803 | static void s3c_hsotg_phy_disable(struct s3c_hsotg *hsotg) | 2780 | static void s3c_hsotg_phy_disable(struct dwc2_hsotg *hsotg) |
| 2804 | { | 2781 | { |
| 2805 | struct platform_device *pdev = to_platform_device(hsotg->dev); | 2782 | struct platform_device *pdev = to_platform_device(hsotg->dev); |
| 2806 | 2783 | ||
| @@ -2818,7 +2795,7 @@ static void s3c_hsotg_phy_disable(struct s3c_hsotg *hsotg) | |||
| 2818 | * s3c_hsotg_init - initalize the usb core | 2795 | * s3c_hsotg_init - initalize the usb core |
| 2819 | * @hsotg: The driver state | 2796 | * @hsotg: The driver state |
| 2820 | */ | 2797 | */ |
| 2821 | static void s3c_hsotg_init(struct s3c_hsotg *hsotg) | 2798 | static void s3c_hsotg_init(struct dwc2_hsotg *hsotg) |
| 2822 | { | 2799 | { |
| 2823 | /* unmask subset of endpoint interrupts */ | 2800 | /* unmask subset of endpoint interrupts */ |
| 2824 | 2801 | ||
| @@ -2868,7 +2845,8 @@ static void s3c_hsotg_init(struct s3c_hsotg *hsotg) | |||
| 2868 | static int s3c_hsotg_udc_start(struct usb_gadget *gadget, | 2845 | static int s3c_hsotg_udc_start(struct usb_gadget *gadget, |
| 2869 | struct usb_gadget_driver *driver) | 2846 | struct usb_gadget_driver *driver) |
| 2870 | { | 2847 | { |
| 2871 | struct s3c_hsotg *hsotg = to_hsotg(gadget); | 2848 | struct dwc2_hsotg *hsotg = to_hsotg(gadget); |
| 2849 | unsigned long flags; | ||
| 2872 | int ret; | 2850 | int ret; |
| 2873 | 2851 | ||
| 2874 | if (!hsotg) { | 2852 | if (!hsotg) { |
| @@ -2889,6 +2867,7 @@ static int s3c_hsotg_udc_start(struct usb_gadget *gadget, | |||
| 2889 | return -EINVAL; | 2867 | return -EINVAL; |
| 2890 | } | 2868 | } |
| 2891 | 2869 | ||
| 2870 | mutex_lock(&hsotg->init_mutex); | ||
| 2892 | WARN_ON(hsotg->driver); | 2871 | WARN_ON(hsotg->driver); |
| 2893 | 2872 | ||
| 2894 | driver->driver.bus = NULL; | 2873 | driver->driver.bus = NULL; |
| @@ -2905,11 +2884,22 @@ static int s3c_hsotg_udc_start(struct usb_gadget *gadget, | |||
| 2905 | goto err; | 2884 | goto err; |
| 2906 | } | 2885 | } |
| 2907 | 2886 | ||
| 2908 | hsotg->last_rst = jiffies; | 2887 | s3c_hsotg_phy_enable(hsotg); |
| 2888 | |||
| 2889 | spin_lock_irqsave(&hsotg->lock, flags); | ||
| 2890 | s3c_hsotg_init(hsotg); | ||
| 2891 | s3c_hsotg_core_init_disconnected(hsotg); | ||
| 2892 | hsotg->enabled = 0; | ||
| 2893 | spin_unlock_irqrestore(&hsotg->lock, flags); | ||
| 2894 | |||
| 2909 | dev_info(hsotg->dev, "bound driver %s\n", driver->driver.name); | 2895 | dev_info(hsotg->dev, "bound driver %s\n", driver->driver.name); |
| 2896 | |||
| 2897 | mutex_unlock(&hsotg->init_mutex); | ||
| 2898 | |||
| 2910 | return 0; | 2899 | return 0; |
| 2911 | 2900 | ||
| 2912 | err: | 2901 | err: |
| 2902 | mutex_unlock(&hsotg->init_mutex); | ||
| 2913 | hsotg->driver = NULL; | 2903 | hsotg->driver = NULL; |
| 2914 | return ret; | 2904 | return ret; |
| 2915 | } | 2905 | } |
| @@ -2921,16 +2911,17 @@ err: | |||
| 2921 | * | 2911 | * |
| 2922 | * Stop udc hw block and stay tunned for future transmissions | 2912 | * Stop udc hw block and stay tunned for future transmissions |
| 2923 | */ | 2913 | */ |
| 2924 | static int s3c_hsotg_udc_stop(struct usb_gadget *gadget, | 2914 | static int s3c_hsotg_udc_stop(struct usb_gadget *gadget) |
| 2925 | struct usb_gadget_driver *driver) | ||
| 2926 | { | 2915 | { |
| 2927 | struct s3c_hsotg *hsotg = to_hsotg(gadget); | 2916 | struct dwc2_hsotg *hsotg = to_hsotg(gadget); |
| 2928 | unsigned long flags = 0; | 2917 | unsigned long flags = 0; |
| 2929 | int ep; | 2918 | int ep; |
| 2930 | 2919 | ||
| 2931 | if (!hsotg) | 2920 | if (!hsotg) |
| 2932 | return -ENODEV; | 2921 | return -ENODEV; |
| 2933 | 2922 | ||
| 2923 | mutex_lock(&hsotg->init_mutex); | ||
| 2924 | |||
| 2934 | /* all endpoints should be shutdown */ | 2925 | /* all endpoints should be shutdown */ |
| 2935 | for (ep = 1; ep < hsotg->num_of_eps; ep++) | 2926 | for (ep = 1; ep < hsotg->num_of_eps; ep++) |
| 2936 | s3c_hsotg_ep_disable(&hsotg->eps[ep].ep); | 2927 | s3c_hsotg_ep_disable(&hsotg->eps[ep].ep); |
| @@ -2939,13 +2930,18 @@ static int s3c_hsotg_udc_stop(struct usb_gadget *gadget, | |||
| 2939 | 2930 | ||
| 2940 | hsotg->driver = NULL; | 2931 | hsotg->driver = NULL; |
| 2941 | hsotg->gadget.speed = USB_SPEED_UNKNOWN; | 2932 | hsotg->gadget.speed = USB_SPEED_UNKNOWN; |
| 2933 | hsotg->enabled = 0; | ||
| 2942 | 2934 | ||
| 2943 | spin_unlock_irqrestore(&hsotg->lock, flags); | 2935 | spin_unlock_irqrestore(&hsotg->lock, flags); |
| 2944 | 2936 | ||
| 2937 | s3c_hsotg_phy_disable(hsotg); | ||
| 2938 | |||
| 2945 | regulator_bulk_disable(ARRAY_SIZE(hsotg->supplies), hsotg->supplies); | 2939 | regulator_bulk_disable(ARRAY_SIZE(hsotg->supplies), hsotg->supplies); |
| 2946 | 2940 | ||
| 2947 | clk_disable(hsotg->clk); | 2941 | clk_disable(hsotg->clk); |
| 2948 | 2942 | ||
| 2943 | mutex_unlock(&hsotg->init_mutex); | ||
| 2944 | |||
| 2949 | return 0; | 2945 | return 0; |
| 2950 | } | 2946 | } |
| 2951 | 2947 | ||
| @@ -2969,23 +2965,26 @@ static int s3c_hsotg_gadget_getframe(struct usb_gadget *gadget) | |||
| 2969 | */ | 2965 | */ |
| 2970 | static int s3c_hsotg_pullup(struct usb_gadget *gadget, int is_on) | 2966 | static int s3c_hsotg_pullup(struct usb_gadget *gadget, int is_on) |
| 2971 | { | 2967 | { |
| 2972 | struct s3c_hsotg *hsotg = to_hsotg(gadget); | 2968 | struct dwc2_hsotg *hsotg = to_hsotg(gadget); |
| 2973 | unsigned long flags = 0; | 2969 | unsigned long flags = 0; |
| 2974 | 2970 | ||
| 2975 | dev_dbg(hsotg->dev, "%s: is_on: %d\n", __func__, is_on); | 2971 | dev_dbg(hsotg->dev, "%s: is_on: %d\n", __func__, is_on); |
| 2976 | 2972 | ||
| 2973 | mutex_lock(&hsotg->init_mutex); | ||
| 2977 | spin_lock_irqsave(&hsotg->lock, flags); | 2974 | spin_lock_irqsave(&hsotg->lock, flags); |
| 2978 | if (is_on) { | 2975 | if (is_on) { |
| 2979 | s3c_hsotg_phy_enable(hsotg); | ||
| 2980 | clk_enable(hsotg->clk); | 2976 | clk_enable(hsotg->clk); |
| 2981 | s3c_hsotg_core_init(hsotg); | 2977 | hsotg->enabled = 1; |
| 2978 | s3c_hsotg_core_connect(hsotg); | ||
| 2982 | } else { | 2979 | } else { |
| 2980 | s3c_hsotg_core_disconnect(hsotg); | ||
| 2981 | hsotg->enabled = 0; | ||
| 2983 | clk_disable(hsotg->clk); | 2982 | clk_disable(hsotg->clk); |
| 2984 | s3c_hsotg_phy_disable(hsotg); | ||
| 2985 | } | 2983 | } |
| 2986 | 2984 | ||
| 2987 | hsotg->gadget.speed = USB_SPEED_UNKNOWN; | 2985 | hsotg->gadget.speed = USB_SPEED_UNKNOWN; |
| 2988 | spin_unlock_irqrestore(&hsotg->lock, flags); | 2986 | spin_unlock_irqrestore(&hsotg->lock, flags); |
| 2987 | mutex_unlock(&hsotg->init_mutex); | ||
| 2989 | 2988 | ||
| 2990 | return 0; | 2989 | return 0; |
| 2991 | } | 2990 | } |
| @@ -3007,7 +3006,7 @@ static const struct usb_gadget_ops s3c_hsotg_gadget_ops = { | |||
| 3007 | * creation) to give to the gadget driver. Setup the endpoint name, any | 3006 | * creation) to give to the gadget driver. Setup the endpoint name, any |
| 3008 | * direction information and other state that may be required. | 3007 | * direction information and other state that may be required. |
| 3009 | */ | 3008 | */ |
| 3010 | static void s3c_hsotg_initep(struct s3c_hsotg *hsotg, | 3009 | static void s3c_hsotg_initep(struct dwc2_hsotg *hsotg, |
| 3011 | struct s3c_hsotg_ep *hs_ep, | 3010 | struct s3c_hsotg_ep *hs_ep, |
| 3012 | int epnum) | 3011 | int epnum) |
| 3013 | { | 3012 | { |
| @@ -3056,7 +3055,7 @@ static void s3c_hsotg_initep(struct s3c_hsotg *hsotg, | |||
| 3056 | * | 3055 | * |
| 3057 | * Read the USB core HW configuration registers | 3056 | * Read the USB core HW configuration registers |
| 3058 | */ | 3057 | */ |
| 3059 | static void s3c_hsotg_hw_cfg(struct s3c_hsotg *hsotg) | 3058 | static void s3c_hsotg_hw_cfg(struct dwc2_hsotg *hsotg) |
| 3060 | { | 3059 | { |
| 3061 | u32 cfg2, cfg3, cfg4; | 3060 | u32 cfg2, cfg3, cfg4; |
| 3062 | /* check hardware configuration */ | 3061 | /* check hardware configuration */ |
| @@ -3080,7 +3079,7 @@ static void s3c_hsotg_hw_cfg(struct s3c_hsotg *hsotg) | |||
| 3080 | * s3c_hsotg_dump - dump state of the udc | 3079 | * s3c_hsotg_dump - dump state of the udc |
| 3081 | * @param: The device state | 3080 | * @param: The device state |
| 3082 | */ | 3081 | */ |
| 3083 | static void s3c_hsotg_dump(struct s3c_hsotg *hsotg) | 3082 | static void s3c_hsotg_dump(struct dwc2_hsotg *hsotg) |
| 3084 | { | 3083 | { |
| 3085 | #ifdef DEBUG | 3084 | #ifdef DEBUG |
| 3086 | struct device *dev = hsotg->dev; | 3085 | struct device *dev = hsotg->dev; |
| @@ -3139,7 +3138,7 @@ static void s3c_hsotg_dump(struct s3c_hsotg *hsotg) | |||
| 3139 | */ | 3138 | */ |
| 3140 | static int state_show(struct seq_file *seq, void *v) | 3139 | static int state_show(struct seq_file *seq, void *v) |
| 3141 | { | 3140 | { |
| 3142 | struct s3c_hsotg *hsotg = seq->private; | 3141 | struct dwc2_hsotg *hsotg = seq->private; |
| 3143 | void __iomem *regs = hsotg->regs; | 3142 | void __iomem *regs = hsotg->regs; |
| 3144 | int idx; | 3143 | int idx; |
| 3145 | 3144 | ||
| @@ -3209,7 +3208,7 @@ static const struct file_operations state_fops = { | |||
| 3209 | */ | 3208 | */ |
| 3210 | static int fifo_show(struct seq_file *seq, void *v) | 3209 | static int fifo_show(struct seq_file *seq, void *v) |
| 3211 | { | 3210 | { |
| 3212 | struct s3c_hsotg *hsotg = seq->private; | 3211 | struct dwc2_hsotg *hsotg = seq->private; |
| 3213 | void __iomem *regs = hsotg->regs; | 3212 | void __iomem *regs = hsotg->regs; |
| 3214 | u32 val; | 3213 | u32 val; |
| 3215 | int idx; | 3214 | int idx; |
| @@ -3265,7 +3264,7 @@ static const char *decode_direction(int is_in) | |||
| 3265 | static int ep_show(struct seq_file *seq, void *v) | 3264 | static int ep_show(struct seq_file *seq, void *v) |
| 3266 | { | 3265 | { |
| 3267 | struct s3c_hsotg_ep *ep = seq->private; | 3266 | struct s3c_hsotg_ep *ep = seq->private; |
| 3268 | struct s3c_hsotg *hsotg = ep->parent; | 3267 | struct dwc2_hsotg *hsotg = ep->parent; |
| 3269 | struct s3c_hsotg_req *req; | 3268 | struct s3c_hsotg_req *req; |
| 3270 | void __iomem *regs = hsotg->regs; | 3269 | void __iomem *regs = hsotg->regs; |
| 3271 | int index = ep->index; | 3270 | int index = ep->index; |
| @@ -3342,7 +3341,7 @@ static const struct file_operations ep_fops = { | |||
| 3342 | * with the same name as the device itself, in case we end up | 3341 | * with the same name as the device itself, in case we end up |
| 3343 | * with multiple blocks in future systems. | 3342 | * with multiple blocks in future systems. |
| 3344 | */ | 3343 | */ |
| 3345 | static void s3c_hsotg_create_debug(struct s3c_hsotg *hsotg) | 3344 | static void s3c_hsotg_create_debug(struct dwc2_hsotg *hsotg) |
| 3346 | { | 3345 | { |
| 3347 | struct dentry *root; | 3346 | struct dentry *root; |
| 3348 | unsigned epidx; | 3347 | unsigned epidx; |
| @@ -3388,7 +3387,7 @@ static void s3c_hsotg_create_debug(struct s3c_hsotg *hsotg) | |||
| 3388 | * | 3387 | * |
| 3389 | * Cleanup (remove) the debugfs files for use on module exit. | 3388 | * Cleanup (remove) the debugfs files for use on module exit. |
| 3390 | */ | 3389 | */ |
| 3391 | static void s3c_hsotg_delete_debug(struct s3c_hsotg *hsotg) | 3390 | static void s3c_hsotg_delete_debug(struct dwc2_hsotg *hsotg) |
| 3392 | { | 3391 | { |
| 3393 | unsigned epidx; | 3392 | unsigned epidx; |
| 3394 | 3393 | ||
| @@ -3403,27 +3402,21 @@ static void s3c_hsotg_delete_debug(struct s3c_hsotg *hsotg) | |||
| 3403 | } | 3402 | } |
| 3404 | 3403 | ||
| 3405 | /** | 3404 | /** |
| 3406 | * s3c_hsotg_probe - probe function for hsotg driver | 3405 | * dwc2_gadget_init - init function for gadget |
| 3407 | * @pdev: The platform information for the driver | 3406 | * @dwc2: The data structure for the DWC2 driver. |
| 3407 | * @irq: The IRQ number for the controller. | ||
| 3408 | */ | 3408 | */ |
| 3409 | 3409 | int dwc2_gadget_init(struct dwc2_hsotg *hsotg, int irq) | |
| 3410 | static int s3c_hsotg_probe(struct platform_device *pdev) | ||
| 3411 | { | 3410 | { |
| 3412 | struct s3c_hsotg_plat *plat = dev_get_platdata(&pdev->dev); | 3411 | struct device *dev = hsotg->dev; |
| 3412 | struct s3c_hsotg_plat *plat = dev->platform_data; | ||
| 3413 | struct phy *phy; | 3413 | struct phy *phy; |
| 3414 | struct usb_phy *uphy; | 3414 | struct usb_phy *uphy; |
| 3415 | struct device *dev = &pdev->dev; | ||
| 3416 | struct s3c_hsotg_ep *eps; | 3415 | struct s3c_hsotg_ep *eps; |
| 3417 | struct s3c_hsotg *hsotg; | ||
| 3418 | struct resource *res; | ||
| 3419 | int epnum; | 3416 | int epnum; |
| 3420 | int ret; | 3417 | int ret; |
| 3421 | int i; | 3418 | int i; |
| 3422 | 3419 | ||
| 3423 | hsotg = devm_kzalloc(&pdev->dev, sizeof(struct s3c_hsotg), GFP_KERNEL); | ||
| 3424 | if (!hsotg) | ||
| 3425 | return -ENOMEM; | ||
| 3426 | |||
| 3427 | /* Set default UTMI width */ | 3420 | /* Set default UTMI width */ |
| 3428 | hsotg->phyif = GUSBCFG_PHYIF16; | 3421 | hsotg->phyif = GUSBCFG_PHYIF16; |
| 3429 | 3422 | ||
| @@ -3431,14 +3424,14 @@ static int s3c_hsotg_probe(struct platform_device *pdev) | |||
| 3431 | * Attempt to find a generic PHY, then look for an old style | 3424 | * Attempt to find a generic PHY, then look for an old style |
| 3432 | * USB PHY, finally fall back to pdata | 3425 | * USB PHY, finally fall back to pdata |
| 3433 | */ | 3426 | */ |
| 3434 | phy = devm_phy_get(&pdev->dev, "usb2-phy"); | 3427 | phy = devm_phy_get(dev, "usb2-phy"); |
| 3435 | if (IS_ERR(phy)) { | 3428 | if (IS_ERR(phy)) { |
| 3436 | uphy = devm_usb_get_phy(dev, USB_PHY_TYPE_USB2); | 3429 | uphy = devm_usb_get_phy(dev, USB_PHY_TYPE_USB2); |
| 3437 | if (IS_ERR(uphy)) { | 3430 | if (IS_ERR(uphy)) { |
| 3438 | /* Fallback for pdata */ | 3431 | /* Fallback for pdata */ |
| 3439 | plat = dev_get_platdata(&pdev->dev); | 3432 | plat = dev_get_platdata(dev); |
| 3440 | if (!plat) { | 3433 | if (!plat) { |
| 3441 | dev_err(&pdev->dev, | 3434 | dev_err(dev, |
| 3442 | "no platform data or transceiver defined\n"); | 3435 | "no platform data or transceiver defined\n"); |
| 3443 | return -EPROBE_DEFER; | 3436 | return -EPROBE_DEFER; |
| 3444 | } | 3437 | } |
| @@ -3455,43 +3448,24 @@ static int s3c_hsotg_probe(struct platform_device *pdev) | |||
| 3455 | hsotg->phyif = GUSBCFG_PHYIF8; | 3448 | hsotg->phyif = GUSBCFG_PHYIF8; |
| 3456 | } | 3449 | } |
| 3457 | 3450 | ||
| 3458 | hsotg->dev = dev; | 3451 | hsotg->clk = devm_clk_get(dev, "otg"); |
| 3459 | |||
| 3460 | hsotg->clk = devm_clk_get(&pdev->dev, "otg"); | ||
| 3461 | if (IS_ERR(hsotg->clk)) { | 3452 | if (IS_ERR(hsotg->clk)) { |
| 3462 | dev_err(dev, "cannot get otg clock\n"); | 3453 | hsotg->clk = NULL; |
| 3463 | return PTR_ERR(hsotg->clk); | 3454 | dev_dbg(dev, "cannot get otg clock\n"); |
| 3464 | } | ||
| 3465 | |||
| 3466 | platform_set_drvdata(pdev, hsotg); | ||
| 3467 | |||
| 3468 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 3469 | |||
| 3470 | hsotg->regs = devm_ioremap_resource(&pdev->dev, res); | ||
| 3471 | if (IS_ERR(hsotg->regs)) { | ||
| 3472 | ret = PTR_ERR(hsotg->regs); | ||
| 3473 | goto err_clk; | ||
| 3474 | } | 3455 | } |
| 3475 | 3456 | ||
| 3476 | ret = platform_get_irq(pdev, 0); | ||
| 3477 | if (ret < 0) { | ||
| 3478 | dev_err(dev, "cannot find IRQ\n"); | ||
| 3479 | goto err_clk; | ||
| 3480 | } | ||
| 3481 | |||
| 3482 | spin_lock_init(&hsotg->lock); | ||
| 3483 | |||
| 3484 | hsotg->irq = ret; | ||
| 3485 | |||
| 3486 | dev_info(dev, "regs %p, irq %d\n", hsotg->regs, hsotg->irq); | ||
| 3487 | |||
| 3488 | hsotg->gadget.max_speed = USB_SPEED_HIGH; | 3457 | hsotg->gadget.max_speed = USB_SPEED_HIGH; |
| 3489 | hsotg->gadget.ops = &s3c_hsotg_gadget_ops; | 3458 | hsotg->gadget.ops = &s3c_hsotg_gadget_ops; |
| 3490 | hsotg->gadget.name = dev_name(dev); | 3459 | hsotg->gadget.name = dev_name(dev); |
| 3491 | 3460 | ||
| 3492 | /* reset the system */ | 3461 | /* reset the system */ |
| 3493 | 3462 | ||
| 3494 | clk_prepare_enable(hsotg->clk); | 3463 | ret = clk_prepare_enable(hsotg->clk); |
| 3464 | if (ret) { | ||
| 3465 | dev_err(dev, "failed to enable otg clk\n"); | ||
| 3466 | goto err_clk; | ||
| 3467 | } | ||
| 3468 | |||
| 3495 | 3469 | ||
| 3496 | /* regulators */ | 3470 | /* regulators */ |
| 3497 | 3471 | ||
| @@ -3509,7 +3483,7 @@ static int s3c_hsotg_probe(struct platform_device *pdev) | |||
| 3509 | hsotg->supplies); | 3483 | hsotg->supplies); |
| 3510 | 3484 | ||
| 3511 | if (ret) { | 3485 | if (ret) { |
| 3512 | dev_err(hsotg->dev, "failed to enable supplies: %d\n", ret); | 3486 | dev_err(dev, "failed to enable supplies: %d\n", ret); |
| 3513 | goto err_supplies; | 3487 | goto err_supplies; |
| 3514 | } | 3488 | } |
| 3515 | 3489 | ||
| @@ -3520,14 +3494,14 @@ static int s3c_hsotg_probe(struct platform_device *pdev) | |||
| 3520 | s3c_hsotg_hw_cfg(hsotg); | 3494 | s3c_hsotg_hw_cfg(hsotg); |
| 3521 | s3c_hsotg_init(hsotg); | 3495 | s3c_hsotg_init(hsotg); |
| 3522 | 3496 | ||
| 3523 | ret = devm_request_irq(&pdev->dev, hsotg->irq, s3c_hsotg_irq, 0, | 3497 | ret = devm_request_irq(hsotg->dev, irq, s3c_hsotg_irq, IRQF_SHARED, |
| 3524 | dev_name(dev), hsotg); | 3498 | dev_name(hsotg->dev), hsotg); |
| 3525 | if (ret < 0) { | 3499 | if (ret < 0) { |
| 3526 | s3c_hsotg_phy_disable(hsotg); | 3500 | s3c_hsotg_phy_disable(hsotg); |
| 3527 | clk_disable_unprepare(hsotg->clk); | 3501 | clk_disable_unprepare(hsotg->clk); |
| 3528 | regulator_bulk_disable(ARRAY_SIZE(hsotg->supplies), | 3502 | regulator_bulk_disable(ARRAY_SIZE(hsotg->supplies), |
| 3529 | hsotg->supplies); | 3503 | hsotg->supplies); |
| 3530 | dev_err(dev, "cannot claim IRQ\n"); | 3504 | dev_err(dev, "cannot claim IRQ for gadget\n"); |
| 3531 | goto err_clk; | 3505 | goto err_clk; |
| 3532 | } | 3506 | } |
| 3533 | 3507 | ||
| @@ -3573,11 +3547,11 @@ static int s3c_hsotg_probe(struct platform_device *pdev) | |||
| 3573 | ret = regulator_bulk_disable(ARRAY_SIZE(hsotg->supplies), | 3547 | ret = regulator_bulk_disable(ARRAY_SIZE(hsotg->supplies), |
| 3574 | hsotg->supplies); | 3548 | hsotg->supplies); |
| 3575 | if (ret) { | 3549 | if (ret) { |
| 3576 | dev_err(hsotg->dev, "failed to disable supplies: %d\n", ret); | 3550 | dev_err(dev, "failed to disable supplies: %d\n", ret); |
| 3577 | goto err_ep_mem; | 3551 | goto err_ep_mem; |
| 3578 | } | 3552 | } |
| 3579 | 3553 | ||
| 3580 | ret = usb_add_gadget_udc(&pdev->dev, &hsotg->gadget); | 3554 | ret = usb_add_gadget_udc(dev, &hsotg->gadget); |
| 3581 | if (ret) | 3555 | if (ret) |
| 3582 | goto err_ep_mem; | 3556 | goto err_ep_mem; |
| 3583 | 3557 | ||
| @@ -3596,47 +3570,44 @@ err_clk: | |||
| 3596 | 3570 | ||
| 3597 | return ret; | 3571 | return ret; |
| 3598 | } | 3572 | } |
| 3573 | EXPORT_SYMBOL_GPL(dwc2_gadget_init); | ||
| 3599 | 3574 | ||
| 3600 | /** | 3575 | /** |
| 3601 | * s3c_hsotg_remove - remove function for hsotg driver | 3576 | * s3c_hsotg_remove - remove function for hsotg driver |
| 3602 | * @pdev: The platform information for the driver | 3577 | * @pdev: The platform information for the driver |
| 3603 | */ | 3578 | */ |
| 3604 | static int s3c_hsotg_remove(struct platform_device *pdev) | 3579 | int s3c_hsotg_remove(struct dwc2_hsotg *hsotg) |
| 3605 | { | 3580 | { |
| 3606 | struct s3c_hsotg *hsotg = platform_get_drvdata(pdev); | ||
| 3607 | |||
| 3608 | usb_del_gadget_udc(&hsotg->gadget); | 3581 | usb_del_gadget_udc(&hsotg->gadget); |
| 3609 | |||
| 3610 | s3c_hsotg_delete_debug(hsotg); | 3582 | s3c_hsotg_delete_debug(hsotg); |
| 3611 | |||
| 3612 | if (hsotg->driver) { | ||
| 3613 | /* should have been done already by driver model core */ | ||
| 3614 | usb_gadget_unregister_driver(hsotg->driver); | ||
| 3615 | } | ||
| 3616 | |||
| 3617 | clk_disable_unprepare(hsotg->clk); | 3583 | clk_disable_unprepare(hsotg->clk); |
| 3618 | 3584 | ||
| 3619 | return 0; | 3585 | return 0; |
| 3620 | } | 3586 | } |
| 3587 | EXPORT_SYMBOL_GPL(s3c_hsotg_remove); | ||
| 3621 | 3588 | ||
| 3622 | static int s3c_hsotg_suspend(struct platform_device *pdev, pm_message_t state) | 3589 | int s3c_hsotg_suspend(struct dwc2_hsotg *hsotg) |
| 3623 | { | 3590 | { |
| 3624 | struct s3c_hsotg *hsotg = platform_get_drvdata(pdev); | ||
| 3625 | unsigned long flags; | 3591 | unsigned long flags; |
| 3626 | int ret = 0; | 3592 | int ret = 0; |
| 3627 | 3593 | ||
| 3628 | if (hsotg->driver) | 3594 | mutex_lock(&hsotg->init_mutex); |
| 3595 | |||
| 3596 | if (hsotg->driver) { | ||
| 3597 | int ep; | ||
| 3598 | |||
| 3629 | dev_info(hsotg->dev, "suspending usb gadget %s\n", | 3599 | dev_info(hsotg->dev, "suspending usb gadget %s\n", |
| 3630 | hsotg->driver->driver.name); | 3600 | hsotg->driver->driver.name); |
| 3631 | 3601 | ||
| 3632 | spin_lock_irqsave(&hsotg->lock, flags); | 3602 | spin_lock_irqsave(&hsotg->lock, flags); |
| 3633 | s3c_hsotg_disconnect(hsotg); | 3603 | if (hsotg->enabled) |
| 3634 | s3c_hsotg_phy_disable(hsotg); | 3604 | s3c_hsotg_core_disconnect(hsotg); |
| 3635 | hsotg->gadget.speed = USB_SPEED_UNKNOWN; | 3605 | s3c_hsotg_disconnect(hsotg); |
| 3636 | spin_unlock_irqrestore(&hsotg->lock, flags); | 3606 | hsotg->gadget.speed = USB_SPEED_UNKNOWN; |
| 3607 | spin_unlock_irqrestore(&hsotg->lock, flags); | ||
| 3608 | |||
| 3609 | s3c_hsotg_phy_disable(hsotg); | ||
| 3637 | 3610 | ||
| 3638 | if (hsotg->driver) { | ||
| 3639 | int ep; | ||
| 3640 | for (ep = 0; ep < hsotg->num_of_eps; ep++) | 3611 | for (ep = 0; ep < hsotg->num_of_eps; ep++) |
| 3641 | s3c_hsotg_ep_disable(&hsotg->eps[ep].ep); | 3612 | s3c_hsotg_ep_disable(&hsotg->eps[ep].ep); |
| 3642 | 3613 | ||
| @@ -3645,57 +3616,37 @@ static int s3c_hsotg_suspend(struct platform_device *pdev, pm_message_t state) | |||
| 3645 | clk_disable(hsotg->clk); | 3616 | clk_disable(hsotg->clk); |
| 3646 | } | 3617 | } |
| 3647 | 3618 | ||
| 3619 | mutex_unlock(&hsotg->init_mutex); | ||
| 3620 | |||
| 3648 | return ret; | 3621 | return ret; |
| 3649 | } | 3622 | } |
| 3623 | EXPORT_SYMBOL_GPL(s3c_hsotg_suspend); | ||
| 3650 | 3624 | ||
| 3651 | static int s3c_hsotg_resume(struct platform_device *pdev) | 3625 | int s3c_hsotg_resume(struct dwc2_hsotg *hsotg) |
| 3652 | { | 3626 | { |
| 3653 | struct s3c_hsotg *hsotg = platform_get_drvdata(pdev); | ||
| 3654 | unsigned long flags; | 3627 | unsigned long flags; |
| 3655 | int ret = 0; | 3628 | int ret = 0; |
| 3656 | 3629 | ||
| 3630 | mutex_lock(&hsotg->init_mutex); | ||
| 3631 | |||
| 3657 | if (hsotg->driver) { | 3632 | if (hsotg->driver) { |
| 3658 | dev_info(hsotg->dev, "resuming usb gadget %s\n", | 3633 | dev_info(hsotg->dev, "resuming usb gadget %s\n", |
| 3659 | hsotg->driver->driver.name); | 3634 | hsotg->driver->driver.name); |
| 3660 | 3635 | ||
| 3661 | clk_enable(hsotg->clk); | 3636 | clk_enable(hsotg->clk); |
| 3662 | ret = regulator_bulk_enable(ARRAY_SIZE(hsotg->supplies), | 3637 | ret = regulator_bulk_enable(ARRAY_SIZE(hsotg->supplies), |
| 3663 | hsotg->supplies); | 3638 | hsotg->supplies); |
| 3664 | } | ||
| 3665 | 3639 | ||
| 3666 | spin_lock_irqsave(&hsotg->lock, flags); | 3640 | s3c_hsotg_phy_enable(hsotg); |
| 3667 | hsotg->last_rst = jiffies; | 3641 | |
| 3668 | s3c_hsotg_phy_enable(hsotg); | 3642 | spin_lock_irqsave(&hsotg->lock, flags); |
| 3669 | s3c_hsotg_core_init(hsotg); | 3643 | s3c_hsotg_core_init_disconnected(hsotg); |
| 3670 | spin_unlock_irqrestore(&hsotg->lock, flags); | 3644 | if (hsotg->enabled) |
| 3645 | s3c_hsotg_core_connect(hsotg); | ||
| 3646 | spin_unlock_irqrestore(&hsotg->lock, flags); | ||
| 3647 | } | ||
| 3648 | mutex_unlock(&hsotg->init_mutex); | ||
| 3671 | 3649 | ||
| 3672 | return ret; | 3650 | return ret; |
| 3673 | } | 3651 | } |
| 3674 | 3652 | EXPORT_SYMBOL_GPL(s3c_hsotg_resume); | |
| 3675 | #ifdef CONFIG_OF | ||
| 3676 | static const struct of_device_id s3c_hsotg_of_ids[] = { | ||
| 3677 | { .compatible = "samsung,s3c6400-hsotg", }, | ||
| 3678 | { .compatible = "snps,dwc2", }, | ||
| 3679 | { /* sentinel */ } | ||
| 3680 | }; | ||
| 3681 | MODULE_DEVICE_TABLE(of, s3c_hsotg_of_ids); | ||
| 3682 | #endif | ||
| 3683 | |||
| 3684 | static struct platform_driver s3c_hsotg_driver = { | ||
| 3685 | .driver = { | ||
| 3686 | .name = "s3c-hsotg", | ||
| 3687 | .owner = THIS_MODULE, | ||
| 3688 | .of_match_table = of_match_ptr(s3c_hsotg_of_ids), | ||
| 3689 | }, | ||
| 3690 | .probe = s3c_hsotg_probe, | ||
| 3691 | .remove = s3c_hsotg_remove, | ||
| 3692 | .suspend = s3c_hsotg_suspend, | ||
| 3693 | .resume = s3c_hsotg_resume, | ||
| 3694 | }; | ||
| 3695 | |||
| 3696 | module_platform_driver(s3c_hsotg_driver); | ||
| 3697 | |||
| 3698 | MODULE_DESCRIPTION("Samsung S3C USB High-speed/OtG device"); | ||
| 3699 | MODULE_AUTHOR("Ben Dooks <ben@simtec.co.uk>"); | ||
| 3700 | MODULE_LICENSE("GPL"); | ||
| 3701 | MODULE_ALIAS("platform:s3c-hsotg"); | ||
diff --git a/drivers/usb/dwc2/hcd.c b/drivers/usb/dwc2/hcd.c index 0a0e6f0ad15f..a0cd9db6f4cd 100644 --- a/drivers/usb/dwc2/hcd.c +++ b/drivers/usb/dwc2/hcd.c | |||
| @@ -1371,6 +1371,8 @@ static void dwc2_conn_id_status_change(struct work_struct *work) | |||
| 1371 | hsotg->op_state = OTG_STATE_B_PERIPHERAL; | 1371 | hsotg->op_state = OTG_STATE_B_PERIPHERAL; |
| 1372 | dwc2_core_init(hsotg, false, -1); | 1372 | dwc2_core_init(hsotg, false, -1); |
| 1373 | dwc2_enable_global_interrupts(hsotg); | 1373 | dwc2_enable_global_interrupts(hsotg); |
| 1374 | s3c_hsotg_core_init_disconnected(hsotg); | ||
| 1375 | s3c_hsotg_core_connect(hsotg); | ||
| 1374 | } else { | 1376 | } else { |
| 1375 | /* A-Device connector (Host Mode) */ | 1377 | /* A-Device connector (Host Mode) */ |
| 1376 | dev_dbg(hsotg->dev, "connId A\n"); | 1378 | dev_dbg(hsotg->dev, "connId A\n"); |
| @@ -1471,6 +1473,30 @@ static void dwc2_port_suspend(struct dwc2_hsotg *hsotg, u16 windex) | |||
| 1471 | } | 1473 | } |
| 1472 | } | 1474 | } |
| 1473 | 1475 | ||
| 1476 | static void dwc2_port_resume(struct dwc2_hsotg *hsotg) | ||
| 1477 | { | ||
| 1478 | u32 hprt0; | ||
| 1479 | |||
| 1480 | /* After clear the Stop PHY clock bit, we should wait for a moment | ||
| 1481 | * for PLL work stable with clock output. | ||
| 1482 | */ | ||
| 1483 | writel(0, hsotg->regs + PCGCTL); | ||
| 1484 | usleep_range(2000, 4000); | ||
| 1485 | |||
| 1486 | hprt0 = dwc2_read_hprt0(hsotg); | ||
| 1487 | hprt0 |= HPRT0_RES; | ||
| 1488 | writel(hprt0, hsotg->regs + HPRT0); | ||
| 1489 | hprt0 &= ~HPRT0_SUSP; | ||
| 1490 | /* according to USB2.0 Spec 7.1.7.7, the host must send the resume | ||
| 1491 | * signal for at least 20ms | ||
| 1492 | */ | ||
| 1493 | usleep_range(20000, 25000); | ||
| 1494 | |||
| 1495 | hprt0 &= ~HPRT0_RES; | ||
| 1496 | writel(hprt0, hsotg->regs + HPRT0); | ||
| 1497 | hsotg->lx_state = DWC2_L0; | ||
| 1498 | } | ||
| 1499 | |||
| 1474 | /* Handles hub class-specific requests */ | 1500 | /* Handles hub class-specific requests */ |
| 1475 | static int dwc2_hcd_hub_control(struct dwc2_hsotg *hsotg, u16 typereq, | 1501 | static int dwc2_hcd_hub_control(struct dwc2_hsotg *hsotg, u16 typereq, |
| 1476 | u16 wvalue, u16 windex, char *buf, u16 wlength) | 1502 | u16 wvalue, u16 windex, char *buf, u16 wlength) |
| @@ -1516,17 +1542,7 @@ static int dwc2_hcd_hub_control(struct dwc2_hsotg *hsotg, u16 typereq, | |||
| 1516 | case USB_PORT_FEAT_SUSPEND: | 1542 | case USB_PORT_FEAT_SUSPEND: |
| 1517 | dev_dbg(hsotg->dev, | 1543 | dev_dbg(hsotg->dev, |
| 1518 | "ClearPortFeature USB_PORT_FEAT_SUSPEND\n"); | 1544 | "ClearPortFeature USB_PORT_FEAT_SUSPEND\n"); |
| 1519 | writel(0, hsotg->regs + PCGCTL); | 1545 | dwc2_port_resume(hsotg); |
| 1520 | usleep_range(20000, 40000); | ||
| 1521 | |||
| 1522 | hprt0 = dwc2_read_hprt0(hsotg); | ||
| 1523 | hprt0 |= HPRT0_RES; | ||
| 1524 | writel(hprt0, hsotg->regs + HPRT0); | ||
| 1525 | hprt0 &= ~HPRT0_SUSP; | ||
| 1526 | usleep_range(100000, 150000); | ||
| 1527 | |||
| 1528 | hprt0 &= ~HPRT0_RES; | ||
| 1529 | writel(hprt0, hsotg->regs + HPRT0); | ||
| 1530 | break; | 1546 | break; |
| 1531 | 1547 | ||
| 1532 | case USB_PORT_FEAT_POWER: | 1548 | case USB_PORT_FEAT_POWER: |
| @@ -2299,6 +2315,55 @@ static void _dwc2_hcd_stop(struct usb_hcd *hcd) | |||
| 2299 | usleep_range(1000, 3000); | 2315 | usleep_range(1000, 3000); |
| 2300 | } | 2316 | } |
| 2301 | 2317 | ||
| 2318 | static int _dwc2_hcd_suspend(struct usb_hcd *hcd) | ||
| 2319 | { | ||
| 2320 | struct dwc2_hsotg *hsotg = dwc2_hcd_to_hsotg(hcd); | ||
| 2321 | u32 hprt0; | ||
| 2322 | |||
| 2323 | if (!((hsotg->op_state == OTG_STATE_B_HOST) || | ||
| 2324 | (hsotg->op_state == OTG_STATE_A_HOST))) | ||
| 2325 | return 0; | ||
| 2326 | |||
| 2327 | /* TODO: We get into suspend from 'on' state, maybe we need to do | ||
| 2328 | * something if we get here from DWC2_L1(LPM sleep) state one day. | ||
| 2329 | */ | ||
| 2330 | if (hsotg->lx_state != DWC2_L0) | ||
| 2331 | return 0; | ||
| 2332 | |||
| 2333 | hprt0 = dwc2_read_hprt0(hsotg); | ||
| 2334 | if (hprt0 & HPRT0_CONNSTS) { | ||
| 2335 | dwc2_port_suspend(hsotg, 1); | ||
| 2336 | } else { | ||
| 2337 | u32 pcgctl = readl(hsotg->regs + PCGCTL); | ||
| 2338 | |||
| 2339 | pcgctl |= PCGCTL_STOPPCLK; | ||
| 2340 | writel(pcgctl, hsotg->regs + PCGCTL); | ||
| 2341 | } | ||
| 2342 | |||
| 2343 | return 0; | ||
| 2344 | } | ||
| 2345 | |||
| 2346 | static int _dwc2_hcd_resume(struct usb_hcd *hcd) | ||
| 2347 | { | ||
| 2348 | struct dwc2_hsotg *hsotg = dwc2_hcd_to_hsotg(hcd); | ||
| 2349 | u32 hprt0; | ||
| 2350 | |||
| 2351 | if (!((hsotg->op_state == OTG_STATE_B_HOST) || | ||
| 2352 | (hsotg->op_state == OTG_STATE_A_HOST))) | ||
| 2353 | return 0; | ||
| 2354 | |||
| 2355 | if (hsotg->lx_state != DWC2_L2) | ||
| 2356 | return 0; | ||
| 2357 | |||
| 2358 | hprt0 = dwc2_read_hprt0(hsotg); | ||
| 2359 | if ((hprt0 & HPRT0_CONNSTS) && (hprt0 & HPRT0_SUSP)) | ||
| 2360 | dwc2_port_resume(hsotg); | ||
| 2361 | else | ||
| 2362 | writel(0, hsotg->regs + PCGCTL); | ||
| 2363 | |||
| 2364 | return 0; | ||
| 2365 | } | ||
| 2366 | |||
| 2302 | /* Returns the current frame number */ | 2367 | /* Returns the current frame number */ |
| 2303 | static int _dwc2_hcd_get_frame_number(struct usb_hcd *hcd) | 2368 | static int _dwc2_hcd_get_frame_number(struct usb_hcd *hcd) |
| 2304 | { | 2369 | { |
| @@ -2669,6 +2734,9 @@ static struct hc_driver dwc2_hc_driver = { | |||
| 2669 | .hub_status_data = _dwc2_hcd_hub_status_data, | 2734 | .hub_status_data = _dwc2_hcd_hub_status_data, |
| 2670 | .hub_control = _dwc2_hcd_hub_control, | 2735 | .hub_control = _dwc2_hcd_hub_control, |
| 2671 | .clear_tt_buffer_complete = _dwc2_hcd_clear_tt_buffer_complete, | 2736 | .clear_tt_buffer_complete = _dwc2_hcd_clear_tt_buffer_complete, |
| 2737 | |||
| 2738 | .bus_suspend = _dwc2_hcd_suspend, | ||
| 2739 | .bus_resume = _dwc2_hcd_resume, | ||
| 2672 | }; | 2740 | }; |
| 2673 | 2741 | ||
| 2674 | /* | 2742 | /* |
| @@ -2778,6 +2846,9 @@ int dwc2_hcd_init(struct dwc2_hsotg *hsotg, int irq, | |||
| 2778 | int i, num_channels; | 2846 | int i, num_channels; |
| 2779 | int retval; | 2847 | int retval; |
| 2780 | 2848 | ||
| 2849 | if (usb_disabled()) | ||
| 2850 | return -ENODEV; | ||
| 2851 | |||
| 2781 | dev_dbg(hsotg->dev, "DWC OTG HCD INIT\n"); | 2852 | dev_dbg(hsotg->dev, "DWC OTG HCD INIT\n"); |
| 2782 | 2853 | ||
| 2783 | /* Detect config values from hardware */ | 2854 | /* Detect config values from hardware */ |
| @@ -2839,7 +2910,6 @@ int dwc2_hcd_init(struct dwc2_hsotg *hsotg, int irq, | |||
| 2839 | 2910 | ||
| 2840 | hcd->has_tt = 1; | 2911 | hcd->has_tt = 1; |
| 2841 | 2912 | ||
| 2842 | spin_lock_init(&hsotg->lock); | ||
| 2843 | ((struct wrapper_priv_data *) &hcd->hcd_priv)->hsotg = hsotg; | 2913 | ((struct wrapper_priv_data *) &hcd->hcd_priv)->hsotg = hsotg; |
| 2844 | hsotg->priv = hcd; | 2914 | hsotg->priv = hcd; |
| 2845 | 2915 | ||
diff --git a/drivers/usb/dwc2/hcd.h b/drivers/usb/dwc2/hcd.h index a12bb1538666..e69a843d8928 100644 --- a/drivers/usb/dwc2/hcd.h +++ b/drivers/usb/dwc2/hcd.h | |||
| @@ -668,9 +668,6 @@ extern irqreturn_t dwc2_handle_hcd_intr(struct dwc2_hsotg *hsotg); | |||
| 668 | */ | 668 | */ |
| 669 | extern void dwc2_hcd_stop(struct dwc2_hsotg *hsotg); | 669 | extern void dwc2_hcd_stop(struct dwc2_hsotg *hsotg); |
| 670 | 670 | ||
| 671 | extern void dwc2_hcd_start(struct dwc2_hsotg *hsotg); | ||
| 672 | extern void dwc2_hcd_disconnect(struct dwc2_hsotg *hsotg); | ||
| 673 | |||
| 674 | /** | 671 | /** |
| 675 | * dwc2_hcd_is_b_host() - Returns 1 if core currently is acting as B host, | 672 | * dwc2_hcd_is_b_host() - Returns 1 if core currently is acting as B host, |
| 676 | * and 0 otherwise | 673 | * and 0 otherwise |
| @@ -680,13 +677,6 @@ extern void dwc2_hcd_disconnect(struct dwc2_hsotg *hsotg); | |||
| 680 | extern int dwc2_hcd_is_b_host(struct dwc2_hsotg *hsotg); | 677 | extern int dwc2_hcd_is_b_host(struct dwc2_hsotg *hsotg); |
| 681 | 678 | ||
| 682 | /** | 679 | /** |
| 683 | * dwc2_hcd_get_frame_number() - Returns current frame number | ||
| 684 | * | ||
| 685 | * @hsotg: The DWC2 HCD | ||
| 686 | */ | ||
| 687 | extern int dwc2_hcd_get_frame_number(struct dwc2_hsotg *hsotg); | ||
| 688 | |||
| 689 | /** | ||
| 690 | * dwc2_hcd_dump_state() - Dumps hsotg state | 680 | * dwc2_hcd_dump_state() - Dumps hsotg state |
| 691 | * | 681 | * |
| 692 | * @hsotg: The DWC2 HCD | 682 | * @hsotg: The DWC2 HCD |
diff --git a/drivers/usb/dwc2/pci.c b/drivers/usb/dwc2/pci.c index c291fca5d21f..a4e724b0a62e 100644 --- a/drivers/usb/dwc2/pci.c +++ b/drivers/usb/dwc2/pci.c | |||
| @@ -141,6 +141,13 @@ static int dwc2_driver_probe(struct pci_dev *dev, | |||
| 141 | 141 | ||
| 142 | pci_set_master(dev); | 142 | pci_set_master(dev); |
| 143 | 143 | ||
| 144 | retval = devm_request_irq(hsotg->dev, dev->irq, | ||
| 145 | dwc2_handle_common_intr, IRQF_SHARED, | ||
| 146 | dev_name(hsotg->dev), hsotg); | ||
| 147 | if (retval) | ||
| 148 | return retval; | ||
| 149 | |||
| 150 | spin_lock_init(&hsotg->lock); | ||
| 144 | retval = dwc2_hcd_init(hsotg, dev->irq, &dwc2_module_params); | 151 | retval = dwc2_hcd_init(hsotg, dev->irq, &dwc2_module_params); |
| 145 | if (retval) { | 152 | if (retval) { |
| 146 | pci_disable_device(dev); | 153 | pci_disable_device(dev); |
diff --git a/drivers/usb/dwc2/platform.c b/drivers/usb/dwc2/platform.c index 121dbdafc06b..6a795aa2ff05 100644 --- a/drivers/usb/dwc2/platform.c +++ b/drivers/usb/dwc2/platform.c | |||
| @@ -40,6 +40,7 @@ | |||
| 40 | #include <linux/device.h> | 40 | #include <linux/device.h> |
| 41 | #include <linux/dma-mapping.h> | 41 | #include <linux/dma-mapping.h> |
| 42 | #include <linux/of_device.h> | 42 | #include <linux/of_device.h> |
| 43 | #include <linux/mutex.h> | ||
| 43 | #include <linux/platform_device.h> | 44 | #include <linux/platform_device.h> |
| 44 | 45 | ||
| 45 | #include <linux/usb/of.h> | 46 | #include <linux/usb/of.h> |
| @@ -121,6 +122,7 @@ static int dwc2_driver_remove(struct platform_device *dev) | |||
| 121 | struct dwc2_hsotg *hsotg = platform_get_drvdata(dev); | 122 | struct dwc2_hsotg *hsotg = platform_get_drvdata(dev); |
| 122 | 123 | ||
| 123 | dwc2_hcd_remove(hsotg); | 124 | dwc2_hcd_remove(hsotg); |
| 125 | s3c_hsotg_remove(hsotg); | ||
| 124 | 126 | ||
| 125 | return 0; | 127 | return 0; |
| 126 | } | 128 | } |
| @@ -129,6 +131,7 @@ static const struct of_device_id dwc2_of_match_table[] = { | |||
| 129 | { .compatible = "brcm,bcm2835-usb", .data = ¶ms_bcm2835 }, | 131 | { .compatible = "brcm,bcm2835-usb", .data = ¶ms_bcm2835 }, |
| 130 | { .compatible = "rockchip,rk3066-usb", .data = ¶ms_rk3066 }, | 132 | { .compatible = "rockchip,rk3066-usb", .data = ¶ms_rk3066 }, |
| 131 | { .compatible = "snps,dwc2", .data = NULL }, | 133 | { .compatible = "snps,dwc2", .data = NULL }, |
| 134 | { .compatible = "samsung,s3c6400-hsotg", .data = NULL}, | ||
| 132 | {}, | 135 | {}, |
| 133 | }; | 136 | }; |
| 134 | MODULE_DEVICE_TABLE(of, dwc2_of_match_table); | 137 | MODULE_DEVICE_TABLE(of, dwc2_of_match_table); |
| @@ -155,9 +158,6 @@ static int dwc2_driver_probe(struct platform_device *dev) | |||
| 155 | int retval; | 158 | int retval; |
| 156 | int irq; | 159 | int irq; |
| 157 | 160 | ||
| 158 | if (usb_disabled()) | ||
| 159 | return -ENODEV; | ||
| 160 | |||
| 161 | match = of_match_device(dwc2_of_match_table, &dev->dev); | 161 | match = of_match_device(dwc2_of_match_table, &dev->dev); |
| 162 | if (match && match->data) { | 162 | if (match && match->data) { |
| 163 | params = match->data; | 163 | params = match->data; |
| @@ -194,6 +194,14 @@ static int dwc2_driver_probe(struct platform_device *dev) | |||
| 194 | return irq; | 194 | return irq; |
| 195 | } | 195 | } |
| 196 | 196 | ||
| 197 | dev_dbg(hsotg->dev, "registering common handler for irq%d\n", | ||
| 198 | irq); | ||
| 199 | retval = devm_request_irq(hsotg->dev, irq, | ||
| 200 | dwc2_handle_common_intr, IRQF_SHARED, | ||
| 201 | dev_name(hsotg->dev), hsotg); | ||
| 202 | if (retval) | ||
| 203 | return retval; | ||
| 204 | |||
| 197 | res = platform_get_resource(dev, IORESOURCE_MEM, 0); | 205 | res = platform_get_resource(dev, IORESOURCE_MEM, 0); |
| 198 | hsotg->regs = devm_ioremap_resource(&dev->dev, res); | 206 | hsotg->regs = devm_ioremap_resource(&dev->dev, res); |
| 199 | if (IS_ERR(hsotg->regs)) | 207 | if (IS_ERR(hsotg->regs)) |
| @@ -204,6 +212,11 @@ static int dwc2_driver_probe(struct platform_device *dev) | |||
| 204 | 212 | ||
| 205 | hsotg->dr_mode = of_usb_get_dr_mode(dev->dev.of_node); | 213 | hsotg->dr_mode = of_usb_get_dr_mode(dev->dev.of_node); |
| 206 | 214 | ||
| 215 | spin_lock_init(&hsotg->lock); | ||
| 216 | mutex_init(&hsotg->init_mutex); | ||
| 217 | retval = dwc2_gadget_init(hsotg, irq); | ||
| 218 | if (retval) | ||
| 219 | return retval; | ||
| 207 | retval = dwc2_hcd_init(hsotg, irq, params); | 220 | retval = dwc2_hcd_init(hsotg, irq, params); |
| 208 | if (retval) | 221 | if (retval) |
| 209 | return retval; | 222 | return retval; |
| @@ -213,10 +226,35 @@ static int dwc2_driver_probe(struct platform_device *dev) | |||
| 213 | return retval; | 226 | return retval; |
| 214 | } | 227 | } |
| 215 | 228 | ||
| 229 | static int __maybe_unused dwc2_suspend(struct device *dev) | ||
| 230 | { | ||
| 231 | struct dwc2_hsotg *dwc2 = dev_get_drvdata(dev); | ||
| 232 | int ret = 0; | ||
| 233 | |||
| 234 | if (dwc2_is_device_mode(dwc2)) | ||
| 235 | ret = s3c_hsotg_suspend(dwc2); | ||
| 236 | return ret; | ||
| 237 | } | ||
| 238 | |||
| 239 | static int __maybe_unused dwc2_resume(struct device *dev) | ||
| 240 | { | ||
| 241 | struct dwc2_hsotg *dwc2 = dev_get_drvdata(dev); | ||
| 242 | int ret = 0; | ||
| 243 | |||
| 244 | if (dwc2_is_device_mode(dwc2)) | ||
| 245 | ret = s3c_hsotg_resume(dwc2); | ||
| 246 | return ret; | ||
| 247 | } | ||
| 248 | |||
| 249 | static const struct dev_pm_ops dwc2_dev_pm_ops = { | ||
| 250 | SET_SYSTEM_SLEEP_PM_OPS(dwc2_suspend, dwc2_resume) | ||
| 251 | }; | ||
| 252 | |||
| 216 | static struct platform_driver dwc2_platform_driver = { | 253 | static struct platform_driver dwc2_platform_driver = { |
| 217 | .driver = { | 254 | .driver = { |
| 218 | .name = dwc2_driver_name, | 255 | .name = dwc2_driver_name, |
| 219 | .of_match_table = dwc2_of_match_table, | 256 | .of_match_table = dwc2_of_match_table, |
| 257 | .pm = &dwc2_dev_pm_ops, | ||
| 220 | }, | 258 | }, |
| 221 | .probe = dwc2_driver_probe, | 259 | .probe = dwc2_driver_probe, |
| 222 | .remove = dwc2_driver_remove, | 260 | .remove = dwc2_driver_remove, |
diff --git a/drivers/usb/dwc3/Kconfig b/drivers/usb/dwc3/Kconfig index f4e5cc60db0b..58b5b2cde4c5 100644 --- a/drivers/usb/dwc3/Kconfig +++ b/drivers/usb/dwc3/Kconfig | |||
| @@ -55,7 +55,7 @@ config USB_DWC3_OMAP | |||
| 55 | 55 | ||
| 56 | config USB_DWC3_EXYNOS | 56 | config USB_DWC3_EXYNOS |
| 57 | tristate "Samsung Exynos Platform" | 57 | tristate "Samsung Exynos Platform" |
| 58 | depends on ARCH_EXYNOS || COMPILE_TEST | 58 | depends on ARCH_EXYNOS && OF || COMPILE_TEST |
| 59 | default USB_DWC3 | 59 | default USB_DWC3 |
| 60 | help | 60 | help |
| 61 | Recent Exynos5 SoCs ship with one DesignWare Core USB3 IP inside, | 61 | Recent Exynos5 SoCs ship with one DesignWare Core USB3 IP inside, |
diff --git a/drivers/usb/dwc3/core.c b/drivers/usb/dwc3/core.c index b0f4d52b7f04..25ddc39efad8 100644 --- a/drivers/usb/dwc3/core.c +++ b/drivers/usb/dwc3/core.c | |||
| @@ -19,6 +19,7 @@ | |||
| 19 | * along with this program. If not, see <http://www.gnu.org/licenses/>. | 19 | * along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 20 | */ | 20 | */ |
| 21 | 21 | ||
| 22 | #include <linux/version.h> | ||
| 22 | #include <linux/module.h> | 23 | #include <linux/module.h> |
| 23 | #include <linux/kernel.h> | 24 | #include <linux/kernel.h> |
| 24 | #include <linux/slab.h> | 25 | #include <linux/slab.h> |
| @@ -32,6 +33,7 @@ | |||
| 32 | #include <linux/delay.h> | 33 | #include <linux/delay.h> |
| 33 | #include <linux/dma-mapping.h> | 34 | #include <linux/dma-mapping.h> |
| 34 | #include <linux/of.h> | 35 | #include <linux/of.h> |
| 36 | #include <linux/acpi.h> | ||
| 35 | 37 | ||
| 36 | #include <linux/usb/ch9.h> | 38 | #include <linux/usb/ch9.h> |
| 37 | #include <linux/usb/gadget.h> | 39 | #include <linux/usb/gadget.h> |
| @@ -363,6 +365,72 @@ static void dwc3_cache_hwparams(struct dwc3 *dwc) | |||
| 363 | } | 365 | } |
| 364 | 366 | ||
| 365 | /** | 367 | /** |
| 368 | * dwc3_phy_setup - Configure USB PHY Interface of DWC3 Core | ||
| 369 | * @dwc: Pointer to our controller context structure | ||
| 370 | */ | ||
| 371 | static void dwc3_phy_setup(struct dwc3 *dwc) | ||
| 372 | { | ||
| 373 | u32 reg; | ||
| 374 | |||
| 375 | reg = dwc3_readl(dwc->regs, DWC3_GUSB3PIPECTL(0)); | ||
| 376 | |||
| 377 | /* | ||
| 378 | * Above 1.94a, it is recommended to set DWC3_GUSB3PIPECTL_SUSPHY | ||
| 379 | * to '0' during coreConsultant configuration. So default value | ||
| 380 | * will be '0' when the core is reset. Application needs to set it | ||
| 381 | * to '1' after the core initialization is completed. | ||
| 382 | */ | ||
| 383 | if (dwc->revision > DWC3_REVISION_194A) | ||
| 384 | reg |= DWC3_GUSB3PIPECTL_SUSPHY; | ||
| 385 | |||
| 386 | if (dwc->u2ss_inp3_quirk) | ||
| 387 | reg |= DWC3_GUSB3PIPECTL_U2SSINP3OK; | ||
| 388 | |||
| 389 | if (dwc->req_p1p2p3_quirk) | ||
| 390 | reg |= DWC3_GUSB3PIPECTL_REQP1P2P3; | ||
| 391 | |||
| 392 | if (dwc->del_p1p2p3_quirk) | ||
| 393 | reg |= DWC3_GUSB3PIPECTL_DEP1P2P3_EN; | ||
| 394 | |||
| 395 | if (dwc->del_phy_power_chg_quirk) | ||
| 396 | reg |= DWC3_GUSB3PIPECTL_DEPOCHANGE; | ||
| 397 | |||
| 398 | if (dwc->lfps_filter_quirk) | ||
| 399 | reg |= DWC3_GUSB3PIPECTL_LFPSFILT; | ||
| 400 | |||
| 401 | if (dwc->rx_detect_poll_quirk) | ||
| 402 | reg |= DWC3_GUSB3PIPECTL_RX_DETOPOLL; | ||
| 403 | |||
| 404 | if (dwc->tx_de_emphasis_quirk) | ||
| 405 | reg |= DWC3_GUSB3PIPECTL_TX_DEEPH(dwc->tx_de_emphasis); | ||
| 406 | |||
| 407 | if (dwc->dis_u3_susphy_quirk) | ||
| 408 | reg &= ~DWC3_GUSB3PIPECTL_SUSPHY; | ||
| 409 | |||
| 410 | dwc3_writel(dwc->regs, DWC3_GUSB3PIPECTL(0), reg); | ||
| 411 | |||
| 412 | mdelay(100); | ||
| 413 | |||
| 414 | reg = dwc3_readl(dwc->regs, DWC3_GUSB2PHYCFG(0)); | ||
| 415 | |||
| 416 | /* | ||
| 417 | * Above 1.94a, it is recommended to set DWC3_GUSB2PHYCFG_SUSPHY to | ||
| 418 | * '0' during coreConsultant configuration. So default value will | ||
| 419 | * be '0' when the core is reset. Application needs to set it to | ||
| 420 | * '1' after the core initialization is completed. | ||
| 421 | */ | ||
| 422 | if (dwc->revision > DWC3_REVISION_194A) | ||
| 423 | reg |= DWC3_GUSB2PHYCFG_SUSPHY; | ||
| 424 | |||
| 425 | if (dwc->dis_u2_susphy_quirk) | ||
| 426 | reg &= ~DWC3_GUSB2PHYCFG_SUSPHY; | ||
| 427 | |||
| 428 | dwc3_writel(dwc->regs, DWC3_GUSB2PHYCFG(0), reg); | ||
| 429 | |||
| 430 | mdelay(100); | ||
| 431 | } | ||
| 432 | |||
| 433 | /** | ||
| 366 | * dwc3_core_init - Low-level initialization of DWC3 Core | 434 | * dwc3_core_init - Low-level initialization of DWC3 Core |
| 367 | * @dwc: Pointer to our controller context structure | 435 | * @dwc: Pointer to our controller context structure |
| 368 | * | 436 | * |
| @@ -384,6 +452,12 @@ static int dwc3_core_init(struct dwc3 *dwc) | |||
| 384 | } | 452 | } |
| 385 | dwc->revision = reg; | 453 | dwc->revision = reg; |
| 386 | 454 | ||
| 455 | /* | ||
| 456 | * Write Linux Version Code to our GUID register so it's easy to figure | ||
| 457 | * out which kernel version a bug was found. | ||
| 458 | */ | ||
| 459 | dwc3_writel(dwc->regs, DWC3_GUID, LINUX_VERSION_CODE); | ||
| 460 | |||
| 387 | /* Handle USB2.0-only core configuration */ | 461 | /* Handle USB2.0-only core configuration */ |
| 388 | if (DWC3_GHWPARAMS3_SSPHY_IFC(dwc->hwparams.hwparams3) == | 462 | if (DWC3_GHWPARAMS3_SSPHY_IFC(dwc->hwparams.hwparams3) == |
| 389 | DWC3_GHWPARAMS3_SSPHY_IFC_DIS) { | 463 | DWC3_GHWPARAMS3_SSPHY_IFC_DIS) { |
| @@ -414,7 +488,6 @@ static int dwc3_core_init(struct dwc3 *dwc) | |||
| 414 | 488 | ||
| 415 | reg = dwc3_readl(dwc->regs, DWC3_GCTL); | 489 | reg = dwc3_readl(dwc->regs, DWC3_GCTL); |
| 416 | reg &= ~DWC3_GCTL_SCALEDOWN_MASK; | 490 | reg &= ~DWC3_GCTL_SCALEDOWN_MASK; |
| 417 | reg &= ~DWC3_GCTL_DISSCRAMBLE; | ||
| 418 | 491 | ||
| 419 | switch (DWC3_GHWPARAMS1_EN_PWROPT(dwc->hwparams.hwparams1)) { | 492 | switch (DWC3_GHWPARAMS1_EN_PWROPT(dwc->hwparams.hwparams1)) { |
| 420 | case DWC3_GHWPARAMS1_EN_PWROPT_CLK: | 493 | case DWC3_GHWPARAMS1_EN_PWROPT_CLK: |
| @@ -441,11 +514,34 @@ static int dwc3_core_init(struct dwc3 *dwc) | |||
| 441 | case DWC3_GHWPARAMS1_EN_PWROPT_HIB: | 514 | case DWC3_GHWPARAMS1_EN_PWROPT_HIB: |
| 442 | /* enable hibernation here */ | 515 | /* enable hibernation here */ |
| 443 | dwc->nr_scratch = DWC3_GHWPARAMS4_HIBER_SCRATCHBUFS(hwparams4); | 516 | dwc->nr_scratch = DWC3_GHWPARAMS4_HIBER_SCRATCHBUFS(hwparams4); |
| 517 | |||
| 518 | /* | ||
| 519 | * REVISIT Enabling this bit so that host-mode hibernation | ||
| 520 | * will work. Device-mode hibernation is not yet implemented. | ||
| 521 | */ | ||
| 522 | reg |= DWC3_GCTL_GBLHIBERNATIONEN; | ||
| 444 | break; | 523 | break; |
| 445 | default: | 524 | default: |
| 446 | dev_dbg(dwc->dev, "No power optimization available\n"); | 525 | dev_dbg(dwc->dev, "No power optimization available\n"); |
| 447 | } | 526 | } |
| 448 | 527 | ||
| 528 | /* check if current dwc3 is on simulation board */ | ||
| 529 | if (dwc->hwparams.hwparams6 & DWC3_GHWPARAMS6_EN_FPGA) { | ||
| 530 | dev_dbg(dwc->dev, "it is on FPGA board\n"); | ||
| 531 | dwc->is_fpga = true; | ||
| 532 | } | ||
| 533 | |||
| 534 | WARN_ONCE(dwc->disable_scramble_quirk && !dwc->is_fpga, | ||
| 535 | "disable_scramble cannot be used on non-FPGA builds\n"); | ||
| 536 | |||
| 537 | if (dwc->disable_scramble_quirk && dwc->is_fpga) | ||
| 538 | reg |= DWC3_GCTL_DISSCRAMBLE; | ||
| 539 | else | ||
| 540 | reg &= ~DWC3_GCTL_DISSCRAMBLE; | ||
| 541 | |||
| 542 | if (dwc->u2exit_lfps_quirk) | ||
| 543 | reg |= DWC3_GCTL_U2EXIT_LFPS; | ||
| 544 | |||
| 449 | /* | 545 | /* |
| 450 | * WORKAROUND: DWC3 revisions <1.90a have a bug | 546 | * WORKAROUND: DWC3 revisions <1.90a have a bug |
| 451 | * where the device can fail to connect at SuperSpeed | 547 | * where the device can fail to connect at SuperSpeed |
| @@ -459,6 +555,8 @@ static int dwc3_core_init(struct dwc3 *dwc) | |||
| 459 | 555 | ||
| 460 | dwc3_writel(dwc->regs, DWC3_GCTL, reg); | 556 | dwc3_writel(dwc->regs, DWC3_GCTL, reg); |
| 461 | 557 | ||
| 558 | dwc3_phy_setup(dwc); | ||
| 559 | |||
| 462 | ret = dwc3_alloc_scratch_buffers(dwc); | 560 | ret = dwc3_alloc_scratch_buffers(dwc); |
| 463 | if (ret) | 561 | if (ret) |
| 464 | goto err1; | 562 | goto err1; |
| @@ -630,6 +728,9 @@ static int dwc3_probe(struct platform_device *pdev) | |||
| 630 | struct device_node *node = dev->of_node; | 728 | struct device_node *node = dev->of_node; |
| 631 | struct resource *res; | 729 | struct resource *res; |
| 632 | struct dwc3 *dwc; | 730 | struct dwc3 *dwc; |
| 731 | u8 lpm_nyet_threshold; | ||
| 732 | u8 tx_de_emphasis; | ||
| 733 | u8 hird_threshold; | ||
| 633 | 734 | ||
| 634 | int ret; | 735 | int ret; |
| 635 | 736 | ||
| @@ -685,22 +786,96 @@ static int dwc3_probe(struct platform_device *pdev) | |||
| 685 | */ | 786 | */ |
| 686 | res->start -= DWC3_GLOBALS_REGS_START; | 787 | res->start -= DWC3_GLOBALS_REGS_START; |
| 687 | 788 | ||
| 789 | /* default to highest possible threshold */ | ||
| 790 | lpm_nyet_threshold = 0xff; | ||
| 791 | |||
| 792 | /* default to -3.5dB de-emphasis */ | ||
| 793 | tx_de_emphasis = 1; | ||
| 794 | |||
| 795 | /* | ||
| 796 | * default to assert utmi_sleep_n and use maximum allowed HIRD | ||
| 797 | * threshold value of 0b1100 | ||
| 798 | */ | ||
| 799 | hird_threshold = 12; | ||
| 800 | |||
| 688 | if (node) { | 801 | if (node) { |
| 689 | dwc->maximum_speed = of_usb_get_maximum_speed(node); | 802 | dwc->maximum_speed = of_usb_get_maximum_speed(node); |
| 690 | 803 | dwc->has_lpm_erratum = of_property_read_bool(node, | |
| 691 | dwc->needs_fifo_resize = of_property_read_bool(node, "tx-fifo-resize"); | 804 | "snps,has-lpm-erratum"); |
| 805 | of_property_read_u8(node, "snps,lpm-nyet-threshold", | ||
| 806 | &lpm_nyet_threshold); | ||
| 807 | dwc->is_utmi_l1_suspend = of_property_read_bool(node, | ||
| 808 | "snps,is-utmi-l1-suspend"); | ||
| 809 | of_property_read_u8(node, "snps,hird-threshold", | ||
| 810 | &hird_threshold); | ||
| 811 | |||
| 812 | dwc->needs_fifo_resize = of_property_read_bool(node, | ||
| 813 | "tx-fifo-resize"); | ||
| 692 | dwc->dr_mode = of_usb_get_dr_mode(node); | 814 | dwc->dr_mode = of_usb_get_dr_mode(node); |
| 815 | |||
| 816 | dwc->disable_scramble_quirk = of_property_read_bool(node, | ||
| 817 | "snps,disable_scramble_quirk"); | ||
| 818 | dwc->u2exit_lfps_quirk = of_property_read_bool(node, | ||
| 819 | "snps,u2exit_lfps_quirk"); | ||
| 820 | dwc->u2ss_inp3_quirk = of_property_read_bool(node, | ||
| 821 | "snps,u2ss_inp3_quirk"); | ||
| 822 | dwc->req_p1p2p3_quirk = of_property_read_bool(node, | ||
| 823 | "snps,req_p1p2p3_quirk"); | ||
| 824 | dwc->del_p1p2p3_quirk = of_property_read_bool(node, | ||
| 825 | "snps,del_p1p2p3_quirk"); | ||
| 826 | dwc->del_phy_power_chg_quirk = of_property_read_bool(node, | ||
| 827 | "snps,del_phy_power_chg_quirk"); | ||
| 828 | dwc->lfps_filter_quirk = of_property_read_bool(node, | ||
| 829 | "snps,lfps_filter_quirk"); | ||
| 830 | dwc->rx_detect_poll_quirk = of_property_read_bool(node, | ||
| 831 | "snps,rx_detect_poll_quirk"); | ||
| 832 | dwc->dis_u3_susphy_quirk = of_property_read_bool(node, | ||
| 833 | "snps,dis_u3_susphy_quirk"); | ||
| 834 | dwc->dis_u2_susphy_quirk = of_property_read_bool(node, | ||
| 835 | "snps,dis_u2_susphy_quirk"); | ||
| 836 | |||
| 837 | dwc->tx_de_emphasis_quirk = of_property_read_bool(node, | ||
| 838 | "snps,tx_de_emphasis_quirk"); | ||
| 839 | of_property_read_u8(node, "snps,tx_de_emphasis", | ||
| 840 | &tx_de_emphasis); | ||
| 693 | } else if (pdata) { | 841 | } else if (pdata) { |
| 694 | dwc->maximum_speed = pdata->maximum_speed; | 842 | dwc->maximum_speed = pdata->maximum_speed; |
| 843 | dwc->has_lpm_erratum = pdata->has_lpm_erratum; | ||
| 844 | if (pdata->lpm_nyet_threshold) | ||
| 845 | lpm_nyet_threshold = pdata->lpm_nyet_threshold; | ||
| 846 | dwc->is_utmi_l1_suspend = pdata->is_utmi_l1_suspend; | ||
| 847 | if (pdata->hird_threshold) | ||
| 848 | hird_threshold = pdata->hird_threshold; | ||
| 695 | 849 | ||
| 696 | dwc->needs_fifo_resize = pdata->tx_fifo_resize; | 850 | dwc->needs_fifo_resize = pdata->tx_fifo_resize; |
| 697 | dwc->dr_mode = pdata->dr_mode; | 851 | dwc->dr_mode = pdata->dr_mode; |
| 852 | |||
| 853 | dwc->disable_scramble_quirk = pdata->disable_scramble_quirk; | ||
| 854 | dwc->u2exit_lfps_quirk = pdata->u2exit_lfps_quirk; | ||
| 855 | dwc->u2ss_inp3_quirk = pdata->u2ss_inp3_quirk; | ||
| 856 | dwc->req_p1p2p3_quirk = pdata->req_p1p2p3_quirk; | ||
| 857 | dwc->del_p1p2p3_quirk = pdata->del_p1p2p3_quirk; | ||
| 858 | dwc->del_phy_power_chg_quirk = pdata->del_phy_power_chg_quirk; | ||
| 859 | dwc->lfps_filter_quirk = pdata->lfps_filter_quirk; | ||
| 860 | dwc->rx_detect_poll_quirk = pdata->rx_detect_poll_quirk; | ||
| 861 | dwc->dis_u3_susphy_quirk = pdata->dis_u3_susphy_quirk; | ||
| 862 | dwc->dis_u2_susphy_quirk = pdata->dis_u2_susphy_quirk; | ||
| 863 | |||
| 864 | dwc->tx_de_emphasis_quirk = pdata->tx_de_emphasis_quirk; | ||
| 865 | if (pdata->tx_de_emphasis) | ||
| 866 | tx_de_emphasis = pdata->tx_de_emphasis; | ||
| 698 | } | 867 | } |
| 699 | 868 | ||
| 700 | /* default to superspeed if no maximum_speed passed */ | 869 | /* default to superspeed if no maximum_speed passed */ |
| 701 | if (dwc->maximum_speed == USB_SPEED_UNKNOWN) | 870 | if (dwc->maximum_speed == USB_SPEED_UNKNOWN) |
| 702 | dwc->maximum_speed = USB_SPEED_SUPER; | 871 | dwc->maximum_speed = USB_SPEED_SUPER; |
| 703 | 872 | ||
| 873 | dwc->lpm_nyet_threshold = lpm_nyet_threshold; | ||
| 874 | dwc->tx_de_emphasis = tx_de_emphasis; | ||
| 875 | |||
| 876 | dwc->hird_threshold = hird_threshold | ||
| 877 | | (dwc->is_utmi_l1_suspend << 4); | ||
| 878 | |||
| 704 | ret = dwc3_core_get_phy(dwc); | 879 | ret = dwc3_core_get_phy(dwc); |
| 705 | if (ret) | 880 | if (ret) |
| 706 | return ret; | 881 | return ret; |
| @@ -708,9 +883,11 @@ static int dwc3_probe(struct platform_device *pdev) | |||
| 708 | spin_lock_init(&dwc->lock); | 883 | spin_lock_init(&dwc->lock); |
| 709 | platform_set_drvdata(pdev, dwc); | 884 | platform_set_drvdata(pdev, dwc); |
| 710 | 885 | ||
| 711 | dev->dma_mask = dev->parent->dma_mask; | 886 | if (!dev->dma_mask) { |
| 712 | dev->dma_parms = dev->parent->dma_parms; | 887 | dev->dma_mask = dev->parent->dma_mask; |
| 713 | dma_set_coherent_mask(dev, dev->parent->coherent_dma_mask); | 888 | dev->dma_parms = dev->parent->dma_parms; |
| 889 | dma_set_coherent_mask(dev, dev->parent->coherent_dma_mask); | ||
| 890 | } | ||
| 714 | 891 | ||
| 715 | pm_runtime_enable(dev); | 892 | pm_runtime_enable(dev); |
| 716 | pm_runtime_get_sync(dev); | 893 | pm_runtime_get_sync(dev); |
| @@ -815,50 +992,6 @@ static int dwc3_remove(struct platform_device *pdev) | |||
| 815 | } | 992 | } |
| 816 | 993 | ||
| 817 | #ifdef CONFIG_PM_SLEEP | 994 | #ifdef CONFIG_PM_SLEEP |
| 818 | static int dwc3_prepare(struct device *dev) | ||
| 819 | { | ||
| 820 | struct dwc3 *dwc = dev_get_drvdata(dev); | ||
| 821 | unsigned long flags; | ||
| 822 | |||
| 823 | spin_lock_irqsave(&dwc->lock, flags); | ||
| 824 | |||
| 825 | switch (dwc->dr_mode) { | ||
| 826 | case USB_DR_MODE_PERIPHERAL: | ||
| 827 | case USB_DR_MODE_OTG: | ||
| 828 | dwc3_gadget_prepare(dwc); | ||
| 829 | /* FALLTHROUGH */ | ||
| 830 | case USB_DR_MODE_HOST: | ||
| 831 | default: | ||
| 832 | dwc3_event_buffers_cleanup(dwc); | ||
| 833 | break; | ||
| 834 | } | ||
| 835 | |||
| 836 | spin_unlock_irqrestore(&dwc->lock, flags); | ||
| 837 | |||
| 838 | return 0; | ||
| 839 | } | ||
| 840 | |||
| 841 | static void dwc3_complete(struct device *dev) | ||
| 842 | { | ||
| 843 | struct dwc3 *dwc = dev_get_drvdata(dev); | ||
| 844 | unsigned long flags; | ||
| 845 | |||
| 846 | spin_lock_irqsave(&dwc->lock, flags); | ||
| 847 | |||
| 848 | dwc3_event_buffers_setup(dwc); | ||
| 849 | switch (dwc->dr_mode) { | ||
| 850 | case USB_DR_MODE_PERIPHERAL: | ||
| 851 | case USB_DR_MODE_OTG: | ||
| 852 | dwc3_gadget_complete(dwc); | ||
| 853 | /* FALLTHROUGH */ | ||
| 854 | case USB_DR_MODE_HOST: | ||
| 855 | default: | ||
| 856 | break; | ||
| 857 | } | ||
| 858 | |||
| 859 | spin_unlock_irqrestore(&dwc->lock, flags); | ||
| 860 | } | ||
| 861 | |||
| 862 | static int dwc3_suspend(struct device *dev) | 995 | static int dwc3_suspend(struct device *dev) |
| 863 | { | 996 | { |
| 864 | struct dwc3 *dwc = dev_get_drvdata(dev); | 997 | struct dwc3 *dwc = dev_get_drvdata(dev); |
| @@ -873,7 +1006,7 @@ static int dwc3_suspend(struct device *dev) | |||
| 873 | /* FALLTHROUGH */ | 1006 | /* FALLTHROUGH */ |
| 874 | case USB_DR_MODE_HOST: | 1007 | case USB_DR_MODE_HOST: |
| 875 | default: | 1008 | default: |
| 876 | /* do nothing */ | 1009 | dwc3_event_buffers_cleanup(dwc); |
| 877 | break; | 1010 | break; |
| 878 | } | 1011 | } |
| 879 | 1012 | ||
| @@ -906,6 +1039,7 @@ static int dwc3_resume(struct device *dev) | |||
| 906 | 1039 | ||
| 907 | spin_lock_irqsave(&dwc->lock, flags); | 1040 | spin_lock_irqsave(&dwc->lock, flags); |
| 908 | 1041 | ||
| 1042 | dwc3_event_buffers_setup(dwc); | ||
| 909 | dwc3_writel(dwc->regs, DWC3_GCTL, dwc->gctl); | 1043 | dwc3_writel(dwc->regs, DWC3_GCTL, dwc->gctl); |
| 910 | 1044 | ||
| 911 | switch (dwc->dr_mode) { | 1045 | switch (dwc->dr_mode) { |
| @@ -934,9 +1068,6 @@ err_usb2phy_init: | |||
| 934 | } | 1068 | } |
| 935 | 1069 | ||
| 936 | static const struct dev_pm_ops dwc3_dev_pm_ops = { | 1070 | static const struct dev_pm_ops dwc3_dev_pm_ops = { |
| 937 | .prepare = dwc3_prepare, | ||
| 938 | .complete = dwc3_complete, | ||
| 939 | |||
| 940 | SET_SYSTEM_SLEEP_PM_OPS(dwc3_suspend, dwc3_resume) | 1071 | SET_SYSTEM_SLEEP_PM_OPS(dwc3_suspend, dwc3_resume) |
| 941 | }; | 1072 | }; |
| 942 | 1073 | ||
| @@ -958,12 +1089,24 @@ static const struct of_device_id of_dwc3_match[] = { | |||
| 958 | MODULE_DEVICE_TABLE(of, of_dwc3_match); | 1089 | MODULE_DEVICE_TABLE(of, of_dwc3_match); |
| 959 | #endif | 1090 | #endif |
| 960 | 1091 | ||
| 1092 | #ifdef CONFIG_ACPI | ||
| 1093 | |||
| 1094 | #define ACPI_ID_INTEL_BSW "808622B7" | ||
| 1095 | |||
| 1096 | static const struct acpi_device_id dwc3_acpi_match[] = { | ||
| 1097 | { ACPI_ID_INTEL_BSW, 0 }, | ||
| 1098 | { }, | ||
| 1099 | }; | ||
| 1100 | MODULE_DEVICE_TABLE(acpi, dwc3_acpi_match); | ||
| 1101 | #endif | ||
| 1102 | |||
| 961 | static struct platform_driver dwc3_driver = { | 1103 | static struct platform_driver dwc3_driver = { |
| 962 | .probe = dwc3_probe, | 1104 | .probe = dwc3_probe, |
| 963 | .remove = dwc3_remove, | 1105 | .remove = dwc3_remove, |
| 964 | .driver = { | 1106 | .driver = { |
| 965 | .name = "dwc3", | 1107 | .name = "dwc3", |
| 966 | .of_match_table = of_match_ptr(of_dwc3_match), | 1108 | .of_match_table = of_match_ptr(of_dwc3_match), |
| 1109 | .acpi_match_table = ACPI_PTR(dwc3_acpi_match), | ||
| 967 | .pm = DWC3_PM_OPS, | 1110 | .pm = DWC3_PM_OPS, |
| 968 | }, | 1111 | }, |
| 969 | }; | 1112 | }; |
diff --git a/drivers/usb/dwc3/core.h b/drivers/usb/dwc3/core.h index 66f62563bcf9..4bb9aa696ede 100644 --- a/drivers/usb/dwc3/core.h +++ b/drivers/usb/dwc3/core.h | |||
| @@ -166,6 +166,7 @@ | |||
| 166 | #define DWC3_GCTL_SCALEDOWN(n) ((n) << 4) | 166 | #define DWC3_GCTL_SCALEDOWN(n) ((n) << 4) |
| 167 | #define DWC3_GCTL_SCALEDOWN_MASK DWC3_GCTL_SCALEDOWN(3) | 167 | #define DWC3_GCTL_SCALEDOWN_MASK DWC3_GCTL_SCALEDOWN(3) |
| 168 | #define DWC3_GCTL_DISSCRAMBLE (1 << 3) | 168 | #define DWC3_GCTL_DISSCRAMBLE (1 << 3) |
| 169 | #define DWC3_GCTL_U2EXIT_LFPS (1 << 2) | ||
| 169 | #define DWC3_GCTL_GBLHIBERNATIONEN (1 << 1) | 170 | #define DWC3_GCTL_GBLHIBERNATIONEN (1 << 1) |
| 170 | #define DWC3_GCTL_DSBLCLKGTNG (1 << 0) | 171 | #define DWC3_GCTL_DSBLCLKGTNG (1 << 0) |
| 171 | 172 | ||
| @@ -175,7 +176,17 @@ | |||
| 175 | 176 | ||
| 176 | /* Global USB3 PIPE Control Register */ | 177 | /* Global USB3 PIPE Control Register */ |
| 177 | #define DWC3_GUSB3PIPECTL_PHYSOFTRST (1 << 31) | 178 | #define DWC3_GUSB3PIPECTL_PHYSOFTRST (1 << 31) |
| 179 | #define DWC3_GUSB3PIPECTL_U2SSINP3OK (1 << 29) | ||
| 180 | #define DWC3_GUSB3PIPECTL_REQP1P2P3 (1 << 24) | ||
| 181 | #define DWC3_GUSB3PIPECTL_DEP1P2P3(n) ((n) << 19) | ||
| 182 | #define DWC3_GUSB3PIPECTL_DEP1P2P3_MASK DWC3_GUSB3PIPECTL_DEP1P2P3(7) | ||
| 183 | #define DWC3_GUSB3PIPECTL_DEP1P2P3_EN DWC3_GUSB3PIPECTL_DEP1P2P3(1) | ||
| 184 | #define DWC3_GUSB3PIPECTL_DEPOCHANGE (1 << 18) | ||
| 178 | #define DWC3_GUSB3PIPECTL_SUSPHY (1 << 17) | 185 | #define DWC3_GUSB3PIPECTL_SUSPHY (1 << 17) |
| 186 | #define DWC3_GUSB3PIPECTL_LFPSFILT (1 << 9) | ||
| 187 | #define DWC3_GUSB3PIPECTL_RX_DETOPOLL (1 << 8) | ||
| 188 | #define DWC3_GUSB3PIPECTL_TX_DEEPH_MASK DWC3_GUSB3PIPECTL_TX_DEEPH(3) | ||
| 189 | #define DWC3_GUSB3PIPECTL_TX_DEEPH(n) ((n) << 1) | ||
| 179 | 190 | ||
| 180 | /* Global TX Fifo Size Register */ | 191 | /* Global TX Fifo Size Register */ |
| 181 | #define DWC3_GTXFIFOSIZ_TXFDEF(n) ((n) & 0xffff) | 192 | #define DWC3_GTXFIFOSIZ_TXFDEF(n) ((n) & 0xffff) |
| @@ -210,6 +221,9 @@ | |||
| 210 | #define DWC3_GHWPARAMS4_HIBER_SCRATCHBUFS(n) (((n) & (0x0f << 13)) >> 13) | 221 | #define DWC3_GHWPARAMS4_HIBER_SCRATCHBUFS(n) (((n) & (0x0f << 13)) >> 13) |
| 211 | #define DWC3_MAX_HIBER_SCRATCHBUFS 15 | 222 | #define DWC3_MAX_HIBER_SCRATCHBUFS 15 |
| 212 | 223 | ||
| 224 | /* Global HWPARAMS6 Register */ | ||
| 225 | #define DWC3_GHWPARAMS6_EN_FPGA (1 << 7) | ||
| 226 | |||
| 213 | /* Device Configuration Register */ | 227 | /* Device Configuration Register */ |
| 214 | #define DWC3_DCFG_DEVADDR(addr) ((addr) << 3) | 228 | #define DWC3_DCFG_DEVADDR(addr) ((addr) << 3) |
| 215 | #define DWC3_DCFG_DEVADDR_MASK DWC3_DCFG_DEVADDR(0x7f) | 229 | #define DWC3_DCFG_DEVADDR_MASK DWC3_DCFG_DEVADDR(0x7f) |
| @@ -243,16 +257,19 @@ | |||
| 243 | #define DWC3_DCTL_TRGTULST_SS_INACT (DWC3_DCTL_TRGTULST(6)) | 257 | #define DWC3_DCTL_TRGTULST_SS_INACT (DWC3_DCTL_TRGTULST(6)) |
| 244 | 258 | ||
| 245 | /* These apply for core versions 1.94a and later */ | 259 | /* These apply for core versions 1.94a and later */ |
| 246 | #define DWC3_DCTL_KEEP_CONNECT (1 << 19) | 260 | #define DWC3_DCTL_LPM_ERRATA_MASK DWC3_DCTL_LPM_ERRATA(0xf) |
| 247 | #define DWC3_DCTL_L1_HIBER_EN (1 << 18) | 261 | #define DWC3_DCTL_LPM_ERRATA(n) ((n) << 20) |
| 248 | #define DWC3_DCTL_CRS (1 << 17) | 262 | |
| 249 | #define DWC3_DCTL_CSS (1 << 16) | 263 | #define DWC3_DCTL_KEEP_CONNECT (1 << 19) |
| 264 | #define DWC3_DCTL_L1_HIBER_EN (1 << 18) | ||
| 265 | #define DWC3_DCTL_CRS (1 << 17) | ||
| 266 | #define DWC3_DCTL_CSS (1 << 16) | ||
| 250 | 267 | ||
| 251 | #define DWC3_DCTL_INITU2ENA (1 << 12) | 268 | #define DWC3_DCTL_INITU2ENA (1 << 12) |
| 252 | #define DWC3_DCTL_ACCEPTU2ENA (1 << 11) | 269 | #define DWC3_DCTL_ACCEPTU2ENA (1 << 11) |
| 253 | #define DWC3_DCTL_INITU1ENA (1 << 10) | 270 | #define DWC3_DCTL_INITU1ENA (1 << 10) |
| 254 | #define DWC3_DCTL_ACCEPTU1ENA (1 << 9) | 271 | #define DWC3_DCTL_ACCEPTU1ENA (1 << 9) |
| 255 | #define DWC3_DCTL_TSTCTRL_MASK (0xf << 1) | 272 | #define DWC3_DCTL_TSTCTRL_MASK (0xf << 1) |
| 256 | 273 | ||
| 257 | #define DWC3_DCTL_ULSTCHNGREQ_MASK (0x0f << 5) | 274 | #define DWC3_DCTL_ULSTCHNGREQ_MASK (0x0f << 5) |
| 258 | #define DWC3_DCTL_ULSTCHNGREQ(n) (((n) << 5) & DWC3_DCTL_ULSTCHNGREQ_MASK) | 275 | #define DWC3_DCTL_ULSTCHNGREQ(n) (((n) << 5) & DWC3_DCTL_ULSTCHNGREQ_MASK) |
| @@ -657,17 +674,41 @@ struct dwc3_scratchpad_array { | |||
| 657 | * @regset: debugfs pointer to regdump file | 674 | * @regset: debugfs pointer to regdump file |
| 658 | * @test_mode: true when we're entering a USB test mode | 675 | * @test_mode: true when we're entering a USB test mode |
| 659 | * @test_mode_nr: test feature selector | 676 | * @test_mode_nr: test feature selector |
| 677 | * @lpm_nyet_threshold: LPM NYET response threshold | ||
| 678 | * @hird_threshold: HIRD threshold | ||
| 660 | * @delayed_status: true when gadget driver asks for delayed status | 679 | * @delayed_status: true when gadget driver asks for delayed status |
| 661 | * @ep0_bounced: true when we used bounce buffer | 680 | * @ep0_bounced: true when we used bounce buffer |
| 662 | * @ep0_expect_in: true when we expect a DATA IN transfer | 681 | * @ep0_expect_in: true when we expect a DATA IN transfer |
| 663 | * @has_hibernation: true when dwc3 was configured with Hibernation | 682 | * @has_hibernation: true when dwc3 was configured with Hibernation |
| 683 | * @has_lpm_erratum: true when core was configured with LPM Erratum. Note that | ||
| 684 | * there's now way for software to detect this in runtime. | ||
| 685 | * @is_utmi_l1_suspend: the core asserts output signal | ||
| 686 | * 0 - utmi_sleep_n | ||
| 687 | * 1 - utmi_l1_suspend_n | ||
| 664 | * @is_selfpowered: true when we are selfpowered | 688 | * @is_selfpowered: true when we are selfpowered |
| 689 | * @is_fpga: true when we are using the FPGA board | ||
| 665 | * @needs_fifo_resize: not all users might want fifo resizing, flag it | 690 | * @needs_fifo_resize: not all users might want fifo resizing, flag it |
| 666 | * @pullups_connected: true when Run/Stop bit is set | 691 | * @pullups_connected: true when Run/Stop bit is set |
| 667 | * @resize_fifos: tells us it's ok to reconfigure our TxFIFO sizes. | 692 | * @resize_fifos: tells us it's ok to reconfigure our TxFIFO sizes. |
| 668 | * @setup_packet_pending: true when there's a Setup Packet in FIFO. Workaround | 693 | * @setup_packet_pending: true when there's a Setup Packet in FIFO. Workaround |
| 669 | * @start_config_issued: true when StartConfig command has been issued | 694 | * @start_config_issued: true when StartConfig command has been issued |
| 670 | * @three_stage_setup: set if we perform a three phase setup | 695 | * @three_stage_setup: set if we perform a three phase setup |
| 696 | * @disable_scramble_quirk: set if we enable the disable scramble quirk | ||
| 697 | * @u2exit_lfps_quirk: set if we enable u2exit lfps quirk | ||
| 698 | * @u2ss_inp3_quirk: set if we enable P3 OK for U2/SS Inactive quirk | ||
| 699 | * @req_p1p2p3_quirk: set if we enable request p1p2p3 quirk | ||
| 700 | * @del_p1p2p3_quirk: set if we enable delay p1p2p3 quirk | ||
| 701 | * @del_phy_power_chg_quirk: set if we enable delay phy power change quirk | ||
| 702 | * @lfps_filter_quirk: set if we enable LFPS filter quirk | ||
| 703 | * @rx_detect_poll_quirk: set if we enable rx_detect to polling lfps quirk | ||
| 704 | * @dis_u3_susphy_quirk: set if we disable usb3 suspend phy | ||
| 705 | * @dis_u2_susphy_quirk: set if we disable usb2 suspend phy | ||
| 706 | * @tx_de_emphasis_quirk: set if we enable Tx de-emphasis quirk | ||
| 707 | * @tx_de_emphasis: Tx de-emphasis value | ||
| 708 | * 0 - -6dB de-emphasis | ||
| 709 | * 1 - -3.5dB de-emphasis | ||
| 710 | * 2 - No de-emphasis | ||
| 711 | * 3 - Reserved | ||
| 671 | */ | 712 | */ |
| 672 | struct dwc3 { | 713 | struct dwc3 { |
| 673 | struct usb_ctrlrequest *ctrl_req; | 714 | struct usb_ctrlrequest *ctrl_req; |
| @@ -759,18 +800,37 @@ struct dwc3 { | |||
| 759 | 800 | ||
| 760 | u8 test_mode; | 801 | u8 test_mode; |
| 761 | u8 test_mode_nr; | 802 | u8 test_mode_nr; |
| 803 | u8 lpm_nyet_threshold; | ||
| 804 | u8 hird_threshold; | ||
| 762 | 805 | ||
| 763 | unsigned delayed_status:1; | 806 | unsigned delayed_status:1; |
| 764 | unsigned ep0_bounced:1; | 807 | unsigned ep0_bounced:1; |
| 765 | unsigned ep0_expect_in:1; | 808 | unsigned ep0_expect_in:1; |
| 766 | unsigned has_hibernation:1; | 809 | unsigned has_hibernation:1; |
| 810 | unsigned has_lpm_erratum:1; | ||
| 811 | unsigned is_utmi_l1_suspend:1; | ||
| 767 | unsigned is_selfpowered:1; | 812 | unsigned is_selfpowered:1; |
| 813 | unsigned is_fpga:1; | ||
| 768 | unsigned needs_fifo_resize:1; | 814 | unsigned needs_fifo_resize:1; |
| 769 | unsigned pullups_connected:1; | 815 | unsigned pullups_connected:1; |
| 770 | unsigned resize_fifos:1; | 816 | unsigned resize_fifos:1; |
| 771 | unsigned setup_packet_pending:1; | 817 | unsigned setup_packet_pending:1; |
| 772 | unsigned start_config_issued:1; | 818 | unsigned start_config_issued:1; |
| 773 | unsigned three_stage_setup:1; | 819 | unsigned three_stage_setup:1; |
| 820 | |||
| 821 | unsigned disable_scramble_quirk:1; | ||
| 822 | unsigned u2exit_lfps_quirk:1; | ||
| 823 | unsigned u2ss_inp3_quirk:1; | ||
| 824 | unsigned req_p1p2p3_quirk:1; | ||
| 825 | unsigned del_p1p2p3_quirk:1; | ||
| 826 | unsigned del_phy_power_chg_quirk:1; | ||
| 827 | unsigned lfps_filter_quirk:1; | ||
| 828 | unsigned rx_detect_poll_quirk:1; | ||
| 829 | unsigned dis_u3_susphy_quirk:1; | ||
| 830 | unsigned dis_u2_susphy_quirk:1; | ||
| 831 | |||
| 832 | unsigned tx_de_emphasis_quirk:1; | ||
| 833 | unsigned tx_de_emphasis:2; | ||
| 774 | }; | 834 | }; |
| 775 | 835 | ||
| 776 | /* -------------------------------------------------------------------------- */ | 836 | /* -------------------------------------------------------------------------- */ |
| @@ -964,20 +1024,9 @@ static inline int dwc3_send_gadget_generic_command(struct dwc3 *dwc, | |||
| 964 | 1024 | ||
| 965 | /* power management interface */ | 1025 | /* power management interface */ |
| 966 | #if !IS_ENABLED(CONFIG_USB_DWC3_HOST) | 1026 | #if !IS_ENABLED(CONFIG_USB_DWC3_HOST) |
| 967 | int dwc3_gadget_prepare(struct dwc3 *dwc); | ||
| 968 | void dwc3_gadget_complete(struct dwc3 *dwc); | ||
| 969 | int dwc3_gadget_suspend(struct dwc3 *dwc); | 1027 | int dwc3_gadget_suspend(struct dwc3 *dwc); |
| 970 | int dwc3_gadget_resume(struct dwc3 *dwc); | 1028 | int dwc3_gadget_resume(struct dwc3 *dwc); |
| 971 | #else | 1029 | #else |
| 972 | static inline int dwc3_gadget_prepare(struct dwc3 *dwc) | ||
| 973 | { | ||
| 974 | return 0; | ||
| 975 | } | ||
| 976 | |||
| 977 | static inline void dwc3_gadget_complete(struct dwc3 *dwc) | ||
| 978 | { | ||
| 979 | } | ||
| 980 | |||
| 981 | static inline int dwc3_gadget_suspend(struct dwc3 *dwc) | 1030 | static inline int dwc3_gadget_suspend(struct dwc3 *dwc) |
| 982 | { | 1031 | { |
| 983 | return 0; | 1032 | return 0; |
diff --git a/drivers/usb/dwc3/dwc3-exynos.c b/drivers/usb/dwc3/dwc3-exynos.c index 3951a65fea04..7bd0a95b2815 100644 --- a/drivers/usb/dwc3/dwc3-exynos.c +++ b/drivers/usb/dwc3/dwc3-exynos.c | |||
| @@ -20,7 +20,6 @@ | |||
| 20 | #include <linux/kernel.h> | 20 | #include <linux/kernel.h> |
| 21 | #include <linux/slab.h> | 21 | #include <linux/slab.h> |
| 22 | #include <linux/platform_device.h> | 22 | #include <linux/platform_device.h> |
| 23 | #include <linux/platform_data/dwc3-exynos.h> | ||
| 24 | #include <linux/dma-mapping.h> | 23 | #include <linux/dma-mapping.h> |
| 25 | #include <linux/clk.h> | 24 | #include <linux/clk.h> |
| 26 | #include <linux/usb/otg.h> | 25 | #include <linux/usb/otg.h> |
| @@ -35,6 +34,9 @@ struct dwc3_exynos { | |||
| 35 | struct device *dev; | 34 | struct device *dev; |
| 36 | 35 | ||
| 37 | struct clk *clk; | 36 | struct clk *clk; |
| 37 | struct clk *susp_clk; | ||
| 38 | struct clk *axius_clk; | ||
| 39 | |||
| 38 | struct regulator *vdd33; | 40 | struct regulator *vdd33; |
| 39 | struct regulator *vdd10; | 41 | struct regulator *vdd10; |
| 40 | }; | 42 | }; |
| @@ -106,7 +108,6 @@ static int dwc3_exynos_remove_child(struct device *dev, void *unused) | |||
| 106 | static int dwc3_exynos_probe(struct platform_device *pdev) | 108 | static int dwc3_exynos_probe(struct platform_device *pdev) |
| 107 | { | 109 | { |
| 108 | struct dwc3_exynos *exynos; | 110 | struct dwc3_exynos *exynos; |
| 109 | struct clk *clk; | ||
| 110 | struct device *dev = &pdev->dev; | 111 | struct device *dev = &pdev->dev; |
| 111 | struct device_node *node = dev->of_node; | 112 | struct device_node *node = dev->of_node; |
| 112 | 113 | ||
| @@ -133,16 +134,32 @@ static int dwc3_exynos_probe(struct platform_device *pdev) | |||
| 133 | return ret; | 134 | return ret; |
| 134 | } | 135 | } |
| 135 | 136 | ||
| 136 | clk = devm_clk_get(dev, "usbdrd30"); | 137 | exynos->dev = dev; |
| 137 | if (IS_ERR(clk)) { | 138 | |
| 139 | exynos->clk = devm_clk_get(dev, "usbdrd30"); | ||
| 140 | if (IS_ERR(exynos->clk)) { | ||
| 138 | dev_err(dev, "couldn't get clock\n"); | 141 | dev_err(dev, "couldn't get clock\n"); |
| 139 | return -EINVAL; | 142 | return -EINVAL; |
| 140 | } | 143 | } |
| 144 | clk_prepare_enable(exynos->clk); | ||
| 141 | 145 | ||
| 142 | exynos->dev = dev; | 146 | exynos->susp_clk = devm_clk_get(dev, "usbdrd30_susp_clk"); |
| 143 | exynos->clk = clk; | 147 | if (IS_ERR(exynos->susp_clk)) { |
| 148 | dev_dbg(dev, "no suspend clk specified\n"); | ||
| 149 | exynos->susp_clk = NULL; | ||
| 150 | } | ||
| 151 | clk_prepare_enable(exynos->susp_clk); | ||
| 144 | 152 | ||
| 145 | clk_prepare_enable(exynos->clk); | 153 | if (of_device_is_compatible(node, "samsung,exynos7-dwusb3")) { |
| 154 | exynos->axius_clk = devm_clk_get(dev, "usbdrd30_axius_clk"); | ||
| 155 | if (IS_ERR(exynos->axius_clk)) { | ||
| 156 | dev_err(dev, "no AXI UpScaler clk specified\n"); | ||
| 157 | return -ENODEV; | ||
| 158 | } | ||
| 159 | clk_prepare_enable(exynos->axius_clk); | ||
| 160 | } else { | ||
| 161 | exynos->axius_clk = NULL; | ||
| 162 | } | ||
| 146 | 163 | ||
| 147 | exynos->vdd33 = devm_regulator_get(dev, "vdd33"); | 164 | exynos->vdd33 = devm_regulator_get(dev, "vdd33"); |
| 148 | if (IS_ERR(exynos->vdd33)) { | 165 | if (IS_ERR(exynos->vdd33)) { |
| @@ -185,7 +202,9 @@ err4: | |||
| 185 | err3: | 202 | err3: |
| 186 | regulator_disable(exynos->vdd33); | 203 | regulator_disable(exynos->vdd33); |
| 187 | err2: | 204 | err2: |
| 188 | clk_disable_unprepare(clk); | 205 | clk_disable_unprepare(exynos->axius_clk); |
| 206 | clk_disable_unprepare(exynos->susp_clk); | ||
| 207 | clk_disable_unprepare(exynos->clk); | ||
| 189 | return ret; | 208 | return ret; |
| 190 | } | 209 | } |
| 191 | 210 | ||
| @@ -197,6 +216,8 @@ static int dwc3_exynos_remove(struct platform_device *pdev) | |||
| 197 | platform_device_unregister(exynos->usb2_phy); | 216 | platform_device_unregister(exynos->usb2_phy); |
| 198 | platform_device_unregister(exynos->usb3_phy); | 217 | platform_device_unregister(exynos->usb3_phy); |
| 199 | 218 | ||
| 219 | clk_disable_unprepare(exynos->axius_clk); | ||
| 220 | clk_disable_unprepare(exynos->susp_clk); | ||
| 200 | clk_disable_unprepare(exynos->clk); | 221 | clk_disable_unprepare(exynos->clk); |
| 201 | 222 | ||
| 202 | regulator_disable(exynos->vdd33); | 223 | regulator_disable(exynos->vdd33); |
| @@ -205,19 +226,19 @@ static int dwc3_exynos_remove(struct platform_device *pdev) | |||
| 205 | return 0; | 226 | return 0; |
| 206 | } | 227 | } |
| 207 | 228 | ||
| 208 | #ifdef CONFIG_OF | ||
| 209 | static const struct of_device_id exynos_dwc3_match[] = { | 229 | static const struct of_device_id exynos_dwc3_match[] = { |
| 210 | { .compatible = "samsung,exynos5250-dwusb3" }, | 230 | { .compatible = "samsung,exynos5250-dwusb3" }, |
| 231 | { .compatible = "samsung,exynos7-dwusb3" }, | ||
| 211 | {}, | 232 | {}, |
| 212 | }; | 233 | }; |
| 213 | MODULE_DEVICE_TABLE(of, exynos_dwc3_match); | 234 | MODULE_DEVICE_TABLE(of, exynos_dwc3_match); |
| 214 | #endif | ||
| 215 | 235 | ||
| 216 | #ifdef CONFIG_PM_SLEEP | 236 | #ifdef CONFIG_PM_SLEEP |
| 217 | static int dwc3_exynos_suspend(struct device *dev) | 237 | static int dwc3_exynos_suspend(struct device *dev) |
| 218 | { | 238 | { |
| 219 | struct dwc3_exynos *exynos = dev_get_drvdata(dev); | 239 | struct dwc3_exynos *exynos = dev_get_drvdata(dev); |
| 220 | 240 | ||
| 241 | clk_disable(exynos->axius_clk); | ||
| 221 | clk_disable(exynos->clk); | 242 | clk_disable(exynos->clk); |
| 222 | 243 | ||
| 223 | regulator_disable(exynos->vdd33); | 244 | regulator_disable(exynos->vdd33); |
| @@ -243,6 +264,7 @@ static int dwc3_exynos_resume(struct device *dev) | |||
| 243 | } | 264 | } |
| 244 | 265 | ||
| 245 | clk_enable(exynos->clk); | 266 | clk_enable(exynos->clk); |
| 267 | clk_enable(exynos->axius_clk); | ||
| 246 | 268 | ||
| 247 | /* runtime set active to reflect active state. */ | 269 | /* runtime set active to reflect active state. */ |
| 248 | pm_runtime_disable(dev); | 270 | pm_runtime_disable(dev); |
| @@ -266,7 +288,7 @@ static struct platform_driver dwc3_exynos_driver = { | |||
| 266 | .remove = dwc3_exynos_remove, | 288 | .remove = dwc3_exynos_remove, |
| 267 | .driver = { | 289 | .driver = { |
| 268 | .name = "exynos-dwc3", | 290 | .name = "exynos-dwc3", |
| 269 | .of_match_table = of_match_ptr(exynos_dwc3_match), | 291 | .of_match_table = exynos_dwc3_match, |
| 270 | .pm = DEV_PM_OPS, | 292 | .pm = DEV_PM_OPS, |
| 271 | }, | 293 | }, |
| 272 | }; | 294 | }; |
diff --git a/drivers/usb/dwc3/dwc3-keystone.c b/drivers/usb/dwc3/dwc3-keystone.c index 7ec8495f4523..fe3b9335a74e 100644 --- a/drivers/usb/dwc3/dwc3-keystone.c +++ b/drivers/usb/dwc3/dwc3-keystone.c | |||
| @@ -104,11 +104,6 @@ static int kdwc3_probe(struct platform_device *pdev) | |||
| 104 | kdwc->dev = dev; | 104 | kdwc->dev = dev; |
| 105 | 105 | ||
| 106 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 106 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 107 | if (!res) { | ||
| 108 | dev_err(dev, "missing usbss resource\n"); | ||
| 109 | return -EINVAL; | ||
| 110 | } | ||
| 111 | |||
| 112 | kdwc->usbss = devm_ioremap_resource(dev, res); | 107 | kdwc->usbss = devm_ioremap_resource(dev, res); |
| 113 | if (IS_ERR(kdwc->usbss)) | 108 | if (IS_ERR(kdwc->usbss)) |
| 114 | return PTR_ERR(kdwc->usbss); | 109 | return PTR_ERR(kdwc->usbss); |
| @@ -128,6 +123,7 @@ static int kdwc3_probe(struct platform_device *pdev) | |||
| 128 | irq = platform_get_irq(pdev, 0); | 123 | irq = platform_get_irq(pdev, 0); |
| 129 | if (irq < 0) { | 124 | if (irq < 0) { |
| 130 | dev_err(&pdev->dev, "missing irq\n"); | 125 | dev_err(&pdev->dev, "missing irq\n"); |
| 126 | error = irq; | ||
| 131 | goto err_irq; | 127 | goto err_irq; |
| 132 | } | 128 | } |
| 133 | 129 | ||
diff --git a/drivers/usb/dwc3/dwc3-omap.c b/drivers/usb/dwc3/dwc3-omap.c index a0aa9f3da441..172d64e585b6 100644 --- a/drivers/usb/dwc3/dwc3-omap.c +++ b/drivers/usb/dwc3/dwc3-omap.c | |||
| @@ -593,27 +593,12 @@ static const struct of_device_id of_dwc3_match[] = { | |||
| 593 | MODULE_DEVICE_TABLE(of, of_dwc3_match); | 593 | MODULE_DEVICE_TABLE(of, of_dwc3_match); |
| 594 | 594 | ||
| 595 | #ifdef CONFIG_PM_SLEEP | 595 | #ifdef CONFIG_PM_SLEEP |
| 596 | static int dwc3_omap_prepare(struct device *dev) | ||
| 597 | { | ||
| 598 | struct dwc3_omap *omap = dev_get_drvdata(dev); | ||
| 599 | |||
| 600 | dwc3_omap_disable_irqs(omap); | ||
| 601 | |||
| 602 | return 0; | ||
| 603 | } | ||
| 604 | |||
| 605 | static void dwc3_omap_complete(struct device *dev) | ||
| 606 | { | ||
| 607 | struct dwc3_omap *omap = dev_get_drvdata(dev); | ||
| 608 | |||
| 609 | dwc3_omap_enable_irqs(omap); | ||
| 610 | } | ||
| 611 | |||
| 612 | static int dwc3_omap_suspend(struct device *dev) | 596 | static int dwc3_omap_suspend(struct device *dev) |
| 613 | { | 597 | { |
| 614 | struct dwc3_omap *omap = dev_get_drvdata(dev); | 598 | struct dwc3_omap *omap = dev_get_drvdata(dev); |
| 615 | 599 | ||
| 616 | omap->utmi_otg_status = dwc3_omap_read_utmi_status(omap); | 600 | omap->utmi_otg_status = dwc3_omap_read_utmi_status(omap); |
| 601 | dwc3_omap_disable_irqs(omap); | ||
| 617 | 602 | ||
| 618 | return 0; | 603 | return 0; |
| 619 | } | 604 | } |
| @@ -623,6 +608,7 @@ static int dwc3_omap_resume(struct device *dev) | |||
| 623 | struct dwc3_omap *omap = dev_get_drvdata(dev); | 608 | struct dwc3_omap *omap = dev_get_drvdata(dev); |
| 624 | 609 | ||
| 625 | dwc3_omap_write_utmi_status(omap, omap->utmi_otg_status); | 610 | dwc3_omap_write_utmi_status(omap, omap->utmi_otg_status); |
| 611 | dwc3_omap_enable_irqs(omap); | ||
| 626 | 612 | ||
| 627 | pm_runtime_disable(dev); | 613 | pm_runtime_disable(dev); |
| 628 | pm_runtime_set_active(dev); | 614 | pm_runtime_set_active(dev); |
| @@ -632,8 +618,6 @@ static int dwc3_omap_resume(struct device *dev) | |||
| 632 | } | 618 | } |
| 633 | 619 | ||
| 634 | static const struct dev_pm_ops dwc3_omap_dev_pm_ops = { | 620 | static const struct dev_pm_ops dwc3_omap_dev_pm_ops = { |
| 635 | .prepare = dwc3_omap_prepare, | ||
| 636 | .complete = dwc3_omap_complete, | ||
| 637 | 621 | ||
| 638 | SET_SYSTEM_SLEEP_PM_OPS(dwc3_omap_suspend, dwc3_omap_resume) | 622 | SET_SYSTEM_SLEEP_PM_OPS(dwc3_omap_suspend, dwc3_omap_resume) |
| 639 | }; | 623 | }; |
diff --git a/drivers/usb/dwc3/dwc3-pci.c b/drivers/usb/dwc3/dwc3-pci.c index a36cf66302fb..7c4faf738747 100644 --- a/drivers/usb/dwc3/dwc3-pci.c +++ b/drivers/usb/dwc3/dwc3-pci.c | |||
| @@ -25,6 +25,8 @@ | |||
| 25 | #include <linux/usb/otg.h> | 25 | #include <linux/usb/otg.h> |
| 26 | #include <linux/usb/usb_phy_generic.h> | 26 | #include <linux/usb/usb_phy_generic.h> |
| 27 | 27 | ||
| 28 | #include "platform_data.h" | ||
| 29 | |||
| 28 | /* FIXME define these in <linux/pci_ids.h> */ | 30 | /* FIXME define these in <linux/pci_ids.h> */ |
| 29 | #define PCI_VENDOR_ID_SYNOPSYS 0x16c3 | 31 | #define PCI_VENDOR_ID_SYNOPSYS 0x16c3 |
| 30 | #define PCI_DEVICE_ID_SYNOPSYS_HAPSUSB3 0xabcd | 32 | #define PCI_DEVICE_ID_SYNOPSYS_HAPSUSB3 0xabcd |
| @@ -102,6 +104,9 @@ static int dwc3_pci_probe(struct pci_dev *pci, | |||
| 102 | struct dwc3_pci *glue; | 104 | struct dwc3_pci *glue; |
| 103 | int ret; | 105 | int ret; |
| 104 | struct device *dev = &pci->dev; | 106 | struct device *dev = &pci->dev; |
| 107 | struct dwc3_platform_data dwc3_pdata; | ||
| 108 | |||
| 109 | memset(&dwc3_pdata, 0x00, sizeof(dwc3_pdata)); | ||
| 105 | 110 | ||
| 106 | glue = devm_kzalloc(dev, sizeof(*glue), GFP_KERNEL); | 111 | glue = devm_kzalloc(dev, sizeof(*glue), GFP_KERNEL); |
| 107 | if (!glue) | 112 | if (!glue) |
| @@ -140,6 +145,31 @@ static int dwc3_pci_probe(struct pci_dev *pci, | |||
| 140 | res[1].name = "dwc_usb3"; | 145 | res[1].name = "dwc_usb3"; |
| 141 | res[1].flags = IORESOURCE_IRQ; | 146 | res[1].flags = IORESOURCE_IRQ; |
| 142 | 147 | ||
| 148 | if (pci->vendor == PCI_VENDOR_ID_AMD && | ||
| 149 | pci->device == PCI_DEVICE_ID_AMD_NL_USB) { | ||
| 150 | dwc3_pdata.has_lpm_erratum = true; | ||
| 151 | dwc3_pdata.lpm_nyet_threshold = 0xf; | ||
| 152 | |||
| 153 | dwc3_pdata.u2exit_lfps_quirk = true; | ||
| 154 | dwc3_pdata.u2ss_inp3_quirk = true; | ||
| 155 | dwc3_pdata.req_p1p2p3_quirk = true; | ||
| 156 | dwc3_pdata.del_p1p2p3_quirk = true; | ||
| 157 | dwc3_pdata.del_phy_power_chg_quirk = true; | ||
| 158 | dwc3_pdata.lfps_filter_quirk = true; | ||
| 159 | dwc3_pdata.rx_detect_poll_quirk = true; | ||
| 160 | |||
| 161 | dwc3_pdata.tx_de_emphasis_quirk = true; | ||
| 162 | dwc3_pdata.tx_de_emphasis = 1; | ||
| 163 | |||
| 164 | /* | ||
| 165 | * FIXME these quirks should be removed when AMD NL | ||
| 166 | * taps out | ||
| 167 | */ | ||
| 168 | dwc3_pdata.disable_scramble_quirk = true; | ||
| 169 | dwc3_pdata.dis_u3_susphy_quirk = true; | ||
| 170 | dwc3_pdata.dis_u2_susphy_quirk = true; | ||
| 171 | } | ||
| 172 | |||
| 143 | ret = platform_device_add_resources(dwc3, res, ARRAY_SIZE(res)); | 173 | ret = platform_device_add_resources(dwc3, res, ARRAY_SIZE(res)); |
| 144 | if (ret) { | 174 | if (ret) { |
| 145 | dev_err(dev, "couldn't add resources to dwc3 device\n"); | 175 | dev_err(dev, "couldn't add resources to dwc3 device\n"); |
| @@ -148,6 +178,10 @@ static int dwc3_pci_probe(struct pci_dev *pci, | |||
| 148 | 178 | ||
| 149 | pci_set_drvdata(pci, glue); | 179 | pci_set_drvdata(pci, glue); |
| 150 | 180 | ||
| 181 | ret = platform_device_add_data(dwc3, &dwc3_pdata, sizeof(dwc3_pdata)); | ||
| 182 | if (ret) | ||
| 183 | goto err3; | ||
| 184 | |||
| 151 | dma_set_coherent_mask(&dwc3->dev, dev->coherent_dma_mask); | 185 | dma_set_coherent_mask(&dwc3->dev, dev->coherent_dma_mask); |
| 152 | 186 | ||
| 153 | dwc3->dev.dma_mask = dev->dma_mask; | 187 | dwc3->dev.dma_mask = dev->dma_mask; |
| @@ -185,6 +219,7 @@ static const struct pci_device_id dwc3_pci_id_table[] = { | |||
| 185 | { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BSW), }, | 219 | { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BSW), }, |
| 186 | { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BYT), }, | 220 | { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BYT), }, |
| 187 | { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_MRFLD), }, | 221 | { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_MRFLD), }, |
| 222 | { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_NL_USB), }, | ||
| 188 | { } /* Terminating Entry */ | 223 | { } /* Terminating Entry */ |
| 189 | }; | 224 | }; |
| 190 | MODULE_DEVICE_TABLE(pci, dwc3_pci_id_table); | 225 | MODULE_DEVICE_TABLE(pci, dwc3_pci_id_table); |
diff --git a/drivers/usb/dwc3/dwc3-st.c b/drivers/usb/dwc3/dwc3-st.c index c7602b5362ad..4a1a543deeda 100644 --- a/drivers/usb/dwc3/dwc3-st.c +++ b/drivers/usb/dwc3/dwc3-st.c | |||
| @@ -243,7 +243,7 @@ static int st_dwc3_probe(struct platform_device *pdev) | |||
| 243 | dwc3_data->rstc_rst = devm_reset_control_get(dev, "softreset"); | 243 | dwc3_data->rstc_rst = devm_reset_control_get(dev, "softreset"); |
| 244 | if (IS_ERR(dwc3_data->rstc_rst)) { | 244 | if (IS_ERR(dwc3_data->rstc_rst)) { |
| 245 | dev_err(&pdev->dev, "could not get reset controller\n"); | 245 | dev_err(&pdev->dev, "could not get reset controller\n"); |
| 246 | ret = PTR_ERR(dwc3_data->rstc_pwrdn); | 246 | ret = PTR_ERR(dwc3_data->rstc_rst); |
| 247 | goto undo_powerdown; | 247 | goto undo_powerdown; |
| 248 | } | 248 | } |
| 249 | 249 | ||
diff --git a/drivers/usb/dwc3/ep0.c b/drivers/usb/dwc3/ep0.c index df38e7ef4976..1bc77a3b4997 100644 --- a/drivers/usb/dwc3/ep0.c +++ b/drivers/usb/dwc3/ep0.c | |||
| @@ -86,6 +86,8 @@ static int dwc3_ep0_start_trans(struct dwc3 *dwc, u8 epnum, dma_addr_t buf_dma, | |||
| 86 | params.param0 = upper_32_bits(dwc->ep0_trb_addr); | 86 | params.param0 = upper_32_bits(dwc->ep0_trb_addr); |
| 87 | params.param1 = lower_32_bits(dwc->ep0_trb_addr); | 87 | params.param1 = lower_32_bits(dwc->ep0_trb_addr); |
| 88 | 88 | ||
| 89 | trace_dwc3_prepare_trb(dep, trb); | ||
| 90 | |||
| 89 | ret = dwc3_send_gadget_ep_cmd(dwc, dep->number, | 91 | ret = dwc3_send_gadget_ep_cmd(dwc, dep->number, |
| 90 | DWC3_DEPCMD_STARTTRANSFER, ¶ms); | 92 | DWC3_DEPCMD_STARTTRANSFER, ¶ms); |
| 91 | if (ret < 0) { | 93 | if (ret < 0) { |
| @@ -441,7 +443,6 @@ static int dwc3_ep0_handle_feature(struct dwc3 *dwc, | |||
| 441 | 443 | ||
| 442 | case USB_DEVICE_LTM_ENABLE: | 444 | case USB_DEVICE_LTM_ENABLE: |
| 443 | return -EINVAL; | 445 | return -EINVAL; |
| 444 | break; | ||
| 445 | 446 | ||
| 446 | case USB_DEVICE_TEST_MODE: | 447 | case USB_DEVICE_TEST_MODE: |
| 447 | if ((wIndex & 0xff) != 0) | 448 | if ((wIndex & 0xff) != 0) |
| @@ -550,7 +551,6 @@ static int dwc3_ep0_set_config(struct dwc3 *dwc, struct usb_ctrlrequest *ctrl) | |||
| 550 | switch (state) { | 551 | switch (state) { |
| 551 | case USB_STATE_DEFAULT: | 552 | case USB_STATE_DEFAULT: |
| 552 | return -EINVAL; | 553 | return -EINVAL; |
| 553 | break; | ||
| 554 | 554 | ||
| 555 | case USB_STATE_ADDRESS: | 555 | case USB_STATE_ADDRESS: |
| 556 | ret = dwc3_ep0_delegate_req(dwc, ctrl); | 556 | ret = dwc3_ep0_delegate_req(dwc, ctrl); |
| @@ -700,35 +700,35 @@ static int dwc3_ep0_std_request(struct dwc3 *dwc, struct usb_ctrlrequest *ctrl) | |||
| 700 | 700 | ||
| 701 | switch (ctrl->bRequest) { | 701 | switch (ctrl->bRequest) { |
| 702 | case USB_REQ_GET_STATUS: | 702 | case USB_REQ_GET_STATUS: |
| 703 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_GET_STATUS\n"); | 703 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_GET_STATUS"); |
| 704 | ret = dwc3_ep0_handle_status(dwc, ctrl); | 704 | ret = dwc3_ep0_handle_status(dwc, ctrl); |
| 705 | break; | 705 | break; |
| 706 | case USB_REQ_CLEAR_FEATURE: | 706 | case USB_REQ_CLEAR_FEATURE: |
| 707 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_CLEAR_FEATURE\n"); | 707 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_CLEAR_FEATURE"); |
| 708 | ret = dwc3_ep0_handle_feature(dwc, ctrl, 0); | 708 | ret = dwc3_ep0_handle_feature(dwc, ctrl, 0); |
| 709 | break; | 709 | break; |
| 710 | case USB_REQ_SET_FEATURE: | 710 | case USB_REQ_SET_FEATURE: |
| 711 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_SET_FEATURE\n"); | 711 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_SET_FEATURE"); |
| 712 | ret = dwc3_ep0_handle_feature(dwc, ctrl, 1); | 712 | ret = dwc3_ep0_handle_feature(dwc, ctrl, 1); |
| 713 | break; | 713 | break; |
| 714 | case USB_REQ_SET_ADDRESS: | 714 | case USB_REQ_SET_ADDRESS: |
| 715 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_SET_ADDRESS\n"); | 715 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_SET_ADDRESS"); |
| 716 | ret = dwc3_ep0_set_address(dwc, ctrl); | 716 | ret = dwc3_ep0_set_address(dwc, ctrl); |
| 717 | break; | 717 | break; |
| 718 | case USB_REQ_SET_CONFIGURATION: | 718 | case USB_REQ_SET_CONFIGURATION: |
| 719 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_SET_CONFIGURATION\n"); | 719 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_SET_CONFIGURATION"); |
| 720 | ret = dwc3_ep0_set_config(dwc, ctrl); | 720 | ret = dwc3_ep0_set_config(dwc, ctrl); |
| 721 | break; | 721 | break; |
| 722 | case USB_REQ_SET_SEL: | 722 | case USB_REQ_SET_SEL: |
| 723 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_SET_SEL\n"); | 723 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_SET_SEL"); |
| 724 | ret = dwc3_ep0_set_sel(dwc, ctrl); | 724 | ret = dwc3_ep0_set_sel(dwc, ctrl); |
| 725 | break; | 725 | break; |
| 726 | case USB_REQ_SET_ISOCH_DELAY: | 726 | case USB_REQ_SET_ISOCH_DELAY: |
| 727 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_SET_ISOCH_DELAY\n"); | 727 | dwc3_trace(trace_dwc3_ep0, "USB_REQ_SET_ISOCH_DELAY"); |
| 728 | ret = dwc3_ep0_set_isoch_delay(dwc, ctrl); | 728 | ret = dwc3_ep0_set_isoch_delay(dwc, ctrl); |
| 729 | break; | 729 | break; |
| 730 | default: | 730 | default: |
| 731 | dwc3_trace(trace_dwc3_ep0, "Forwarding to gadget driver\n"); | 731 | dwc3_trace(trace_dwc3_ep0, "Forwarding to gadget driver"); |
| 732 | ret = dwc3_ep0_delegate_req(dwc, ctrl); | 732 | ret = dwc3_ep0_delegate_req(dwc, ctrl); |
| 733 | break; | 733 | break; |
| 734 | } | 734 | } |
| @@ -791,6 +791,8 @@ static void dwc3_ep0_complete_data(struct dwc3 *dwc, | |||
| 791 | 791 | ||
| 792 | trb = dwc->ep0_trb; | 792 | trb = dwc->ep0_trb; |
| 793 | 793 | ||
| 794 | trace_dwc3_complete_trb(ep0, trb); | ||
| 795 | |||
| 794 | r = next_request(&ep0->request_list); | 796 | r = next_request(&ep0->request_list); |
| 795 | if (!r) | 797 | if (!r) |
| 796 | return; | 798 | return; |
| @@ -855,6 +857,8 @@ static void dwc3_ep0_complete_status(struct dwc3 *dwc, | |||
| 855 | dep = dwc->eps[0]; | 857 | dep = dwc->eps[0]; |
| 856 | trb = dwc->ep0_trb; | 858 | trb = dwc->ep0_trb; |
| 857 | 859 | ||
| 860 | trace_dwc3_complete_trb(dep, trb); | ||
| 861 | |||
| 858 | if (!list_empty(&dep->request_list)) { | 862 | if (!list_empty(&dep->request_list)) { |
| 859 | r = next_request(&dep->request_list); | 863 | r = next_request(&dep->request_list); |
| 860 | 864 | ||
| @@ -875,7 +879,7 @@ static void dwc3_ep0_complete_status(struct dwc3 *dwc, | |||
| 875 | 879 | ||
| 876 | status = DWC3_TRB_SIZE_TRBSTS(trb->size); | 880 | status = DWC3_TRB_SIZE_TRBSTS(trb->size); |
| 877 | if (status == DWC3_TRBSTS_SETUP_PENDING) | 881 | if (status == DWC3_TRBSTS_SETUP_PENDING) |
| 878 | dwc3_trace(trace_dwc3_ep0, "Setup Pending received\n"); | 882 | dwc3_trace(trace_dwc3_ep0, "Setup Pending received"); |
| 879 | 883 | ||
| 880 | dwc->ep0state = EP0_SETUP_PHASE; | 884 | dwc->ep0state = EP0_SETUP_PHASE; |
| 881 | dwc3_ep0_out_start(dwc); | 885 | dwc3_ep0_out_start(dwc); |
diff --git a/drivers/usb/dwc3/gadget.c b/drivers/usb/dwc3/gadget.c index 546ea5431b8c..f03b136ecfce 100644 --- a/drivers/usb/dwc3/gadget.c +++ b/drivers/usb/dwc3/gadget.c | |||
| @@ -1140,8 +1140,14 @@ static int dwc3_gadget_ep_queue(struct usb_ep *ep, struct usb_request *request, | |||
| 1140 | if (!dep->endpoint.desc) { | 1140 | if (!dep->endpoint.desc) { |
| 1141 | dev_dbg(dwc->dev, "trying to queue request %p to disabled %s\n", | 1141 | dev_dbg(dwc->dev, "trying to queue request %p to disabled %s\n", |
| 1142 | request, ep->name); | 1142 | request, ep->name); |
| 1143 | spin_unlock_irqrestore(&dwc->lock, flags); | 1143 | ret = -ESHUTDOWN; |
| 1144 | return -ESHUTDOWN; | 1144 | goto out; |
| 1145 | } | ||
| 1146 | |||
| 1147 | if (WARN(req->dep != dep, "request %p belongs to '%s'\n", | ||
| 1148 | request, req->dep->name)) { | ||
| 1149 | ret = -EINVAL; | ||
| 1150 | goto out; | ||
| 1145 | } | 1151 | } |
| 1146 | 1152 | ||
| 1147 | dev_vdbg(dwc->dev, "queing request %p to %s length %d\n", | 1153 | dev_vdbg(dwc->dev, "queing request %p to %s length %d\n", |
| @@ -1149,6 +1155,8 @@ static int dwc3_gadget_ep_queue(struct usb_ep *ep, struct usb_request *request, | |||
| 1149 | trace_dwc3_ep_queue(req); | 1155 | trace_dwc3_ep_queue(req); |
| 1150 | 1156 | ||
| 1151 | ret = __dwc3_gadget_ep_queue(dep, req); | 1157 | ret = __dwc3_gadget_ep_queue(dep, req); |
| 1158 | |||
| 1159 | out: | ||
| 1152 | spin_unlock_irqrestore(&dwc->lock, flags); | 1160 | spin_unlock_irqrestore(&dwc->lock, flags); |
| 1153 | 1161 | ||
| 1154 | return ret; | 1162 | return ret; |
| @@ -1622,8 +1630,7 @@ err0: | |||
| 1622 | return ret; | 1630 | return ret; |
| 1623 | } | 1631 | } |
| 1624 | 1632 | ||
| 1625 | static int dwc3_gadget_stop(struct usb_gadget *g, | 1633 | static int dwc3_gadget_stop(struct usb_gadget *g) |
| 1626 | struct usb_gadget_driver *driver) | ||
| 1627 | { | 1634 | { |
| 1628 | struct dwc3 *dwc = gadget_to_dwc(g); | 1635 | struct dwc3 *dwc = gadget_to_dwc(g); |
| 1629 | unsigned long flags; | 1636 | unsigned long flags; |
| @@ -2034,6 +2041,17 @@ static void dwc3_resume_gadget(struct dwc3 *dwc) | |||
| 2034 | if (dwc->gadget_driver && dwc->gadget_driver->resume) { | 2041 | if (dwc->gadget_driver && dwc->gadget_driver->resume) { |
| 2035 | spin_unlock(&dwc->lock); | 2042 | spin_unlock(&dwc->lock); |
| 2036 | dwc->gadget_driver->resume(&dwc->gadget); | 2043 | dwc->gadget_driver->resume(&dwc->gadget); |
| 2044 | } | ||
| 2045 | } | ||
| 2046 | |||
| 2047 | static void dwc3_reset_gadget(struct dwc3 *dwc) | ||
| 2048 | { | ||
| 2049 | if (!dwc->gadget_driver) | ||
| 2050 | return; | ||
| 2051 | |||
| 2052 | if (dwc->gadget.speed != USB_SPEED_UNKNOWN) { | ||
| 2053 | spin_unlock(&dwc->lock); | ||
| 2054 | usb_gadget_udc_reset(&dwc->gadget, dwc->gadget_driver); | ||
| 2037 | spin_lock(&dwc->lock); | 2055 | spin_lock(&dwc->lock); |
| 2038 | } | 2056 | } |
| 2039 | } | 2057 | } |
| @@ -2140,6 +2158,7 @@ static void dwc3_gadget_disconnect_interrupt(struct dwc3 *dwc) | |||
| 2140 | 2158 | ||
| 2141 | dwc->gadget.speed = USB_SPEED_UNKNOWN; | 2159 | dwc->gadget.speed = USB_SPEED_UNKNOWN; |
| 2142 | dwc->setup_packet_pending = false; | 2160 | dwc->setup_packet_pending = false; |
| 2161 | usb_gadget_set_state(&dwc->gadget, USB_STATE_NOTATTACHED); | ||
| 2143 | } | 2162 | } |
| 2144 | 2163 | ||
| 2145 | static void dwc3_gadget_reset_interrupt(struct dwc3 *dwc) | 2164 | static void dwc3_gadget_reset_interrupt(struct dwc3 *dwc) |
| @@ -2177,11 +2196,7 @@ static void dwc3_gadget_reset_interrupt(struct dwc3 *dwc) | |||
| 2177 | dwc3_gadget_disconnect_interrupt(dwc); | 2196 | dwc3_gadget_disconnect_interrupt(dwc); |
| 2178 | } | 2197 | } |
| 2179 | 2198 | ||
| 2180 | /* after reset -> Default State */ | 2199 | dwc3_reset_gadget(dwc); |
| 2181 | usb_gadget_set_state(&dwc->gadget, USB_STATE_DEFAULT); | ||
| 2182 | |||
| 2183 | if (dwc->gadget.speed != USB_SPEED_UNKNOWN) | ||
| 2184 | dwc3_disconnect_gadget(dwc); | ||
| 2185 | 2200 | ||
| 2186 | reg = dwc3_readl(dwc->regs, DWC3_DCTL); | 2201 | reg = dwc3_readl(dwc->regs, DWC3_DCTL); |
| 2187 | reg &= ~DWC3_DCTL_TSTCTRL_MASK; | 2202 | reg &= ~DWC3_DCTL_TSTCTRL_MASK; |
| @@ -2287,11 +2302,20 @@ static void dwc3_gadget_conndone_interrupt(struct dwc3 *dwc) | |||
| 2287 | reg = dwc3_readl(dwc->regs, DWC3_DCTL); | 2302 | reg = dwc3_readl(dwc->regs, DWC3_DCTL); |
| 2288 | reg &= ~(DWC3_DCTL_HIRD_THRES_MASK | DWC3_DCTL_L1_HIBER_EN); | 2303 | reg &= ~(DWC3_DCTL_HIRD_THRES_MASK | DWC3_DCTL_L1_HIBER_EN); |
| 2289 | 2304 | ||
| 2305 | reg |= DWC3_DCTL_HIRD_THRES(dwc->hird_threshold); | ||
| 2306 | |||
| 2290 | /* | 2307 | /* |
| 2291 | * TODO: This should be configurable. For now using | 2308 | * When dwc3 revisions >= 2.40a, LPM Erratum is enabled and |
| 2292 | * maximum allowed HIRD threshold value of 0b1100 | 2309 | * DCFG.LPMCap is set, core responses with an ACK and the |
| 2310 | * BESL value in the LPM token is less than or equal to LPM | ||
| 2311 | * NYET threshold. | ||
| 2293 | */ | 2312 | */ |
| 2294 | reg |= DWC3_DCTL_HIRD_THRES(12); | 2313 | WARN_ONCE(dwc->revision < DWC3_REVISION_240A |
| 2314 | && dwc->has_lpm_erratum, | ||
| 2315 | "LPM Erratum not available on dwc3 revisisions < 2.40a\n"); | ||
| 2316 | |||
| 2317 | if (dwc->has_lpm_erratum && dwc->revision >= DWC3_REVISION_240A) | ||
| 2318 | reg |= DWC3_DCTL_LPM_ERRATA(dwc->lpm_nyet_threshold); | ||
| 2295 | 2319 | ||
| 2296 | dwc3_writel(dwc->regs, DWC3_DCTL, reg); | 2320 | dwc3_writel(dwc->regs, DWC3_DCTL, reg); |
| 2297 | } else { | 2321 | } else { |
| @@ -2744,26 +2768,13 @@ void dwc3_gadget_exit(struct dwc3 *dwc) | |||
| 2744 | dwc->ctrl_req, dwc->ctrl_req_addr); | 2768 | dwc->ctrl_req, dwc->ctrl_req_addr); |
| 2745 | } | 2769 | } |
| 2746 | 2770 | ||
| 2747 | int dwc3_gadget_prepare(struct dwc3 *dwc) | 2771 | int dwc3_gadget_suspend(struct dwc3 *dwc) |
| 2748 | { | 2772 | { |
| 2749 | if (dwc->pullups_connected) { | 2773 | if (dwc->pullups_connected) { |
| 2750 | dwc3_gadget_disable_irq(dwc); | 2774 | dwc3_gadget_disable_irq(dwc); |
| 2751 | dwc3_gadget_run_stop(dwc, true, true); | 2775 | dwc3_gadget_run_stop(dwc, true, true); |
| 2752 | } | 2776 | } |
| 2753 | 2777 | ||
| 2754 | return 0; | ||
| 2755 | } | ||
| 2756 | |||
| 2757 | void dwc3_gadget_complete(struct dwc3 *dwc) | ||
| 2758 | { | ||
| 2759 | if (dwc->pullups_connected) { | ||
| 2760 | dwc3_gadget_enable_irq(dwc); | ||
| 2761 | dwc3_gadget_run_stop(dwc, true, false); | ||
| 2762 | } | ||
| 2763 | } | ||
| 2764 | |||
| 2765 | int dwc3_gadget_suspend(struct dwc3 *dwc) | ||
| 2766 | { | ||
| 2767 | __dwc3_gadget_ep_disable(dwc->eps[0]); | 2778 | __dwc3_gadget_ep_disable(dwc->eps[0]); |
| 2768 | __dwc3_gadget_ep_disable(dwc->eps[1]); | 2779 | __dwc3_gadget_ep_disable(dwc->eps[1]); |
| 2769 | 2780 | ||
| @@ -2798,6 +2809,11 @@ int dwc3_gadget_resume(struct dwc3 *dwc) | |||
| 2798 | 2809 | ||
| 2799 | dwc3_writel(dwc->regs, DWC3_DCFG, dwc->dcfg); | 2810 | dwc3_writel(dwc->regs, DWC3_DCFG, dwc->dcfg); |
| 2800 | 2811 | ||
| 2812 | if (dwc->pullups_connected) { | ||
| 2813 | dwc3_gadget_enable_irq(dwc); | ||
| 2814 | dwc3_gadget_run_stop(dwc, true, false); | ||
| 2815 | } | ||
| 2816 | |||
| 2801 | return 0; | 2817 | return 0; |
| 2802 | 2818 | ||
| 2803 | err1: | 2819 | err1: |
diff --git a/drivers/usb/dwc3/host.c b/drivers/usb/dwc3/host.c index dcb8ca084598..12bfd3c5405e 100644 --- a/drivers/usb/dwc3/host.c +++ b/drivers/usb/dwc3/host.c | |||
| @@ -29,8 +29,7 @@ int dwc3_host_init(struct dwc3 *dwc) | |||
| 29 | xhci = platform_device_alloc("xhci-hcd", PLATFORM_DEVID_AUTO); | 29 | xhci = platform_device_alloc("xhci-hcd", PLATFORM_DEVID_AUTO); |
| 30 | if (!xhci) { | 30 | if (!xhci) { |
| 31 | dev_err(dwc->dev, "couldn't allocate xHCI device\n"); | 31 | dev_err(dwc->dev, "couldn't allocate xHCI device\n"); |
| 32 | ret = -ENOMEM; | 32 | return -ENOMEM; |
| 33 | goto err0; | ||
| 34 | } | 33 | } |
| 35 | 34 | ||
| 36 | dma_set_coherent_mask(&xhci->dev, dwc->dev->coherent_dma_mask); | 35 | dma_set_coherent_mask(&xhci->dev, dwc->dev->coherent_dma_mask); |
| @@ -60,22 +59,33 @@ int dwc3_host_init(struct dwc3 *dwc) | |||
| 60 | goto err1; | 59 | goto err1; |
| 61 | } | 60 | } |
| 62 | 61 | ||
| 62 | phy_create_lookup(dwc->usb2_generic_phy, "usb2-phy", | ||
| 63 | dev_name(&xhci->dev)); | ||
| 64 | phy_create_lookup(dwc->usb3_generic_phy, "usb3-phy", | ||
| 65 | dev_name(&xhci->dev)); | ||
| 66 | |||
| 63 | ret = platform_device_add(xhci); | 67 | ret = platform_device_add(xhci); |
| 64 | if (ret) { | 68 | if (ret) { |
| 65 | dev_err(dwc->dev, "failed to register xHCI device\n"); | 69 | dev_err(dwc->dev, "failed to register xHCI device\n"); |
| 66 | goto err1; | 70 | goto err2; |
| 67 | } | 71 | } |
| 68 | 72 | ||
| 69 | return 0; | 73 | return 0; |
| 70 | 74 | err2: | |
| 75 | phy_remove_lookup(dwc->usb2_generic_phy, "usb2-phy", | ||
| 76 | dev_name(&xhci->dev)); | ||
| 77 | phy_remove_lookup(dwc->usb3_generic_phy, "usb3-phy", | ||
| 78 | dev_name(&xhci->dev)); | ||
| 71 | err1: | 79 | err1: |
| 72 | platform_device_put(xhci); | 80 | platform_device_put(xhci); |
| 73 | |||
| 74 | err0: | ||
| 75 | return ret; | 81 | return ret; |
| 76 | } | 82 | } |
| 77 | 83 | ||
| 78 | void dwc3_host_exit(struct dwc3 *dwc) | 84 | void dwc3_host_exit(struct dwc3 *dwc) |
| 79 | { | 85 | { |
| 86 | phy_remove_lookup(dwc->usb2_generic_phy, "usb2-phy", | ||
| 87 | dev_name(&dwc->xhci->dev)); | ||
| 88 | phy_remove_lookup(dwc->usb3_generic_phy, "usb3-phy", | ||
| 89 | dev_name(&dwc->xhci->dev)); | ||
| 80 | platform_device_unregister(dwc->xhci); | 90 | platform_device_unregister(dwc->xhci); |
| 81 | } | 91 | } |
diff --git a/drivers/usb/dwc3/platform_data.h b/drivers/usb/dwc3/platform_data.h index 7db34f00b89a..a3a3b6d5668c 100644 --- a/drivers/usb/dwc3/platform_data.h +++ b/drivers/usb/dwc3/platform_data.h | |||
| @@ -24,4 +24,24 @@ struct dwc3_platform_data { | |||
| 24 | enum usb_device_speed maximum_speed; | 24 | enum usb_device_speed maximum_speed; |
| 25 | enum usb_dr_mode dr_mode; | 25 | enum usb_dr_mode dr_mode; |
| 26 | bool tx_fifo_resize; | 26 | bool tx_fifo_resize; |
| 27 | |||
| 28 | unsigned is_utmi_l1_suspend:1; | ||
| 29 | u8 hird_threshold; | ||
| 30 | |||
| 31 | u8 lpm_nyet_threshold; | ||
| 32 | |||
| 33 | unsigned disable_scramble_quirk:1; | ||
| 34 | unsigned has_lpm_erratum:1; | ||
| 35 | unsigned u2exit_lfps_quirk:1; | ||
| 36 | unsigned u2ss_inp3_quirk:1; | ||
| 37 | unsigned req_p1p2p3_quirk:1; | ||
| 38 | unsigned del_p1p2p3_quirk:1; | ||
| 39 | unsigned del_phy_power_chg_quirk:1; | ||
| 40 | unsigned lfps_filter_quirk:1; | ||
| 41 | unsigned rx_detect_poll_quirk:1; | ||
| 42 | unsigned dis_u3_susphy_quirk:1; | ||
| 43 | unsigned dis_u2_susphy_quirk:1; | ||
| 44 | |||
| 45 | unsigned tx_de_emphasis_quirk:1; | ||
| 46 | unsigned tx_de_emphasis:2; | ||
| 27 | }; | 47 | }; |
diff --git a/drivers/usb/dwc3/trace.h b/drivers/usb/dwc3/trace.h index 60b0f41eafc4..9fc20b33dd8e 100644 --- a/drivers/usb/dwc3/trace.h +++ b/drivers/usb/dwc3/trace.h | |||
| @@ -61,7 +61,7 @@ DECLARE_EVENT_CLASS(dwc3_log_event, | |||
| 61 | TP_fast_assign( | 61 | TP_fast_assign( |
| 62 | __entry->event = event; | 62 | __entry->event = event; |
| 63 | ), | 63 | ), |
| 64 | TP_printk("event %08x\n", __entry->event) | 64 | TP_printk("event %08x", __entry->event) |
| 65 | ); | 65 | ); |
| 66 | 66 | ||
| 67 | DEFINE_EVENT(dwc3_log_event, dwc3_event, | 67 | DEFINE_EVENT(dwc3_log_event, dwc3_event, |
| @@ -157,7 +157,7 @@ DECLARE_EVENT_CLASS(dwc3_log_generic_cmd, | |||
| 157 | __entry->cmd = cmd; | 157 | __entry->cmd = cmd; |
| 158 | __entry->param = param; | 158 | __entry->param = param; |
| 159 | ), | 159 | ), |
| 160 | TP_printk("cmd '%s' [%d] param %08x\n", | 160 | TP_printk("cmd '%s' [%d] param %08x", |
| 161 | dwc3_gadget_generic_cmd_string(__entry->cmd), | 161 | dwc3_gadget_generic_cmd_string(__entry->cmd), |
| 162 | __entry->cmd, __entry->param | 162 | __entry->cmd, __entry->param |
| 163 | ) | 163 | ) |
| @@ -175,17 +175,21 @@ DECLARE_EVENT_CLASS(dwc3_log_gadget_ep_cmd, | |||
| 175 | TP_STRUCT__entry( | 175 | TP_STRUCT__entry( |
| 176 | __dynamic_array(char, name, DWC3_MSG_MAX) | 176 | __dynamic_array(char, name, DWC3_MSG_MAX) |
| 177 | __field(unsigned int, cmd) | 177 | __field(unsigned int, cmd) |
| 178 | __field(struct dwc3_gadget_ep_cmd_params *, params) | 178 | __field(u32, param0) |
| 179 | __field(u32, param1) | ||
| 180 | __field(u32, param2) | ||
| 179 | ), | 181 | ), |
| 180 | TP_fast_assign( | 182 | TP_fast_assign( |
| 181 | snprintf(__get_str(name), DWC3_MSG_MAX, "%s", dep->name); | 183 | snprintf(__get_str(name), DWC3_MSG_MAX, "%s", dep->name); |
| 182 | __entry->cmd = cmd; | 184 | __entry->cmd = cmd; |
| 183 | __entry->params = params; | 185 | __entry->param0 = params->param0; |
| 186 | __entry->param1 = params->param1; | ||
| 187 | __entry->param2 = params->param2; | ||
| 184 | ), | 188 | ), |
| 185 | TP_printk("%s: cmd '%s' [%d] params %08x %08x %08x\n", | 189 | TP_printk("%s: cmd '%s' [%d] params %08x %08x %08x", |
| 186 | __get_str(name), dwc3_gadget_ep_cmd_string(__entry->cmd), | 190 | __get_str(name), dwc3_gadget_ep_cmd_string(__entry->cmd), |
| 187 | __entry->cmd, __entry->params->param0, | 191 | __entry->cmd, __entry->param0, |
| 188 | __entry->params->param1, __entry->params->param2 | 192 | __entry->param1, __entry->param2 |
| 189 | ) | 193 | ) |
| 190 | ); | 194 | ); |
| 191 | 195 | ||
| @@ -214,7 +218,7 @@ DECLARE_EVENT_CLASS(dwc3_log_trb, | |||
| 214 | __entry->size = trb->size; | 218 | __entry->size = trb->size; |
| 215 | __entry->ctrl = trb->ctrl; | 219 | __entry->ctrl = trb->ctrl; |
| 216 | ), | 220 | ), |
| 217 | TP_printk("%s: trb %p bph %08x bpl %08x size %08x ctrl %08x\n", | 221 | TP_printk("%s: trb %p bph %08x bpl %08x size %08x ctrl %08x", |
| 218 | __get_str(name), __entry->trb, __entry->bph, __entry->bpl, | 222 | __get_str(name), __entry->trb, __entry->bph, __entry->bpl, |
| 219 | __entry->size, __entry->ctrl | 223 | __entry->size, __entry->ctrl |
| 220 | ) | 224 | ) |
diff --git a/drivers/usb/gadget/Kconfig b/drivers/usb/gadget/Kconfig index c4880fc0d86e..747ef53bda14 100644 --- a/drivers/usb/gadget/Kconfig +++ b/drivers/usb/gadget/Kconfig | |||
| @@ -190,6 +190,12 @@ config USB_F_UAC2 | |||
| 190 | config USB_F_UVC | 190 | config USB_F_UVC |
| 191 | tristate | 191 | tristate |
| 192 | 192 | ||
| 193 | config USB_F_MIDI | ||
| 194 | tristate | ||
| 195 | |||
| 196 | config USB_F_HID | ||
| 197 | tristate | ||
| 198 | |||
| 193 | choice | 199 | choice |
| 194 | tristate "USB Gadget Drivers" | 200 | tristate "USB Gadget Drivers" |
| 195 | default USB_ETH | 201 | default USB_ETH |
| @@ -362,6 +368,61 @@ config USB_CONFIGFS_F_FS | |||
| 362 | implemented in kernel space (for instance Ethernet, serial or | 368 | implemented in kernel space (for instance Ethernet, serial or |
| 363 | mass storage) and other are implemented in user space. | 369 | mass storage) and other are implemented in user space. |
| 364 | 370 | ||
| 371 | config USB_CONFIGFS_F_UAC1 | ||
| 372 | boolean "Audio Class 1.0" | ||
| 373 | depends on USB_CONFIGFS | ||
| 374 | depends on SND | ||
| 375 | select USB_LIBCOMPOSITE | ||
| 376 | select SND_PCM | ||
| 377 | select USB_F_UAC1 | ||
| 378 | help | ||
| 379 | This Audio function implements 1 AudioControl interface, | ||
| 380 | 1 AudioStreaming Interface each for USB-OUT and USB-IN. | ||
| 381 | This driver requires a real Audio codec to be present | ||
| 382 | on the device. | ||
| 383 | |||
| 384 | config USB_CONFIGFS_F_UAC2 | ||
| 385 | boolean "Audio Class 2.0" | ||
| 386 | depends on USB_CONFIGFS | ||
| 387 | depends on SND | ||
| 388 | select USB_LIBCOMPOSITE | ||
| 389 | select SND_PCM | ||
| 390 | select USB_F_UAC2 | ||
| 391 | help | ||
| 392 | This Audio function is compatible with USB Audio Class | ||
| 393 | specification 2.0. It implements 1 AudioControl interface, | ||
| 394 | 1 AudioStreaming Interface each for USB-OUT and USB-IN. | ||
| 395 | This driver doesn't expect any real Audio codec to be present | ||
| 396 | on the device - the audio streams are simply sinked to and | ||
| 397 | sourced from a virtual ALSA sound card created. The user-space | ||
| 398 | application may choose to do whatever it wants with the data | ||
| 399 | received from the USB Host and choose to provide whatever it | ||
| 400 | wants as audio data to the USB Host. | ||
| 401 | |||
| 402 | config USB_CONFIGFS_F_MIDI | ||
| 403 | boolean "MIDI function" | ||
| 404 | depends on USB_CONFIGFS | ||
| 405 | depends on SND | ||
| 406 | select USB_LIBCOMPOSITE | ||
| 407 | select SND_RAWMIDI | ||
| 408 | select USB_F_MIDI | ||
| 409 | help | ||
| 410 | The MIDI Function acts as a USB Audio device, with one MIDI | ||
| 411 | input and one MIDI output. These MIDI jacks appear as | ||
| 412 | a sound "card" in the ALSA sound system. Other MIDI | ||
| 413 | connections can then be made on the gadget system, using | ||
| 414 | ALSA's aconnect utility etc. | ||
| 415 | |||
| 416 | config USB_CONFIGFS_F_HID | ||
| 417 | boolean "HID function" | ||
| 418 | depends on USB_CONFIGFS | ||
| 419 | select USB_F_HID | ||
| 420 | help | ||
| 421 | The HID function driver provides generic emulation of USB | ||
| 422 | Human Interface Devices (HID). | ||
| 423 | |||
| 424 | For more information, see Documentation/usb/gadget_hid.txt. | ||
| 425 | |||
| 365 | source "drivers/usb/gadget/legacy/Kconfig" | 426 | source "drivers/usb/gadget/legacy/Kconfig" |
| 366 | 427 | ||
| 367 | endchoice | 428 | endchoice |
diff --git a/drivers/usb/gadget/composite.c b/drivers/usb/gadget/composite.c index f6a51fddd5b5..617835348569 100644 --- a/drivers/usb/gadget/composite.c +++ b/drivers/usb/gadget/composite.c | |||
| @@ -1246,10 +1246,49 @@ EXPORT_SYMBOL_GPL(usb_string_ids_n); | |||
| 1246 | 1246 | ||
| 1247 | static void composite_setup_complete(struct usb_ep *ep, struct usb_request *req) | 1247 | static void composite_setup_complete(struct usb_ep *ep, struct usb_request *req) |
| 1248 | { | 1248 | { |
| 1249 | struct usb_composite_dev *cdev; | ||
| 1250 | |||
| 1249 | if (req->status || req->actual != req->length) | 1251 | if (req->status || req->actual != req->length) |
| 1250 | DBG((struct usb_composite_dev *) ep->driver_data, | 1252 | DBG((struct usb_composite_dev *) ep->driver_data, |
| 1251 | "setup complete --> %d, %d/%d\n", | 1253 | "setup complete --> %d, %d/%d\n", |
| 1252 | req->status, req->actual, req->length); | 1254 | req->status, req->actual, req->length); |
| 1255 | |||
| 1256 | /* | ||
| 1257 | * REVIST The same ep0 requests are shared with function drivers | ||
| 1258 | * so they don't have to maintain the same ->complete() stubs. | ||
| 1259 | * | ||
| 1260 | * Because of that, we need to check for the validity of ->context | ||
| 1261 | * here, even though we know we've set it to something useful. | ||
| 1262 | */ | ||
| 1263 | if (!req->context) | ||
| 1264 | return; | ||
| 1265 | |||
| 1266 | cdev = req->context; | ||
| 1267 | |||
| 1268 | if (cdev->req == req) | ||
| 1269 | cdev->setup_pending = false; | ||
| 1270 | else if (cdev->os_desc_req == req) | ||
| 1271 | cdev->os_desc_pending = false; | ||
| 1272 | else | ||
| 1273 | WARN(1, "unknown request %p\n", req); | ||
| 1274 | } | ||
| 1275 | |||
| 1276 | static int composite_ep0_queue(struct usb_composite_dev *cdev, | ||
| 1277 | struct usb_request *req, gfp_t gfp_flags) | ||
| 1278 | { | ||
| 1279 | int ret; | ||
| 1280 | |||
| 1281 | ret = usb_ep_queue(cdev->gadget->ep0, req, gfp_flags); | ||
| 1282 | if (ret == 0) { | ||
| 1283 | if (cdev->req == req) | ||
| 1284 | cdev->setup_pending = true; | ||
| 1285 | else if (cdev->os_desc_req == req) | ||
| 1286 | cdev->os_desc_pending = true; | ||
| 1287 | else | ||
| 1288 | WARN(1, "unknown request %p\n", req); | ||
| 1289 | } | ||
| 1290 | |||
| 1291 | return ret; | ||
| 1253 | } | 1292 | } |
| 1254 | 1293 | ||
| 1255 | static int count_ext_compat(struct usb_configuration *c) | 1294 | static int count_ext_compat(struct usb_configuration *c) |
| @@ -1428,6 +1467,7 @@ composite_setup(struct usb_gadget *gadget, const struct usb_ctrlrequest *ctrl) | |||
| 1428 | * when we delegate to it. | 1467 | * when we delegate to it. |
| 1429 | */ | 1468 | */ |
| 1430 | req->zero = 0; | 1469 | req->zero = 0; |
| 1470 | req->context = cdev; | ||
| 1431 | req->complete = composite_setup_complete; | 1471 | req->complete = composite_setup_complete; |
| 1432 | req->length = 0; | 1472 | req->length = 0; |
| 1433 | gadget->ep0->driver_data = cdev; | 1473 | gadget->ep0->driver_data = cdev; |
| @@ -1624,6 +1664,7 @@ unknown: | |||
| 1624 | int count = 0; | 1664 | int count = 0; |
| 1625 | 1665 | ||
| 1626 | req = cdev->os_desc_req; | 1666 | req = cdev->os_desc_req; |
| 1667 | req->context = cdev; | ||
| 1627 | req->complete = composite_setup_complete; | 1668 | req->complete = composite_setup_complete; |
| 1628 | buf = req->buf; | 1669 | buf = req->buf; |
| 1629 | os_desc_cfg = cdev->os_desc_config; | 1670 | os_desc_cfg = cdev->os_desc_config; |
| @@ -1686,8 +1727,9 @@ unknown: | |||
| 1686 | break; | 1727 | break; |
| 1687 | } | 1728 | } |
| 1688 | req->length = value; | 1729 | req->length = value; |
| 1730 | req->context = cdev; | ||
| 1689 | req->zero = value < w_length; | 1731 | req->zero = value < w_length; |
| 1690 | value = usb_ep_queue(gadget->ep0, req, GFP_ATOMIC); | 1732 | value = composite_ep0_queue(cdev, req, GFP_ATOMIC); |
| 1691 | if (value < 0) { | 1733 | if (value < 0) { |
| 1692 | DBG(cdev, "ep_queue --> %d\n", value); | 1734 | DBG(cdev, "ep_queue --> %d\n", value); |
| 1693 | req->status = 0; | 1735 | req->status = 0; |
| @@ -1757,8 +1799,9 @@ unknown: | |||
| 1757 | /* respond with data transfer before status phase? */ | 1799 | /* respond with data transfer before status phase? */ |
| 1758 | if (value >= 0 && value != USB_GADGET_DELAYED_STATUS) { | 1800 | if (value >= 0 && value != USB_GADGET_DELAYED_STATUS) { |
| 1759 | req->length = value; | 1801 | req->length = value; |
| 1802 | req->context = cdev; | ||
| 1760 | req->zero = value < w_length; | 1803 | req->zero = value < w_length; |
| 1761 | value = usb_ep_queue(gadget->ep0, req, GFP_ATOMIC); | 1804 | value = composite_ep0_queue(cdev, req, GFP_ATOMIC); |
| 1762 | if (value < 0) { | 1805 | if (value < 0) { |
| 1763 | DBG(cdev, "ep_queue --> %d\n", value); | 1806 | DBG(cdev, "ep_queue --> %d\n", value); |
| 1764 | req->status = 0; | 1807 | req->status = 0; |
| @@ -1893,6 +1936,7 @@ int composite_dev_prepare(struct usb_composite_driver *composite, | |||
| 1893 | goto fail_dev; | 1936 | goto fail_dev; |
| 1894 | 1937 | ||
| 1895 | cdev->req->complete = composite_setup_complete; | 1938 | cdev->req->complete = composite_setup_complete; |
| 1939 | cdev->req->context = cdev; | ||
| 1896 | gadget->ep0->driver_data = cdev; | 1940 | gadget->ep0->driver_data = cdev; |
| 1897 | 1941 | ||
| 1898 | cdev->driver = composite; | 1942 | cdev->driver = composite; |
| @@ -1937,6 +1981,7 @@ int composite_os_desc_req_prepare(struct usb_composite_dev *cdev, | |||
| 1937 | kfree(cdev->os_desc_req); | 1981 | kfree(cdev->os_desc_req); |
| 1938 | goto end; | 1982 | goto end; |
| 1939 | } | 1983 | } |
| 1984 | cdev->os_desc_req->context = cdev; | ||
| 1940 | cdev->os_desc_req->complete = composite_setup_complete; | 1985 | cdev->os_desc_req->complete = composite_setup_complete; |
| 1941 | end: | 1986 | end: |
| 1942 | return ret; | 1987 | return ret; |
| @@ -1951,10 +1996,16 @@ void composite_dev_cleanup(struct usb_composite_dev *cdev) | |||
| 1951 | kfree(uc); | 1996 | kfree(uc); |
| 1952 | } | 1997 | } |
| 1953 | if (cdev->os_desc_req) { | 1998 | if (cdev->os_desc_req) { |
| 1999 | if (cdev->os_desc_pending) | ||
| 2000 | usb_ep_dequeue(cdev->gadget->ep0, cdev->os_desc_req); | ||
| 2001 | |||
| 1954 | kfree(cdev->os_desc_req->buf); | 2002 | kfree(cdev->os_desc_req->buf); |
| 1955 | usb_ep_free_request(cdev->gadget->ep0, cdev->os_desc_req); | 2003 | usb_ep_free_request(cdev->gadget->ep0, cdev->os_desc_req); |
| 1956 | } | 2004 | } |
| 1957 | if (cdev->req) { | 2005 | if (cdev->req) { |
| 2006 | if (cdev->setup_pending) | ||
| 2007 | usb_ep_dequeue(cdev->gadget->ep0, cdev->req); | ||
| 2008 | |||
| 1958 | kfree(cdev->req->buf); | 2009 | kfree(cdev->req->buf); |
| 1959 | usb_ep_free_request(cdev->gadget->ep0, cdev->req); | 2010 | usb_ep_free_request(cdev->gadget->ep0, cdev->req); |
| 1960 | } | 2011 | } |
| @@ -2013,8 +2064,7 @@ fail: | |||
| 2013 | 2064 | ||
| 2014 | /*-------------------------------------------------------------------------*/ | 2065 | /*-------------------------------------------------------------------------*/ |
| 2015 | 2066 | ||
| 2016 | static void | 2067 | void composite_suspend(struct usb_gadget *gadget) |
| 2017 | composite_suspend(struct usb_gadget *gadget) | ||
| 2018 | { | 2068 | { |
| 2019 | struct usb_composite_dev *cdev = get_gadget_data(gadget); | 2069 | struct usb_composite_dev *cdev = get_gadget_data(gadget); |
| 2020 | struct usb_function *f; | 2070 | struct usb_function *f; |
| @@ -2037,8 +2087,7 @@ composite_suspend(struct usb_gadget *gadget) | |||
| 2037 | usb_gadget_vbus_draw(gadget, 2); | 2087 | usb_gadget_vbus_draw(gadget, 2); |
| 2038 | } | 2088 | } |
| 2039 | 2089 | ||
| 2040 | static void | 2090 | void composite_resume(struct usb_gadget *gadget) |
| 2041 | composite_resume(struct usb_gadget *gadget) | ||
| 2042 | { | 2091 | { |
| 2043 | struct usb_composite_dev *cdev = get_gadget_data(gadget); | 2092 | struct usb_composite_dev *cdev = get_gadget_data(gadget); |
| 2044 | struct usb_function *f; | 2093 | struct usb_function *f; |
| @@ -2158,7 +2207,8 @@ void usb_composite_setup_continue(struct usb_composite_dev *cdev) | |||
| 2158 | } else if (--cdev->delayed_status == 0) { | 2207 | } else if (--cdev->delayed_status == 0) { |
| 2159 | DBG(cdev, "%s: Completing delayed status\n", __func__); | 2208 | DBG(cdev, "%s: Completing delayed status\n", __func__); |
| 2160 | req->length = 0; | 2209 | req->length = 0; |
| 2161 | value = usb_ep_queue(cdev->gadget->ep0, req, GFP_ATOMIC); | 2210 | req->context = cdev; |
| 2211 | value = composite_ep0_queue(cdev, req, GFP_ATOMIC); | ||
| 2162 | if (value < 0) { | 2212 | if (value < 0) { |
| 2163 | DBG(cdev, "ep_queue --> %d\n", value); | 2213 | DBG(cdev, "ep_queue --> %d\n", value); |
| 2164 | req->status = 0; | 2214 | req->status = 0; |
diff --git a/drivers/usb/gadget/configfs.c b/drivers/usb/gadget/configfs.c index 34034333f7f6..75648145dc1b 100644 --- a/drivers/usb/gadget/configfs.c +++ b/drivers/usb/gadget/configfs.c | |||
| @@ -271,7 +271,7 @@ static ssize_t gadget_dev_desc_UDC_store(struct gadget_info *gi, | |||
| 271 | ret = -EBUSY; | 271 | ret = -EBUSY; |
| 272 | goto err; | 272 | goto err; |
| 273 | } | 273 | } |
| 274 | ret = udc_attach_driver(name, &gi->composite.gadget_driver); | 274 | ret = usb_udc_attach_driver(name, &gi->composite.gadget_driver); |
| 275 | if (ret) | 275 | if (ret) |
| 276 | goto err; | 276 | goto err; |
| 277 | gi->udc_name = name; | 277 | gi->udc_name = name; |
| @@ -1453,6 +1453,9 @@ static const struct usb_gadget_driver configfs_driver_template = { | |||
| 1453 | .reset = composite_disconnect, | 1453 | .reset = composite_disconnect, |
| 1454 | .disconnect = composite_disconnect, | 1454 | .disconnect = composite_disconnect, |
| 1455 | 1455 | ||
| 1456 | .suspend = composite_suspend, | ||
| 1457 | .resume = composite_resume, | ||
| 1458 | |||
| 1456 | .max_speed = USB_SPEED_SUPER, | 1459 | .max_speed = USB_SPEED_SUPER, |
| 1457 | .driver = { | 1460 | .driver = { |
| 1458 | .owner = THIS_MODULE, | 1461 | .owner = THIS_MODULE, |
diff --git a/drivers/usb/gadget/function/Makefile b/drivers/usb/gadget/function/Makefile index 90701aa5a826..dd68091d92f0 100644 --- a/drivers/usb/gadget/function/Makefile +++ b/drivers/usb/gadget/function/Makefile | |||
| @@ -38,3 +38,7 @@ usb_f_uac2-y := f_uac2.o | |||
| 38 | obj-$(CONFIG_USB_F_UAC2) += usb_f_uac2.o | 38 | obj-$(CONFIG_USB_F_UAC2) += usb_f_uac2.o |
| 39 | usb_f_uvc-y := f_uvc.o uvc_queue.o uvc_v4l2.o uvc_video.o | 39 | usb_f_uvc-y := f_uvc.o uvc_queue.o uvc_v4l2.o uvc_video.o |
| 40 | obj-$(CONFIG_USB_F_UVC) += usb_f_uvc.o | 40 | obj-$(CONFIG_USB_F_UVC) += usb_f_uvc.o |
| 41 | usb_f_midi-y := f_midi.o | ||
| 42 | obj-$(CONFIG_USB_F_MIDI) += usb_f_midi.o | ||
| 43 | usb_f_hid-y := f_hid.o | ||
| 44 | obj-$(CONFIG_USB_F_HID) += usb_f_hid.o | ||
diff --git a/drivers/usb/gadget/function/f_hid.c b/drivers/usb/gadget/function/f_hid.c index ea2b9c374305..6e04e302dc3a 100644 --- a/drivers/usb/gadget/function/f_hid.c +++ b/drivers/usb/gadget/function/f_hid.c | |||
| @@ -12,6 +12,7 @@ | |||
| 12 | #include <linux/kernel.h> | 12 | #include <linux/kernel.h> |
| 13 | #include <linux/module.h> | 13 | #include <linux/module.h> |
| 14 | #include <linux/hid.h> | 14 | #include <linux/hid.h> |
| 15 | #include <linux/idr.h> | ||
| 15 | #include <linux/cdev.h> | 16 | #include <linux/cdev.h> |
| 16 | #include <linux/mutex.h> | 17 | #include <linux/mutex.h> |
| 17 | #include <linux/poll.h> | 18 | #include <linux/poll.h> |
| @@ -21,9 +22,14 @@ | |||
| 21 | #include <linux/usb/g_hid.h> | 22 | #include <linux/usb/g_hid.h> |
| 22 | 23 | ||
| 23 | #include "u_f.h" | 24 | #include "u_f.h" |
| 25 | #include "u_hid.h" | ||
| 26 | |||
| 27 | #define HIDG_MINORS 4 | ||
| 24 | 28 | ||
| 25 | static int major, minors; | 29 | static int major, minors; |
| 26 | static struct class *hidg_class; | 30 | static struct class *hidg_class; |
| 31 | static DEFINE_IDA(hidg_ida); | ||
| 32 | static DEFINE_MUTEX(hidg_ida_lock); /* protects access to hidg_ida */ | ||
| 27 | 33 | ||
| 28 | /*-------------------------------------------------------------------------*/ | 34 | /*-------------------------------------------------------------------------*/ |
| 29 | /* HID gadget struct */ | 35 | /* HID gadget struct */ |
| @@ -161,6 +167,26 @@ static struct usb_descriptor_header *hidg_fs_descriptors[] = { | |||
| 161 | }; | 167 | }; |
| 162 | 168 | ||
| 163 | /*-------------------------------------------------------------------------*/ | 169 | /*-------------------------------------------------------------------------*/ |
| 170 | /* Strings */ | ||
| 171 | |||
| 172 | #define CT_FUNC_HID_IDX 0 | ||
| 173 | |||
| 174 | static struct usb_string ct_func_string_defs[] = { | ||
| 175 | [CT_FUNC_HID_IDX].s = "HID Interface", | ||
| 176 | {}, /* end of list */ | ||
| 177 | }; | ||
| 178 | |||
| 179 | static struct usb_gadget_strings ct_func_string_table = { | ||
| 180 | .language = 0x0409, /* en-US */ | ||
| 181 | .strings = ct_func_string_defs, | ||
| 182 | }; | ||
| 183 | |||
| 184 | static struct usb_gadget_strings *ct_func_strings[] = { | ||
| 185 | &ct_func_string_table, | ||
| 186 | NULL, | ||
| 187 | }; | ||
| 188 | |||
| 189 | /*-------------------------------------------------------------------------*/ | ||
| 164 | /* Char Device */ | 190 | /* Char Device */ |
| 165 | 191 | ||
| 166 | static ssize_t f_hidg_read(struct file *file, char __user *buffer, | 192 | static ssize_t f_hidg_read(struct file *file, char __user *buffer, |
| @@ -552,13 +578,22 @@ const struct file_operations f_hidg_fops = { | |||
| 552 | .llseek = noop_llseek, | 578 | .llseek = noop_llseek, |
| 553 | }; | 579 | }; |
| 554 | 580 | ||
| 555 | static int __init hidg_bind(struct usb_configuration *c, struct usb_function *f) | 581 | static int hidg_bind(struct usb_configuration *c, struct usb_function *f) |
| 556 | { | 582 | { |
| 557 | struct usb_ep *ep; | 583 | struct usb_ep *ep; |
| 558 | struct f_hidg *hidg = func_to_hidg(f); | 584 | struct f_hidg *hidg = func_to_hidg(f); |
| 585 | struct usb_string *us; | ||
| 586 | struct device *device; | ||
| 559 | int status; | 587 | int status; |
| 560 | dev_t dev; | 588 | dev_t dev; |
| 561 | 589 | ||
| 590 | /* maybe allocate device-global string IDs, and patch descriptors */ | ||
| 591 | us = usb_gstrings_attach(c->cdev, ct_func_strings, | ||
| 592 | ARRAY_SIZE(ct_func_string_defs)); | ||
| 593 | if (IS_ERR(us)) | ||
| 594 | return PTR_ERR(us); | ||
| 595 | hidg_interface_desc.iInterface = us[CT_FUNC_HID_IDX].id; | ||
| 596 | |||
| 562 | /* allocate instance-specific interface IDs, and patch descriptors */ | 597 | /* allocate instance-specific interface IDs, and patch descriptors */ |
| 563 | status = usb_interface_id(c, f); | 598 | status = usb_interface_id(c, f); |
| 564 | if (status < 0) | 599 | if (status < 0) |
| @@ -623,10 +658,16 @@ static int __init hidg_bind(struct usb_configuration *c, struct usb_function *f) | |||
| 623 | if (status) | 658 | if (status) |
| 624 | goto fail_free_descs; | 659 | goto fail_free_descs; |
| 625 | 660 | ||
| 626 | device_create(hidg_class, NULL, dev, NULL, "%s%d", "hidg", hidg->minor); | 661 | device = device_create(hidg_class, NULL, dev, NULL, |
| 662 | "%s%d", "hidg", hidg->minor); | ||
| 663 | if (IS_ERR(device)) { | ||
| 664 | status = PTR_ERR(device); | ||
| 665 | goto del; | ||
| 666 | } | ||
| 627 | 667 | ||
| 628 | return 0; | 668 | return 0; |
| 629 | 669 | del: | |
| 670 | cdev_del(&hidg->cdev); | ||
| 630 | fail_free_descs: | 671 | fail_free_descs: |
| 631 | usb_free_all_descriptors(f); | 672 | usb_free_all_descriptors(f); |
| 632 | fail: | 673 | fail: |
| @@ -640,116 +681,313 @@ fail: | |||
| 640 | return status; | 681 | return status; |
| 641 | } | 682 | } |
| 642 | 683 | ||
| 643 | static void hidg_unbind(struct usb_configuration *c, struct usb_function *f) | 684 | static inline int hidg_get_minor(void) |
| 644 | { | 685 | { |
| 645 | struct f_hidg *hidg = func_to_hidg(f); | 686 | int ret; |
| 646 | 687 | ||
| 647 | device_destroy(hidg_class, MKDEV(major, hidg->minor)); | 688 | ret = ida_simple_get(&hidg_ida, 0, 0, GFP_KERNEL); |
| 648 | cdev_del(&hidg->cdev); | ||
| 649 | 689 | ||
| 650 | /* disable/free request and end point */ | 690 | return ret; |
| 651 | usb_ep_disable(hidg->in_ep); | 691 | } |
| 652 | usb_ep_dequeue(hidg->in_ep, hidg->req); | ||
| 653 | kfree(hidg->req->buf); | ||
| 654 | usb_ep_free_request(hidg->in_ep, hidg->req); | ||
| 655 | |||
| 656 | usb_free_all_descriptors(f); | ||
| 657 | 692 | ||
| 658 | kfree(hidg->report_desc); | 693 | static inline struct f_hid_opts *to_f_hid_opts(struct config_item *item) |
| 659 | kfree(hidg); | 694 | { |
| 695 | return container_of(to_config_group(item), struct f_hid_opts, | ||
| 696 | func_inst.group); | ||
| 660 | } | 697 | } |
| 661 | 698 | ||
| 662 | /*-------------------------------------------------------------------------*/ | 699 | CONFIGFS_ATTR_STRUCT(f_hid_opts); |
| 663 | /* Strings */ | 700 | CONFIGFS_ATTR_OPS(f_hid_opts); |
| 664 | 701 | ||
| 665 | #define CT_FUNC_HID_IDX 0 | 702 | static void hid_attr_release(struct config_item *item) |
| 703 | { | ||
| 704 | struct f_hid_opts *opts = to_f_hid_opts(item); | ||
| 666 | 705 | ||
| 667 | static struct usb_string ct_func_string_defs[] = { | 706 | usb_put_function_instance(&opts->func_inst); |
| 668 | [CT_FUNC_HID_IDX].s = "HID Interface", | 707 | } |
| 669 | {}, /* end of list */ | ||
| 670 | }; | ||
| 671 | 708 | ||
| 672 | static struct usb_gadget_strings ct_func_string_table = { | 709 | static struct configfs_item_operations hidg_item_ops = { |
| 673 | .language = 0x0409, /* en-US */ | 710 | .release = hid_attr_release, |
| 674 | .strings = ct_func_string_defs, | 711 | .show_attribute = f_hid_opts_attr_show, |
| 712 | .store_attribute = f_hid_opts_attr_store, | ||
| 675 | }; | 713 | }; |
| 676 | 714 | ||
| 677 | static struct usb_gadget_strings *ct_func_strings[] = { | 715 | #define F_HID_OPT(name, prec, limit) \ |
| 678 | &ct_func_string_table, | 716 | static ssize_t f_hid_opts_##name##_show(struct f_hid_opts *opts, char *page)\ |
| 717 | { \ | ||
| 718 | int result; \ | ||
| 719 | \ | ||
| 720 | mutex_lock(&opts->lock); \ | ||
| 721 | result = sprintf(page, "%d\n", opts->name); \ | ||
| 722 | mutex_unlock(&opts->lock); \ | ||
| 723 | \ | ||
| 724 | return result; \ | ||
| 725 | } \ | ||
| 726 | \ | ||
| 727 | static ssize_t f_hid_opts_##name##_store(struct f_hid_opts *opts, \ | ||
| 728 | const char *page, size_t len) \ | ||
| 729 | { \ | ||
| 730 | int ret; \ | ||
| 731 | u##prec num; \ | ||
| 732 | \ | ||
| 733 | mutex_lock(&opts->lock); \ | ||
| 734 | if (opts->refcnt) { \ | ||
| 735 | ret = -EBUSY; \ | ||
| 736 | goto end; \ | ||
| 737 | } \ | ||
| 738 | \ | ||
| 739 | ret = kstrtou##prec(page, 0, &num); \ | ||
| 740 | if (ret) \ | ||
| 741 | goto end; \ | ||
| 742 | \ | ||
| 743 | if (num > limit) { \ | ||
| 744 | ret = -EINVAL; \ | ||
| 745 | goto end; \ | ||
| 746 | } \ | ||
| 747 | opts->name = num; \ | ||
| 748 | ret = len; \ | ||
| 749 | \ | ||
| 750 | end: \ | ||
| 751 | mutex_unlock(&opts->lock); \ | ||
| 752 | return ret; \ | ||
| 753 | } \ | ||
| 754 | \ | ||
| 755 | static struct f_hid_opts_attribute f_hid_opts_##name = \ | ||
| 756 | __CONFIGFS_ATTR(name, S_IRUGO | S_IWUSR, f_hid_opts_##name##_show,\ | ||
| 757 | f_hid_opts_##name##_store) | ||
| 758 | |||
| 759 | F_HID_OPT(subclass, 8, 255); | ||
| 760 | F_HID_OPT(protocol, 8, 255); | ||
| 761 | F_HID_OPT(report_length, 16, 65536); | ||
| 762 | |||
| 763 | static ssize_t f_hid_opts_report_desc_show(struct f_hid_opts *opts, char *page) | ||
| 764 | { | ||
| 765 | int result; | ||
| 766 | |||
| 767 | mutex_lock(&opts->lock); | ||
| 768 | result = opts->report_desc_length; | ||
| 769 | memcpy(page, opts->report_desc, opts->report_desc_length); | ||
| 770 | mutex_unlock(&opts->lock); | ||
| 771 | |||
| 772 | return result; | ||
| 773 | } | ||
| 774 | |||
| 775 | static ssize_t f_hid_opts_report_desc_store(struct f_hid_opts *opts, | ||
| 776 | const char *page, size_t len) | ||
| 777 | { | ||
| 778 | int ret = -EBUSY; | ||
| 779 | char *d; | ||
| 780 | |||
| 781 | mutex_lock(&opts->lock); | ||
| 782 | |||
| 783 | if (opts->refcnt) | ||
| 784 | goto end; | ||
| 785 | if (len > PAGE_SIZE) { | ||
| 786 | ret = -ENOSPC; | ||
| 787 | goto end; | ||
| 788 | } | ||
| 789 | d = kmemdup(page, len, GFP_KERNEL); | ||
| 790 | if (!d) { | ||
| 791 | ret = -ENOMEM; | ||
| 792 | goto end; | ||
| 793 | } | ||
| 794 | kfree(opts->report_desc); | ||
| 795 | opts->report_desc = d; | ||
| 796 | opts->report_desc_length = len; | ||
| 797 | opts->report_desc_alloc = true; | ||
| 798 | ret = len; | ||
| 799 | end: | ||
| 800 | mutex_unlock(&opts->lock); | ||
| 801 | return ret; | ||
| 802 | } | ||
| 803 | |||
| 804 | static struct f_hid_opts_attribute f_hid_opts_report_desc = | ||
| 805 | __CONFIGFS_ATTR(report_desc, S_IRUGO | S_IWUSR, | ||
| 806 | f_hid_opts_report_desc_show, | ||
| 807 | f_hid_opts_report_desc_store); | ||
| 808 | |||
| 809 | static struct configfs_attribute *hid_attrs[] = { | ||
| 810 | &f_hid_opts_subclass.attr, | ||
| 811 | &f_hid_opts_protocol.attr, | ||
| 812 | &f_hid_opts_report_length.attr, | ||
| 813 | &f_hid_opts_report_desc.attr, | ||
| 679 | NULL, | 814 | NULL, |
| 680 | }; | 815 | }; |
| 681 | 816 | ||
| 682 | /*-------------------------------------------------------------------------*/ | 817 | static struct config_item_type hid_func_type = { |
| 683 | /* usb_configuration */ | 818 | .ct_item_ops = &hidg_item_ops, |
| 819 | .ct_attrs = hid_attrs, | ||
| 820 | .ct_owner = THIS_MODULE, | ||
| 821 | }; | ||
| 684 | 822 | ||
| 685 | int __init hidg_bind_config(struct usb_configuration *c, | 823 | static inline void hidg_put_minor(int minor) |
| 686 | struct hidg_func_descriptor *fdesc, int index) | ||
| 687 | { | 824 | { |
| 688 | struct f_hidg *hidg; | 825 | ida_simple_remove(&hidg_ida, minor); |
| 689 | int status; | 826 | } |
| 690 | 827 | ||
| 691 | if (index >= minors) | 828 | static void hidg_free_inst(struct usb_function_instance *f) |
| 692 | return -ENOENT; | 829 | { |
| 830 | struct f_hid_opts *opts; | ||
| 693 | 831 | ||
| 694 | /* maybe allocate device-global string IDs, and patch descriptors */ | 832 | opts = container_of(f, struct f_hid_opts, func_inst); |
| 695 | if (ct_func_string_defs[CT_FUNC_HID_IDX].id == 0) { | 833 | |
| 696 | status = usb_string_id(c->cdev); | 834 | mutex_lock(&hidg_ida_lock); |
| 697 | if (status < 0) | 835 | |
| 698 | return status; | 836 | hidg_put_minor(opts->minor); |
| 699 | ct_func_string_defs[CT_FUNC_HID_IDX].id = status; | 837 | if (idr_is_empty(&hidg_ida.idr)) |
| 700 | hidg_interface_desc.iInterface = status; | 838 | ghid_cleanup(); |
| 839 | |||
| 840 | mutex_unlock(&hidg_ida_lock); | ||
| 841 | |||
| 842 | if (opts->report_desc_alloc) | ||
| 843 | kfree(opts->report_desc); | ||
| 844 | |||
| 845 | kfree(opts); | ||
| 846 | } | ||
| 847 | |||
| 848 | static struct usb_function_instance *hidg_alloc_inst(void) | ||
| 849 | { | ||
| 850 | struct f_hid_opts *opts; | ||
| 851 | struct usb_function_instance *ret; | ||
| 852 | int status = 0; | ||
| 853 | |||
| 854 | opts = kzalloc(sizeof(*opts), GFP_KERNEL); | ||
| 855 | if (!opts) | ||
| 856 | return ERR_PTR(-ENOMEM); | ||
| 857 | mutex_init(&opts->lock); | ||
| 858 | opts->func_inst.free_func_inst = hidg_free_inst; | ||
| 859 | ret = &opts->func_inst; | ||
| 860 | |||
| 861 | mutex_lock(&hidg_ida_lock); | ||
| 862 | |||
| 863 | if (idr_is_empty(&hidg_ida.idr)) { | ||
| 864 | status = ghid_setup(NULL, HIDG_MINORS); | ||
| 865 | if (status) { | ||
| 866 | ret = ERR_PTR(status); | ||
| 867 | kfree(opts); | ||
| 868 | goto unlock; | ||
| 869 | } | ||
| 870 | } | ||
| 871 | |||
| 872 | opts->minor = hidg_get_minor(); | ||
| 873 | if (opts->minor < 0) { | ||
| 874 | ret = ERR_PTR(opts->minor); | ||
| 875 | kfree(opts); | ||
| 876 | if (idr_is_empty(&hidg_ida.idr)) | ||
| 877 | ghid_cleanup(); | ||
| 878 | goto unlock; | ||
| 701 | } | 879 | } |
| 880 | config_group_init_type_name(&opts->func_inst.group, "", &hid_func_type); | ||
| 881 | |||
| 882 | unlock: | ||
| 883 | mutex_unlock(&hidg_ida_lock); | ||
| 884 | return ret; | ||
| 885 | } | ||
| 886 | |||
| 887 | static void hidg_free(struct usb_function *f) | ||
| 888 | { | ||
| 889 | struct f_hidg *hidg; | ||
| 890 | struct f_hid_opts *opts; | ||
| 891 | |||
| 892 | hidg = func_to_hidg(f); | ||
| 893 | opts = container_of(f->fi, struct f_hid_opts, func_inst); | ||
| 894 | kfree(hidg->report_desc); | ||
| 895 | kfree(hidg); | ||
| 896 | mutex_lock(&opts->lock); | ||
| 897 | --opts->refcnt; | ||
| 898 | mutex_unlock(&opts->lock); | ||
| 899 | } | ||
| 900 | |||
| 901 | static void hidg_unbind(struct usb_configuration *c, struct usb_function *f) | ||
| 902 | { | ||
| 903 | struct f_hidg *hidg = func_to_hidg(f); | ||
| 904 | |||
| 905 | device_destroy(hidg_class, MKDEV(major, hidg->minor)); | ||
| 906 | cdev_del(&hidg->cdev); | ||
| 907 | |||
| 908 | /* disable/free request and end point */ | ||
| 909 | usb_ep_disable(hidg->in_ep); | ||
| 910 | usb_ep_dequeue(hidg->in_ep, hidg->req); | ||
| 911 | kfree(hidg->req->buf); | ||
| 912 | usb_ep_free_request(hidg->in_ep, hidg->req); | ||
| 913 | |||
| 914 | usb_free_all_descriptors(f); | ||
| 915 | } | ||
| 916 | |||
| 917 | static struct usb_function *hidg_alloc(struct usb_function_instance *fi) | ||
| 918 | { | ||
| 919 | struct f_hidg *hidg; | ||
| 920 | struct f_hid_opts *opts; | ||
| 702 | 921 | ||
| 703 | /* allocate and initialize one new instance */ | 922 | /* allocate and initialize one new instance */ |
| 704 | hidg = kzalloc(sizeof *hidg, GFP_KERNEL); | 923 | hidg = kzalloc(sizeof(*hidg), GFP_KERNEL); |
| 705 | if (!hidg) | 924 | if (!hidg) |
| 706 | return -ENOMEM; | 925 | return ERR_PTR(-ENOMEM); |
| 707 | 926 | ||
| 708 | hidg->minor = index; | 927 | opts = container_of(fi, struct f_hid_opts, func_inst); |
| 709 | hidg->bInterfaceSubClass = fdesc->subclass; | 928 | |
| 710 | hidg->bInterfaceProtocol = fdesc->protocol; | 929 | mutex_lock(&opts->lock); |
| 711 | hidg->report_length = fdesc->report_length; | 930 | ++opts->refcnt; |
| 712 | hidg->report_desc_length = fdesc->report_desc_length; | 931 | |
| 713 | hidg->report_desc = kmemdup(fdesc->report_desc, | 932 | hidg->minor = opts->minor; |
| 714 | fdesc->report_desc_length, | 933 | hidg->bInterfaceSubClass = opts->subclass; |
| 715 | GFP_KERNEL); | 934 | hidg->bInterfaceProtocol = opts->protocol; |
| 716 | if (!hidg->report_desc) { | 935 | hidg->report_length = opts->report_length; |
| 717 | kfree(hidg); | 936 | hidg->report_desc_length = opts->report_desc_length; |
| 718 | return -ENOMEM; | 937 | if (opts->report_desc) { |
| 938 | hidg->report_desc = kmemdup(opts->report_desc, | ||
| 939 | opts->report_desc_length, | ||
| 940 | GFP_KERNEL); | ||
| 941 | if (!hidg->report_desc) { | ||
| 942 | kfree(hidg); | ||
| 943 | mutex_unlock(&opts->lock); | ||
| 944 | return ERR_PTR(-ENOMEM); | ||
| 945 | } | ||
| 719 | } | 946 | } |
| 720 | 947 | ||
| 948 | mutex_unlock(&opts->lock); | ||
| 949 | |||
| 721 | hidg->func.name = "hid"; | 950 | hidg->func.name = "hid"; |
| 722 | hidg->func.strings = ct_func_strings; | ||
| 723 | hidg->func.bind = hidg_bind; | 951 | hidg->func.bind = hidg_bind; |
| 724 | hidg->func.unbind = hidg_unbind; | 952 | hidg->func.unbind = hidg_unbind; |
| 725 | hidg->func.set_alt = hidg_set_alt; | 953 | hidg->func.set_alt = hidg_set_alt; |
| 726 | hidg->func.disable = hidg_disable; | 954 | hidg->func.disable = hidg_disable; |
| 727 | hidg->func.setup = hidg_setup; | 955 | hidg->func.setup = hidg_setup; |
| 956 | hidg->func.free_func = hidg_free; | ||
| 728 | 957 | ||
| 729 | /* this could me made configurable at some point */ | 958 | /* this could me made configurable at some point */ |
| 730 | hidg->qlen = 4; | 959 | hidg->qlen = 4; |
| 731 | 960 | ||
| 732 | status = usb_add_function(c, &hidg->func); | 961 | return &hidg->func; |
| 733 | if (status) | ||
| 734 | kfree(hidg); | ||
| 735 | |||
| 736 | return status; | ||
| 737 | } | 962 | } |
| 738 | 963 | ||
| 739 | int __init ghid_setup(struct usb_gadget *g, int count) | 964 | DECLARE_USB_FUNCTION_INIT(hid, hidg_alloc_inst, hidg_alloc); |
| 965 | MODULE_LICENSE("GPL"); | ||
| 966 | MODULE_AUTHOR("Fabien Chouteau"); | ||
| 967 | |||
| 968 | int ghid_setup(struct usb_gadget *g, int count) | ||
| 740 | { | 969 | { |
| 741 | int status; | 970 | int status; |
| 742 | dev_t dev; | 971 | dev_t dev; |
| 743 | 972 | ||
| 744 | hidg_class = class_create(THIS_MODULE, "hidg"); | 973 | hidg_class = class_create(THIS_MODULE, "hidg"); |
| 974 | if (IS_ERR(hidg_class)) { | ||
| 975 | status = PTR_ERR(hidg_class); | ||
| 976 | hidg_class = NULL; | ||
| 977 | return status; | ||
| 978 | } | ||
| 745 | 979 | ||
| 746 | status = alloc_chrdev_region(&dev, 0, count, "hidg"); | 980 | status = alloc_chrdev_region(&dev, 0, count, "hidg"); |
| 747 | if (!status) { | 981 | if (status) { |
| 748 | major = MAJOR(dev); | 982 | class_destroy(hidg_class); |
| 749 | minors = count; | 983 | hidg_class = NULL; |
| 984 | return status; | ||
| 750 | } | 985 | } |
| 751 | 986 | ||
| 752 | return status; | 987 | major = MAJOR(dev); |
| 988 | minors = count; | ||
| 989 | |||
| 990 | return 0; | ||
| 753 | } | 991 | } |
| 754 | 992 | ||
| 755 | void ghid_cleanup(void) | 993 | void ghid_cleanup(void) |
diff --git a/drivers/usb/gadget/function/f_midi.c b/drivers/usb/gadget/function/f_midi.c index 807b31c0edc3..a90440300735 100644 --- a/drivers/usb/gadget/function/f_midi.c +++ b/drivers/usb/gadget/function/f_midi.c | |||
| @@ -20,6 +20,7 @@ | |||
| 20 | */ | 20 | */ |
| 21 | 21 | ||
| 22 | #include <linux/kernel.h> | 22 | #include <linux/kernel.h> |
| 23 | #include <linux/module.h> | ||
| 23 | #include <linux/slab.h> | 24 | #include <linux/slab.h> |
| 24 | #include <linux/device.h> | 25 | #include <linux/device.h> |
| 25 | 26 | ||
| @@ -33,6 +34,7 @@ | |||
| 33 | #include <linux/usb/midi.h> | 34 | #include <linux/usb/midi.h> |
| 34 | 35 | ||
| 35 | #include "u_f.h" | 36 | #include "u_f.h" |
| 37 | #include "u_midi.h" | ||
| 36 | 38 | ||
| 37 | MODULE_AUTHOR("Ben Williamson"); | 39 | MODULE_AUTHOR("Ben Williamson"); |
| 38 | MODULE_LICENSE("GPL v2"); | 40 | MODULE_LICENSE("GPL v2"); |
| @@ -99,7 +101,7 @@ DECLARE_USB_MIDI_OUT_JACK_DESCRIPTOR(1); | |||
| 99 | DECLARE_USB_MS_ENDPOINT_DESCRIPTOR(16); | 101 | DECLARE_USB_MS_ENDPOINT_DESCRIPTOR(16); |
| 100 | 102 | ||
| 101 | /* B.3.1 Standard AC Interface Descriptor */ | 103 | /* B.3.1 Standard AC Interface Descriptor */ |
| 102 | static struct usb_interface_descriptor ac_interface_desc __initdata = { | 104 | static struct usb_interface_descriptor ac_interface_desc = { |
| 103 | .bLength = USB_DT_INTERFACE_SIZE, | 105 | .bLength = USB_DT_INTERFACE_SIZE, |
| 104 | .bDescriptorType = USB_DT_INTERFACE, | 106 | .bDescriptorType = USB_DT_INTERFACE, |
| 105 | /* .bInterfaceNumber = DYNAMIC */ | 107 | /* .bInterfaceNumber = DYNAMIC */ |
| @@ -110,7 +112,7 @@ static struct usb_interface_descriptor ac_interface_desc __initdata = { | |||
| 110 | }; | 112 | }; |
| 111 | 113 | ||
| 112 | /* B.3.2 Class-Specific AC Interface Descriptor */ | 114 | /* B.3.2 Class-Specific AC Interface Descriptor */ |
| 113 | static struct uac1_ac_header_descriptor_1 ac_header_desc __initdata = { | 115 | static struct uac1_ac_header_descriptor_1 ac_header_desc = { |
| 114 | .bLength = UAC_DT_AC_HEADER_SIZE(1), | 116 | .bLength = UAC_DT_AC_HEADER_SIZE(1), |
| 115 | .bDescriptorType = USB_DT_CS_INTERFACE, | 117 | .bDescriptorType = USB_DT_CS_INTERFACE, |
| 116 | .bDescriptorSubtype = USB_MS_HEADER, | 118 | .bDescriptorSubtype = USB_MS_HEADER, |
| @@ -121,7 +123,7 @@ static struct uac1_ac_header_descriptor_1 ac_header_desc __initdata = { | |||
| 121 | }; | 123 | }; |
| 122 | 124 | ||
| 123 | /* B.4.1 Standard MS Interface Descriptor */ | 125 | /* B.4.1 Standard MS Interface Descriptor */ |
| 124 | static struct usb_interface_descriptor ms_interface_desc __initdata = { | 126 | static struct usb_interface_descriptor ms_interface_desc = { |
| 125 | .bLength = USB_DT_INTERFACE_SIZE, | 127 | .bLength = USB_DT_INTERFACE_SIZE, |
| 126 | .bDescriptorType = USB_DT_INTERFACE, | 128 | .bDescriptorType = USB_DT_INTERFACE, |
| 127 | /* .bInterfaceNumber = DYNAMIC */ | 129 | /* .bInterfaceNumber = DYNAMIC */ |
| @@ -132,7 +134,7 @@ static struct usb_interface_descriptor ms_interface_desc __initdata = { | |||
| 132 | }; | 134 | }; |
| 133 | 135 | ||
| 134 | /* B.4.2 Class-Specific MS Interface Descriptor */ | 136 | /* B.4.2 Class-Specific MS Interface Descriptor */ |
| 135 | static struct usb_ms_header_descriptor ms_header_desc __initdata = { | 137 | static struct usb_ms_header_descriptor ms_header_desc = { |
| 136 | .bLength = USB_DT_MS_HEADER_SIZE, | 138 | .bLength = USB_DT_MS_HEADER_SIZE, |
| 137 | .bDescriptorType = USB_DT_CS_INTERFACE, | 139 | .bDescriptorType = USB_DT_CS_INTERFACE, |
| 138 | .bDescriptorSubtype = USB_MS_HEADER, | 140 | .bDescriptorSubtype = USB_MS_HEADER, |
| @@ -387,29 +389,6 @@ static void f_midi_disable(struct usb_function *f) | |||
| 387 | usb_ep_disable(midi->out_ep); | 389 | usb_ep_disable(midi->out_ep); |
| 388 | } | 390 | } |
| 389 | 391 | ||
| 390 | static void f_midi_unbind(struct usb_configuration *c, struct usb_function *f) | ||
| 391 | { | ||
| 392 | struct usb_composite_dev *cdev = f->config->cdev; | ||
| 393 | struct f_midi *midi = func_to_midi(f); | ||
| 394 | struct snd_card *card; | ||
| 395 | |||
| 396 | DBG(cdev, "unbind\n"); | ||
| 397 | |||
| 398 | /* just to be sure */ | ||
| 399 | f_midi_disable(f); | ||
| 400 | |||
| 401 | card = midi->card; | ||
| 402 | midi->card = NULL; | ||
| 403 | if (card) | ||
| 404 | snd_card_free(card); | ||
| 405 | |||
| 406 | kfree(midi->id); | ||
| 407 | midi->id = NULL; | ||
| 408 | |||
| 409 | usb_free_all_descriptors(f); | ||
| 410 | kfree(midi); | ||
| 411 | } | ||
| 412 | |||
| 413 | static int f_midi_snd_free(struct snd_device *device) | 392 | static int f_midi_snd_free(struct snd_device *device) |
| 414 | { | 393 | { |
| 415 | return 0; | 394 | return 0; |
| @@ -654,6 +633,14 @@ static struct snd_rawmidi_ops gmidi_out_ops = { | |||
| 654 | .trigger = f_midi_out_trigger | 633 | .trigger = f_midi_out_trigger |
| 655 | }; | 634 | }; |
| 656 | 635 | ||
| 636 | static inline void f_midi_unregister_card(struct f_midi *midi) | ||
| 637 | { | ||
| 638 | if (midi->card) { | ||
| 639 | snd_card_free(midi->card); | ||
| 640 | midi->card = NULL; | ||
| 641 | } | ||
| 642 | } | ||
| 643 | |||
| 657 | /* register as a sound "card" */ | 644 | /* register as a sound "card" */ |
| 658 | static int f_midi_register_card(struct f_midi *midi) | 645 | static int f_midi_register_card(struct f_midi *midi) |
| 659 | { | 646 | { |
| @@ -715,17 +702,13 @@ static int f_midi_register_card(struct f_midi *midi) | |||
| 715 | return 0; | 702 | return 0; |
| 716 | 703 | ||
| 717 | fail: | 704 | fail: |
| 718 | if (midi->card) { | 705 | f_midi_unregister_card(midi); |
| 719 | snd_card_free(midi->card); | ||
| 720 | midi->card = NULL; | ||
| 721 | } | ||
| 722 | return err; | 706 | return err; |
| 723 | } | 707 | } |
| 724 | 708 | ||
| 725 | /* MIDI function driver setup/binding */ | 709 | /* MIDI function driver setup/binding */ |
| 726 | 710 | ||
| 727 | static int __init | 711 | static int f_midi_bind(struct usb_configuration *c, struct usb_function *f) |
| 728 | f_midi_bind(struct usb_configuration *c, struct usb_function *f) | ||
| 729 | { | 712 | { |
| 730 | struct usb_descriptor_header **midi_function; | 713 | struct usb_descriptor_header **midi_function; |
| 731 | struct usb_midi_in_jack_descriptor jack_in_ext_desc[MAX_PORTS]; | 714 | struct usb_midi_in_jack_descriptor jack_in_ext_desc[MAX_PORTS]; |
| @@ -734,15 +717,23 @@ f_midi_bind(struct usb_configuration *c, struct usb_function *f) | |||
| 734 | struct usb_midi_out_jack_descriptor_1 jack_out_emb_desc[MAX_PORTS]; | 717 | struct usb_midi_out_jack_descriptor_1 jack_out_emb_desc[MAX_PORTS]; |
| 735 | struct usb_composite_dev *cdev = c->cdev; | 718 | struct usb_composite_dev *cdev = c->cdev; |
| 736 | struct f_midi *midi = func_to_midi(f); | 719 | struct f_midi *midi = func_to_midi(f); |
| 720 | struct usb_string *us; | ||
| 737 | int status, n, jack = 1, i = 0; | 721 | int status, n, jack = 1, i = 0; |
| 738 | 722 | ||
| 723 | midi->gadget = cdev->gadget; | ||
| 724 | tasklet_init(&midi->tasklet, f_midi_in_tasklet, (unsigned long) midi); | ||
| 725 | status = f_midi_register_card(midi); | ||
| 726 | if (status < 0) | ||
| 727 | goto fail_register; | ||
| 728 | |||
| 739 | /* maybe allocate device-global string ID */ | 729 | /* maybe allocate device-global string ID */ |
| 740 | if (midi_string_defs[0].id == 0) { | 730 | us = usb_gstrings_attach(c->cdev, midi_strings, |
| 741 | status = usb_string_id(c->cdev); | 731 | ARRAY_SIZE(midi_string_defs)); |
| 742 | if (status < 0) | 732 | if (IS_ERR(us)) { |
| 743 | goto fail; | 733 | status = PTR_ERR(us); |
| 744 | midi_string_defs[0].id = status; | 734 | goto fail; |
| 745 | } | 735 | } |
| 736 | ac_interface_desc.iInterface = us[STRING_FUNC_IDX].id; | ||
| 746 | 737 | ||
| 747 | /* We have two interfaces, AudioControl and MIDIStreaming */ | 738 | /* We have two interfaces, AudioControl and MIDIStreaming */ |
| 748 | status = usb_interface_id(c, f); | 739 | status = usb_interface_id(c, f); |
| @@ -892,6 +883,8 @@ fail_f_midi: | |||
| 892 | kfree(midi_function); | 883 | kfree(midi_function); |
| 893 | usb_free_descriptors(f->hs_descriptors); | 884 | usb_free_descriptors(f->hs_descriptors); |
| 894 | fail: | 885 | fail: |
| 886 | f_midi_unregister_card(midi); | ||
| 887 | fail_register: | ||
| 895 | /* we might as well release our claims on endpoints */ | 888 | /* we might as well release our claims on endpoints */ |
| 896 | if (midi->out_ep) | 889 | if (midi->out_ep) |
| 897 | midi->out_ep->driver_data = NULL; | 890 | midi->out_ep->driver_data = NULL; |
| @@ -903,42 +896,235 @@ fail: | |||
| 903 | return status; | 896 | return status; |
| 904 | } | 897 | } |
| 905 | 898 | ||
| 906 | /** | 899 | static inline struct f_midi_opts *to_f_midi_opts(struct config_item *item) |
| 907 | * f_midi_bind_config - add USB MIDI function to a configuration | 900 | { |
| 908 | * @c: the configuration to supcard the USB audio function | 901 | return container_of(to_config_group(item), struct f_midi_opts, |
| 909 | * @index: the soundcard index to use for the ALSA device creation | 902 | func_inst.group); |
| 910 | * @id: the soundcard id to use for the ALSA device creation | 903 | } |
| 911 | * @buflen: the buffer length to use | 904 | |
| 912 | * @qlen the number of read requests to pre-allocate | 905 | CONFIGFS_ATTR_STRUCT(f_midi_opts); |
| 913 | * Context: single threaded during gadget setup | 906 | CONFIGFS_ATTR_OPS(f_midi_opts); |
| 914 | * | 907 | |
| 915 | * Returns zero on success, else negative errno. | 908 | static void midi_attr_release(struct config_item *item) |
| 916 | */ | 909 | { |
| 917 | int __init f_midi_bind_config(struct usb_configuration *c, | 910 | struct f_midi_opts *opts = to_f_midi_opts(item); |
| 918 | int index, char *id, | 911 | |
| 919 | unsigned int in_ports, | 912 | usb_put_function_instance(&opts->func_inst); |
| 920 | unsigned int out_ports, | 913 | } |
| 921 | unsigned int buflen, | 914 | |
| 922 | unsigned int qlen) | 915 | static struct configfs_item_operations midi_item_ops = { |
| 916 | .release = midi_attr_release, | ||
| 917 | .show_attribute = f_midi_opts_attr_show, | ||
| 918 | .store_attribute = f_midi_opts_attr_store, | ||
| 919 | }; | ||
| 920 | |||
| 921 | #define F_MIDI_OPT(name, test_limit, limit) \ | ||
| 922 | static ssize_t f_midi_opts_##name##_show(struct f_midi_opts *opts, char *page) \ | ||
| 923 | { \ | ||
| 924 | int result; \ | ||
| 925 | \ | ||
| 926 | mutex_lock(&opts->lock); \ | ||
| 927 | result = sprintf(page, "%d\n", opts->name); \ | ||
| 928 | mutex_unlock(&opts->lock); \ | ||
| 929 | \ | ||
| 930 | return result; \ | ||
| 931 | } \ | ||
| 932 | \ | ||
| 933 | static ssize_t f_midi_opts_##name##_store(struct f_midi_opts *opts, \ | ||
| 934 | const char *page, size_t len) \ | ||
| 935 | { \ | ||
| 936 | int ret; \ | ||
| 937 | u32 num; \ | ||
| 938 | \ | ||
| 939 | mutex_lock(&opts->lock); \ | ||
| 940 | if (opts->refcnt) { \ | ||
| 941 | ret = -EBUSY; \ | ||
| 942 | goto end; \ | ||
| 943 | } \ | ||
| 944 | \ | ||
| 945 | ret = kstrtou32(page, 0, &num); \ | ||
| 946 | if (ret) \ | ||
| 947 | goto end; \ | ||
| 948 | \ | ||
| 949 | if (test_limit && num > limit) { \ | ||
| 950 | ret = -EINVAL; \ | ||
| 951 | goto end; \ | ||
| 952 | } \ | ||
| 953 | opts->name = num; \ | ||
| 954 | ret = len; \ | ||
| 955 | \ | ||
| 956 | end: \ | ||
| 957 | mutex_unlock(&opts->lock); \ | ||
| 958 | return ret; \ | ||
| 959 | } \ | ||
| 960 | \ | ||
| 961 | static struct f_midi_opts_attribute f_midi_opts_##name = \ | ||
| 962 | __CONFIGFS_ATTR(name, S_IRUGO | S_IWUSR, f_midi_opts_##name##_show, \ | ||
| 963 | f_midi_opts_##name##_store) | ||
| 964 | |||
| 965 | F_MIDI_OPT(index, true, SNDRV_CARDS); | ||
| 966 | F_MIDI_OPT(buflen, false, 0); | ||
| 967 | F_MIDI_OPT(qlen, false, 0); | ||
| 968 | F_MIDI_OPT(in_ports, true, MAX_PORTS); | ||
| 969 | F_MIDI_OPT(out_ports, true, MAX_PORTS); | ||
| 970 | |||
| 971 | static ssize_t f_midi_opts_id_show(struct f_midi_opts *opts, char *page) | ||
| 972 | { | ||
| 973 | int result; | ||
| 974 | |||
| 975 | mutex_lock(&opts->lock); | ||
| 976 | result = strlcpy(page, opts->id, PAGE_SIZE); | ||
| 977 | mutex_unlock(&opts->lock); | ||
| 978 | |||
| 979 | return result; | ||
| 980 | } | ||
| 981 | |||
| 982 | static ssize_t f_midi_opts_id_store(struct f_midi_opts *opts, | ||
| 983 | const char *page, size_t len) | ||
| 984 | { | ||
| 985 | int ret; | ||
| 986 | char *c; | ||
| 987 | |||
| 988 | mutex_lock(&opts->lock); | ||
| 989 | if (opts->refcnt) { | ||
| 990 | ret = -EBUSY; | ||
| 991 | goto end; | ||
| 992 | } | ||
| 993 | |||
| 994 | c = kstrndup(page, len, GFP_KERNEL); | ||
| 995 | if (!c) { | ||
| 996 | ret = -ENOMEM; | ||
| 997 | goto end; | ||
| 998 | } | ||
| 999 | if (opts->id_allocated) | ||
| 1000 | kfree(opts->id); | ||
| 1001 | opts->id = c; | ||
| 1002 | opts->id_allocated = true; | ||
| 1003 | ret = len; | ||
| 1004 | end: | ||
| 1005 | mutex_unlock(&opts->lock); | ||
| 1006 | return ret; | ||
| 1007 | } | ||
| 1008 | |||
| 1009 | static struct f_midi_opts_attribute f_midi_opts_id = | ||
| 1010 | __CONFIGFS_ATTR(id, S_IRUGO | S_IWUSR, f_midi_opts_id_show, | ||
| 1011 | f_midi_opts_id_store); | ||
| 1012 | |||
| 1013 | static struct configfs_attribute *midi_attrs[] = { | ||
| 1014 | &f_midi_opts_index.attr, | ||
| 1015 | &f_midi_opts_buflen.attr, | ||
| 1016 | &f_midi_opts_qlen.attr, | ||
| 1017 | &f_midi_opts_in_ports.attr, | ||
| 1018 | &f_midi_opts_out_ports.attr, | ||
| 1019 | &f_midi_opts_id.attr, | ||
| 1020 | NULL, | ||
| 1021 | }; | ||
| 1022 | |||
| 1023 | static struct config_item_type midi_func_type = { | ||
| 1024 | .ct_item_ops = &midi_item_ops, | ||
| 1025 | .ct_attrs = midi_attrs, | ||
| 1026 | .ct_owner = THIS_MODULE, | ||
| 1027 | }; | ||
| 1028 | |||
| 1029 | static void f_midi_free_inst(struct usb_function_instance *f) | ||
| 1030 | { | ||
| 1031 | struct f_midi_opts *opts; | ||
| 1032 | |||
| 1033 | opts = container_of(f, struct f_midi_opts, func_inst); | ||
| 1034 | |||
| 1035 | if (opts->id_allocated) | ||
| 1036 | kfree(opts->id); | ||
| 1037 | |||
| 1038 | kfree(opts); | ||
| 1039 | } | ||
| 1040 | |||
| 1041 | static struct usb_function_instance *f_midi_alloc_inst(void) | ||
| 1042 | { | ||
| 1043 | struct f_midi_opts *opts; | ||
| 1044 | |||
| 1045 | opts = kzalloc(sizeof(*opts), GFP_KERNEL); | ||
| 1046 | if (!opts) | ||
| 1047 | return ERR_PTR(-ENOMEM); | ||
| 1048 | |||
| 1049 | mutex_init(&opts->lock); | ||
| 1050 | opts->func_inst.free_func_inst = f_midi_free_inst; | ||
| 1051 | opts->index = SNDRV_DEFAULT_IDX1; | ||
| 1052 | opts->id = SNDRV_DEFAULT_STR1; | ||
| 1053 | opts->buflen = 256; | ||
| 1054 | opts->qlen = 32; | ||
| 1055 | opts->in_ports = 1; | ||
| 1056 | opts->out_ports = 1; | ||
| 1057 | |||
| 1058 | config_group_init_type_name(&opts->func_inst.group, "", | ||
| 1059 | &midi_func_type); | ||
| 1060 | |||
| 1061 | return &opts->func_inst; | ||
| 1062 | } | ||
| 1063 | |||
| 1064 | static void f_midi_free(struct usb_function *f) | ||
| 1065 | { | ||
| 1066 | struct f_midi *midi; | ||
| 1067 | struct f_midi_opts *opts; | ||
| 1068 | int i; | ||
| 1069 | |||
| 1070 | midi = func_to_midi(f); | ||
| 1071 | opts = container_of(f->fi, struct f_midi_opts, func_inst); | ||
| 1072 | kfree(midi->id); | ||
| 1073 | mutex_lock(&opts->lock); | ||
| 1074 | for (i = opts->in_ports - 1; i >= 0; --i) | ||
| 1075 | kfree(midi->in_port[i]); | ||
| 1076 | kfree(midi); | ||
| 1077 | --opts->refcnt; | ||
| 1078 | mutex_unlock(&opts->lock); | ||
| 1079 | } | ||
| 1080 | |||
| 1081 | static void f_midi_unbind(struct usb_configuration *c, struct usb_function *f) | ||
| 1082 | { | ||
| 1083 | struct usb_composite_dev *cdev = f->config->cdev; | ||
| 1084 | struct f_midi *midi = func_to_midi(f); | ||
| 1085 | struct snd_card *card; | ||
| 1086 | |||
| 1087 | DBG(cdev, "unbind\n"); | ||
| 1088 | |||
| 1089 | /* just to be sure */ | ||
| 1090 | f_midi_disable(f); | ||
| 1091 | |||
| 1092 | card = midi->card; | ||
| 1093 | midi->card = NULL; | ||
| 1094 | if (card) | ||
| 1095 | snd_card_free(card); | ||
| 1096 | |||
| 1097 | usb_free_all_descriptors(f); | ||
| 1098 | } | ||
| 1099 | |||
| 1100 | static struct usb_function *f_midi_alloc(struct usb_function_instance *fi) | ||
| 923 | { | 1101 | { |
| 924 | struct f_midi *midi; | 1102 | struct f_midi *midi; |
| 1103 | struct f_midi_opts *opts; | ||
| 925 | int status, i; | 1104 | int status, i; |
| 926 | 1105 | ||
| 1106 | opts = container_of(fi, struct f_midi_opts, func_inst); | ||
| 1107 | |||
| 1108 | mutex_lock(&opts->lock); | ||
| 927 | /* sanity check */ | 1109 | /* sanity check */ |
| 928 | if (in_ports > MAX_PORTS || out_ports > MAX_PORTS) | 1110 | if (opts->in_ports > MAX_PORTS || opts->out_ports > MAX_PORTS) { |
| 929 | return -EINVAL; | 1111 | mutex_unlock(&opts->lock); |
| 1112 | return ERR_PTR(-EINVAL); | ||
| 1113 | } | ||
| 930 | 1114 | ||
| 931 | /* allocate and initialize one new instance */ | 1115 | /* allocate and initialize one new instance */ |
| 932 | midi = kzalloc(sizeof *midi, GFP_KERNEL); | 1116 | midi = kzalloc(sizeof(*midi), GFP_KERNEL); |
| 933 | if (!midi) { | 1117 | if (!midi) { |
| 934 | status = -ENOMEM; | 1118 | mutex_unlock(&opts->lock); |
| 935 | goto fail; | 1119 | return ERR_PTR(-ENOMEM); |
| 936 | } | 1120 | } |
| 937 | 1121 | ||
| 938 | for (i = 0; i < in_ports; i++) { | 1122 | for (i = 0; i < opts->in_ports; i++) { |
| 939 | struct gmidi_in_port *port = kzalloc(sizeof(*port), GFP_KERNEL); | 1123 | struct gmidi_in_port *port = kzalloc(sizeof(*port), GFP_KERNEL); |
| 1124 | |||
| 940 | if (!port) { | 1125 | if (!port) { |
| 941 | status = -ENOMEM; | 1126 | status = -ENOMEM; |
| 1127 | mutex_unlock(&opts->lock); | ||
| 942 | goto setup_fail; | 1128 | goto setup_fail; |
| 943 | } | 1129 | } |
| 944 | 1130 | ||
| @@ -948,39 +1134,37 @@ int __init f_midi_bind_config(struct usb_configuration *c, | |||
| 948 | midi->in_port[i] = port; | 1134 | midi->in_port[i] = port; |
| 949 | } | 1135 | } |
| 950 | 1136 | ||
| 951 | midi->gadget = c->cdev->gadget; | ||
| 952 | tasklet_init(&midi->tasklet, f_midi_in_tasklet, (unsigned long) midi); | ||
| 953 | |||
| 954 | /* set up ALSA midi devices */ | 1137 | /* set up ALSA midi devices */ |
| 955 | midi->in_ports = in_ports; | 1138 | midi->id = kstrdup(opts->id, GFP_KERNEL); |
| 956 | midi->out_ports = out_ports; | 1139 | if (opts->id && !midi->id) { |
| 957 | status = f_midi_register_card(midi); | 1140 | status = -ENOMEM; |
| 958 | if (status < 0) | 1141 | mutex_unlock(&opts->lock); |
| 959 | goto setup_fail; | 1142 | goto kstrdup_fail; |
| 960 | 1143 | } | |
| 961 | midi->func.name = "gmidi function"; | 1144 | midi->in_ports = opts->in_ports; |
| 962 | midi->func.strings = midi_strings; | 1145 | midi->out_ports = opts->out_ports; |
| 963 | midi->func.bind = f_midi_bind; | 1146 | midi->index = opts->index; |
| 964 | midi->func.unbind = f_midi_unbind; | 1147 | midi->buflen = opts->buflen; |
| 965 | midi->func.set_alt = f_midi_set_alt; | 1148 | midi->qlen = opts->qlen; |
| 966 | midi->func.disable = f_midi_disable; | 1149 | ++opts->refcnt; |
| 967 | 1150 | mutex_unlock(&opts->lock); | |
| 968 | midi->id = kstrdup(id, GFP_KERNEL); | 1151 | |
| 969 | midi->index = index; | 1152 | midi->func.name = "gmidi function"; |
| 970 | midi->buflen = buflen; | 1153 | midi->func.bind = f_midi_bind; |
| 971 | midi->qlen = qlen; | 1154 | midi->func.unbind = f_midi_unbind; |
| 972 | 1155 | midi->func.set_alt = f_midi_set_alt; | |
| 973 | status = usb_add_function(c, &midi->func); | 1156 | midi->func.disable = f_midi_disable; |
| 974 | if (status) | 1157 | midi->func.free_func = f_midi_free; |
| 975 | goto setup_fail; | 1158 | |
| 976 | 1159 | return &midi->func; | |
| 977 | return 0; | 1160 | |
| 978 | 1161 | kstrdup_fail: | |
| 1162 | f_midi_unregister_card(midi); | ||
| 979 | setup_fail: | 1163 | setup_fail: |
| 980 | for (--i; i >= 0; i--) | 1164 | for (--i; i >= 0; i--) |
| 981 | kfree(midi->in_port[i]); | 1165 | kfree(midi->in_port[i]); |
| 982 | kfree(midi); | 1166 | kfree(midi); |
| 983 | fail: | 1167 | return ERR_PTR(status); |
| 984 | return status; | ||
| 985 | } | 1168 | } |
| 986 | 1169 | ||
| 1170 | DECLARE_USB_FUNCTION_INIT(midi, f_midi_alloc_inst, f_midi_alloc); | ||
diff --git a/drivers/usb/gadget/function/f_ncm.c b/drivers/usb/gadget/function/f_ncm.c index 16361b0a8b46..bdcda9f5148e 100644 --- a/drivers/usb/gadget/function/f_ncm.c +++ b/drivers/usb/gadget/function/f_ncm.c | |||
| @@ -1441,6 +1441,9 @@ static int ncm_bind(struct usb_configuration *c, struct usb_function *f) | |||
| 1441 | 1441 | ||
| 1442 | status = usb_assign_descriptors(f, ncm_fs_function, ncm_hs_function, | 1442 | status = usb_assign_descriptors(f, ncm_fs_function, ncm_hs_function, |
| 1443 | NULL); | 1443 | NULL); |
| 1444 | if (status) | ||
| 1445 | goto fail; | ||
| 1446 | |||
| 1444 | /* | 1447 | /* |
| 1445 | * NOTE: all that is done without knowing or caring about | 1448 | * NOTE: all that is done without knowing or caring about |
| 1446 | * the network link ... which is unavailable to this code | 1449 | * the network link ... which is unavailable to this code |
diff --git a/drivers/usb/gadget/function/f_rndis.c b/drivers/usb/gadget/function/f_rndis.c index f13fc6a58565..829edf878dac 100644 --- a/drivers/usb/gadget/function/f_rndis.c +++ b/drivers/usb/gadget/function/f_rndis.c | |||
| @@ -375,8 +375,7 @@ static struct sk_buff *rndis_add_header(struct gether *port, | |||
| 375 | struct sk_buff *skb2; | 375 | struct sk_buff *skb2; |
| 376 | 376 | ||
| 377 | skb2 = skb_realloc_headroom(skb, sizeof(struct rndis_packet_msg_type)); | 377 | skb2 = skb_realloc_headroom(skb, sizeof(struct rndis_packet_msg_type)); |
| 378 | if (skb2) | 378 | rndis_add_hdr(skb2); |
| 379 | rndis_add_hdr(skb2); | ||
| 380 | 379 | ||
| 381 | dev_kfree_skb(skb); | 380 | dev_kfree_skb(skb); |
| 382 | return skb2; | 381 | return skb2; |
diff --git a/drivers/usb/gadget/function/u_hid.h b/drivers/usb/gadget/function/u_hid.h new file mode 100644 index 000000000000..aaa0e368a159 --- /dev/null +++ b/drivers/usb/gadget/function/u_hid.h | |||
| @@ -0,0 +1,42 @@ | |||
| 1 | /* | ||
| 2 | * u_hid.h | ||
| 3 | * | ||
| 4 | * Utility definitions for the hid function | ||
| 5 | * | ||
| 6 | * Copyright (c) 2014 Samsung Electronics Co., Ltd. | ||
| 7 | * http://www.samsung.com | ||
| 8 | * | ||
| 9 | * Author: Andrzej Pietrasiewicz <andrzej.p@samsung.com> | ||
| 10 | * | ||
| 11 | * This program is free software; you can redistribute it and/or modify | ||
| 12 | * it under the terms of the GNU General Public License version 2 as | ||
| 13 | * published by the Free Software Foundation. | ||
| 14 | */ | ||
| 15 | |||
| 16 | #ifndef U_HID_H | ||
| 17 | #define U_HID_H | ||
| 18 | |||
| 19 | #include <linux/usb/composite.h> | ||
| 20 | |||
| 21 | struct f_hid_opts { | ||
| 22 | struct usb_function_instance func_inst; | ||
| 23 | int minor; | ||
| 24 | unsigned char subclass; | ||
| 25 | unsigned char protocol; | ||
| 26 | unsigned short report_length; | ||
| 27 | unsigned short report_desc_length; | ||
| 28 | unsigned char *report_desc; | ||
| 29 | bool report_desc_alloc; | ||
| 30 | |||
| 31 | /* | ||
| 32 | * Protect the data form concurrent access by read/write | ||
| 33 | * and create symlink/remove symlink. | ||
| 34 | */ | ||
| 35 | struct mutex lock; | ||
| 36 | int refcnt; | ||
| 37 | }; | ||
| 38 | |||
| 39 | int ghid_setup(struct usb_gadget *g, int count); | ||
| 40 | void ghid_cleanup(void); | ||
| 41 | |||
| 42 | #endif /* U_HID_H */ | ||
diff --git a/drivers/usb/gadget/function/u_midi.h b/drivers/usb/gadget/function/u_midi.h new file mode 100644 index 000000000000..22510189758e --- /dev/null +++ b/drivers/usb/gadget/function/u_midi.h | |||
| @@ -0,0 +1,40 @@ | |||
| 1 | /* | ||
| 2 | * u_midi.h | ||
| 3 | * | ||
| 4 | * Utility definitions for the midi function | ||
| 5 | * | ||
| 6 | * Copyright (c) 2014 Samsung Electronics Co., Ltd. | ||
| 7 | * http://www.samsung.com | ||
| 8 | * | ||
| 9 | * Author: Andrzej Pietrasiewicz <andrzej.p@samsung.com> | ||
| 10 | * | ||
| 11 | * This program is free software; you can redistribute it and/or modify | ||
| 12 | * it under the terms of the GNU General Public License version 2 as | ||
| 13 | * published by the Free Software Foundation. | ||
| 14 | */ | ||
| 15 | |||
| 16 | #ifndef U_MIDI_H | ||
| 17 | #define U_MIDI_H | ||
| 18 | |||
| 19 | #include <linux/usb/composite.h> | ||
| 20 | |||
| 21 | struct f_midi_opts { | ||
| 22 | struct usb_function_instance func_inst; | ||
| 23 | int index; | ||
| 24 | char *id; | ||
| 25 | bool id_allocated; | ||
| 26 | unsigned int in_ports; | ||
| 27 | unsigned int out_ports; | ||
| 28 | unsigned int buflen; | ||
| 29 | unsigned int qlen; | ||
| 30 | |||
| 31 | /* | ||
| 32 | * Protect the data form concurrent access by read/write | ||
| 33 | * and create symlink/remove symlink. | ||
| 34 | */ | ||
| 35 | struct mutex lock; | ||
| 36 | int refcnt; | ||
| 37 | }; | ||
| 38 | |||
| 39 | #endif /* U_MIDI_H */ | ||
| 40 | |||
diff --git a/drivers/usb/gadget/function/u_uac1.c b/drivers/usb/gadget/function/u_uac1.c index a44a07f30281..53842a1b947f 100644 --- a/drivers/usb/gadget/function/u_uac1.c +++ b/drivers/usb/gadget/function/u_uac1.c | |||
| @@ -213,9 +213,6 @@ static int gaudio_open_snd_dev(struct gaudio *card) | |||
| 213 | fn_cap = opts->fn_cap; | 213 | fn_cap = opts->fn_cap; |
| 214 | fn_cntl = opts->fn_cntl; | 214 | fn_cntl = opts->fn_cntl; |
| 215 | 215 | ||
| 216 | if (!card) | ||
| 217 | return -ENODEV; | ||
| 218 | |||
| 219 | /* Open control device */ | 216 | /* Open control device */ |
| 220 | snd = &card->control; | 217 | snd = &card->control; |
| 221 | snd->filp = filp_open(fn_cntl, O_RDWR, 0); | 218 | snd->filp = filp_open(fn_cntl, O_RDWR, 0); |
diff --git a/drivers/usb/gadget/legacy/Kconfig b/drivers/usb/gadget/legacy/Kconfig index 24392d269709..fd48ef3af4eb 100644 --- a/drivers/usb/gadget/legacy/Kconfig +++ b/drivers/usb/gadget/legacy/Kconfig | |||
| @@ -287,6 +287,7 @@ config USB_MIDI_GADGET | |||
| 287 | depends on SND | 287 | depends on SND |
| 288 | select USB_LIBCOMPOSITE | 288 | select USB_LIBCOMPOSITE |
| 289 | select SND_RAWMIDI | 289 | select SND_RAWMIDI |
| 290 | select USB_F_MIDI | ||
| 290 | help | 291 | help |
| 291 | The MIDI Gadget acts as a USB Audio device, with one MIDI | 292 | The MIDI Gadget acts as a USB Audio device, with one MIDI |
| 292 | input and one MIDI output. These MIDI jacks appear as | 293 | input and one MIDI output. These MIDI jacks appear as |
| @@ -419,6 +420,7 @@ endif # TTY | |||
| 419 | config USB_G_HID | 420 | config USB_G_HID |
| 420 | tristate "HID Gadget" | 421 | tristate "HID Gadget" |
| 421 | select USB_LIBCOMPOSITE | 422 | select USB_LIBCOMPOSITE |
| 423 | select USB_F_HID | ||
| 422 | help | 424 | help |
| 423 | The HID gadget driver provides generic emulation of USB | 425 | The HID gadget driver provides generic emulation of USB |
| 424 | Human Interface Devices (HID). | 426 | Human Interface Devices (HID). |
diff --git a/drivers/usb/gadget/legacy/dbgp.c b/drivers/usb/gadget/legacy/dbgp.c index 1b075132f8f1..633683a72a11 100644 --- a/drivers/usb/gadget/legacy/dbgp.c +++ b/drivers/usb/gadget/legacy/dbgp.c | |||
| @@ -237,7 +237,7 @@ static void dbgp_unbind(struct usb_gadget *gadget) | |||
| 237 | static unsigned char tty_line; | 237 | static unsigned char tty_line; |
| 238 | #endif | 238 | #endif |
| 239 | 239 | ||
| 240 | static int __init dbgp_configure_endpoints(struct usb_gadget *gadget) | 240 | static int dbgp_configure_endpoints(struct usb_gadget *gadget) |
| 241 | { | 241 | { |
| 242 | int stp; | 242 | int stp; |
| 243 | 243 | ||
| @@ -273,19 +273,10 @@ static int __init dbgp_configure_endpoints(struct usb_gadget *gadget) | |||
| 273 | 273 | ||
| 274 | dbgp.serial->in->desc = &i_desc; | 274 | dbgp.serial->in->desc = &i_desc; |
| 275 | dbgp.serial->out->desc = &o_desc; | 275 | dbgp.serial->out->desc = &o_desc; |
| 276 | 276 | #endif | |
| 277 | if (gserial_alloc_line(&tty_line)) { | ||
| 278 | stp = 3; | ||
| 279 | goto fail_3; | ||
| 280 | } | ||
| 281 | 277 | ||
| 282 | return 0; | 278 | return 0; |
| 283 | 279 | ||
| 284 | fail_3: | ||
| 285 | dbgp.o_ep->driver_data = NULL; | ||
| 286 | #else | ||
| 287 | return 0; | ||
| 288 | #endif | ||
| 289 | fail_2: | 280 | fail_2: |
| 290 | dbgp.i_ep->driver_data = NULL; | 281 | dbgp.i_ep->driver_data = NULL; |
| 291 | fail_1: | 282 | fail_1: |
| @@ -324,10 +315,17 @@ static int __init dbgp_bind(struct usb_gadget *gadget, | |||
| 324 | err = -ENOMEM; | 315 | err = -ENOMEM; |
| 325 | goto fail; | 316 | goto fail; |
| 326 | } | 317 | } |
| 318 | |||
| 319 | if (gserial_alloc_line(&tty_line)) { | ||
| 320 | stp = 4; | ||
| 321 | err = -ENODEV; | ||
| 322 | goto fail; | ||
| 323 | } | ||
| 327 | #endif | 324 | #endif |
| 325 | |||
| 328 | err = dbgp_configure_endpoints(gadget); | 326 | err = dbgp_configure_endpoints(gadget); |
| 329 | if (err < 0) { | 327 | if (err < 0) { |
| 330 | stp = 4; | 328 | stp = 5; |
| 331 | goto fail; | 329 | goto fail; |
| 332 | } | 330 | } |
| 333 | 331 | ||
| @@ -383,6 +381,10 @@ static int dbgp_setup(struct usb_gadget *gadget, | |||
| 383 | #ifdef CONFIG_USB_G_DBGP_PRINTK | 381 | #ifdef CONFIG_USB_G_DBGP_PRINTK |
| 384 | err = dbgp_enable_ep(); | 382 | err = dbgp_enable_ep(); |
| 385 | #else | 383 | #else |
| 384 | err = dbgp_configure_endpoints(gadget); | ||
| 385 | if (err < 0) { | ||
| 386 | goto fail; | ||
| 387 | } | ||
| 386 | err = gserial_connect(dbgp.serial, tty_line); | 388 | err = gserial_connect(dbgp.serial, tty_line); |
| 387 | #endif | 389 | #endif |
| 388 | if (err < 0) | 390 | if (err < 0) |
diff --git a/drivers/usb/gadget/legacy/gmidi.c b/drivers/usb/gadget/legacy/gmidi.c index 3d696b86ff76..e02a095294ac 100644 --- a/drivers/usb/gadget/legacy/gmidi.c +++ b/drivers/usb/gadget/legacy/gmidi.c | |||
| @@ -37,7 +37,7 @@ | |||
| 37 | 37 | ||
| 38 | #include "gadget_chips.h" | 38 | #include "gadget_chips.h" |
| 39 | 39 | ||
| 40 | #include "f_midi.c" | 40 | #include "u_midi.h" |
| 41 | 41 | ||
| 42 | /*-------------------------------------------------------------------------*/ | 42 | /*-------------------------------------------------------------------------*/ |
| 43 | 43 | ||
| @@ -115,8 +115,13 @@ static struct usb_gadget_strings *dev_strings[] = { | |||
| 115 | NULL, | 115 | NULL, |
| 116 | }; | 116 | }; |
| 117 | 117 | ||
| 118 | static struct usb_function_instance *fi_midi; | ||
| 119 | static struct usb_function *f_midi; | ||
| 120 | |||
| 118 | static int __exit midi_unbind(struct usb_composite_dev *dev) | 121 | static int __exit midi_unbind(struct usb_composite_dev *dev) |
| 119 | { | 122 | { |
| 123 | usb_put_function(f_midi); | ||
| 124 | usb_put_function_instance(fi_midi); | ||
| 120 | return 0; | 125 | return 0; |
| 121 | } | 126 | } |
| 122 | 127 | ||
| @@ -130,28 +135,54 @@ static struct usb_configuration midi_config = { | |||
| 130 | 135 | ||
| 131 | static int __init midi_bind_config(struct usb_configuration *c) | 136 | static int __init midi_bind_config(struct usb_configuration *c) |
| 132 | { | 137 | { |
| 133 | return f_midi_bind_config(c, index, id, | 138 | int status; |
| 134 | in_ports, out_ports, | 139 | |
| 135 | buflen, qlen); | 140 | f_midi = usb_get_function(fi_midi); |
| 141 | if (IS_ERR(f_midi)) | ||
| 142 | return PTR_ERR(f_midi); | ||
| 143 | |||
| 144 | status = usb_add_function(c, f_midi); | ||
| 145 | if (status < 0) { | ||
| 146 | usb_put_function(f_midi); | ||
| 147 | return status; | ||
| 148 | } | ||
| 149 | |||
| 150 | return 0; | ||
| 136 | } | 151 | } |
| 137 | 152 | ||
| 138 | static int __init midi_bind(struct usb_composite_dev *cdev) | 153 | static int __init midi_bind(struct usb_composite_dev *cdev) |
| 139 | { | 154 | { |
| 155 | struct f_midi_opts *midi_opts; | ||
| 140 | int status; | 156 | int status; |
| 141 | 157 | ||
| 158 | fi_midi = usb_get_function_instance("midi"); | ||
| 159 | if (IS_ERR(fi_midi)) | ||
| 160 | return PTR_ERR(fi_midi); | ||
| 161 | |||
| 162 | midi_opts = container_of(fi_midi, struct f_midi_opts, func_inst); | ||
| 163 | midi_opts->index = index; | ||
| 164 | midi_opts->id = id; | ||
| 165 | midi_opts->in_ports = in_ports; | ||
| 166 | midi_opts->out_ports = out_ports; | ||
| 167 | midi_opts->buflen = buflen; | ||
| 168 | midi_opts->qlen = qlen; | ||
| 169 | |||
| 142 | status = usb_string_ids_tab(cdev, strings_dev); | 170 | status = usb_string_ids_tab(cdev, strings_dev); |
| 143 | if (status < 0) | 171 | if (status < 0) |
| 144 | return status; | 172 | goto put; |
| 145 | device_desc.iManufacturer = strings_dev[USB_GADGET_MANUFACTURER_IDX].id; | 173 | device_desc.iManufacturer = strings_dev[USB_GADGET_MANUFACTURER_IDX].id; |
| 146 | device_desc.iProduct = strings_dev[USB_GADGET_PRODUCT_IDX].id; | 174 | device_desc.iProduct = strings_dev[USB_GADGET_PRODUCT_IDX].id; |
| 147 | midi_config.iConfiguration = strings_dev[STRING_DESCRIPTION_IDX].id; | 175 | midi_config.iConfiguration = strings_dev[STRING_DESCRIPTION_IDX].id; |
| 148 | 176 | ||
| 149 | status = usb_add_config(cdev, &midi_config, midi_bind_config); | 177 | status = usb_add_config(cdev, &midi_config, midi_bind_config); |
| 150 | if (status < 0) | 178 | if (status < 0) |
| 151 | return status; | 179 | goto put; |
| 152 | usb_composite_overwrite_options(cdev, &coverwrite); | 180 | usb_composite_overwrite_options(cdev, &coverwrite); |
| 153 | pr_info("%s\n", longname); | 181 | pr_info("%s\n", longname); |
| 154 | return 0; | 182 | return 0; |
| 183 | put: | ||
| 184 | usb_put_function_instance(fi_midi); | ||
| 185 | return status; | ||
| 155 | } | 186 | } |
| 156 | 187 | ||
| 157 | static __refdata struct usb_composite_driver midi_driver = { | 188 | static __refdata struct usb_composite_driver midi_driver = { |
diff --git a/drivers/usb/gadget/legacy/hid.c b/drivers/usb/gadget/legacy/hid.c index 778613eb37af..633fe7e07688 100644 --- a/drivers/usb/gadget/legacy/hid.c +++ b/drivers/usb/gadget/legacy/hid.c | |||
| @@ -17,11 +17,14 @@ | |||
| 17 | #include <linux/list.h> | 17 | #include <linux/list.h> |
| 18 | #include <linux/module.h> | 18 | #include <linux/module.h> |
| 19 | #include <linux/usb/composite.h> | 19 | #include <linux/usb/composite.h> |
| 20 | #include <linux/usb/g_hid.h> | ||
| 20 | 21 | ||
| 21 | #include "gadget_chips.h" | 22 | #include "gadget_chips.h" |
| 22 | #define DRIVER_DESC "HID Gadget" | 23 | #define DRIVER_DESC "HID Gadget" |
| 23 | #define DRIVER_VERSION "2010/03/16" | 24 | #define DRIVER_VERSION "2010/03/16" |
| 24 | 25 | ||
| 26 | #include "u_hid.h" | ||
| 27 | |||
| 25 | /*-------------------------------------------------------------------------*/ | 28 | /*-------------------------------------------------------------------------*/ |
| 26 | 29 | ||
| 27 | #define HIDG_VENDOR_NUM 0x0525 /* XXX NetChip */ | 30 | #define HIDG_VENDOR_NUM 0x0525 /* XXX NetChip */ |
| @@ -29,17 +32,9 @@ | |||
| 29 | 32 | ||
| 30 | /*-------------------------------------------------------------------------*/ | 33 | /*-------------------------------------------------------------------------*/ |
| 31 | 34 | ||
| 32 | /* | ||
| 33 | * kbuild is not very cooperative with respect to linking separately | ||
| 34 | * compiled library objects into one module. So for now we won't use | ||
| 35 | * separate compilation ... ensuring init/exit sections work to shrink | ||
| 36 | * the runtime footprint, and giving us at least some parts of what | ||
| 37 | * a "gcc --combine ... part1.c part2.c part3.c ... " build would. | ||
| 38 | */ | ||
| 39 | #include "f_hid.c" | ||
| 40 | |||
| 41 | |||
| 42 | struct hidg_func_node { | 35 | struct hidg_func_node { |
| 36 | struct usb_function_instance *fi; | ||
| 37 | struct usb_function *f; | ||
| 43 | struct list_head node; | 38 | struct list_head node; |
| 44 | struct hidg_func_descriptor *func; | 39 | struct hidg_func_descriptor *func; |
| 45 | }; | 40 | }; |
| @@ -113,8 +108,8 @@ static struct usb_gadget_strings *dev_strings[] = { | |||
| 113 | 108 | ||
| 114 | static int __init do_config(struct usb_configuration *c) | 109 | static int __init do_config(struct usb_configuration *c) |
| 115 | { | 110 | { |
| 116 | struct hidg_func_node *e; | 111 | struct hidg_func_node *e, *n; |
| 117 | int func = 0, status = 0; | 112 | int status = 0; |
| 118 | 113 | ||
| 119 | if (gadget_is_otg(c->cdev->gadget)) { | 114 | if (gadget_is_otg(c->cdev->gadget)) { |
| 120 | c->descriptors = otg_desc; | 115 | c->descriptors = otg_desc; |
| @@ -122,11 +117,24 @@ static int __init do_config(struct usb_configuration *c) | |||
| 122 | } | 117 | } |
| 123 | 118 | ||
| 124 | list_for_each_entry(e, &hidg_func_list, node) { | 119 | list_for_each_entry(e, &hidg_func_list, node) { |
| 125 | status = hidg_bind_config(c, e->func, func++); | 120 | e->f = usb_get_function(e->fi); |
| 126 | if (status) | 121 | if (IS_ERR(e->f)) |
| 127 | break; | 122 | goto put; |
| 123 | status = usb_add_function(c, e->f); | ||
| 124 | if (status < 0) { | ||
| 125 | usb_put_function(e->f); | ||
| 126 | goto put; | ||
| 127 | } | ||
| 128 | } | 128 | } |
| 129 | 129 | ||
| 130 | return 0; | ||
| 131 | put: | ||
| 132 | list_for_each_entry(n, &hidg_func_list, node) { | ||
| 133 | if (n == e) | ||
| 134 | break; | ||
| 135 | usb_remove_function(c, n->f); | ||
| 136 | usb_put_function(n->f); | ||
| 137 | } | ||
| 130 | return status; | 138 | return status; |
| 131 | } | 139 | } |
| 132 | 140 | ||
| @@ -143,6 +151,8 @@ static int __init hid_bind(struct usb_composite_dev *cdev) | |||
| 143 | { | 151 | { |
| 144 | struct usb_gadget *gadget = cdev->gadget; | 152 | struct usb_gadget *gadget = cdev->gadget; |
| 145 | struct list_head *tmp; | 153 | struct list_head *tmp; |
| 154 | struct hidg_func_node *n, *m; | ||
| 155 | struct f_hid_opts *hid_opts; | ||
| 146 | int status, funcs = 0; | 156 | int status, funcs = 0; |
| 147 | 157 | ||
| 148 | list_for_each(tmp, &hidg_func_list) | 158 | list_for_each(tmp, &hidg_func_list) |
| @@ -151,10 +161,20 @@ static int __init hid_bind(struct usb_composite_dev *cdev) | |||
| 151 | if (!funcs) | 161 | if (!funcs) |
| 152 | return -ENODEV; | 162 | return -ENODEV; |
| 153 | 163 | ||
| 154 | /* set up HID */ | 164 | list_for_each_entry(n, &hidg_func_list, node) { |
| 155 | status = ghid_setup(cdev->gadget, funcs); | 165 | n->fi = usb_get_function_instance("hid"); |
| 156 | if (status < 0) | 166 | if (IS_ERR(n->fi)) { |
| 157 | return status; | 167 | status = PTR_ERR(n->fi); |
| 168 | goto put; | ||
| 169 | } | ||
| 170 | hid_opts = container_of(n->fi, struct f_hid_opts, func_inst); | ||
| 171 | hid_opts->subclass = n->func->subclass; | ||
| 172 | hid_opts->protocol = n->func->protocol; | ||
| 173 | hid_opts->report_length = n->func->report_length; | ||
| 174 | hid_opts->report_desc_length = n->func->report_desc_length; | ||
| 175 | hid_opts->report_desc = n->func->report_desc; | ||
| 176 | } | ||
| 177 | |||
| 158 | 178 | ||
| 159 | /* Allocate string descriptor numbers ... note that string | 179 | /* Allocate string descriptor numbers ... note that string |
| 160 | * contents can be overridden by the composite_dev glue. | 180 | * contents can be overridden by the composite_dev glue. |
| @@ -162,24 +182,37 @@ static int __init hid_bind(struct usb_composite_dev *cdev) | |||
| 162 | 182 | ||
| 163 | status = usb_string_ids_tab(cdev, strings_dev); | 183 | status = usb_string_ids_tab(cdev, strings_dev); |
| 164 | if (status < 0) | 184 | if (status < 0) |
| 165 | return status; | 185 | goto put; |
| 166 | device_desc.iManufacturer = strings_dev[USB_GADGET_MANUFACTURER_IDX].id; | 186 | device_desc.iManufacturer = strings_dev[USB_GADGET_MANUFACTURER_IDX].id; |
| 167 | device_desc.iProduct = strings_dev[USB_GADGET_PRODUCT_IDX].id; | 187 | device_desc.iProduct = strings_dev[USB_GADGET_PRODUCT_IDX].id; |
| 168 | 188 | ||
| 169 | /* register our configuration */ | 189 | /* register our configuration */ |
| 170 | status = usb_add_config(cdev, &config_driver, do_config); | 190 | status = usb_add_config(cdev, &config_driver, do_config); |
| 171 | if (status < 0) | 191 | if (status < 0) |
| 172 | return status; | 192 | goto put; |
| 173 | 193 | ||
| 174 | usb_composite_overwrite_options(cdev, &coverwrite); | 194 | usb_composite_overwrite_options(cdev, &coverwrite); |
| 175 | dev_info(&gadget->dev, DRIVER_DESC ", version: " DRIVER_VERSION "\n"); | 195 | dev_info(&gadget->dev, DRIVER_DESC ", version: " DRIVER_VERSION "\n"); |
| 176 | 196 | ||
| 177 | return 0; | 197 | return 0; |
| 198 | |||
| 199 | put: | ||
| 200 | list_for_each_entry(m, &hidg_func_list, node) { | ||
| 201 | if (m == n) | ||
| 202 | break; | ||
| 203 | usb_put_function_instance(m->fi); | ||
| 204 | } | ||
| 205 | return status; | ||
| 178 | } | 206 | } |
| 179 | 207 | ||
| 180 | static int __exit hid_unbind(struct usb_composite_dev *cdev) | 208 | static int __exit hid_unbind(struct usb_composite_dev *cdev) |
| 181 | { | 209 | { |
| 182 | ghid_cleanup(); | 210 | struct hidg_func_node *n; |
| 211 | |||
| 212 | list_for_each_entry(n, &hidg_func_list, node) { | ||
| 213 | usb_put_function(n->f); | ||
| 214 | usb_put_function_instance(n->fi); | ||
| 215 | } | ||
| 183 | return 0; | 216 | return 0; |
| 184 | } | 217 | } |
| 185 | 218 | ||
| @@ -260,7 +293,7 @@ module_init(hidg_init); | |||
| 260 | 293 | ||
| 261 | static void __exit hidg_cleanup(void) | 294 | static void __exit hidg_cleanup(void) |
| 262 | { | 295 | { |
| 263 | platform_driver_unregister(&hidg_plat_driver); | ||
| 264 | usb_composite_unregister(&hidg_driver); | 296 | usb_composite_unregister(&hidg_driver); |
| 297 | platform_driver_unregister(&hidg_plat_driver); | ||
| 265 | } | 298 | } |
| 266 | module_exit(hidg_cleanup); | 299 | module_exit(hidg_cleanup); |
diff --git a/drivers/usb/gadget/legacy/printer.c b/drivers/usb/gadget/legacy/printer.c index 6474081dcbaf..90545980542f 100644 --- a/drivers/usb/gadget/legacy/printer.c +++ b/drivers/usb/gadget/legacy/printer.c | |||
| @@ -208,6 +208,43 @@ static struct usb_descriptor_header *hs_printer_function[] = { | |||
| 208 | NULL | 208 | NULL |
| 209 | }; | 209 | }; |
| 210 | 210 | ||
| 211 | /* | ||
| 212 | * Added endpoint descriptors for 3.0 devices | ||
| 213 | */ | ||
| 214 | |||
| 215 | static struct usb_endpoint_descriptor ss_ep_in_desc = { | ||
| 216 | .bLength = USB_DT_ENDPOINT_SIZE, | ||
| 217 | .bDescriptorType = USB_DT_ENDPOINT, | ||
| 218 | .bmAttributes = USB_ENDPOINT_XFER_BULK, | ||
| 219 | .wMaxPacketSize = cpu_to_le16(1024), | ||
| 220 | }; | ||
| 221 | |||
| 222 | static struct usb_ss_ep_comp_descriptor ss_ep_in_comp_desc = { | ||
| 223 | .bLength = sizeof(ss_ep_in_comp_desc), | ||
| 224 | .bDescriptorType = USB_DT_SS_ENDPOINT_COMP, | ||
| 225 | }; | ||
| 226 | |||
| 227 | static struct usb_endpoint_descriptor ss_ep_out_desc = { | ||
| 228 | .bLength = USB_DT_ENDPOINT_SIZE, | ||
| 229 | .bDescriptorType = USB_DT_ENDPOINT, | ||
| 230 | .bmAttributes = USB_ENDPOINT_XFER_BULK, | ||
| 231 | .wMaxPacketSize = cpu_to_le16(1024), | ||
| 232 | }; | ||
| 233 | |||
| 234 | static struct usb_ss_ep_comp_descriptor ss_ep_out_comp_desc = { | ||
| 235 | .bLength = sizeof(ss_ep_out_comp_desc), | ||
| 236 | .bDescriptorType = USB_DT_SS_ENDPOINT_COMP, | ||
| 237 | }; | ||
| 238 | |||
| 239 | static struct usb_descriptor_header *ss_printer_function[] = { | ||
| 240 | (struct usb_descriptor_header *) &intf_desc, | ||
| 241 | (struct usb_descriptor_header *) &ss_ep_in_desc, | ||
| 242 | (struct usb_descriptor_header *) &ss_ep_in_comp_desc, | ||
| 243 | (struct usb_descriptor_header *) &ss_ep_out_desc, | ||
| 244 | (struct usb_descriptor_header *) &ss_ep_out_comp_desc, | ||
| 245 | NULL | ||
| 246 | }; | ||
| 247 | |||
| 211 | static struct usb_otg_descriptor otg_descriptor = { | 248 | static struct usb_otg_descriptor otg_descriptor = { |
| 212 | .bLength = sizeof otg_descriptor, | 249 | .bLength = sizeof otg_descriptor, |
| 213 | .bDescriptorType = USB_DT_OTG, | 250 | .bDescriptorType = USB_DT_OTG, |
| @@ -220,7 +257,20 @@ static const struct usb_descriptor_header *otg_desc[] = { | |||
| 220 | }; | 257 | }; |
| 221 | 258 | ||
| 222 | /* maxpacket and other transfer characteristics vary by speed. */ | 259 | /* maxpacket and other transfer characteristics vary by speed. */ |
| 223 | #define ep_desc(g, hs, fs) (((g)->speed == USB_SPEED_HIGH)?(hs):(fs)) | 260 | static inline struct usb_endpoint_descriptor *ep_desc(struct usb_gadget *gadget, |
| 261 | struct usb_endpoint_descriptor *fs, | ||
| 262 | struct usb_endpoint_descriptor *hs, | ||
| 263 | struct usb_endpoint_descriptor *ss) | ||
| 264 | { | ||
| 265 | switch (gadget->speed) { | ||
| 266 | case USB_SPEED_SUPER: | ||
| 267 | return ss; | ||
| 268 | case USB_SPEED_HIGH: | ||
| 269 | return hs; | ||
| 270 | default: | ||
| 271 | return fs; | ||
| 272 | } | ||
| 273 | } | ||
| 224 | 274 | ||
| 225 | /*-------------------------------------------------------------------------*/ | 275 | /*-------------------------------------------------------------------------*/ |
| 226 | 276 | ||
| @@ -793,11 +843,12 @@ set_printer_interface(struct printer_dev *dev) | |||
| 793 | { | 843 | { |
| 794 | int result = 0; | 844 | int result = 0; |
| 795 | 845 | ||
| 796 | dev->in_ep->desc = ep_desc(dev->gadget, &hs_ep_in_desc, &fs_ep_in_desc); | 846 | dev->in_ep->desc = ep_desc(dev->gadget, &fs_ep_in_desc, &hs_ep_in_desc, |
| 847 | &ss_ep_in_desc); | ||
| 797 | dev->in_ep->driver_data = dev; | 848 | dev->in_ep->driver_data = dev; |
| 798 | 849 | ||
| 799 | dev->out_ep->desc = ep_desc(dev->gadget, &hs_ep_out_desc, | 850 | dev->out_ep->desc = ep_desc(dev->gadget, &fs_ep_out_desc, |
| 800 | &fs_ep_out_desc); | 851 | &hs_ep_out_desc, &ss_ep_out_desc); |
| 801 | dev->out_ep->driver_data = dev; | 852 | dev->out_ep->driver_data = dev; |
| 802 | 853 | ||
| 803 | result = usb_ep_enable(dev->in_ep); | 854 | result = usb_ep_enable(dev->in_ep); |
| @@ -1016,9 +1067,11 @@ autoconf_fail: | |||
| 1016 | /* assumes that all endpoints are dual-speed */ | 1067 | /* assumes that all endpoints are dual-speed */ |
| 1017 | hs_ep_in_desc.bEndpointAddress = fs_ep_in_desc.bEndpointAddress; | 1068 | hs_ep_in_desc.bEndpointAddress = fs_ep_in_desc.bEndpointAddress; |
| 1018 | hs_ep_out_desc.bEndpointAddress = fs_ep_out_desc.bEndpointAddress; | 1069 | hs_ep_out_desc.bEndpointAddress = fs_ep_out_desc.bEndpointAddress; |
| 1070 | ss_ep_in_desc.bEndpointAddress = fs_ep_in_desc.bEndpointAddress; | ||
| 1071 | ss_ep_out_desc.bEndpointAddress = fs_ep_out_desc.bEndpointAddress; | ||
| 1019 | 1072 | ||
| 1020 | ret = usb_assign_descriptors(f, fs_printer_function, | 1073 | ret = usb_assign_descriptors(f, fs_printer_function, |
| 1021 | hs_printer_function, NULL); | 1074 | hs_printer_function, ss_printer_function); |
| 1022 | if (ret) | 1075 | if (ret) |
| 1023 | return ret; | 1076 | return ret; |
| 1024 | 1077 | ||
| @@ -1253,7 +1306,7 @@ static __refdata struct usb_composite_driver printer_driver = { | |||
| 1253 | .name = shortname, | 1306 | .name = shortname, |
| 1254 | .dev = &device_desc, | 1307 | .dev = &device_desc, |
| 1255 | .strings = dev_strings, | 1308 | .strings = dev_strings, |
| 1256 | .max_speed = USB_SPEED_HIGH, | 1309 | .max_speed = USB_SPEED_SUPER, |
| 1257 | .bind = printer_bind, | 1310 | .bind = printer_bind, |
| 1258 | .unbind = printer_unbind, | 1311 | .unbind = printer_unbind, |
| 1259 | }; | 1312 | }; |
diff --git a/drivers/usb/gadget/udc/Kconfig b/drivers/usb/gadget/udc/Kconfig index 217365d35a25..b8e213eb36cc 100644 --- a/drivers/usb/gadget/udc/Kconfig +++ b/drivers/usb/gadget/udc/Kconfig | |||
| @@ -241,6 +241,8 @@ config USB_M66592 | |||
| 241 | dynamically linked module called "m66592_udc" and force all | 241 | dynamically linked module called "m66592_udc" and force all |
| 242 | gadget drivers to also be dynamically linked. | 242 | gadget drivers to also be dynamically linked. |
| 243 | 243 | ||
| 244 | source "drivers/usb/gadget/udc/bdc/Kconfig" | ||
| 245 | |||
| 244 | # | 246 | # |
| 245 | # Controllers available only in discrete form (and all PCI controllers) | 247 | # Controllers available only in discrete form (and all PCI controllers) |
| 246 | # | 248 | # |
diff --git a/drivers/usb/gadget/udc/Makefile b/drivers/usb/gadget/udc/Makefile index a7f4491593f1..fba2049bf985 100644 --- a/drivers/usb/gadget/udc/Makefile +++ b/drivers/usb/gadget/udc/Makefile | |||
| @@ -30,3 +30,4 @@ obj-$(CONFIG_USB_FOTG210_UDC) += fotg210-udc.o | |||
| 30 | obj-$(CONFIG_USB_MV_U3D) += mv_u3d_core.o | 30 | obj-$(CONFIG_USB_MV_U3D) += mv_u3d_core.o |
| 31 | obj-$(CONFIG_USB_GR_UDC) += gr_udc.o | 31 | obj-$(CONFIG_USB_GR_UDC) += gr_udc.o |
| 32 | obj-$(CONFIG_USB_GADGET_XILINX) += udc-xilinx.o | 32 | obj-$(CONFIG_USB_GADGET_XILINX) += udc-xilinx.o |
| 33 | obj-$(CONFIG_USB_BDC_UDC) += bdc/ | ||
diff --git a/drivers/usb/gadget/udc/amd5536udc.c b/drivers/usb/gadget/udc/amd5536udc.c index 3b9d13848a4f..de7e5e2ccf1c 100644 --- a/drivers/usb/gadget/udc/amd5536udc.c +++ b/drivers/usb/gadget/udc/amd5536udc.c | |||
| @@ -1401,9 +1401,8 @@ static int udc_wakeup(struct usb_gadget *gadget) | |||
| 1401 | 1401 | ||
| 1402 | static int amd5536_udc_start(struct usb_gadget *g, | 1402 | static int amd5536_udc_start(struct usb_gadget *g, |
| 1403 | struct usb_gadget_driver *driver); | 1403 | struct usb_gadget_driver *driver); |
| 1404 | static int amd5536_udc_stop(struct usb_gadget *g, | 1404 | static int amd5536_udc_stop(struct usb_gadget *g); |
| 1405 | struct usb_gadget_driver *driver); | 1405 | |
| 1406 | /* gadget operations */ | ||
| 1407 | static const struct usb_gadget_ops udc_ops = { | 1406 | static const struct usb_gadget_ops udc_ops = { |
| 1408 | .wakeup = udc_wakeup, | 1407 | .wakeup = udc_wakeup, |
| 1409 | .get_frame = udc_get_frame, | 1408 | .get_frame = udc_get_frame, |
| @@ -1962,8 +1961,7 @@ __acquires(dev->lock) | |||
| 1962 | } | 1961 | } |
| 1963 | 1962 | ||
| 1964 | /* Called by gadget driver to unregister itself */ | 1963 | /* Called by gadget driver to unregister itself */ |
| 1965 | static int amd5536_udc_stop(struct usb_gadget *g, | 1964 | static int amd5536_udc_stop(struct usb_gadget *g) |
| 1966 | struct usb_gadget_driver *driver) | ||
| 1967 | { | 1965 | { |
| 1968 | struct udc *dev = to_amd5536_udc(g); | 1966 | struct udc *dev = to_amd5536_udc(g); |
| 1969 | unsigned long flags; | 1967 | unsigned long flags; |
| @@ -1971,7 +1969,7 @@ static int amd5536_udc_stop(struct usb_gadget *g, | |||
| 1971 | 1969 | ||
| 1972 | spin_lock_irqsave(&dev->lock, flags); | 1970 | spin_lock_irqsave(&dev->lock, flags); |
| 1973 | udc_mask_unused_interrupts(dev); | 1971 | udc_mask_unused_interrupts(dev); |
| 1974 | shutdown(dev, driver); | 1972 | shutdown(dev, NULL); |
| 1975 | spin_unlock_irqrestore(&dev->lock, flags); | 1973 | spin_unlock_irqrestore(&dev->lock, flags); |
| 1976 | 1974 | ||
| 1977 | dev->driver = NULL; | 1975 | dev->driver = NULL; |
| @@ -2873,7 +2871,7 @@ __acquires(dev->lock) | |||
| 2873 | dev->driver->resume(&dev->gadget); | 2871 | dev->driver->resume(&dev->gadget); |
| 2874 | dev->sys_suspended = 0; | 2872 | dev->sys_suspended = 0; |
| 2875 | } | 2873 | } |
| 2876 | dev->driver->disconnect(&dev->gadget); | 2874 | usb_gadget_udc_reset(&dev->gadget, dev->driver); |
| 2877 | spin_lock(&dev->lock); | 2875 | spin_lock(&dev->lock); |
| 2878 | 2876 | ||
| 2879 | /* disable ep0 to empty req queue */ | 2877 | /* disable ep0 to empty req queue */ |
diff --git a/drivers/usb/gadget/udc/at91_udc.c b/drivers/usb/gadget/udc/at91_udc.c index 9968f5331fe4..eb2999c5d03c 100644 --- a/drivers/usb/gadget/udc/at91_udc.c +++ b/drivers/usb/gadget/udc/at91_udc.c | |||
| @@ -840,6 +840,31 @@ static void udc_reinit(struct at91_udc *udc) | |||
| 840 | } | 840 | } |
| 841 | } | 841 | } |
| 842 | 842 | ||
| 843 | static void reset_gadget(struct at91_udc *udc) | ||
| 844 | { | ||
| 845 | struct usb_gadget_driver *driver = udc->driver; | ||
| 846 | int i; | ||
| 847 | |||
| 848 | if (udc->gadget.speed == USB_SPEED_UNKNOWN) | ||
| 849 | driver = NULL; | ||
| 850 | udc->gadget.speed = USB_SPEED_UNKNOWN; | ||
| 851 | udc->suspended = 0; | ||
| 852 | |||
| 853 | for (i = 0; i < NUM_ENDPOINTS; i++) { | ||
| 854 | struct at91_ep *ep = &udc->ep[i]; | ||
| 855 | |||
| 856 | ep->stopped = 1; | ||
| 857 | nuke(ep, -ESHUTDOWN); | ||
| 858 | } | ||
| 859 | if (driver) { | ||
| 860 | spin_unlock(&udc->lock); | ||
| 861 | usb_gadget_udc_reset(&udc->gadget, driver); | ||
| 862 | spin_lock(&udc->lock); | ||
| 863 | } | ||
| 864 | |||
| 865 | udc_reinit(udc); | ||
| 866 | } | ||
| 867 | |||
| 843 | static void stop_activity(struct at91_udc *udc) | 868 | static void stop_activity(struct at91_udc *udc) |
| 844 | { | 869 | { |
| 845 | struct usb_gadget_driver *driver = udc->driver; | 870 | struct usb_gadget_driver *driver = udc->driver; |
| @@ -870,12 +895,10 @@ static void clk_on(struct at91_udc *udc) | |||
| 870 | return; | 895 | return; |
| 871 | udc->clocked = 1; | 896 | udc->clocked = 1; |
| 872 | 897 | ||
| 873 | if (IS_ENABLED(CONFIG_COMMON_CLK)) { | 898 | if (IS_ENABLED(CONFIG_COMMON_CLK)) |
| 874 | clk_set_rate(udc->uclk, 48000000); | 899 | clk_enable(udc->uclk); |
| 875 | clk_prepare_enable(udc->uclk); | 900 | clk_enable(udc->iclk); |
| 876 | } | 901 | clk_enable(udc->fclk); |
| 877 | clk_prepare_enable(udc->iclk); | ||
| 878 | clk_prepare_enable(udc->fclk); | ||
| 879 | } | 902 | } |
| 880 | 903 | ||
| 881 | static void clk_off(struct at91_udc *udc) | 904 | static void clk_off(struct at91_udc *udc) |
| @@ -884,10 +907,10 @@ static void clk_off(struct at91_udc *udc) | |||
| 884 | return; | 907 | return; |
| 885 | udc->clocked = 0; | 908 | udc->clocked = 0; |
| 886 | udc->gadget.speed = USB_SPEED_UNKNOWN; | 909 | udc->gadget.speed = USB_SPEED_UNKNOWN; |
| 887 | clk_disable_unprepare(udc->fclk); | 910 | clk_disable(udc->fclk); |
| 888 | clk_disable_unprepare(udc->iclk); | 911 | clk_disable(udc->iclk); |
| 889 | if (IS_ENABLED(CONFIG_COMMON_CLK)) | 912 | if (IS_ENABLED(CONFIG_COMMON_CLK)) |
| 890 | clk_disable_unprepare(udc->uclk); | 913 | clk_disable(udc->uclk); |
| 891 | } | 914 | } |
| 892 | 915 | ||
| 893 | /* | 916 | /* |
| @@ -984,8 +1007,8 @@ static int at91_set_selfpowered(struct usb_gadget *gadget, int is_on) | |||
| 984 | 1007 | ||
| 985 | static int at91_start(struct usb_gadget *gadget, | 1008 | static int at91_start(struct usb_gadget *gadget, |
| 986 | struct usb_gadget_driver *driver); | 1009 | struct usb_gadget_driver *driver); |
| 987 | static int at91_stop(struct usb_gadget *gadget, | 1010 | static int at91_stop(struct usb_gadget *gadget); |
| 988 | struct usb_gadget_driver *driver); | 1011 | |
| 989 | static const struct usb_gadget_ops at91_udc_ops = { | 1012 | static const struct usb_gadget_ops at91_udc_ops = { |
| 990 | .get_frame = at91_get_frame, | 1013 | .get_frame = at91_get_frame, |
| 991 | .wakeup = at91_wakeup, | 1014 | .wakeup = at91_wakeup, |
| @@ -1426,7 +1449,7 @@ static irqreturn_t at91_udc_irq (int irq, void *_udc) | |||
| 1426 | at91_udp_write(udc, AT91_UDP_ICR, AT91_UDP_ENDBUSRES); | 1449 | at91_udp_write(udc, AT91_UDP_ICR, AT91_UDP_ENDBUSRES); |
| 1427 | VDBG("end bus reset\n"); | 1450 | VDBG("end bus reset\n"); |
| 1428 | udc->addr = 0; | 1451 | udc->addr = 0; |
| 1429 | stop_activity(udc); | 1452 | reset_gadget(udc); |
| 1430 | 1453 | ||
| 1431 | /* enable ep0 */ | 1454 | /* enable ep0 */ |
| 1432 | at91_udp_write(udc, AT91_UDP_CSR(0), | 1455 | at91_udp_write(udc, AT91_UDP_CSR(0), |
| @@ -1512,20 +1535,11 @@ static irqreturn_t at91_udc_irq (int irq, void *_udc) | |||
| 1512 | 1535 | ||
| 1513 | /*-------------------------------------------------------------------------*/ | 1536 | /*-------------------------------------------------------------------------*/ |
| 1514 | 1537 | ||
| 1515 | static void nop_release(struct device *dev) | ||
| 1516 | { | ||
| 1517 | /* nothing to free */ | ||
| 1518 | } | ||
| 1519 | |||
| 1520 | static struct at91_udc controller = { | 1538 | static struct at91_udc controller = { |
| 1521 | .gadget = { | 1539 | .gadget = { |
| 1522 | .ops = &at91_udc_ops, | 1540 | .ops = &at91_udc_ops, |
| 1523 | .ep0 = &controller.ep[0].ep, | 1541 | .ep0 = &controller.ep[0].ep, |
| 1524 | .name = driver_name, | 1542 | .name = driver_name, |
| 1525 | .dev = { | ||
| 1526 | .init_name = "gadget", | ||
| 1527 | .release = nop_release, | ||
| 1528 | } | ||
| 1529 | }, | 1543 | }, |
| 1530 | .ep[0] = { | 1544 | .ep[0] = { |
| 1531 | .ep = { | 1545 | .ep = { |
| @@ -1641,12 +1655,10 @@ static int at91_start(struct usb_gadget *gadget, | |||
| 1641 | udc->enabled = 1; | 1655 | udc->enabled = 1; |
| 1642 | udc->selfpowered = 1; | 1656 | udc->selfpowered = 1; |
| 1643 | 1657 | ||
| 1644 | DBG("bound to %s\n", driver->driver.name); | ||
| 1645 | return 0; | 1658 | return 0; |
| 1646 | } | 1659 | } |
| 1647 | 1660 | ||
| 1648 | static int at91_stop(struct usb_gadget *gadget, | 1661 | static int at91_stop(struct usb_gadget *gadget) |
| 1649 | struct usb_gadget_driver *driver) | ||
| 1650 | { | 1662 | { |
| 1651 | struct at91_udc *udc; | 1663 | struct at91_udc *udc; |
| 1652 | unsigned long flags; | 1664 | unsigned long flags; |
| @@ -1659,7 +1671,6 @@ static int at91_stop(struct usb_gadget *gadget, | |||
| 1659 | 1671 | ||
| 1660 | udc->driver = NULL; | 1672 | udc->driver = NULL; |
| 1661 | 1673 | ||
| 1662 | DBG("unbound from %s\n", driver->driver.name); | ||
| 1663 | return 0; | 1674 | return 0; |
| 1664 | } | 1675 | } |
| 1665 | 1676 | ||
| @@ -1780,14 +1791,24 @@ static int at91udc_probe(struct platform_device *pdev) | |||
| 1780 | } | 1791 | } |
| 1781 | 1792 | ||
| 1782 | /* don't do anything until we have both gadget driver and VBUS */ | 1793 | /* don't do anything until we have both gadget driver and VBUS */ |
| 1794 | if (IS_ENABLED(CONFIG_COMMON_CLK)) { | ||
| 1795 | clk_set_rate(udc->uclk, 48000000); | ||
| 1796 | retval = clk_prepare(udc->uclk); | ||
| 1797 | if (retval) | ||
| 1798 | goto fail1; | ||
| 1799 | } | ||
| 1800 | retval = clk_prepare(udc->fclk); | ||
| 1801 | if (retval) | ||
| 1802 | goto fail1a; | ||
| 1803 | |||
| 1783 | retval = clk_prepare_enable(udc->iclk); | 1804 | retval = clk_prepare_enable(udc->iclk); |
| 1784 | if (retval) | 1805 | if (retval) |
| 1785 | goto fail1; | 1806 | goto fail1b; |
| 1786 | at91_udp_write(udc, AT91_UDP_TXVC, AT91_UDP_TXVC_TXVDIS); | 1807 | at91_udp_write(udc, AT91_UDP_TXVC, AT91_UDP_TXVC_TXVDIS); |
| 1787 | at91_udp_write(udc, AT91_UDP_IDR, 0xffffffff); | 1808 | at91_udp_write(udc, AT91_UDP_IDR, 0xffffffff); |
| 1788 | /* Clear all pending interrupts - UDP may be used by bootloader. */ | 1809 | /* Clear all pending interrupts - UDP may be used by bootloader. */ |
| 1789 | at91_udp_write(udc, AT91_UDP_ICR, 0xffffffff); | 1810 | at91_udp_write(udc, AT91_UDP_ICR, 0xffffffff); |
| 1790 | clk_disable_unprepare(udc->iclk); | 1811 | clk_disable(udc->iclk); |
| 1791 | 1812 | ||
| 1792 | /* request UDC and maybe VBUS irqs */ | 1813 | /* request UDC and maybe VBUS irqs */ |
| 1793 | udc->udp_irq = platform_get_irq(pdev, 0); | 1814 | udc->udp_irq = platform_get_irq(pdev, 0); |
| @@ -1795,7 +1816,7 @@ static int at91udc_probe(struct platform_device *pdev) | |||
| 1795 | 0, driver_name, udc); | 1816 | 0, driver_name, udc); |
| 1796 | if (retval < 0) { | 1817 | if (retval < 0) { |
| 1797 | DBG("request irq %d failed\n", udc->udp_irq); | 1818 | DBG("request irq %d failed\n", udc->udp_irq); |
| 1798 | goto fail1; | 1819 | goto fail1c; |
| 1799 | } | 1820 | } |
| 1800 | if (gpio_is_valid(udc->board.vbus_pin)) { | 1821 | if (gpio_is_valid(udc->board.vbus_pin)) { |
| 1801 | retval = gpio_request(udc->board.vbus_pin, "udc_vbus"); | 1822 | retval = gpio_request(udc->board.vbus_pin, "udc_vbus"); |
| @@ -1848,6 +1869,13 @@ fail3: | |||
| 1848 | gpio_free(udc->board.vbus_pin); | 1869 | gpio_free(udc->board.vbus_pin); |
| 1849 | fail2: | 1870 | fail2: |
| 1850 | free_irq(udc->udp_irq, udc); | 1871 | free_irq(udc->udp_irq, udc); |
| 1872 | fail1c: | ||
| 1873 | clk_unprepare(udc->iclk); | ||
| 1874 | fail1b: | ||
| 1875 | clk_unprepare(udc->fclk); | ||
| 1876 | fail1a: | ||
| 1877 | if (IS_ENABLED(CONFIG_COMMON_CLK)) | ||
| 1878 | clk_unprepare(udc->uclk); | ||
| 1851 | fail1: | 1879 | fail1: |
| 1852 | if (IS_ENABLED(CONFIG_COMMON_CLK) && !IS_ERR(udc->uclk)) | 1880 | if (IS_ENABLED(CONFIG_COMMON_CLK) && !IS_ERR(udc->uclk)) |
| 1853 | clk_put(udc->uclk); | 1881 | clk_put(udc->uclk); |
| @@ -1896,6 +1924,11 @@ static int __exit at91udc_remove(struct platform_device *pdev) | |||
| 1896 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 1924 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 1897 | release_mem_region(res->start, resource_size(res)); | 1925 | release_mem_region(res->start, resource_size(res)); |
| 1898 | 1926 | ||
| 1927 | if (IS_ENABLED(CONFIG_COMMON_CLK)) | ||
| 1928 | clk_unprepare(udc->uclk); | ||
| 1929 | clk_unprepare(udc->fclk); | ||
| 1930 | clk_unprepare(udc->iclk); | ||
| 1931 | |||
| 1899 | clk_put(udc->iclk); | 1932 | clk_put(udc->iclk); |
| 1900 | clk_put(udc->fclk); | 1933 | clk_put(udc->fclk); |
| 1901 | if (IS_ENABLED(CONFIG_COMMON_CLK)) | 1934 | if (IS_ENABLED(CONFIG_COMMON_CLK)) |
diff --git a/drivers/usb/gadget/udc/atmel_usba_udc.c b/drivers/usb/gadget/udc/atmel_usba_udc.c index 1529926e20a0..b31747979c4a 100644 --- a/drivers/usb/gadget/udc/atmel_usba_udc.c +++ b/drivers/usb/gadget/udc/atmel_usba_udc.c | |||
| @@ -987,8 +987,8 @@ usba_udc_set_selfpowered(struct usb_gadget *gadget, int is_selfpowered) | |||
| 987 | 987 | ||
| 988 | static int atmel_usba_start(struct usb_gadget *gadget, | 988 | static int atmel_usba_start(struct usb_gadget *gadget, |
| 989 | struct usb_gadget_driver *driver); | 989 | struct usb_gadget_driver *driver); |
| 990 | static int atmel_usba_stop(struct usb_gadget *gadget, | 990 | static int atmel_usba_stop(struct usb_gadget *gadget); |
| 991 | struct usb_gadget_driver *driver); | 991 | |
| 992 | static const struct usb_gadget_ops usba_udc_ops = { | 992 | static const struct usb_gadget_ops usba_udc_ops = { |
| 993 | .get_frame = usba_udc_get_frame, | 993 | .get_frame = usba_udc_get_frame, |
| 994 | .wakeup = usba_udc_wakeup, | 994 | .wakeup = usba_udc_wakeup, |
| @@ -1007,19 +1007,10 @@ static struct usb_endpoint_descriptor usba_ep0_desc = { | |||
| 1007 | .bInterval = 1, | 1007 | .bInterval = 1, |
| 1008 | }; | 1008 | }; |
| 1009 | 1009 | ||
| 1010 | static void nop_release(struct device *dev) | ||
| 1011 | { | ||
| 1012 | |||
| 1013 | } | ||
| 1014 | |||
| 1015 | static struct usb_gadget usba_gadget_template = { | 1010 | static struct usb_gadget usba_gadget_template = { |
| 1016 | .ops = &usba_udc_ops, | 1011 | .ops = &usba_udc_ops, |
| 1017 | .max_speed = USB_SPEED_HIGH, | 1012 | .max_speed = USB_SPEED_HIGH, |
| 1018 | .name = "atmel_usba_udc", | 1013 | .name = "atmel_usba_udc", |
| 1019 | .dev = { | ||
| 1020 | .init_name = "gadget", | ||
| 1021 | .release = nop_release, | ||
| 1022 | }, | ||
| 1023 | }; | 1014 | }; |
| 1024 | 1015 | ||
| 1025 | /* | 1016 | /* |
| @@ -1685,11 +1676,10 @@ static irqreturn_t usba_udc_irq(int irq, void *devid) | |||
| 1685 | usba_writel(udc, INT_CLR, USBA_END_OF_RESET); | 1676 | usba_writel(udc, INT_CLR, USBA_END_OF_RESET); |
| 1686 | reset_all_endpoints(udc); | 1677 | reset_all_endpoints(udc); |
| 1687 | 1678 | ||
| 1688 | if (udc->gadget.speed != USB_SPEED_UNKNOWN | 1679 | if (udc->gadget.speed != USB_SPEED_UNKNOWN && udc->driver) { |
| 1689 | && udc->driver && udc->driver->disconnect) { | ||
| 1690 | udc->gadget.speed = USB_SPEED_UNKNOWN; | 1680 | udc->gadget.speed = USB_SPEED_UNKNOWN; |
| 1691 | spin_unlock(&udc->lock); | 1681 | spin_unlock(&udc->lock); |
| 1692 | udc->driver->disconnect(&udc->gadget); | 1682 | usb_gadget_udc_reset(&udc->gadget, udc->driver); |
| 1693 | spin_lock(&udc->lock); | 1683 | spin_lock(&udc->lock); |
| 1694 | } | 1684 | } |
| 1695 | 1685 | ||
| @@ -1791,8 +1781,6 @@ static int atmel_usba_start(struct usb_gadget *gadget, | |||
| 1791 | return ret; | 1781 | return ret; |
| 1792 | } | 1782 | } |
| 1793 | 1783 | ||
| 1794 | DBG(DBG_GADGET, "registered driver `%s'\n", driver->driver.name); | ||
| 1795 | |||
| 1796 | udc->vbus_prev = 0; | 1784 | udc->vbus_prev = 0; |
| 1797 | if (gpio_is_valid(udc->vbus_pin)) | 1785 | if (gpio_is_valid(udc->vbus_pin)) |
| 1798 | enable_irq(gpio_to_irq(udc->vbus_pin)); | 1786 | enable_irq(gpio_to_irq(udc->vbus_pin)); |
| @@ -1809,8 +1797,7 @@ static int atmel_usba_start(struct usb_gadget *gadget, | |||
| 1809 | return 0; | 1797 | return 0; |
| 1810 | } | 1798 | } |
| 1811 | 1799 | ||
| 1812 | static int atmel_usba_stop(struct usb_gadget *gadget, | 1800 | static int atmel_usba_stop(struct usb_gadget *gadget) |
| 1813 | struct usb_gadget_driver *driver) | ||
| 1814 | { | 1801 | { |
| 1815 | struct usba_udc *udc = container_of(gadget, struct usba_udc, gadget); | 1802 | struct usba_udc *udc = container_of(gadget, struct usba_udc, gadget); |
| 1816 | unsigned long flags; | 1803 | unsigned long flags; |
| @@ -1830,8 +1817,6 @@ static int atmel_usba_stop(struct usb_gadget *gadget, | |||
| 1830 | clk_disable_unprepare(udc->hclk); | 1817 | clk_disable_unprepare(udc->hclk); |
| 1831 | clk_disable_unprepare(udc->pclk); | 1818 | clk_disable_unprepare(udc->pclk); |
| 1832 | 1819 | ||
| 1833 | DBG(DBG_GADGET, "unregistered driver `%s'\n", udc->driver->driver.name); | ||
| 1834 | |||
| 1835 | udc->driver = NULL; | 1820 | udc->driver = NULL; |
| 1836 | 1821 | ||
| 1837 | return 0; | 1822 | return 0; |
diff --git a/drivers/usb/gadget/udc/bcm63xx_udc.c b/drivers/usb/gadget/udc/bcm63xx_udc.c index 2235b8808700..c790918b337b 100644 --- a/drivers/usb/gadget/udc/bcm63xx_udc.c +++ b/drivers/usb/gadget/udc/bcm63xx_udc.c | |||
| @@ -1836,8 +1836,7 @@ static int bcm63xx_udc_start(struct usb_gadget *gadget, | |||
| 1836 | * @gadget: USB slave device. | 1836 | * @gadget: USB slave device. |
| 1837 | * @driver: Driver for USB slave devices. | 1837 | * @driver: Driver for USB slave devices. |
| 1838 | */ | 1838 | */ |
| 1839 | static int bcm63xx_udc_stop(struct usb_gadget *gadget, | 1839 | static int bcm63xx_udc_stop(struct usb_gadget *gadget) |
| 1840 | struct usb_gadget_driver *driver) | ||
| 1841 | { | 1840 | { |
| 1842 | struct bcm63xx_udc *udc = gadget_to_udc(gadget); | 1841 | struct bcm63xx_udc *udc = gadget_to_udc(gadget); |
| 1843 | unsigned long flags; | 1842 | unsigned long flags; |
| @@ -1963,7 +1962,7 @@ static irqreturn_t bcm63xx_udc_ctrl_isr(int irq, void *dev_id) | |||
| 1963 | { | 1962 | { |
| 1964 | struct bcm63xx_udc *udc = dev_id; | 1963 | struct bcm63xx_udc *udc = dev_id; |
| 1965 | u32 stat; | 1964 | u32 stat; |
| 1966 | bool disconnected = false; | 1965 | bool disconnected = false, bus_reset = false; |
| 1967 | 1966 | ||
| 1968 | stat = usbd_readl(udc, USBD_EVENT_IRQ_STATUS_REG) & | 1967 | stat = usbd_readl(udc, USBD_EVENT_IRQ_STATUS_REG) & |
| 1969 | usbd_readl(udc, USBD_EVENT_IRQ_MASK_REG); | 1968 | usbd_readl(udc, USBD_EVENT_IRQ_MASK_REG); |
| @@ -1991,7 +1990,7 @@ static irqreturn_t bcm63xx_udc_ctrl_isr(int irq, void *dev_id) | |||
| 1991 | 1990 | ||
| 1992 | udc->ep0_req_reset = 1; | 1991 | udc->ep0_req_reset = 1; |
| 1993 | schedule_work(&udc->ep0_wq); | 1992 | schedule_work(&udc->ep0_wq); |
| 1994 | disconnected = true; | 1993 | bus_reset = true; |
| 1995 | } | 1994 | } |
| 1996 | if (stat & BIT(USBD_EVENT_IRQ_SETUP)) { | 1995 | if (stat & BIT(USBD_EVENT_IRQ_SETUP)) { |
| 1997 | if (bcm63xx_update_link_speed(udc)) { | 1996 | if (bcm63xx_update_link_speed(udc)) { |
| @@ -2014,6 +2013,8 @@ static irqreturn_t bcm63xx_udc_ctrl_isr(int irq, void *dev_id) | |||
| 2014 | 2013 | ||
| 2015 | if (disconnected && udc->driver) | 2014 | if (disconnected && udc->driver) |
| 2016 | udc->driver->disconnect(&udc->gadget); | 2015 | udc->driver->disconnect(&udc->gadget); |
| 2016 | else if (bus_reset && udc->driver) | ||
| 2017 | usb_gadget_udc_reset(&udc->gadget, udc->driver); | ||
| 2017 | 2018 | ||
| 2018 | return IRQ_HANDLED; | 2019 | return IRQ_HANDLED; |
| 2019 | } | 2020 | } |
| @@ -2324,10 +2325,8 @@ static int bcm63xx_udc_probe(struct platform_device *pdev) | |||
| 2324 | int rc = -ENOMEM, i, irq; | 2325 | int rc = -ENOMEM, i, irq; |
| 2325 | 2326 | ||
| 2326 | udc = devm_kzalloc(dev, sizeof(*udc), GFP_KERNEL); | 2327 | udc = devm_kzalloc(dev, sizeof(*udc), GFP_KERNEL); |
| 2327 | if (!udc) { | 2328 | if (!udc) |
| 2328 | dev_err(dev, "cannot allocate memory\n"); | ||
| 2329 | return -ENOMEM; | 2329 | return -ENOMEM; |
| 2330 | } | ||
| 2331 | 2330 | ||
| 2332 | platform_set_drvdata(pdev, udc); | 2331 | platform_set_drvdata(pdev, udc); |
| 2333 | udc->dev = dev; | 2332 | udc->dev = dev; |
diff --git a/drivers/usb/gadget/udc/bdc/Kconfig b/drivers/usb/gadget/udc/bdc/Kconfig new file mode 100644 index 000000000000..0d7b8c9f72fd --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/Kconfig | |||
| @@ -0,0 +1,21 @@ | |||
| 1 | config USB_BDC_UDC | ||
| 2 | tristate "Broadcom USB3.0 device controller IP driver(BDC)" | ||
| 3 | depends on USB_GADGET && HAS_DMA | ||
| 4 | |||
| 5 | help | ||
| 6 | BDC is Broadcom's USB3.0 device controller IP. If your SOC has a BDC IP | ||
| 7 | then select this driver. | ||
| 8 | |||
| 9 | Say "y" here to link the driver statically, or "m" to build a dynamically | ||
| 10 | linked module called "bdc". | ||
| 11 | |||
| 12 | if USB_BDC_UDC | ||
| 13 | |||
| 14 | comment "Platform Support" | ||
| 15 | config USB_BDC_PCI | ||
| 16 | tristate "BDC support for PCIe based platforms" | ||
| 17 | depends on PCI | ||
| 18 | default USB_BDC_UDC | ||
| 19 | help | ||
| 20 | Enable support for platforms which have BDC connected through PCIe, such as Lego3 FPGA platform. | ||
| 21 | endif | ||
diff --git a/drivers/usb/gadget/udc/bdc/Makefile b/drivers/usb/gadget/udc/bdc/Makefile new file mode 100644 index 000000000000..5cf6a3bcdf0f --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/Makefile | |||
| @@ -0,0 +1,8 @@ | |||
| 1 | obj-$(CONFIG_USB_BDC_UDC) += bdc.o | ||
| 2 | bdc-y := bdc_core.o bdc_cmd.o bdc_ep.o bdc_udc.o | ||
| 3 | |||
| 4 | ifneq ($(CONFIG_USB_GADGET_VERBOSE),) | ||
| 5 | bdc-y += bdc_dbg.o | ||
| 6 | endif | ||
| 7 | |||
| 8 | obj-$(CONFIG_USB_BDC_PCI) += bdc_pci.o | ||
diff --git a/drivers/usb/gadget/udc/bdc/bdc.h b/drivers/usb/gadget/udc/bdc/bdc.h new file mode 100644 index 000000000000..dc18a20bf040 --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/bdc.h | |||
| @@ -0,0 +1,490 @@ | |||
| 1 | /* | ||
| 2 | * bdc.h - header for the BRCM BDC USB3.0 device controller | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Broadcom Corporation | ||
| 5 | * | ||
| 6 | * Author: Ashwini Pahuja | ||
| 7 | * | ||
| 8 | * This program is free software; you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | * | ||
| 13 | */ | ||
| 14 | |||
| 15 | #ifndef __LINUX_BDC_H__ | ||
| 16 | #define __LINUX_BDC_H__ | ||
| 17 | |||
| 18 | #include <linux/kernel.h> | ||
| 19 | #include <linux/usb.h> | ||
| 20 | #include <linux/device.h> | ||
| 21 | #include <linux/spinlock.h> | ||
| 22 | #include <linux/list.h> | ||
| 23 | #include <linux/dma-mapping.h> | ||
| 24 | #include <linux/mm.h> | ||
| 25 | #include <linux/debugfs.h> | ||
| 26 | #include <linux/usb/ch9.h> | ||
| 27 | #include <linux/usb/gadget.h> | ||
| 28 | #include <asm/unaligned.h> | ||
| 29 | |||
| 30 | #define BRCM_BDC_NAME "bdc_usb3" | ||
| 31 | #define BRCM_BDC_DESC "BDC device controller driver" | ||
| 32 | |||
| 33 | #define DMA_ADDR_INVALID (~(dma_addr_t)0) | ||
| 34 | |||
| 35 | /* BDC command operation timeout in usec*/ | ||
| 36 | #define BDC_CMD_TIMEOUT 1000 | ||
| 37 | /* BDC controller operation timeout in usec*/ | ||
| 38 | #define BDC_COP_TIMEOUT 500 | ||
| 39 | |||
| 40 | /* | ||
| 41 | * Maximum size of ep0 response buffer for ch9 requests, | ||
| 42 | * the set_sel request uses 6 so far, the max. | ||
| 43 | */ | ||
| 44 | #define EP0_RESPONSE_BUFF 6 | ||
| 45 | /* Start with SS as default */ | ||
| 46 | #define EP0_MAX_PKT_SIZE 512 | ||
| 47 | |||
| 48 | /* 64 entries in a SRR */ | ||
| 49 | #define NUM_SR_ENTRIES 64 | ||
| 50 | |||
| 51 | /* Num of bds per table */ | ||
| 52 | #define NUM_BDS_PER_TABLE 32 | ||
| 53 | |||
| 54 | /* Num of tables in bd list for control,bulk and Int ep */ | ||
| 55 | #define NUM_TABLES 2 | ||
| 56 | |||
| 57 | /* Num of tables in bd list for Isoch ep */ | ||
| 58 | #define NUM_TABLES_ISOCH 6 | ||
| 59 | |||
| 60 | /* U1 Timeout default: 248usec */ | ||
| 61 | #define U1_TIMEOUT 0xf8 | ||
| 62 | |||
| 63 | /* Interrupt coalescence in usec */ | ||
| 64 | #define INT_CLS 500 | ||
| 65 | |||
| 66 | /* Register offsets */ | ||
| 67 | /* Configuration and Capability registers */ | ||
| 68 | #define BDC_BDCCFG0 0x00 | ||
| 69 | #define BDC_BDCCFG1 0x04 | ||
| 70 | #define BDC_BDCCAP0 0x08 | ||
| 71 | #define BDC_BDCCAP1 0x0c | ||
| 72 | #define BDC_CMDPAR0 0x10 | ||
| 73 | #define BDC_CMDPAR1 0x14 | ||
| 74 | #define BDC_CMDPAR2 0x18 | ||
| 75 | #define BDC_CMDSC 0x1c | ||
| 76 | #define BDC_USPC 0x20 | ||
| 77 | #define BDC_USPPMS 0x28 | ||
| 78 | #define BDC_USPPM2 0x2c | ||
| 79 | #define BDC_SPBBAL 0x38 | ||
| 80 | #define BDC_SPBBAH 0x3c | ||
| 81 | #define BDC_BDCSC 0x40 | ||
| 82 | #define BDC_XSFNTF 0x4c | ||
| 83 | |||
| 84 | #define BDC_DVCSA 0x50 | ||
| 85 | #define BDC_DVCSB 0x54 | ||
| 86 | #define BDC_EPSTS0(n) (0x60 + (n * 0x10)) | ||
| 87 | #define BDC_EPSTS1(n) (0x64 + (n * 0x10)) | ||
| 88 | #define BDC_EPSTS2(n) (0x68 + (n * 0x10)) | ||
| 89 | #define BDC_EPSTS3(n) (0x6c + (n * 0x10)) | ||
| 90 | #define BDC_EPSTS4(n) (0x70 + (n * 0x10)) | ||
| 91 | #define BDC_EPSTS5(n) (0x74 + (n * 0x10)) | ||
| 92 | #define BDC_EPSTS6(n) (0x78 + (n * 0x10)) | ||
| 93 | #define BDC_EPSTS7(n) (0x7c + (n * 0x10)) | ||
| 94 | #define BDC_SRRBAL(n) (0x200 + (n * 0x10)) | ||
| 95 | #define BDC_SRRBAH(n) (0x204 + (n * 0x10)) | ||
| 96 | #define BDC_SRRINT(n) (0x208 + (n * 0x10)) | ||
| 97 | #define BDC_INTCTLS(n) (0x20c + (n * 0x10)) | ||
| 98 | |||
| 99 | /* Extended capability regs */ | ||
| 100 | #define BDC_FSCNOC 0xcd4 | ||
| 101 | #define BDC_FSCNIC 0xce4 | ||
| 102 | #define NUM_NCS(p) (p >> 28) | ||
| 103 | |||
| 104 | /* Register bit fields and Masks */ | ||
| 105 | /* BDC Configuration 0 */ | ||
| 106 | #define BDC_PGS(p) (((p) & (0x7 << 8)) >> 8) | ||
| 107 | #define BDC_SPB(p) (p & 0x7) | ||
| 108 | |||
| 109 | /* BDC Capability1 */ | ||
| 110 | #define BDC_P64 (1 << 0) | ||
| 111 | |||
| 112 | /* BDC Command register */ | ||
| 113 | #define BDC_CMD_FH 0xe | ||
| 114 | #define BDC_CMD_DNC 0x6 | ||
| 115 | #define BDC_CMD_EPO 0x4 | ||
| 116 | #define BDC_CMD_BLA 0x3 | ||
| 117 | #define BDC_CMD_EPC 0x2 | ||
| 118 | #define BDC_CMD_DVC 0x1 | ||
| 119 | #define BDC_CMD_CWS (0x1 << 5) | ||
| 120 | #define BDC_CMD_CST(p) (((p) & (0xf << 6))>>6) | ||
| 121 | #define BDC_CMD_EPN(p) ((p & 0x1f) << 10) | ||
| 122 | #define BDC_SUB_CMD_ADD (0x1 << 17) | ||
| 123 | #define BDC_SUB_CMD_FWK (0x4 << 17) | ||
| 124 | /* Reset sequence number */ | ||
| 125 | #define BDC_CMD_EPO_RST_SN (0x1 << 16) | ||
| 126 | #define BDC_CMD_EP0_XSD (0x1 << 16) | ||
| 127 | #define BDC_SUB_CMD_ADD_EP (0x1 << 17) | ||
| 128 | #define BDC_SUB_CMD_DRP_EP (0x2 << 17) | ||
| 129 | #define BDC_SUB_CMD_EP_STP (0x2 << 17) | ||
| 130 | #define BDC_SUB_CMD_EP_STL (0x4 << 17) | ||
| 131 | #define BDC_SUB_CMD_EP_RST (0x1 << 17) | ||
| 132 | #define BDC_CMD_SRD (1 << 27) | ||
| 133 | |||
| 134 | /* CMD completion status */ | ||
| 135 | #define BDC_CMDS_SUCC 0x1 | ||
| 136 | #define BDC_CMDS_PARA 0x3 | ||
| 137 | #define BDC_CMDS_STAT 0x4 | ||
| 138 | #define BDC_CMDS_FAIL 0x5 | ||
| 139 | #define BDC_CMDS_INTL 0x6 | ||
| 140 | #define BDC_CMDS_BUSY 0xf | ||
| 141 | |||
| 142 | /* CMDSC Param 2 shifts */ | ||
| 143 | #define EPT_SHIFT 22 | ||
| 144 | #define MP_SHIFT 10 | ||
| 145 | #define MB_SHIFT 6 | ||
| 146 | #define EPM_SHIFT 4 | ||
| 147 | |||
| 148 | /* BDC USPSC */ | ||
| 149 | #define BDC_VBC (1 << 31) | ||
| 150 | #define BDC_PRC (1 << 30) | ||
| 151 | #define BDC_PCE (1 << 29) | ||
| 152 | #define BDC_CFC (1 << 28) | ||
| 153 | #define BDC_PCC (1 << 27) | ||
| 154 | #define BDC_PSC (1 << 26) | ||
| 155 | #define BDC_VBS (1 << 25) | ||
| 156 | #define BDC_PRS (1 << 24) | ||
| 157 | #define BDC_PCS (1 << 23) | ||
| 158 | #define BDC_PSP(p) (((p) & (0x7 << 20))>>20) | ||
| 159 | #define BDC_SCN (1 << 8) | ||
| 160 | #define BDC_SDC (1 << 7) | ||
| 161 | #define BDC_SWS (1 << 4) | ||
| 162 | |||
| 163 | #define BDC_USPSC_RW (BDC_SCN|BDC_SDC|BDC_SWS|0xf) | ||
| 164 | #define BDC_PSP(p) (((p) & (0x7 << 20))>>20) | ||
| 165 | |||
| 166 | #define BDC_SPEED_FS 0x1 | ||
| 167 | #define BDC_SPEED_LS 0x2 | ||
| 168 | #define BDC_SPEED_HS 0x3 | ||
| 169 | #define BDC_SPEED_SS 0x4 | ||
| 170 | |||
| 171 | #define BDC_PST(p) (p & 0xf) | ||
| 172 | #define BDC_PST_MASK 0xf | ||
| 173 | |||
| 174 | /* USPPMS */ | ||
| 175 | #define BDC_U2E (0x1 << 31) | ||
| 176 | #define BDC_U1E (0x1 << 30) | ||
| 177 | #define BDC_U2A (0x1 << 29) | ||
| 178 | #define BDC_PORT_W1S (0x1 << 17) | ||
| 179 | #define BDC_U1T(p) ((p) & 0xff) | ||
| 180 | #define BDC_U2T(p) (((p) & 0xff) << 8) | ||
| 181 | #define BDC_U1T_MASK 0xff | ||
| 182 | |||
| 183 | /* USBPM2 */ | ||
| 184 | /* Hardware LPM Enable */ | ||
| 185 | #define BDC_HLE (1 << 16) | ||
| 186 | |||
| 187 | /* BDC Status and Control */ | ||
| 188 | #define BDC_COP_RST (1 << 29) | ||
| 189 | #define BDC_COP_RUN (2 << 29) | ||
| 190 | #define BDC_COP_STP (4 << 29) | ||
| 191 | |||
| 192 | #define BDC_COP_MASK (BDC_COP_RST|BDC_COP_RUN|BDC_COP_STP) | ||
| 193 | |||
| 194 | #define BDC_COS (1 << 28) | ||
| 195 | #define BDC_CSTS(p) (((p) & (0x7 << 20)) >> 20) | ||
| 196 | #define BDC_MASK_MCW (1 << 7) | ||
| 197 | #define BDC_GIE (1 << 1) | ||
| 198 | #define BDC_GIP (1 << 0) | ||
| 199 | |||
| 200 | #define BDC_HLT 1 | ||
| 201 | #define BDC_NOR 2 | ||
| 202 | #define BDC_OIP 7 | ||
| 203 | |||
| 204 | /* Buffer descriptor and Status report bit fields and masks */ | ||
| 205 | #define BD_TYPE_BITMASK (0xf) | ||
| 206 | #define BD_CHAIN 0xf | ||
| 207 | |||
| 208 | #define BD_TFS_SHIFT 4 | ||
| 209 | #define BD_SOT (1 << 26) | ||
| 210 | #define BD_EOT (1 << 27) | ||
| 211 | #define BD_ISP (1 << 29) | ||
| 212 | #define BD_IOC (1 << 30) | ||
| 213 | #define BD_SBF (1 << 31) | ||
| 214 | |||
| 215 | #define BD_INTR_TARGET(p) (((p) & 0x1f) << 27) | ||
| 216 | |||
| 217 | #define BDC_SRR_RWS (1 << 4) | ||
| 218 | #define BDC_SRR_RST (1 << 3) | ||
| 219 | #define BDC_SRR_ISR (1 << 2) | ||
| 220 | #define BDC_SRR_IE (1 << 1) | ||
| 221 | #define BDC_SRR_IP (1 << 0) | ||
| 222 | #define BDC_SRR_EPI(p) (((p) & (0xff << 24)) >> 24) | ||
| 223 | #define BDC_SRR_DPI(p) (((p) & (0xff << 16)) >> 16) | ||
| 224 | #define BDC_SRR_DPI_MASK 0x00ff0000 | ||
| 225 | |||
| 226 | #define MARK_CHAIN_BD (BD_CHAIN|BD_EOT|BD_SOT) | ||
| 227 | |||
| 228 | /* Control transfer BD specific fields */ | ||
| 229 | #define BD_DIR_IN (1 << 25) | ||
| 230 | |||
| 231 | #define BDC_PTC_MASK 0xf0000000 | ||
| 232 | |||
| 233 | /* status report defines */ | ||
| 234 | #define SR_XSF 0 | ||
| 235 | #define SR_USPC 4 | ||
| 236 | #define SR_BD_LEN(p) (p & 0xffffff) | ||
| 237 | |||
| 238 | #define XSF_SUCC 0x1 | ||
| 239 | #define XSF_SHORT 0x3 | ||
| 240 | #define XSF_BABB 0x4 | ||
| 241 | #define XSF_SETUP_RECV 0x6 | ||
| 242 | #define XSF_DATA_START 0x7 | ||
| 243 | #define XSF_STATUS_START 0x8 | ||
| 244 | |||
| 245 | #define XSF_STS(p) (((p) >> 28) & 0xf) | ||
| 246 | |||
| 247 | /* Transfer BD fields */ | ||
| 248 | #define BD_LEN(p) ((p) & 0x1ffff) | ||
| 249 | #define BD_LTF (1 << 25) | ||
| 250 | #define BD_TYPE_DS 0x1 | ||
| 251 | #define BD_TYPE_SS 0x2 | ||
| 252 | |||
| 253 | #define BDC_EP_ENABLED (1 << 0) | ||
| 254 | #define BDC_EP_STALL (1 << 1) | ||
| 255 | #define BDC_EP_STOP (1 << 2) | ||
| 256 | |||
| 257 | /* One BD can transfer max 65536 bytes */ | ||
| 258 | #define BD_MAX_BUFF_SIZE (1 << 16) | ||
| 259 | /* Maximum bytes in one XFR, Refer to BDC spec */ | ||
| 260 | #define MAX_XFR_LEN 16777215 | ||
| 261 | |||
| 262 | /* defines for Force Header command */ | ||
| 263 | #define DEV_NOTF_TYPE 6 | ||
| 264 | #define FWK_SUBTYPE 1 | ||
| 265 | #define TRA_PACKET 4 | ||
| 266 | |||
| 267 | #define to_bdc_ep(e) container_of(e, struct bdc_ep, usb_ep) | ||
| 268 | #define to_bdc_req(r) container_of(r, struct bdc_req, usb_req) | ||
| 269 | #define gadget_to_bdc(g) container_of(g, struct bdc, gadget) | ||
| 270 | |||
| 271 | /* FUNCTION WAKE DEV NOTIFICATION interval, USB3 spec table 8.13 */ | ||
| 272 | #define BDC_TNOTIFY 2500 /*in ms*/ | ||
| 273 | /* Devstatus bitfields */ | ||
| 274 | #define REMOTE_WAKEUP_ISSUED (1 << 16) | ||
| 275 | #define DEVICE_SUSPENDED (1 << 17) | ||
| 276 | #define FUNC_WAKE_ISSUED (1 << 18) | ||
| 277 | #define REMOTE_WAKE_ENABLE (1 << USB_DEVICE_REMOTE_WAKEUP) | ||
| 278 | |||
| 279 | /* On disconnect, preserve these bits and clear rest */ | ||
| 280 | #define DEVSTATUS_CLEAR (1 << USB_DEVICE_SELF_POWERED) | ||
| 281 | /* Hardware and software Data structures */ | ||
| 282 | |||
| 283 | /* Endpoint bd: buffer descriptor */ | ||
| 284 | struct bdc_bd { | ||
| 285 | __le32 offset[4]; | ||
| 286 | }; | ||
| 287 | |||
| 288 | /* Status report in Status report ring(srr) */ | ||
| 289 | struct bdc_sr { | ||
| 290 | __le32 offset[4]; | ||
| 291 | }; | ||
| 292 | |||
| 293 | /* bd_table: contigous bd's in a table */ | ||
| 294 | struct bd_table { | ||
| 295 | struct bdc_bd *start_bd; | ||
| 296 | /* dma address of start bd of table*/ | ||
| 297 | dma_addr_t dma; | ||
| 298 | }; | ||
| 299 | |||
| 300 | /* | ||
| 301 | * Each endpoint has a bdl(buffer descriptor list), bdl consists of 1 or more bd | ||
| 302 | * table's chained to each other through a chain bd, every table has equal | ||
| 303 | * number of bds. the software uses bdi(bd index) to refer to particular bd in | ||
| 304 | * the list. | ||
| 305 | */ | ||
| 306 | struct bd_list { | ||
| 307 | /* Array of bd table pointers*/ | ||
| 308 | struct bd_table **bd_table_array; | ||
| 309 | /* How many tables chained to each other */ | ||
| 310 | int num_tabs; | ||
| 311 | /* Max_bdi = num_tabs * num_bds_table - 1 */ | ||
| 312 | int max_bdi; | ||
| 313 | /* current enq bdi from sw point of view */ | ||
| 314 | int eqp_bdi; | ||
| 315 | /* current deq bdi from sw point of view */ | ||
| 316 | int hwd_bdi; | ||
| 317 | /* numbers of bds per table */ | ||
| 318 | int num_bds_table; | ||
| 319 | }; | ||
| 320 | |||
| 321 | struct bdc_req; | ||
| 322 | |||
| 323 | /* Representation of a transfer, one transfer can have multiple bd's */ | ||
| 324 | struct bd_transfer { | ||
| 325 | struct bdc_req *req; | ||
| 326 | /* start bd index */ | ||
| 327 | int start_bdi; | ||
| 328 | /* this will be the next hw dqp when this transfer completes */ | ||
| 329 | int next_hwd_bdi; | ||
| 330 | /* number of bds in this transfer */ | ||
| 331 | int num_bds; | ||
| 332 | }; | ||
| 333 | |||
| 334 | /* | ||
| 335 | * Representation of a gadget request, every gadget request is contained | ||
| 336 | * by 1 bd_transfer. | ||
| 337 | */ | ||
| 338 | struct bdc_req { | ||
| 339 | struct usb_request usb_req; | ||
| 340 | struct list_head queue; | ||
| 341 | struct bdc_ep *ep; | ||
| 342 | /* only one Transfer per request */ | ||
| 343 | struct bd_transfer bd_xfr; | ||
| 344 | int epnum; | ||
| 345 | }; | ||
| 346 | |||
| 347 | /* scratchpad buffer needed by bdc hardware */ | ||
| 348 | struct bdc_scratchpad { | ||
| 349 | dma_addr_t sp_dma; | ||
| 350 | void *buff; | ||
| 351 | u32 size; | ||
| 352 | }; | ||
| 353 | |||
| 354 | /* endpoint representation */ | ||
| 355 | struct bdc_ep { | ||
| 356 | struct usb_ep usb_ep; | ||
| 357 | struct list_head queue; | ||
| 358 | struct bdc *bdc; | ||
| 359 | u8 ep_type; | ||
| 360 | u8 dir; | ||
| 361 | u8 ep_num; | ||
| 362 | const struct usb_ss_ep_comp_descriptor *comp_desc; | ||
| 363 | const struct usb_endpoint_descriptor *desc; | ||
| 364 | unsigned int flags; | ||
| 365 | char name[20]; | ||
| 366 | /* endpoint bd list*/ | ||
| 367 | struct bd_list bd_list; | ||
| 368 | /* | ||
| 369 | * HW generates extra event for multi bd tranfers, this flag helps in | ||
| 370 | * ignoring the extra event | ||
| 371 | */ | ||
| 372 | bool ignore_next_sr; | ||
| 373 | }; | ||
| 374 | |||
| 375 | /* bdc cmmand parameter structure */ | ||
| 376 | struct bdc_cmd_params { | ||
| 377 | u32 param2; | ||
| 378 | u32 param1; | ||
| 379 | u32 param0; | ||
| 380 | }; | ||
| 381 | |||
| 382 | /* status report ring(srr), currently one srr is supported for entire system */ | ||
| 383 | struct srr { | ||
| 384 | struct bdc_sr *sr_bds; | ||
| 385 | u16 eqp_index; | ||
| 386 | u16 dqp_index; | ||
| 387 | dma_addr_t dma_addr; | ||
| 388 | }; | ||
| 389 | |||
| 390 | /* EP0 states */ | ||
| 391 | enum bdc_ep0_state { | ||
| 392 | WAIT_FOR_SETUP = 0, | ||
| 393 | WAIT_FOR_DATA_START, | ||
| 394 | WAIT_FOR_DATA_XMIT, | ||
| 395 | WAIT_FOR_STATUS_START, | ||
| 396 | WAIT_FOR_STATUS_XMIT, | ||
| 397 | STATUS_PENDING | ||
| 398 | }; | ||
| 399 | |||
| 400 | /* Link states */ | ||
| 401 | enum bdc_link_state { | ||
| 402 | BDC_LINK_STATE_U0 = 0x00, | ||
| 403 | BDC_LINK_STATE_U3 = 0x03, | ||
| 404 | BDC_LINK_STATE_RX_DET = 0x05, | ||
| 405 | BDC_LINK_STATE_RESUME = 0x0f | ||
| 406 | }; | ||
| 407 | |||
| 408 | /* representation of bdc */ | ||
| 409 | struct bdc { | ||
| 410 | struct usb_gadget gadget; | ||
| 411 | struct usb_gadget_driver *gadget_driver; | ||
| 412 | struct device *dev; | ||
| 413 | /* device lock */ | ||
| 414 | spinlock_t lock; | ||
| 415 | |||
| 416 | /* num of endpoints for a particular instantiation of IP */ | ||
| 417 | unsigned int num_eps; | ||
| 418 | /* | ||
| 419 | * Array of ep's, it uses the same index covention as bdc hw i.e. | ||
| 420 | * 1 for ep0, 2 for 1out,3 for 1in .... | ||
| 421 | */ | ||
| 422 | struct bdc_ep **bdc_ep_array; | ||
| 423 | void __iomem *regs; | ||
| 424 | struct bdc_scratchpad scratchpad; | ||
| 425 | u32 sp_buff_size; | ||
| 426 | /* current driver supports 1 status ring */ | ||
| 427 | struct srr srr; | ||
| 428 | /* Last received setup packet */ | ||
| 429 | struct usb_ctrlrequest setup_pkt; | ||
| 430 | struct bdc_req ep0_req; | ||
| 431 | struct bdc_req status_req; | ||
| 432 | enum bdc_ep0_state ep0_state; | ||
| 433 | bool delayed_status; | ||
| 434 | bool zlp_needed; | ||
| 435 | bool reinit; | ||
| 436 | bool pullup; | ||
| 437 | /* Bits 0-15 are standard and 16-31 for proprietary information */ | ||
| 438 | u32 devstatus; | ||
| 439 | int irq; | ||
| 440 | void *mem; | ||
| 441 | u32 dev_addr; | ||
| 442 | /* DMA pools */ | ||
| 443 | struct dma_pool *bd_table_pool; | ||
| 444 | u8 test_mode; | ||
| 445 | /* array of callbacks for various status report handlers */ | ||
| 446 | void (*sr_handler[2])(struct bdc *, struct bdc_sr *); | ||
| 447 | /* ep0 callback handlers */ | ||
| 448 | void (*sr_xsf_ep0[3])(struct bdc *, struct bdc_sr *); | ||
| 449 | /* ep0 response buffer for ch9 requests like GET_STATUS and SET_SEL */ | ||
| 450 | unsigned char ep0_response_buff[EP0_RESPONSE_BUFF]; | ||
| 451 | /* | ||
| 452 | * Timer to check if host resumed transfer after bdc sent Func wake | ||
| 453 | * notification packet after a remote wakeup. if not, then resend the | ||
| 454 | * Func Wake packet every 2.5 secs. Refer to USB3 spec section 8.5.6.4 | ||
| 455 | */ | ||
| 456 | struct delayed_work func_wake_notify; | ||
| 457 | }; | ||
| 458 | |||
| 459 | static inline u32 bdc_readl(void __iomem *base, u32 offset) | ||
| 460 | { | ||
| 461 | return readl(base + offset); | ||
| 462 | } | ||
| 463 | |||
| 464 | static inline void bdc_writel(void __iomem *base, u32 offset, u32 value) | ||
| 465 | { | ||
| 466 | writel(value, base + offset); | ||
| 467 | } | ||
| 468 | |||
| 469 | /* Buffer descriptor list operations */ | ||
| 470 | void bdc_notify_xfr(struct bdc *, u32); | ||
| 471 | void bdc_softconn(struct bdc *); | ||
| 472 | void bdc_softdisconn(struct bdc *); | ||
| 473 | int bdc_run(struct bdc *); | ||
| 474 | int bdc_stop(struct bdc *); | ||
| 475 | int bdc_reset(struct bdc *); | ||
| 476 | int bdc_udc_init(struct bdc *); | ||
| 477 | void bdc_udc_exit(struct bdc *); | ||
| 478 | int bdc_reinit(struct bdc *); | ||
| 479 | |||
| 480 | /* Status report handlers */ | ||
| 481 | /* Upstream port status change sr */ | ||
| 482 | void bdc_sr_uspc(struct bdc *, struct bdc_sr *); | ||
| 483 | /* transfer sr */ | ||
| 484 | void bdc_sr_xsf(struct bdc *, struct bdc_sr *); | ||
| 485 | /* EP0 XSF handlers */ | ||
| 486 | void bdc_xsf_ep0_setup_recv(struct bdc *, struct bdc_sr *); | ||
| 487 | void bdc_xsf_ep0_data_start(struct bdc *, struct bdc_sr *); | ||
| 488 | void bdc_xsf_ep0_status_start(struct bdc *, struct bdc_sr *); | ||
| 489 | |||
| 490 | #endif /* __LINUX_BDC_H__ */ | ||
diff --git a/drivers/usb/gadget/udc/bdc/bdc_cmd.c b/drivers/usb/gadget/udc/bdc/bdc_cmd.c new file mode 100644 index 000000000000..6a4155c4bd86 --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/bdc_cmd.c | |||
| @@ -0,0 +1,376 @@ | |||
| 1 | /* | ||
| 2 | * bdc_cmd.c - BRCM BDC USB3.0 device controller | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Broadcom Corporation | ||
| 5 | * | ||
| 6 | * Author: Ashwini Pahuja | ||
| 7 | * | ||
| 8 | * This program is free software; you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | * | ||
| 13 | */ | ||
| 14 | #include <linux/scatterlist.h> | ||
| 15 | #include <linux/slab.h> | ||
| 16 | |||
| 17 | #include "bdc.h" | ||
| 18 | #include "bdc_cmd.h" | ||
| 19 | #include "bdc_dbg.h" | ||
| 20 | |||
| 21 | /* Issues a cmd to cmd processor and waits for cmd completion */ | ||
| 22 | static int bdc_issue_cmd(struct bdc *bdc, u32 cmd_sc, u32 param0, | ||
| 23 | u32 param1, u32 param2) | ||
| 24 | { | ||
| 25 | u32 timeout = BDC_CMD_TIMEOUT; | ||
| 26 | u32 cmd_status; | ||
| 27 | u32 temp; | ||
| 28 | |||
| 29 | bdc_writel(bdc->regs, BDC_CMDPAR0, param0); | ||
| 30 | bdc_writel(bdc->regs, BDC_CMDPAR1, param1); | ||
| 31 | bdc_writel(bdc->regs, BDC_CMDPAR2, param2); | ||
| 32 | |||
| 33 | /* Issue the cmd */ | ||
| 34 | /* Make sure the cmd params are written before asking HW to exec cmd */ | ||
| 35 | wmb(); | ||
| 36 | bdc_writel(bdc->regs, BDC_CMDSC, cmd_sc | BDC_CMD_CWS | BDC_CMD_SRD); | ||
| 37 | do { | ||
| 38 | temp = bdc_readl(bdc->regs, BDC_CMDSC); | ||
| 39 | dev_dbg_ratelimited(bdc->dev, "cmdsc=%x", temp); | ||
| 40 | cmd_status = BDC_CMD_CST(temp); | ||
| 41 | if (cmd_status != BDC_CMDS_BUSY) { | ||
| 42 | dev_dbg(bdc->dev, | ||
| 43 | "command completed cmd_sts:%x\n", cmd_status); | ||
| 44 | return cmd_status; | ||
| 45 | } | ||
| 46 | udelay(1); | ||
| 47 | } while (timeout--); | ||
| 48 | |||
| 49 | dev_err(bdc->dev, | ||
| 50 | "command operation timedout cmd_status=%d\n", cmd_status); | ||
| 51 | |||
| 52 | return cmd_status; | ||
| 53 | } | ||
| 54 | |||
| 55 | /* Submits cmd and analyze the return value of bdc_issue_cmd */ | ||
| 56 | static int bdc_submit_cmd(struct bdc *bdc, u32 cmd_sc, | ||
| 57 | u32 param0, u32 param1, u32 param2) | ||
| 58 | { | ||
| 59 | u32 temp, cmd_status; | ||
| 60 | int reset_bdc = 0; | ||
| 61 | int ret; | ||
| 62 | |||
| 63 | temp = bdc_readl(bdc->regs, BDC_CMDSC); | ||
| 64 | dev_dbg(bdc->dev, | ||
| 65 | "%s:CMDSC:%08x cmdsc:%08x param0=%08x param1=%08x param2=%08x\n", | ||
| 66 | __func__, temp, cmd_sc, param0, param1, param2); | ||
| 67 | |||
| 68 | cmd_status = BDC_CMD_CST(temp); | ||
| 69 | if (cmd_status == BDC_CMDS_BUSY) { | ||
| 70 | dev_err(bdc->dev, "command processor busy: %x\n", cmd_status); | ||
| 71 | return -EBUSY; | ||
| 72 | } | ||
| 73 | ret = bdc_issue_cmd(bdc, cmd_sc, param0, param1, param2); | ||
| 74 | switch (ret) { | ||
| 75 | case BDC_CMDS_SUCC: | ||
| 76 | dev_dbg(bdc->dev, "command completed successfully\n"); | ||
| 77 | ret = 0; | ||
| 78 | break; | ||
| 79 | |||
| 80 | case BDC_CMDS_PARA: | ||
| 81 | dev_err(bdc->dev, "command parameter error\n"); | ||
| 82 | ret = -EINVAL; | ||
| 83 | break; | ||
| 84 | |||
| 85 | case BDC_CMDS_STAT: | ||
| 86 | dev_err(bdc->dev, "Invalid device/ep state\n"); | ||
| 87 | ret = -EINVAL; | ||
| 88 | break; | ||
| 89 | |||
| 90 | case BDC_CMDS_FAIL: | ||
| 91 | dev_err(bdc->dev, "Command failed?\n"); | ||
| 92 | ret = -EAGAIN; | ||
| 93 | break; | ||
| 94 | |||
| 95 | case BDC_CMDS_INTL: | ||
| 96 | dev_err(bdc->dev, "BDC Internal error\n"); | ||
| 97 | reset_bdc = 1; | ||
| 98 | ret = -ECONNRESET; | ||
| 99 | break; | ||
| 100 | |||
| 101 | case BDC_CMDS_BUSY: | ||
| 102 | dev_err(bdc->dev, | ||
| 103 | "command timedout waited for %dusec\n", | ||
| 104 | BDC_CMD_TIMEOUT); | ||
| 105 | reset_bdc = 1; | ||
| 106 | ret = -ECONNRESET; | ||
| 107 | break; | ||
| 108 | default: | ||
| 109 | dev_dbg(bdc->dev, "Unknown command completion code:%x\n", ret); | ||
| 110 | } | ||
| 111 | |||
| 112 | return ret; | ||
| 113 | } | ||
| 114 | |||
| 115 | /* Deconfigure the endpoint from HW */ | ||
| 116 | int bdc_dconfig_ep(struct bdc *bdc, struct bdc_ep *ep) | ||
| 117 | { | ||
| 118 | u32 cmd_sc; | ||
| 119 | |||
| 120 | cmd_sc = BDC_SUB_CMD_DRP_EP|BDC_CMD_EPN(ep->ep_num)|BDC_CMD_EPC; | ||
| 121 | dev_dbg(bdc->dev, "%s ep->ep_num =%d cmd_sc=%x\n", __func__, | ||
| 122 | ep->ep_num, cmd_sc); | ||
| 123 | |||
| 124 | return bdc_submit_cmd(bdc, cmd_sc, 0, 0, 0); | ||
| 125 | } | ||
| 126 | |||
| 127 | /* Reinitalize the bdlist after config ep command */ | ||
| 128 | static void ep_bd_list_reinit(struct bdc_ep *ep) | ||
| 129 | { | ||
| 130 | struct bdc *bdc = ep->bdc; | ||
| 131 | struct bdc_bd *bd; | ||
| 132 | |||
| 133 | ep->bd_list.eqp_bdi = 0; | ||
| 134 | ep->bd_list.hwd_bdi = 0; | ||
| 135 | bd = ep->bd_list.bd_table_array[0]->start_bd; | ||
| 136 | dev_dbg(bdc->dev, "%s ep:%p bd:%p\n", __func__, ep, bd); | ||
| 137 | memset(bd, 0, sizeof(struct bdc_bd)); | ||
| 138 | bd->offset[3] |= cpu_to_le32(BD_SBF); | ||
| 139 | } | ||
| 140 | |||
| 141 | /* Configure an endpoint */ | ||
| 142 | int bdc_config_ep(struct bdc *bdc, struct bdc_ep *ep) | ||
| 143 | { | ||
| 144 | const struct usb_ss_ep_comp_descriptor *comp_desc; | ||
| 145 | const struct usb_endpoint_descriptor *desc; | ||
| 146 | u32 param0, param1, param2, cmd_sc; | ||
| 147 | u32 mps, mbs, mul, si; | ||
| 148 | int ret; | ||
| 149 | |||
| 150 | desc = ep->desc; | ||
| 151 | comp_desc = ep->comp_desc; | ||
| 152 | cmd_sc = mul = mbs = param2 = 0; | ||
| 153 | param0 = lower_32_bits(ep->bd_list.bd_table_array[0]->dma); | ||
| 154 | param1 = upper_32_bits(ep->bd_list.bd_table_array[0]->dma); | ||
| 155 | cpu_to_le32s(¶m0); | ||
| 156 | cpu_to_le32s(¶m1); | ||
| 157 | |||
| 158 | dev_dbg(bdc->dev, "%s: param0=%08x param1=%08x", | ||
| 159 | __func__, param0, param1); | ||
| 160 | si = desc->bInterval; | ||
| 161 | si = clamp_val(si, 1, 16) - 1; | ||
| 162 | |||
| 163 | mps = usb_endpoint_maxp(desc); | ||
| 164 | mps &= 0x7ff; | ||
| 165 | param2 |= mps << MP_SHIFT; | ||
| 166 | param2 |= usb_endpoint_type(desc) << EPT_SHIFT; | ||
| 167 | |||
| 168 | switch (bdc->gadget.speed) { | ||
| 169 | case USB_SPEED_SUPER: | ||
| 170 | if (usb_endpoint_xfer_int(desc) || | ||
| 171 | usb_endpoint_xfer_isoc(desc)) { | ||
| 172 | param2 |= si; | ||
| 173 | if (usb_endpoint_xfer_isoc(desc) && comp_desc) | ||
| 174 | mul = comp_desc->bmAttributes; | ||
| 175 | |||
| 176 | } | ||
| 177 | param2 |= mul << EPM_SHIFT; | ||
| 178 | if (comp_desc) | ||
| 179 | mbs = comp_desc->bMaxBurst; | ||
| 180 | param2 |= mbs << MB_SHIFT; | ||
| 181 | break; | ||
| 182 | |||
| 183 | case USB_SPEED_HIGH: | ||
| 184 | if (usb_endpoint_xfer_isoc(desc) || | ||
| 185 | usb_endpoint_xfer_int(desc)) { | ||
| 186 | param2 |= si; | ||
| 187 | |||
| 188 | mbs = (usb_endpoint_maxp(desc) & 0x1800) >> 11; | ||
| 189 | param2 |= mbs << MB_SHIFT; | ||
| 190 | } | ||
| 191 | break; | ||
| 192 | |||
| 193 | case USB_SPEED_FULL: | ||
| 194 | case USB_SPEED_LOW: | ||
| 195 | /* the hardware accepts SI in 125usec range */ | ||
| 196 | if (usb_endpoint_xfer_isoc(desc)) | ||
| 197 | si += 3; | ||
| 198 | |||
| 199 | /* | ||
| 200 | * FS Int endpoints can have si of 1-255ms but the controller | ||
| 201 | * accepts 2^bInterval*125usec, so convert ms to nearest power | ||
| 202 | * of 2 | ||
| 203 | */ | ||
| 204 | if (usb_endpoint_xfer_int(desc)) | ||
| 205 | si = fls(desc->bInterval * 8) - 1; | ||
| 206 | |||
| 207 | param2 |= si; | ||
| 208 | break; | ||
| 209 | default: | ||
| 210 | dev_err(bdc->dev, "UNKNOWN speed ERR\n"); | ||
| 211 | return -EINVAL; | ||
| 212 | } | ||
| 213 | |||
| 214 | cmd_sc |= BDC_CMD_EPC|BDC_CMD_EPN(ep->ep_num)|BDC_SUB_CMD_ADD_EP; | ||
| 215 | |||
| 216 | dev_dbg(bdc->dev, "cmd_sc=%x param2=%08x\n", cmd_sc, param2); | ||
| 217 | ret = bdc_submit_cmd(bdc, cmd_sc, param0, param1, param2); | ||
| 218 | if (ret) { | ||
| 219 | dev_err(bdc->dev, "command failed :%x\n", ret); | ||
| 220 | return ret; | ||
| 221 | } | ||
| 222 | ep_bd_list_reinit(ep); | ||
| 223 | |||
| 224 | return ret; | ||
| 225 | } | ||
| 226 | |||
| 227 | /* | ||
| 228 | * Change the HW deq pointer, if this command is successful, HW will start | ||
| 229 | * fetching the next bd from address dma_addr. | ||
| 230 | */ | ||
| 231 | int bdc_ep_bla(struct bdc *bdc, struct bdc_ep *ep, dma_addr_t dma_addr) | ||
| 232 | { | ||
| 233 | u32 param0, param1; | ||
| 234 | u32 cmd_sc = 0; | ||
| 235 | |||
| 236 | dev_dbg(bdc->dev, "%s: add=%08llx\n", __func__, | ||
| 237 | (unsigned long long)(dma_addr)); | ||
| 238 | param0 = lower_32_bits(dma_addr); | ||
| 239 | param1 = upper_32_bits(dma_addr); | ||
| 240 | cpu_to_le32s(¶m0); | ||
| 241 | cpu_to_le32s(¶m1); | ||
| 242 | |||
| 243 | cmd_sc |= BDC_CMD_EPN(ep->ep_num)|BDC_CMD_BLA; | ||
| 244 | dev_dbg(bdc->dev, "cmd_sc=%x\n", cmd_sc); | ||
| 245 | |||
| 246 | return bdc_submit_cmd(bdc, cmd_sc, param0, param1, 0); | ||
| 247 | } | ||
| 248 | |||
| 249 | /* Set the address sent bu Host in SET_ADD request */ | ||
| 250 | int bdc_address_device(struct bdc *bdc, u32 add) | ||
| 251 | { | ||
| 252 | u32 cmd_sc = 0; | ||
| 253 | u32 param2; | ||
| 254 | |||
| 255 | dev_dbg(bdc->dev, "%s: add=%d\n", __func__, add); | ||
| 256 | cmd_sc |= BDC_SUB_CMD_ADD|BDC_CMD_DVC; | ||
| 257 | param2 = add & 0x7f; | ||
| 258 | |||
| 259 | return bdc_submit_cmd(bdc, cmd_sc, 0, 0, param2); | ||
| 260 | } | ||
| 261 | |||
| 262 | /* Send a Function Wake notification packet using FH command */ | ||
| 263 | int bdc_function_wake_fh(struct bdc *bdc, u8 intf) | ||
| 264 | { | ||
| 265 | u32 param0, param1; | ||
| 266 | u32 cmd_sc = 0; | ||
| 267 | |||
| 268 | param0 = param1 = 0; | ||
| 269 | dev_dbg(bdc->dev, "%s intf=%d\n", __func__, intf); | ||
| 270 | cmd_sc |= BDC_CMD_FH; | ||
| 271 | param0 |= TRA_PACKET; | ||
| 272 | param0 |= (bdc->dev_addr << 25); | ||
| 273 | param1 |= DEV_NOTF_TYPE; | ||
| 274 | param1 |= (FWK_SUBTYPE<<4); | ||
| 275 | dev_dbg(bdc->dev, "param0=%08x param1=%08x\n", param0, param1); | ||
| 276 | |||
| 277 | return bdc_submit_cmd(bdc, cmd_sc, param0, param1, 0); | ||
| 278 | } | ||
| 279 | |||
| 280 | /* Send a Function Wake notification packet using DNC command */ | ||
| 281 | int bdc_function_wake(struct bdc *bdc, u8 intf) | ||
| 282 | { | ||
| 283 | u32 cmd_sc = 0; | ||
| 284 | u32 param2 = 0; | ||
| 285 | |||
| 286 | dev_dbg(bdc->dev, "%s intf=%d", __func__, intf); | ||
| 287 | param2 |= intf; | ||
| 288 | cmd_sc |= BDC_SUB_CMD_FWK|BDC_CMD_DNC; | ||
| 289 | |||
| 290 | return bdc_submit_cmd(bdc, cmd_sc, 0, 0, param2); | ||
| 291 | } | ||
| 292 | |||
| 293 | /* Stall the endpoint */ | ||
| 294 | int bdc_ep_set_stall(struct bdc *bdc, int epnum) | ||
| 295 | { | ||
| 296 | u32 cmd_sc = 0; | ||
| 297 | |||
| 298 | dev_dbg(bdc->dev, "%s epnum=%d\n", __func__, epnum); | ||
| 299 | /* issue a stall endpoint command */ | ||
| 300 | cmd_sc |= BDC_SUB_CMD_EP_STL | BDC_CMD_EPN(epnum) | BDC_CMD_EPO; | ||
| 301 | |||
| 302 | return bdc_submit_cmd(bdc, cmd_sc, 0, 0, 0); | ||
| 303 | } | ||
| 304 | |||
| 305 | /* resets the endpoint, called when host sends CLEAR_FEATURE(HALT) */ | ||
| 306 | int bdc_ep_clear_stall(struct bdc *bdc, int epnum) | ||
| 307 | { | ||
| 308 | struct bdc_ep *ep; | ||
| 309 | u32 cmd_sc = 0; | ||
| 310 | int ret; | ||
| 311 | |||
| 312 | dev_dbg(bdc->dev, "%s: epnum=%d\n", __func__, epnum); | ||
| 313 | ep = bdc->bdc_ep_array[epnum]; | ||
| 314 | /* | ||
| 315 | * If we are not in stalled then stall Endpoint and issue clear stall, | ||
| 316 | * his will reset the seq number for non EP0. | ||
| 317 | */ | ||
| 318 | if (epnum != 1) { | ||
| 319 | /* if the endpoint it not stallled */ | ||
| 320 | if (!(ep->flags & BDC_EP_STALL)) { | ||
| 321 | ret = bdc_ep_set_stall(bdc, epnum); | ||
| 322 | if (ret) | ||
| 323 | return ret; | ||
| 324 | } | ||
| 325 | } | ||
| 326 | /* Preserve the seq number for ep0 only */ | ||
| 327 | if (epnum != 1) | ||
| 328 | cmd_sc |= BDC_CMD_EPO_RST_SN; | ||
| 329 | |||
| 330 | /* issue a reset endpoint command */ | ||
| 331 | cmd_sc |= BDC_SUB_CMD_EP_RST | BDC_CMD_EPN(epnum) | BDC_CMD_EPO; | ||
| 332 | |||
| 333 | ret = bdc_submit_cmd(bdc, cmd_sc, 0, 0, 0); | ||
| 334 | if (ret) { | ||
| 335 | dev_err(bdc->dev, "command failed:%x\n", ret); | ||
| 336 | return ret; | ||
| 337 | } | ||
| 338 | bdc_notify_xfr(bdc, epnum); | ||
| 339 | |||
| 340 | return ret; | ||
| 341 | } | ||
| 342 | |||
| 343 | /* Stop the endpoint, called when software wants to dequeue some request */ | ||
| 344 | int bdc_stop_ep(struct bdc *bdc, int epnum) | ||
| 345 | { | ||
| 346 | struct bdc_ep *ep; | ||
| 347 | u32 cmd_sc = 0; | ||
| 348 | int ret; | ||
| 349 | |||
| 350 | ep = bdc->bdc_ep_array[epnum]; | ||
| 351 | dev_dbg(bdc->dev, "%s: ep:%s ep->flags:%08x\n", __func__, | ||
| 352 | ep->name, ep->flags); | ||
| 353 | /* Endpoint has to be in running state to execute stop ep command */ | ||
| 354 | if (!(ep->flags & BDC_EP_ENABLED)) { | ||
| 355 | dev_err(bdc->dev, "stop endpoint called for disabled ep\n"); | ||
| 356 | return -EINVAL; | ||
| 357 | } | ||
| 358 | if ((ep->flags & BDC_EP_STALL) || (ep->flags & BDC_EP_STOP)) | ||
| 359 | return 0; | ||
| 360 | |||
| 361 | /* issue a stop endpoint command */ | ||
| 362 | cmd_sc |= BDC_CMD_EP0_XSD | BDC_SUB_CMD_EP_STP | ||
| 363 | | BDC_CMD_EPN(epnum) | BDC_CMD_EPO; | ||
| 364 | |||
| 365 | ret = bdc_submit_cmd(bdc, cmd_sc, 0, 0, 0); | ||
| 366 | if (ret) { | ||
| 367 | dev_err(bdc->dev, | ||
| 368 | "stop endpoint command didn't complete:%d ep:%s\n", | ||
| 369 | ret, ep->name); | ||
| 370 | return ret; | ||
| 371 | } | ||
| 372 | ep->flags |= BDC_EP_STOP; | ||
| 373 | bdc_dump_epsts(bdc); | ||
| 374 | |||
| 375 | return ret; | ||
| 376 | } | ||
diff --git a/drivers/usb/gadget/udc/bdc/bdc_cmd.h b/drivers/usb/gadget/udc/bdc/bdc_cmd.h new file mode 100644 index 000000000000..61d0e3bf9853 --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/bdc_cmd.h | |||
| @@ -0,0 +1,29 @@ | |||
| 1 | /* | ||
| 2 | * bdc_cmd.h - header for the BDC debug functions | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Broadcom Corporation | ||
| 5 | * | ||
| 6 | * Author: Ashwini Pahuja | ||
| 7 | * | ||
| 8 | * This program is free software; you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | * | ||
| 13 | */ | ||
| 14 | #ifndef __LINUX_BDC_CMD_H__ | ||
| 15 | #define __LINUX_BDC_CMD_H__ | ||
| 16 | |||
| 17 | /* Command operations */ | ||
| 18 | int bdc_address_device(struct bdc *, u32); | ||
| 19 | int bdc_config_ep(struct bdc *, struct bdc_ep *); | ||
| 20 | int bdc_dconfig_ep(struct bdc *, struct bdc_ep *); | ||
| 21 | int bdc_stop_ep(struct bdc *, int); | ||
| 22 | int bdc_ep_set_stall(struct bdc *, int); | ||
| 23 | int bdc_ep_clear_stall(struct bdc *, int); | ||
| 24 | int bdc_ep_set_halt(struct bdc_ep *, u32 , int); | ||
| 25 | int bdc_ep_bla(struct bdc *, struct bdc_ep *, dma_addr_t); | ||
| 26 | int bdc_function_wake(struct bdc*, u8); | ||
| 27 | int bdc_function_wake_fh(struct bdc*, u8); | ||
| 28 | |||
| 29 | #endif /* __LINUX_BDC_CMD_H__ */ | ||
diff --git a/drivers/usb/gadget/udc/bdc/bdc_core.c b/drivers/usb/gadget/udc/bdc/bdc_core.c new file mode 100644 index 000000000000..c6dfef8c7bbc --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/bdc_core.c | |||
| @@ -0,0 +1,533 @@ | |||
| 1 | /* | ||
| 2 | * bdc_core.c - BRCM BDC USB3.0 device controller core operations | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Broadcom Corporation | ||
| 5 | * | ||
| 6 | * Author: Ashwini Pahuja | ||
| 7 | * | ||
| 8 | * This program is free software; you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | * | ||
| 13 | */ | ||
| 14 | #include <linux/module.h> | ||
| 15 | #include <linux/kernel.h> | ||
| 16 | #include <linux/slab.h> | ||
| 17 | #include <linux/spinlock.h> | ||
| 18 | #include <linux/platform_device.h> | ||
| 19 | #include <linux/interrupt.h> | ||
| 20 | #include <linux/ioport.h> | ||
| 21 | #include <linux/io.h> | ||
| 22 | #include <linux/list.h> | ||
| 23 | #include <linux/delay.h> | ||
| 24 | #include <linux/dma-mapping.h> | ||
| 25 | #include <linux/dmapool.h> | ||
| 26 | #include <linux/of.h> | ||
| 27 | #include <linux/moduleparam.h> | ||
| 28 | #include <linux/usb/ch9.h> | ||
| 29 | #include <linux/usb/gadget.h> | ||
| 30 | |||
| 31 | #include "bdc.h" | ||
| 32 | #include "bdc_dbg.h" | ||
| 33 | |||
| 34 | /* Poll till controller status is not OIP */ | ||
| 35 | static int poll_oip(struct bdc *bdc, int usec) | ||
| 36 | { | ||
| 37 | u32 status; | ||
| 38 | /* Poll till STS!= OIP */ | ||
| 39 | while (usec) { | ||
| 40 | status = bdc_readl(bdc->regs, BDC_BDCSC); | ||
| 41 | if (BDC_CSTS(status) != BDC_OIP) { | ||
| 42 | dev_dbg(bdc->dev, | ||
| 43 | "poll_oip complete status=%d", | ||
| 44 | BDC_CSTS(status)); | ||
| 45 | return 0; | ||
| 46 | } | ||
| 47 | udelay(10); | ||
| 48 | usec -= 10; | ||
| 49 | } | ||
| 50 | dev_err(bdc->dev, "Err: operation timedout BDCSC: 0x%08x\n", status); | ||
| 51 | |||
| 52 | return -ETIMEDOUT; | ||
| 53 | } | ||
| 54 | |||
| 55 | /* Stop the BDC controller */ | ||
| 56 | int bdc_stop(struct bdc *bdc) | ||
| 57 | { | ||
| 58 | int ret; | ||
| 59 | u32 temp; | ||
| 60 | |||
| 61 | dev_dbg(bdc->dev, "%s ()\n\n", __func__); | ||
| 62 | temp = bdc_readl(bdc->regs, BDC_BDCSC); | ||
| 63 | /* Check if BDC is already halted */ | ||
| 64 | if (BDC_CSTS(temp) == BDC_HLT) { | ||
| 65 | dev_vdbg(bdc->dev, "BDC already halted\n"); | ||
| 66 | return 0; | ||
| 67 | } | ||
| 68 | temp &= ~BDC_COP_MASK; | ||
| 69 | temp |= BDC_COS|BDC_COP_STP; | ||
| 70 | bdc_writel(bdc->regs, BDC_BDCSC, temp); | ||
| 71 | |||
| 72 | ret = poll_oip(bdc, BDC_COP_TIMEOUT); | ||
| 73 | if (ret) | ||
| 74 | dev_err(bdc->dev, "bdc stop operation failed"); | ||
| 75 | |||
| 76 | return ret; | ||
| 77 | } | ||
| 78 | |||
| 79 | /* Issue a reset to BDC controller */ | ||
| 80 | int bdc_reset(struct bdc *bdc) | ||
| 81 | { | ||
| 82 | u32 temp; | ||
| 83 | int ret; | ||
| 84 | |||
| 85 | dev_dbg(bdc->dev, "%s ()\n", __func__); | ||
| 86 | /* First halt the controller */ | ||
| 87 | ret = bdc_stop(bdc); | ||
| 88 | if (ret) | ||
| 89 | return ret; | ||
| 90 | |||
| 91 | temp = bdc_readl(bdc->regs, BDC_BDCSC); | ||
| 92 | temp &= ~BDC_COP_MASK; | ||
| 93 | temp |= BDC_COS|BDC_COP_RST; | ||
| 94 | bdc_writel(bdc->regs, BDC_BDCSC, temp); | ||
| 95 | ret = poll_oip(bdc, BDC_COP_TIMEOUT); | ||
| 96 | if (ret) | ||
| 97 | dev_err(bdc->dev, "bdc reset operation failed"); | ||
| 98 | |||
| 99 | return ret; | ||
| 100 | } | ||
| 101 | |||
| 102 | /* Run the BDC controller */ | ||
| 103 | int bdc_run(struct bdc *bdc) | ||
| 104 | { | ||
| 105 | u32 temp; | ||
| 106 | int ret; | ||
| 107 | |||
| 108 | dev_dbg(bdc->dev, "%s ()\n", __func__); | ||
| 109 | temp = bdc_readl(bdc->regs, BDC_BDCSC); | ||
| 110 | /* if BDC is already in running state then do not do anything */ | ||
| 111 | if (BDC_CSTS(temp) == BDC_NOR) { | ||
| 112 | dev_warn(bdc->dev, "bdc is already in running state\n"); | ||
| 113 | return 0; | ||
| 114 | } | ||
| 115 | temp &= ~BDC_COP_MASK; | ||
| 116 | temp |= BDC_COP_RUN; | ||
| 117 | temp |= BDC_COS; | ||
| 118 | bdc_writel(bdc->regs, BDC_BDCSC, temp); | ||
| 119 | ret = poll_oip(bdc, BDC_COP_TIMEOUT); | ||
| 120 | if (ret) { | ||
| 121 | dev_err(bdc->dev, "bdc run operation failed:%d", ret); | ||
| 122 | return ret; | ||
| 123 | } | ||
| 124 | temp = bdc_readl(bdc->regs, BDC_BDCSC); | ||
| 125 | if (BDC_CSTS(temp) != BDC_NOR) { | ||
| 126 | dev_err(bdc->dev, "bdc not in normal mode after RUN op :%d\n", | ||
| 127 | BDC_CSTS(temp)); | ||
| 128 | return -ESHUTDOWN; | ||
| 129 | } | ||
| 130 | |||
| 131 | return 0; | ||
| 132 | } | ||
| 133 | |||
| 134 | /* | ||
| 135 | * Present the termination to the host, typically called from upstream port | ||
| 136 | * event with Vbus present =1 | ||
| 137 | */ | ||
| 138 | void bdc_softconn(struct bdc *bdc) | ||
| 139 | { | ||
| 140 | u32 uspc; | ||
| 141 | |||
| 142 | uspc = bdc_readl(bdc->regs, BDC_USPC); | ||
| 143 | uspc &= ~BDC_PST_MASK; | ||
| 144 | uspc |= BDC_LINK_STATE_RX_DET; | ||
| 145 | uspc |= BDC_SWS; | ||
| 146 | dev_dbg(bdc->dev, "%s () uspc=%08x\n", __func__, uspc); | ||
| 147 | bdc_writel(bdc->regs, BDC_USPC, uspc); | ||
| 148 | } | ||
| 149 | |||
| 150 | /* Remove the termination */ | ||
| 151 | void bdc_softdisconn(struct bdc *bdc) | ||
| 152 | { | ||
| 153 | u32 uspc; | ||
| 154 | |||
| 155 | uspc = bdc_readl(bdc->regs, BDC_USPC); | ||
| 156 | uspc |= BDC_SDC; | ||
| 157 | uspc &= ~BDC_SCN; | ||
| 158 | dev_dbg(bdc->dev, "%s () uspc=%x\n", __func__, uspc); | ||
| 159 | bdc_writel(bdc->regs, BDC_USPC, uspc); | ||
| 160 | } | ||
| 161 | |||
| 162 | /* Set up the scratchpad buffer array and scratchpad buffers, if needed. */ | ||
| 163 | static int scratchpad_setup(struct bdc *bdc) | ||
| 164 | { | ||
| 165 | int sp_buff_size; | ||
| 166 | u32 low32; | ||
| 167 | u32 upp32; | ||
| 168 | |||
| 169 | sp_buff_size = BDC_SPB(bdc_readl(bdc->regs, BDC_BDCCFG0)); | ||
| 170 | dev_dbg(bdc->dev, "%s() sp_buff_size=%d\n", __func__, sp_buff_size); | ||
| 171 | if (!sp_buff_size) { | ||
| 172 | dev_dbg(bdc->dev, "Scratchpad buffer not needed\n"); | ||
| 173 | return 0; | ||
| 174 | } | ||
| 175 | /* Refer to BDC spec, Table 4 for description of SPB */ | ||
| 176 | sp_buff_size = 1 << (sp_buff_size + 5); | ||
| 177 | dev_dbg(bdc->dev, "Allocating %d bytes for scratchpad\n", sp_buff_size); | ||
| 178 | bdc->scratchpad.buff = dma_zalloc_coherent(bdc->dev, sp_buff_size, | ||
| 179 | &bdc->scratchpad.sp_dma, GFP_KERNEL); | ||
| 180 | |||
| 181 | if (!bdc->scratchpad.buff) | ||
| 182 | goto fail; | ||
| 183 | |||
| 184 | bdc->sp_buff_size = sp_buff_size; | ||
| 185 | bdc->scratchpad.size = sp_buff_size; | ||
| 186 | low32 = lower_32_bits(bdc->scratchpad.sp_dma); | ||
| 187 | upp32 = upper_32_bits(bdc->scratchpad.sp_dma); | ||
| 188 | cpu_to_le32s(&low32); | ||
| 189 | cpu_to_le32s(&upp32); | ||
| 190 | bdc_writel(bdc->regs, BDC_SPBBAL, low32); | ||
| 191 | bdc_writel(bdc->regs, BDC_SPBBAH, upp32); | ||
| 192 | return 0; | ||
| 193 | |||
| 194 | fail: | ||
| 195 | bdc->scratchpad.buff = NULL; | ||
| 196 | |||
| 197 | return -ENOMEM; | ||
| 198 | } | ||
| 199 | |||
| 200 | /* Allocate the status report ring */ | ||
| 201 | static int setup_srr(struct bdc *bdc, int interrupter) | ||
| 202 | { | ||
| 203 | dev_dbg(bdc->dev, "%s() NUM_SR_ENTRIES:%d\n", __func__, NUM_SR_ENTRIES); | ||
| 204 | /* Reset the SRR */ | ||
| 205 | bdc_writel(bdc->regs, BDC_SRRINT(0), BDC_SRR_RWS | BDC_SRR_RST); | ||
| 206 | bdc->srr.dqp_index = 0; | ||
| 207 | /* allocate the status report descriptors */ | ||
| 208 | bdc->srr.sr_bds = dma_zalloc_coherent( | ||
| 209 | bdc->dev, | ||
| 210 | NUM_SR_ENTRIES * sizeof(struct bdc_bd), | ||
| 211 | &bdc->srr.dma_addr, | ||
| 212 | GFP_KERNEL); | ||
| 213 | if (!bdc->srr.sr_bds) | ||
| 214 | return -ENOMEM; | ||
| 215 | |||
| 216 | return 0; | ||
| 217 | } | ||
| 218 | |||
| 219 | /* Initialize the HW regs and internal data structures */ | ||
| 220 | static void bdc_mem_init(struct bdc *bdc, bool reinit) | ||
| 221 | { | ||
| 222 | u8 size = 0; | ||
| 223 | u32 usb2_pm; | ||
| 224 | u32 low32; | ||
| 225 | u32 upp32; | ||
| 226 | u32 temp; | ||
| 227 | |||
| 228 | dev_dbg(bdc->dev, "%s ()\n", __func__); | ||
| 229 | bdc->ep0_state = WAIT_FOR_SETUP; | ||
| 230 | bdc->dev_addr = 0; | ||
| 231 | bdc->srr.eqp_index = 0; | ||
| 232 | bdc->srr.dqp_index = 0; | ||
| 233 | bdc->zlp_needed = false; | ||
| 234 | bdc->delayed_status = false; | ||
| 235 | |||
| 236 | bdc_writel(bdc->regs, BDC_SPBBAL, bdc->scratchpad.sp_dma); | ||
| 237 | /* Init the SRR */ | ||
| 238 | temp = BDC_SRR_RWS | BDC_SRR_RST; | ||
| 239 | /* Reset the SRR */ | ||
| 240 | bdc_writel(bdc->regs, BDC_SRRINT(0), temp); | ||
| 241 | dev_dbg(bdc->dev, "bdc->srr.sr_bds =%p\n", bdc->srr.sr_bds); | ||
| 242 | temp = lower_32_bits(bdc->srr.dma_addr); | ||
| 243 | size = fls(NUM_SR_ENTRIES) - 2; | ||
| 244 | temp |= size; | ||
| 245 | dev_dbg(bdc->dev, "SRRBAL[0]=%08x NUM_SR_ENTRIES:%d size:%d\n", | ||
| 246 | temp, NUM_SR_ENTRIES, size); | ||
| 247 | |||
| 248 | low32 = lower_32_bits(temp); | ||
| 249 | upp32 = upper_32_bits(bdc->srr.dma_addr); | ||
| 250 | cpu_to_le32s(&low32); | ||
| 251 | cpu_to_le32s(&upp32); | ||
| 252 | |||
| 253 | /* Write the dma addresses into regs*/ | ||
| 254 | bdc_writel(bdc->regs, BDC_SRRBAL(0), low32); | ||
| 255 | bdc_writel(bdc->regs, BDC_SRRBAH(0), upp32); | ||
| 256 | |||
| 257 | temp = bdc_readl(bdc->regs, BDC_SRRINT(0)); | ||
| 258 | temp |= BDC_SRR_IE; | ||
| 259 | temp &= ~(BDC_SRR_RST | BDC_SRR_RWS); | ||
| 260 | bdc_writel(bdc->regs, BDC_SRRINT(0), temp); | ||
| 261 | |||
| 262 | /* Set the Interrupt Coalescence ~500 usec */ | ||
| 263 | temp = bdc_readl(bdc->regs, BDC_INTCTLS(0)); | ||
| 264 | temp &= ~0xffff; | ||
| 265 | temp |= INT_CLS; | ||
| 266 | bdc_writel(bdc->regs, BDC_INTCTLS(0), temp); | ||
| 267 | |||
| 268 | usb2_pm = bdc_readl(bdc->regs, BDC_USPPM2); | ||
| 269 | dev_dbg(bdc->dev, "usb2_pm=%08x", usb2_pm); | ||
| 270 | /* Enable hardware LPM Enable */ | ||
| 271 | usb2_pm |= BDC_HLE; | ||
| 272 | bdc_writel(bdc->regs, BDC_USPPM2, usb2_pm); | ||
| 273 | |||
| 274 | /* readback for debug */ | ||
| 275 | usb2_pm = bdc_readl(bdc->regs, BDC_USPPM2); | ||
| 276 | dev_dbg(bdc->dev, "usb2_pm=%08x\n", usb2_pm); | ||
| 277 | |||
| 278 | /* Disable any unwanted SR's on SRR */ | ||
| 279 | temp = bdc_readl(bdc->regs, BDC_BDCSC); | ||
| 280 | /* We don't want Microframe counter wrap SR */ | ||
| 281 | temp |= BDC_MASK_MCW; | ||
| 282 | bdc_writel(bdc->regs, BDC_BDCSC, temp); | ||
| 283 | |||
| 284 | /* | ||
| 285 | * In some error cases, driver has to reset the entire BDC controller | ||
| 286 | * in that case reinit is passed as 1 | ||
| 287 | */ | ||
| 288 | if (reinit) { | ||
| 289 | /* Enable interrupts */ | ||
| 290 | temp = bdc_readl(bdc->regs, BDC_BDCSC); | ||
| 291 | temp |= BDC_GIE; | ||
| 292 | bdc_writel(bdc->regs, BDC_BDCSC, temp); | ||
| 293 | /* Init scratchpad to 0 */ | ||
| 294 | memset(bdc->scratchpad.buff, 0, bdc->sp_buff_size); | ||
| 295 | /* Initialize SRR to 0 */ | ||
| 296 | memset(bdc->srr.sr_bds, 0, | ||
| 297 | NUM_SR_ENTRIES * sizeof(struct bdc_bd)); | ||
| 298 | } else { | ||
| 299 | /* One time initiaization only */ | ||
| 300 | /* Enable status report function pointers */ | ||
| 301 | bdc->sr_handler[0] = bdc_sr_xsf; | ||
| 302 | bdc->sr_handler[1] = bdc_sr_uspc; | ||
| 303 | |||
| 304 | /* EP0 status report function pointers */ | ||
| 305 | bdc->sr_xsf_ep0[0] = bdc_xsf_ep0_setup_recv; | ||
| 306 | bdc->sr_xsf_ep0[1] = bdc_xsf_ep0_data_start; | ||
| 307 | bdc->sr_xsf_ep0[2] = bdc_xsf_ep0_status_start; | ||
| 308 | } | ||
| 309 | } | ||
| 310 | |||
| 311 | /* Free the dynamic memory */ | ||
| 312 | static void bdc_mem_free(struct bdc *bdc) | ||
| 313 | { | ||
| 314 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 315 | /* Free SRR */ | ||
| 316 | if (bdc->srr.sr_bds) | ||
| 317 | dma_free_coherent(bdc->dev, | ||
| 318 | NUM_SR_ENTRIES * sizeof(struct bdc_bd), | ||
| 319 | bdc->srr.sr_bds, bdc->srr.dma_addr); | ||
| 320 | |||
| 321 | /* Free scratchpad */ | ||
| 322 | if (bdc->scratchpad.buff) | ||
| 323 | dma_free_coherent(bdc->dev, bdc->sp_buff_size, | ||
| 324 | bdc->scratchpad.buff, bdc->scratchpad.sp_dma); | ||
| 325 | |||
| 326 | /* Destroy the dma pools */ | ||
| 327 | if (bdc->bd_table_pool) | ||
| 328 | dma_pool_destroy(bdc->bd_table_pool); | ||
| 329 | |||
| 330 | /* Free the bdc_ep array */ | ||
| 331 | kfree(bdc->bdc_ep_array); | ||
| 332 | |||
| 333 | bdc->srr.sr_bds = NULL; | ||
| 334 | bdc->scratchpad.buff = NULL; | ||
| 335 | bdc->bd_table_pool = NULL; | ||
| 336 | bdc->bdc_ep_array = NULL; | ||
| 337 | } | ||
| 338 | |||
| 339 | /* | ||
| 340 | * bdc reinit gives a controller reset and reinitialize the registers, | ||
| 341 | * called from disconnect/bus reset scenario's, to ensure proper HW cleanup | ||
| 342 | */ | ||
| 343 | int bdc_reinit(struct bdc *bdc) | ||
| 344 | { | ||
| 345 | int ret; | ||
| 346 | |||
| 347 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 348 | ret = bdc_stop(bdc); | ||
| 349 | if (ret) | ||
| 350 | goto out; | ||
| 351 | |||
| 352 | ret = bdc_reset(bdc); | ||
| 353 | if (ret) | ||
| 354 | goto out; | ||
| 355 | |||
| 356 | /* the reinit flag is 1 */ | ||
| 357 | bdc_mem_init(bdc, true); | ||
| 358 | ret = bdc_run(bdc); | ||
| 359 | out: | ||
| 360 | bdc->reinit = false; | ||
| 361 | |||
| 362 | return ret; | ||
| 363 | } | ||
| 364 | |||
| 365 | /* Allocate all the dyanmic memory */ | ||
| 366 | static int bdc_mem_alloc(struct bdc *bdc) | ||
| 367 | { | ||
| 368 | u32 page_size; | ||
| 369 | unsigned int num_ieps, num_oeps; | ||
| 370 | |||
| 371 | dev_dbg(bdc->dev, | ||
| 372 | "%s() NUM_BDS_PER_TABLE:%d\n", __func__, | ||
| 373 | NUM_BDS_PER_TABLE); | ||
| 374 | page_size = BDC_PGS(bdc_readl(bdc->regs, BDC_BDCCFG0)); | ||
| 375 | /* page size is 2^pgs KB */ | ||
| 376 | page_size = 1 << page_size; | ||
| 377 | /* KB */ | ||
| 378 | page_size <<= 10; | ||
| 379 | dev_dbg(bdc->dev, "page_size=%d\n", page_size); | ||
| 380 | |||
| 381 | /* Create a pool of bd tables */ | ||
| 382 | bdc->bd_table_pool = | ||
| 383 | dma_pool_create("BDC BD tables", bdc->dev, NUM_BDS_PER_TABLE * 16, | ||
| 384 | 16, page_size); | ||
| 385 | |||
| 386 | if (!bdc->bd_table_pool) | ||
| 387 | goto fail; | ||
| 388 | |||
| 389 | if (scratchpad_setup(bdc)) | ||
| 390 | goto fail; | ||
| 391 | |||
| 392 | /* read from regs */ | ||
| 393 | num_ieps = NUM_NCS(bdc_readl(bdc->regs, BDC_FSCNIC)); | ||
| 394 | num_oeps = NUM_NCS(bdc_readl(bdc->regs, BDC_FSCNOC)); | ||
| 395 | /* +2: 1 for ep0 and the other is rsvd i.e. bdc_ep[0] is rsvd */ | ||
| 396 | bdc->num_eps = num_ieps + num_oeps + 2; | ||
| 397 | dev_dbg(bdc->dev, | ||
| 398 | "ieps:%d eops:%d num_eps:%d\n", | ||
| 399 | num_ieps, num_oeps, bdc->num_eps); | ||
| 400 | /* allocate array of ep pointers */ | ||
| 401 | bdc->bdc_ep_array = kcalloc(bdc->num_eps, sizeof(struct bdc_ep *), | ||
| 402 | GFP_KERNEL); | ||
| 403 | if (!bdc->bdc_ep_array) | ||
| 404 | goto fail; | ||
| 405 | |||
| 406 | dev_dbg(bdc->dev, "Allocating sr report0\n"); | ||
| 407 | if (setup_srr(bdc, 0)) | ||
| 408 | goto fail; | ||
| 409 | |||
| 410 | return 0; | ||
| 411 | fail: | ||
| 412 | dev_warn(bdc->dev, "Couldn't initialize memory\n"); | ||
| 413 | bdc_mem_free(bdc); | ||
| 414 | |||
| 415 | return -ENOMEM; | ||
| 416 | } | ||
| 417 | |||
| 418 | /* opposite to bdc_hw_init */ | ||
| 419 | static void bdc_hw_exit(struct bdc *bdc) | ||
| 420 | { | ||
| 421 | dev_dbg(bdc->dev, "%s ()\n", __func__); | ||
| 422 | bdc_mem_free(bdc); | ||
| 423 | } | ||
| 424 | |||
| 425 | /* Initialize the bdc HW and memory */ | ||
| 426 | static int bdc_hw_init(struct bdc *bdc) | ||
| 427 | { | ||
| 428 | int ret; | ||
| 429 | |||
| 430 | dev_dbg(bdc->dev, "%s ()\n", __func__); | ||
| 431 | ret = bdc_reset(bdc); | ||
| 432 | if (ret) { | ||
| 433 | dev_err(bdc->dev, "err resetting bdc abort bdc init%d\n", ret); | ||
| 434 | return ret; | ||
| 435 | } | ||
| 436 | ret = bdc_mem_alloc(bdc); | ||
| 437 | if (ret) { | ||
| 438 | dev_err(bdc->dev, "Mem alloc failed, aborting\n"); | ||
| 439 | return -ENOMEM; | ||
| 440 | } | ||
| 441 | bdc_mem_init(bdc, 0); | ||
| 442 | bdc_dbg_regs(bdc); | ||
| 443 | dev_dbg(bdc->dev, "HW Init done\n"); | ||
| 444 | |||
| 445 | return 0; | ||
| 446 | } | ||
| 447 | |||
| 448 | static int bdc_probe(struct platform_device *pdev) | ||
| 449 | { | ||
| 450 | struct bdc *bdc; | ||
| 451 | struct resource *res; | ||
| 452 | int ret = -ENOMEM; | ||
| 453 | int irq; | ||
| 454 | u32 temp; | ||
| 455 | struct device *dev = &pdev->dev; | ||
| 456 | |||
| 457 | dev_dbg(dev, "%s()\n", __func__); | ||
| 458 | bdc = devm_kzalloc(dev, sizeof(*bdc), GFP_KERNEL); | ||
| 459 | if (!bdc) | ||
| 460 | return -ENOMEM; | ||
| 461 | |||
| 462 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 463 | bdc->regs = devm_ioremap_resource(dev, res); | ||
| 464 | if (IS_ERR(bdc->regs)) { | ||
| 465 | dev_err(dev, "ioremap error\n"); | ||
| 466 | return -ENOMEM; | ||
| 467 | } | ||
| 468 | irq = platform_get_irq(pdev, 0); | ||
| 469 | if (irq < 0) { | ||
| 470 | dev_err(dev, "platform_get_irq failed:%d\n", irq); | ||
| 471 | return irq; | ||
| 472 | } | ||
| 473 | spin_lock_init(&bdc->lock); | ||
| 474 | platform_set_drvdata(pdev, bdc); | ||
| 475 | bdc->irq = irq; | ||
| 476 | bdc->dev = dev; | ||
| 477 | dev_dbg(bdc->dev, "bdc->regs: %p irq=%d\n", bdc->regs, bdc->irq); | ||
| 478 | |||
| 479 | temp = bdc_readl(bdc->regs, BDC_BDCSC); | ||
| 480 | if ((temp & BDC_P64) && | ||
| 481 | !dma_set_mask_and_coherent(dev, DMA_BIT_MASK(64))) { | ||
| 482 | dev_dbg(bdc->dev, "Using 64-bit address\n"); | ||
| 483 | } else { | ||
| 484 | ret = dma_set_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(32)); | ||
| 485 | if (ret) { | ||
| 486 | dev_err(bdc->dev, "No suitable DMA config available, abort\n"); | ||
| 487 | return -ENOTSUPP; | ||
| 488 | } | ||
| 489 | dev_dbg(bdc->dev, "Using 32-bit address\n"); | ||
| 490 | } | ||
| 491 | ret = bdc_hw_init(bdc); | ||
| 492 | if (ret) { | ||
| 493 | dev_err(bdc->dev, "BDC init failure:%d\n", ret); | ||
| 494 | return ret; | ||
| 495 | } | ||
| 496 | ret = bdc_udc_init(bdc); | ||
| 497 | if (ret) { | ||
| 498 | dev_err(bdc->dev, "BDC Gadget init failure:%d\n", ret); | ||
| 499 | goto cleanup; | ||
| 500 | } | ||
| 501 | return 0; | ||
| 502 | |||
| 503 | cleanup: | ||
| 504 | bdc_hw_exit(bdc); | ||
| 505 | |||
| 506 | return ret; | ||
| 507 | } | ||
| 508 | |||
| 509 | static int bdc_remove(struct platform_device *pdev) | ||
| 510 | { | ||
| 511 | struct bdc *bdc; | ||
| 512 | |||
| 513 | bdc = platform_get_drvdata(pdev); | ||
| 514 | dev_dbg(bdc->dev, "%s ()\n", __func__); | ||
| 515 | bdc_udc_exit(bdc); | ||
| 516 | bdc_hw_exit(bdc); | ||
| 517 | |||
| 518 | return 0; | ||
| 519 | } | ||
| 520 | |||
| 521 | static struct platform_driver bdc_driver = { | ||
| 522 | .driver = { | ||
| 523 | .name = BRCM_BDC_NAME, | ||
| 524 | .owner = THIS_MODULE | ||
| 525 | }, | ||
| 526 | .probe = bdc_probe, | ||
| 527 | .remove = bdc_remove, | ||
| 528 | }; | ||
| 529 | |||
| 530 | module_platform_driver(bdc_driver); | ||
| 531 | MODULE_AUTHOR("Ashwini Pahuja <ashwini.linux@gmail.com>"); | ||
| 532 | MODULE_LICENSE("GPL"); | ||
| 533 | MODULE_DESCRIPTION(BRCM_BDC_DESC); | ||
diff --git a/drivers/usb/gadget/udc/bdc/bdc_dbg.c b/drivers/usb/gadget/udc/bdc/bdc_dbg.c new file mode 100644 index 000000000000..5945dbc47825 --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/bdc_dbg.c | |||
| @@ -0,0 +1,123 @@ | |||
| 1 | /* | ||
| 2 | * bdc_dbg.c - BRCM BDC USB3.0 device controller debug functions | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Broadcom Corporation | ||
| 5 | * | ||
| 6 | * Author: Ashwini Pahuja | ||
| 7 | * | ||
| 8 | * This program is free software; you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | * | ||
| 13 | */ | ||
| 14 | |||
| 15 | #include "bdc.h" | ||
| 16 | #include "bdc_dbg.h" | ||
| 17 | |||
| 18 | void bdc_dbg_regs(struct bdc *bdc) | ||
| 19 | { | ||
| 20 | u32 temp; | ||
| 21 | |||
| 22 | dev_vdbg(bdc->dev, "bdc->regs:%p\n", bdc->regs); | ||
| 23 | temp = bdc_readl(bdc->regs, BDC_BDCCFG0); | ||
| 24 | dev_vdbg(bdc->dev, "bdccfg0:0x%08x\n", temp); | ||
| 25 | temp = bdc_readl(bdc->regs, BDC_BDCCFG1); | ||
| 26 | dev_vdbg(bdc->dev, "bdccfg1:0x%08x\n", temp); | ||
| 27 | temp = bdc_readl(bdc->regs, BDC_BDCCAP0); | ||
| 28 | dev_vdbg(bdc->dev, "bdccap0:0x%08x\n", temp); | ||
| 29 | temp = bdc_readl(bdc->regs, BDC_BDCCAP1); | ||
| 30 | dev_vdbg(bdc->dev, "bdccap1:0x%08x\n", temp); | ||
| 31 | temp = bdc_readl(bdc->regs, BDC_USPC); | ||
| 32 | dev_vdbg(bdc->dev, "uspc:0x%08x\n", temp); | ||
| 33 | temp = bdc_readl(bdc->regs, BDC_DVCSA); | ||
| 34 | dev_vdbg(bdc->dev, "dvcsa:0x%08x\n", temp); | ||
| 35 | temp = bdc_readl(bdc->regs, BDC_DVCSB); | ||
| 36 | dev_vdbg(bdc->dev, "dvcsb:0x%x08\n", temp); | ||
| 37 | } | ||
| 38 | |||
| 39 | void bdc_dump_epsts(struct bdc *bdc) | ||
| 40 | { | ||
| 41 | u32 temp; | ||
| 42 | |||
| 43 | temp = bdc_readl(bdc->regs, BDC_EPSTS0(0)); | ||
| 44 | dev_vdbg(bdc->dev, "BDC_EPSTS0:0x%08x\n", temp); | ||
| 45 | |||
| 46 | temp = bdc_readl(bdc->regs, BDC_EPSTS1(0)); | ||
| 47 | dev_vdbg(bdc->dev, "BDC_EPSTS1:0x%x\n", temp); | ||
| 48 | |||
| 49 | temp = bdc_readl(bdc->regs, BDC_EPSTS2(0)); | ||
| 50 | dev_vdbg(bdc->dev, "BDC_EPSTS2:0x%08x\n", temp); | ||
| 51 | |||
| 52 | temp = bdc_readl(bdc->regs, BDC_EPSTS3(0)); | ||
| 53 | dev_vdbg(bdc->dev, "BDC_EPSTS3:0x%08x\n", temp); | ||
| 54 | |||
| 55 | temp = bdc_readl(bdc->regs, BDC_EPSTS4(0)); | ||
| 56 | dev_vdbg(bdc->dev, "BDC_EPSTS4:0x%08x\n", temp); | ||
| 57 | |||
| 58 | temp = bdc_readl(bdc->regs, BDC_EPSTS5(0)); | ||
| 59 | dev_vdbg(bdc->dev, "BDC_EPSTS5:0x%08x\n", temp); | ||
| 60 | |||
| 61 | temp = bdc_readl(bdc->regs, BDC_EPSTS6(0)); | ||
| 62 | dev_vdbg(bdc->dev, "BDC_EPSTS6:0x%08x\n", temp); | ||
| 63 | |||
| 64 | temp = bdc_readl(bdc->regs, BDC_EPSTS7(0)); | ||
| 65 | dev_vdbg(bdc->dev, "BDC_EPSTS7:0x%08x\n", temp); | ||
| 66 | } | ||
| 67 | |||
| 68 | void bdc_dbg_srr(struct bdc *bdc, u32 srr_num) | ||
| 69 | { | ||
| 70 | struct bdc_sr *sr; | ||
| 71 | dma_addr_t addr; | ||
| 72 | int i; | ||
| 73 | |||
| 74 | sr = bdc->srr.sr_bds; | ||
| 75 | addr = bdc->srr.dma_addr; | ||
| 76 | dev_vdbg(bdc->dev, "bdc_dbg_srr sr:%p dqp_index:%d\n", | ||
| 77 | sr, bdc->srr.dqp_index); | ||
| 78 | for (i = 0; i < NUM_SR_ENTRIES; i++) { | ||
| 79 | sr = &bdc->srr.sr_bds[i]; | ||
| 80 | dev_vdbg(bdc->dev, "%llx %08x %08x %08x %08x\n", | ||
| 81 | (unsigned long long)addr, | ||
| 82 | le32_to_cpu(sr->offset[0]), | ||
| 83 | le32_to_cpu(sr->offset[1]), | ||
| 84 | le32_to_cpu(sr->offset[2]), | ||
| 85 | le32_to_cpu(sr->offset[3])); | ||
| 86 | addr += sizeof(*sr); | ||
| 87 | } | ||
| 88 | } | ||
| 89 | |||
| 90 | void bdc_dbg_bd_list(struct bdc *bdc, struct bdc_ep *ep) | ||
| 91 | { | ||
| 92 | struct bd_list *bd_list = &ep->bd_list; | ||
| 93 | struct bd_table *bd_table; | ||
| 94 | struct bdc_bd *bd; | ||
| 95 | int tbi, bdi, gbdi; | ||
| 96 | dma_addr_t dma; | ||
| 97 | |||
| 98 | gbdi = 0; | ||
| 99 | dev_vdbg(bdc->dev, | ||
| 100 | "Dump bd list for %s epnum:%d\n", | ||
| 101 | ep->name, ep->ep_num); | ||
| 102 | |||
| 103 | dev_vdbg(bdc->dev, | ||
| 104 | "tabs:%d max_bdi:%d eqp_bdi:%d hwd_bdi:%d num_bds_table:%d\n", | ||
| 105 | bd_list->num_tabs, bd_list->max_bdi, bd_list->eqp_bdi, | ||
| 106 | bd_list->hwd_bdi, bd_list->num_bds_table); | ||
| 107 | |||
| 108 | for (tbi = 0; tbi < bd_list->num_tabs; tbi++) { | ||
| 109 | bd_table = bd_list->bd_table_array[tbi]; | ||
| 110 | for (bdi = 0; bdi < bd_list->num_bds_table; bdi++) { | ||
| 111 | bd = bd_table->start_bd + bdi; | ||
| 112 | dma = bd_table->dma + (sizeof(struct bdc_bd) * bdi); | ||
| 113 | dev_vdbg(bdc->dev, | ||
| 114 | "tbi:%2d bdi:%2d gbdi:%2d virt:%p phys:%llx %08x %08x %08x %08x\n", | ||
| 115 | tbi, bdi, gbdi++, bd, (unsigned long long)dma, | ||
| 116 | le32_to_cpu(bd->offset[0]), | ||
| 117 | le32_to_cpu(bd->offset[1]), | ||
| 118 | le32_to_cpu(bd->offset[2]), | ||
| 119 | le32_to_cpu(bd->offset[3])); | ||
| 120 | } | ||
| 121 | dev_vdbg(bdc->dev, "\n\n"); | ||
| 122 | } | ||
| 123 | } | ||
diff --git a/drivers/usb/gadget/udc/bdc/bdc_dbg.h b/drivers/usb/gadget/udc/bdc/bdc_dbg.h new file mode 100644 index 000000000000..338a6c701315 --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/bdc_dbg.h | |||
| @@ -0,0 +1,37 @@ | |||
| 1 | /* | ||
| 2 | * bdc_dbg.h - header for the BDC debug functions | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Broadcom Corporation | ||
| 5 | * | ||
| 6 | * Author: Ashwini Pahuja | ||
| 7 | * | ||
| 8 | * This program is free software; you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | * | ||
| 13 | */ | ||
| 14 | #ifndef __LINUX_BDC_DBG_H__ | ||
| 15 | #define __LINUX_BDC_DBG_H__ | ||
| 16 | |||
| 17 | #include "bdc.h" | ||
| 18 | |||
| 19 | #ifdef CONFIG_USB_GADGET_VERBOSE | ||
| 20 | void bdc_dbg_bd_list(struct bdc *, struct bdc_ep*); | ||
| 21 | void bdc_dbg_srr(struct bdc *, u32); | ||
| 22 | void bdc_dbg_regs(struct bdc *); | ||
| 23 | void bdc_dump_epsts(struct bdc *); | ||
| 24 | #else | ||
| 25 | static inline void bdc_dbg_regs(struct bdc *bdc) | ||
| 26 | { } | ||
| 27 | |||
| 28 | static inline void bdc_dbg_srr(struct bdc *bdc, u32 srr_num) | ||
| 29 | { } | ||
| 30 | |||
| 31 | static inline void bdc_dbg_bd_list(struct bdc *bdc, struct bdc_ep *ep) | ||
| 32 | { } | ||
| 33 | |||
| 34 | static inline void bdc_dump_epsts(struct bdc *bdc) | ||
| 35 | { } | ||
| 36 | #endif /* CONFIG_USB_GADGET_VERBOSE */ | ||
| 37 | #endif /* __LINUX_BDC_DBG_H__ */ | ||
diff --git a/drivers/usb/gadget/udc/bdc/bdc_ep.c b/drivers/usb/gadget/udc/bdc/bdc_ep.c new file mode 100644 index 000000000000..ff67ceac77c4 --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/bdc_ep.c | |||
| @@ -0,0 +1,2024 @@ | |||
| 1 | /* | ||
| 2 | * bdc_ep.c - BRCM BDC USB3.0 device controller endpoint related functions | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Broadcom Corporation | ||
| 5 | * | ||
| 6 | * Author: Ashwini Pahuja | ||
| 7 | * | ||
| 8 | * Based on drivers under drivers/usb/ | ||
| 9 | * | ||
| 10 | * This program is free software; you can redistribute it and/or modify it | ||
| 11 | * under the terms of the GNU General Public License as published by the | ||
| 12 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 13 | * option) any later version. | ||
| 14 | * | ||
| 15 | */ | ||
| 16 | #include <linux/module.h> | ||
| 17 | #include <linux/pci.h> | ||
| 18 | #include <linux/dma-mapping.h> | ||
| 19 | #include <linux/kernel.h> | ||
| 20 | #include <linux/delay.h> | ||
| 21 | #include <linux/dmapool.h> | ||
| 22 | #include <linux/ioport.h> | ||
| 23 | #include <linux/sched.h> | ||
| 24 | #include <linux/slab.h> | ||
| 25 | #include <linux/errno.h> | ||
| 26 | #include <linux/init.h> | ||
| 27 | #include <linux/timer.h> | ||
| 28 | #include <linux/list.h> | ||
| 29 | #include <linux/interrupt.h> | ||
| 30 | #include <linux/moduleparam.h> | ||
| 31 | #include <linux/device.h> | ||
| 32 | #include <linux/usb/ch9.h> | ||
| 33 | #include <linux/usb/gadget.h> | ||
| 34 | #include <linux/usb/otg.h> | ||
| 35 | #include <linux/pm.h> | ||
| 36 | #include <linux/io.h> | ||
| 37 | #include <linux/irq.h> | ||
| 38 | #include <asm/unaligned.h> | ||
| 39 | #include <linux/platform_device.h> | ||
| 40 | #include <linux/usb/composite.h> | ||
| 41 | |||
| 42 | #include "bdc.h" | ||
| 43 | #include "bdc_ep.h" | ||
| 44 | #include "bdc_cmd.h" | ||
| 45 | #include "bdc_dbg.h" | ||
| 46 | |||
| 47 | static const char * const ep0_state_string[] = { | ||
| 48 | "WAIT_FOR_SETUP", | ||
| 49 | "WAIT_FOR_DATA_START", | ||
| 50 | "WAIT_FOR_DATA_XMIT", | ||
| 51 | "WAIT_FOR_STATUS_START", | ||
| 52 | "WAIT_FOR_STATUS_XMIT", | ||
| 53 | "STATUS_PENDING" | ||
| 54 | }; | ||
| 55 | |||
| 56 | /* Free the bdl during ep disable */ | ||
| 57 | static void ep_bd_list_free(struct bdc_ep *ep, u32 num_tabs) | ||
| 58 | { | ||
| 59 | struct bd_list *bd_list = &ep->bd_list; | ||
| 60 | struct bdc *bdc = ep->bdc; | ||
| 61 | struct bd_table *bd_table; | ||
| 62 | int index; | ||
| 63 | |||
| 64 | dev_dbg(bdc->dev, "%s ep:%s num_tabs:%d\n", | ||
| 65 | __func__, ep->name, num_tabs); | ||
| 66 | |||
| 67 | if (!bd_list->bd_table_array) { | ||
| 68 | dev_dbg(bdc->dev, "%s already freed\n", ep->name); | ||
| 69 | return; | ||
| 70 | } | ||
| 71 | for (index = 0; index < num_tabs; index++) { | ||
| 72 | /* | ||
| 73 | * check if the bd_table struct is allocated ? | ||
| 74 | * if yes, then check if bd memory has been allocated, then | ||
| 75 | * free the dma_pool and also the bd_table struct memory | ||
| 76 | */ | ||
| 77 | bd_table = bd_list->bd_table_array[index]; | ||
| 78 | dev_dbg(bdc->dev, "bd_table:%p index:%d\n", bd_table, index); | ||
| 79 | if (!bd_table) { | ||
| 80 | dev_dbg(bdc->dev, "bd_table not allocated\n"); | ||
| 81 | continue; | ||
| 82 | } | ||
| 83 | if (!bd_table->start_bd) { | ||
| 84 | dev_dbg(bdc->dev, "bd dma pool not allocted\n"); | ||
| 85 | continue; | ||
| 86 | } | ||
| 87 | |||
| 88 | dev_dbg(bdc->dev, | ||
| 89 | "Free dma pool start_bd:%p dma:%llx\n", | ||
| 90 | bd_table->start_bd, | ||
| 91 | (unsigned long long)bd_table->dma); | ||
| 92 | |||
| 93 | dma_pool_free(bdc->bd_table_pool, | ||
| 94 | bd_table->start_bd, | ||
| 95 | bd_table->dma); | ||
| 96 | /* Free the bd_table structure */ | ||
| 97 | kfree(bd_table); | ||
| 98 | } | ||
| 99 | /* Free the bd table array */ | ||
| 100 | kfree(ep->bd_list.bd_table_array); | ||
| 101 | } | ||
| 102 | |||
| 103 | /* | ||
| 104 | * chain the tables, by insteting a chain bd at the end of prev_table, pointing | ||
| 105 | * to next_table | ||
| 106 | */ | ||
| 107 | static inline void chain_table(struct bd_table *prev_table, | ||
| 108 | struct bd_table *next_table, | ||
| 109 | u32 bd_p_tab) | ||
| 110 | { | ||
| 111 | /* Chain the prev table to next table */ | ||
| 112 | prev_table->start_bd[bd_p_tab-1].offset[0] = | ||
| 113 | cpu_to_le32(lower_32_bits(next_table->dma)); | ||
| 114 | |||
| 115 | prev_table->start_bd[bd_p_tab-1].offset[1] = | ||
| 116 | cpu_to_le32(upper_32_bits(next_table->dma)); | ||
| 117 | |||
| 118 | prev_table->start_bd[bd_p_tab-1].offset[2] = | ||
| 119 | 0x0; | ||
| 120 | |||
| 121 | prev_table->start_bd[bd_p_tab-1].offset[3] = | ||
| 122 | cpu_to_le32(MARK_CHAIN_BD); | ||
| 123 | } | ||
| 124 | |||
| 125 | /* Allocate the bdl for ep, during config ep */ | ||
| 126 | static int ep_bd_list_alloc(struct bdc_ep *ep) | ||
| 127 | { | ||
| 128 | struct bd_table *prev_table = NULL; | ||
| 129 | int index, num_tabs, bd_p_tab; | ||
| 130 | struct bdc *bdc = ep->bdc; | ||
| 131 | struct bd_table *bd_table; | ||
| 132 | dma_addr_t dma; | ||
| 133 | |||
| 134 | if (usb_endpoint_xfer_isoc(ep->desc)) | ||
| 135 | num_tabs = NUM_TABLES_ISOCH; | ||
| 136 | else | ||
| 137 | num_tabs = NUM_TABLES; | ||
| 138 | |||
| 139 | bd_p_tab = NUM_BDS_PER_TABLE; | ||
| 140 | /* if there is only 1 table in bd list then loop chain to self */ | ||
| 141 | dev_dbg(bdc->dev, | ||
| 142 | "%s ep:%p num_tabs:%d\n", | ||
| 143 | __func__, ep, num_tabs); | ||
| 144 | |||
| 145 | /* Allocate memory for table array */ | ||
| 146 | ep->bd_list.bd_table_array = kzalloc( | ||
| 147 | num_tabs * sizeof(struct bd_table *), | ||
| 148 | GFP_ATOMIC); | ||
| 149 | if (!ep->bd_list.bd_table_array) | ||
| 150 | return -ENOMEM; | ||
| 151 | |||
| 152 | /* Allocate memory for each table */ | ||
| 153 | for (index = 0; index < num_tabs; index++) { | ||
| 154 | /* Allocate memory for bd_table structure */ | ||
| 155 | bd_table = kzalloc(sizeof(struct bd_table), GFP_ATOMIC); | ||
| 156 | if (!bd_table) | ||
| 157 | goto fail; | ||
| 158 | |||
| 159 | bd_table->start_bd = dma_pool_alloc(bdc->bd_table_pool, | ||
| 160 | GFP_ATOMIC, | ||
| 161 | &dma); | ||
| 162 | if (!bd_table->start_bd) | ||
| 163 | goto fail; | ||
| 164 | |||
| 165 | bd_table->dma = dma; | ||
| 166 | |||
| 167 | dev_dbg(bdc->dev, | ||
| 168 | "index:%d start_bd:%p dma=%08llx prev_table:%p\n", | ||
| 169 | index, bd_table->start_bd, | ||
| 170 | (unsigned long long)bd_table->dma, prev_table); | ||
| 171 | |||
| 172 | ep->bd_list.bd_table_array[index] = bd_table; | ||
| 173 | memset(bd_table->start_bd, 0, bd_p_tab * sizeof(struct bdc_bd)); | ||
| 174 | if (prev_table) | ||
| 175 | chain_table(prev_table, bd_table, bd_p_tab); | ||
| 176 | |||
| 177 | prev_table = bd_table; | ||
| 178 | } | ||
| 179 | chain_table(prev_table, ep->bd_list.bd_table_array[0], bd_p_tab); | ||
| 180 | /* Memory allocation is successful, now init the internal fields */ | ||
| 181 | ep->bd_list.num_tabs = num_tabs; | ||
| 182 | ep->bd_list.max_bdi = (num_tabs * bd_p_tab) - 1; | ||
| 183 | ep->bd_list.num_tabs = num_tabs; | ||
| 184 | ep->bd_list.num_bds_table = bd_p_tab; | ||
| 185 | ep->bd_list.eqp_bdi = 0; | ||
| 186 | ep->bd_list.hwd_bdi = 0; | ||
| 187 | |||
| 188 | return 0; | ||
| 189 | fail: | ||
| 190 | /* Free the bd_table_array, bd_table struct, bd's */ | ||
| 191 | ep_bd_list_free(ep, num_tabs); | ||
| 192 | |||
| 193 | return -ENOMEM; | ||
| 194 | } | ||
| 195 | |||
| 196 | /* returns how many bd's are need for this transfer */ | ||
| 197 | static inline int bd_needed_req(struct bdc_req *req) | ||
| 198 | { | ||
| 199 | int bd_needed = 0; | ||
| 200 | int remaining; | ||
| 201 | |||
| 202 | /* 1 bd needed for 0 byte transfer */ | ||
| 203 | if (req->usb_req.length == 0) | ||
| 204 | return 1; | ||
| 205 | |||
| 206 | /* remaining bytes after tranfering all max BD size BD's */ | ||
| 207 | remaining = req->usb_req.length % BD_MAX_BUFF_SIZE; | ||
| 208 | if (remaining) | ||
| 209 | bd_needed++; | ||
| 210 | |||
| 211 | /* How many maximum BUFF size BD's ? */ | ||
| 212 | remaining = req->usb_req.length / BD_MAX_BUFF_SIZE; | ||
| 213 | bd_needed += remaining; | ||
| 214 | |||
| 215 | return bd_needed; | ||
| 216 | } | ||
| 217 | |||
| 218 | /* returns the bd index(bdi) corresponding to bd dma address */ | ||
| 219 | static int bd_add_to_bdi(struct bdc_ep *ep, dma_addr_t bd_dma_addr) | ||
| 220 | { | ||
| 221 | struct bd_list *bd_list = &ep->bd_list; | ||
| 222 | dma_addr_t dma_first_bd, dma_last_bd; | ||
| 223 | struct bdc *bdc = ep->bdc; | ||
| 224 | struct bd_table *bd_table; | ||
| 225 | bool found = false; | ||
| 226 | int tbi, bdi; | ||
| 227 | |||
| 228 | dma_first_bd = dma_last_bd = 0; | ||
| 229 | dev_dbg(bdc->dev, "%s %llx\n", | ||
| 230 | __func__, (unsigned long long)bd_dma_addr); | ||
| 231 | /* | ||
| 232 | * Find in which table this bd_dma_addr belongs?, go through the table | ||
| 233 | * array and compare addresses of first and last address of bd of each | ||
| 234 | * table | ||
| 235 | */ | ||
| 236 | for (tbi = 0; tbi < bd_list->num_tabs; tbi++) { | ||
| 237 | bd_table = bd_list->bd_table_array[tbi]; | ||
| 238 | dma_first_bd = bd_table->dma; | ||
| 239 | dma_last_bd = bd_table->dma + | ||
| 240 | (sizeof(struct bdc_bd) * | ||
| 241 | (bd_list->num_bds_table - 1)); | ||
| 242 | dev_dbg(bdc->dev, "dma_first_bd:%llx dma_last_bd:%llx\n", | ||
| 243 | (unsigned long long)dma_first_bd, | ||
| 244 | (unsigned long long)dma_last_bd); | ||
| 245 | if (bd_dma_addr >= dma_first_bd && bd_dma_addr <= dma_last_bd) { | ||
| 246 | found = true; | ||
| 247 | break; | ||
| 248 | } | ||
| 249 | } | ||
| 250 | if (unlikely(!found)) { | ||
| 251 | dev_err(bdc->dev, "%s FATAL err, bd not found\n", __func__); | ||
| 252 | return -EINVAL; | ||
| 253 | } | ||
| 254 | /* Now we know the table, find the bdi */ | ||
| 255 | bdi = (bd_dma_addr - dma_first_bd) / sizeof(struct bdc_bd); | ||
| 256 | |||
| 257 | /* return the global bdi, to compare with ep eqp_bdi */ | ||
| 258 | return (bdi + (tbi * bd_list->num_bds_table)); | ||
| 259 | } | ||
| 260 | |||
| 261 | /* returns the table index(tbi) of the given bdi */ | ||
| 262 | static int bdi_to_tbi(struct bdc_ep *ep, int bdi) | ||
| 263 | { | ||
| 264 | int tbi; | ||
| 265 | |||
| 266 | tbi = bdi / ep->bd_list.num_bds_table; | ||
| 267 | dev_vdbg(ep->bdc->dev, | ||
| 268 | "bdi:%d num_bds_table:%d tbi:%d\n", | ||
| 269 | bdi, ep->bd_list.num_bds_table, tbi); | ||
| 270 | |||
| 271 | return tbi; | ||
| 272 | } | ||
| 273 | |||
| 274 | /* Find the bdi last bd in the transfer */ | ||
| 275 | static inline int find_end_bdi(struct bdc_ep *ep, int next_hwd_bdi) | ||
| 276 | { | ||
| 277 | int end_bdi; | ||
| 278 | |||
| 279 | end_bdi = next_hwd_bdi - 1; | ||
| 280 | if (end_bdi < 0) | ||
| 281 | end_bdi = ep->bd_list.max_bdi - 1; | ||
| 282 | else if ((end_bdi % (ep->bd_list.num_bds_table-1)) == 0) | ||
| 283 | end_bdi--; | ||
| 284 | |||
| 285 | return end_bdi; | ||
| 286 | } | ||
| 287 | |||
| 288 | /* | ||
| 289 | * How many transfer bd's are available on this ep bdl, chain bds are not | ||
| 290 | * counted in available bds | ||
| 291 | */ | ||
| 292 | static int bd_available_ep(struct bdc_ep *ep) | ||
| 293 | { | ||
| 294 | struct bd_list *bd_list = &ep->bd_list; | ||
| 295 | int available1, available2; | ||
| 296 | struct bdc *bdc = ep->bdc; | ||
| 297 | int chain_bd1, chain_bd2; | ||
| 298 | int available_bd = 0; | ||
| 299 | |||
| 300 | available1 = available2 = chain_bd1 = chain_bd2 = 0; | ||
| 301 | /* if empty then we have all bd's available - number of chain bd's */ | ||
| 302 | if (bd_list->eqp_bdi == bd_list->hwd_bdi) | ||
| 303 | return bd_list->max_bdi - bd_list->num_tabs; | ||
| 304 | |||
| 305 | /* | ||
| 306 | * Depending upon where eqp and dqp pointers are, caculate number | ||
| 307 | * of avaialble bd's | ||
| 308 | */ | ||
| 309 | if (bd_list->hwd_bdi < bd_list->eqp_bdi) { | ||
| 310 | /* available bd's are from eqp..max_bds + 0..dqp - chain_bds */ | ||
| 311 | available1 = bd_list->max_bdi - bd_list->eqp_bdi; | ||
| 312 | available2 = bd_list->hwd_bdi; | ||
| 313 | chain_bd1 = available1 / bd_list->num_bds_table; | ||
| 314 | chain_bd2 = available2 / bd_list->num_bds_table; | ||
| 315 | dev_vdbg(bdc->dev, "chain_bd1:%d chain_bd2:%d\n", | ||
| 316 | chain_bd1, chain_bd2); | ||
| 317 | available_bd = available1 + available2 - chain_bd1 - chain_bd2; | ||
| 318 | } else { | ||
| 319 | /* available bd's are from eqp..dqp - number of chain bd's */ | ||
| 320 | available1 = bd_list->hwd_bdi - bd_list->eqp_bdi; | ||
| 321 | /* if gap between eqp and dqp is less than NUM_BDS_PER_TABLE */ | ||
| 322 | if ((bd_list->hwd_bdi - bd_list->eqp_bdi) | ||
| 323 | <= bd_list->num_bds_table) { | ||
| 324 | /* If there any chain bd in between */ | ||
| 325 | if (!(bdi_to_tbi(ep, bd_list->hwd_bdi) | ||
| 326 | == bdi_to_tbi(ep, bd_list->eqp_bdi))) { | ||
| 327 | available_bd = available1 - 1; | ||
| 328 | } | ||
| 329 | } else { | ||
| 330 | chain_bd1 = available1 / bd_list->num_bds_table; | ||
| 331 | available_bd = available1 - chain_bd1; | ||
| 332 | } | ||
| 333 | } | ||
| 334 | /* | ||
| 335 | * we need to keep one extra bd to check if ring is full or empty so | ||
| 336 | * reduce by 1 | ||
| 337 | */ | ||
| 338 | available_bd--; | ||
| 339 | dev_vdbg(bdc->dev, "available_bd:%d\n", available_bd); | ||
| 340 | |||
| 341 | return available_bd; | ||
| 342 | } | ||
| 343 | |||
| 344 | /* Notify the hardware after queueing the bd to bdl */ | ||
| 345 | void bdc_notify_xfr(struct bdc *bdc, u32 epnum) | ||
| 346 | { | ||
| 347 | struct bdc_ep *ep = bdc->bdc_ep_array[epnum]; | ||
| 348 | |||
| 349 | dev_vdbg(bdc->dev, "%s epnum:%d\n", __func__, epnum); | ||
| 350 | /* | ||
| 351 | * We don't have anyway to check if ep state is running, | ||
| 352 | * except the software flags. | ||
| 353 | */ | ||
| 354 | if (unlikely(ep->flags & BDC_EP_STOP)) | ||
| 355 | ep->flags &= ~BDC_EP_STOP; | ||
| 356 | |||
| 357 | bdc_writel(bdc->regs, BDC_XSFNTF, epnum); | ||
| 358 | } | ||
| 359 | |||
| 360 | /* returns the bd corresponding to bdi */ | ||
| 361 | static struct bdc_bd *bdi_to_bd(struct bdc_ep *ep, int bdi) | ||
| 362 | { | ||
| 363 | int tbi = bdi_to_tbi(ep, bdi); | ||
| 364 | int local_bdi = 0; | ||
| 365 | |||
| 366 | local_bdi = bdi - (tbi * ep->bd_list.num_bds_table); | ||
| 367 | dev_vdbg(ep->bdc->dev, | ||
| 368 | "%s bdi:%d local_bdi:%d\n", | ||
| 369 | __func__, bdi, local_bdi); | ||
| 370 | |||
| 371 | return (ep->bd_list.bd_table_array[tbi]->start_bd + local_bdi); | ||
| 372 | } | ||
| 373 | |||
| 374 | /* Advance the enqueue pointer */ | ||
| 375 | static void ep_bdlist_eqp_adv(struct bdc_ep *ep) | ||
| 376 | { | ||
| 377 | ep->bd_list.eqp_bdi++; | ||
| 378 | /* if it's chain bd, then move to next */ | ||
| 379 | if (((ep->bd_list.eqp_bdi + 1) % ep->bd_list.num_bds_table) == 0) | ||
| 380 | ep->bd_list.eqp_bdi++; | ||
| 381 | |||
| 382 | /* if the eqp is pointing to last + 1 then move back to 0 */ | ||
| 383 | if (ep->bd_list.eqp_bdi == (ep->bd_list.max_bdi + 1)) | ||
| 384 | ep->bd_list.eqp_bdi = 0; | ||
| 385 | } | ||
| 386 | |||
| 387 | /* Setup the first bd for ep0 transfer */ | ||
| 388 | static int setup_first_bd_ep0(struct bdc *bdc, struct bdc_req *req, u32 *dword3) | ||
| 389 | { | ||
| 390 | u16 wValue; | ||
| 391 | u32 req_len; | ||
| 392 | |||
| 393 | req->ep->dir = 0; | ||
| 394 | req_len = req->usb_req.length; | ||
| 395 | switch (bdc->ep0_state) { | ||
| 396 | case WAIT_FOR_DATA_START: | ||
| 397 | *dword3 |= BD_TYPE_DS; | ||
| 398 | if (bdc->setup_pkt.bRequestType & USB_DIR_IN) | ||
| 399 | *dword3 |= BD_DIR_IN; | ||
| 400 | |||
| 401 | /* check if zlp will be needed */ | ||
| 402 | wValue = le16_to_cpu(bdc->setup_pkt.wValue); | ||
| 403 | if ((wValue > req_len) && | ||
| 404 | (req_len % bdc->gadget.ep0->maxpacket == 0)) { | ||
| 405 | dev_dbg(bdc->dev, "ZLP needed wVal:%d len:%d MaxP:%d\n", | ||
| 406 | wValue, req_len, | ||
| 407 | bdc->gadget.ep0->maxpacket); | ||
| 408 | bdc->zlp_needed = true; | ||
| 409 | } | ||
| 410 | break; | ||
| 411 | |||
| 412 | case WAIT_FOR_STATUS_START: | ||
| 413 | *dword3 |= BD_TYPE_SS; | ||
| 414 | if (!le16_to_cpu(bdc->setup_pkt.wLength) || | ||
| 415 | !(bdc->setup_pkt.bRequestType & USB_DIR_IN)) | ||
| 416 | *dword3 |= BD_DIR_IN; | ||
| 417 | break; | ||
| 418 | default: | ||
| 419 | dev_err(bdc->dev, | ||
| 420 | "Unknown ep0 state for queueing bd ep0_state:%s\n", | ||
| 421 | ep0_state_string[bdc->ep0_state]); | ||
| 422 | return -EINVAL; | ||
| 423 | } | ||
| 424 | |||
| 425 | return 0; | ||
| 426 | } | ||
| 427 | |||
| 428 | /* Setup the bd dma descriptor for a given request */ | ||
| 429 | static int setup_bd_list_xfr(struct bdc *bdc, struct bdc_req *req, int num_bds) | ||
| 430 | { | ||
| 431 | dma_addr_t buf_add = req->usb_req.dma; | ||
| 432 | u32 maxp, tfs, dword2, dword3; | ||
| 433 | struct bd_transfer *bd_xfr; | ||
| 434 | struct bd_list *bd_list; | ||
| 435 | struct bdc_ep *ep; | ||
| 436 | struct bdc_bd *bd; | ||
| 437 | int ret, bdnum; | ||
| 438 | u32 req_len; | ||
| 439 | |||
| 440 | ep = req->ep; | ||
| 441 | bd_list = &ep->bd_list; | ||
| 442 | bd_xfr = &req->bd_xfr; | ||
| 443 | bd_xfr->req = req; | ||
| 444 | bd_xfr->start_bdi = bd_list->eqp_bdi; | ||
| 445 | bd = bdi_to_bd(ep, bd_list->eqp_bdi); | ||
| 446 | req_len = req->usb_req.length; | ||
| 447 | maxp = usb_endpoint_maxp(ep->desc) & 0x7ff; | ||
| 448 | tfs = roundup(req->usb_req.length, maxp); | ||
| 449 | tfs = tfs/maxp; | ||
| 450 | dev_vdbg(bdc->dev, "%s ep:%s num_bds:%d tfs:%d r_len:%d bd:%p\n", | ||
| 451 | __func__, ep->name, num_bds, tfs, req_len, bd); | ||
| 452 | |||
| 453 | for (bdnum = 0; bdnum < num_bds; bdnum++) { | ||
| 454 | dword2 = dword3 = 0; | ||
| 455 | /* First bd */ | ||
| 456 | if (!bdnum) { | ||
| 457 | dword3 |= BD_SOT|BD_SBF|(tfs<<BD_TFS_SHIFT); | ||
| 458 | dword2 |= BD_LTF; | ||
| 459 | /* format of first bd for ep0 is different than other */ | ||
| 460 | if (ep->ep_num == 1) { | ||
| 461 | ret = setup_first_bd_ep0(bdc, req, &dword3); | ||
| 462 | if (ret) | ||
| 463 | return ret; | ||
| 464 | } | ||
| 465 | } | ||
| 466 | if (!req->ep->dir) | ||
| 467 | dword3 |= BD_ISP; | ||
| 468 | |||
| 469 | if (req_len > BD_MAX_BUFF_SIZE) { | ||
| 470 | dword2 |= BD_MAX_BUFF_SIZE; | ||
| 471 | req_len -= BD_MAX_BUFF_SIZE; | ||
| 472 | } else { | ||
| 473 | /* this should be the last bd */ | ||
| 474 | dword2 |= req_len; | ||
| 475 | dword3 |= BD_IOC; | ||
| 476 | dword3 |= BD_EOT; | ||
| 477 | } | ||
| 478 | /* Currently only 1 INT target is supported */ | ||
| 479 | dword2 |= BD_INTR_TARGET(0); | ||
| 480 | bd = bdi_to_bd(ep, ep->bd_list.eqp_bdi); | ||
| 481 | if (unlikely(!bd)) { | ||
| 482 | dev_err(bdc->dev, "Err bd pointing to wrong addr\n"); | ||
| 483 | return -EINVAL; | ||
| 484 | } | ||
| 485 | /* write bd */ | ||
| 486 | bd->offset[0] = cpu_to_le32(lower_32_bits(buf_add)); | ||
| 487 | bd->offset[1] = cpu_to_le32(upper_32_bits(buf_add)); | ||
| 488 | bd->offset[2] = cpu_to_le32(dword2); | ||
| 489 | bd->offset[3] = cpu_to_le32(dword3); | ||
| 490 | /* advance eqp pointer */ | ||
| 491 | ep_bdlist_eqp_adv(ep); | ||
| 492 | /* advance the buff pointer */ | ||
| 493 | buf_add += BD_MAX_BUFF_SIZE; | ||
| 494 | dev_vdbg(bdc->dev, "buf_add:%08llx req_len:%d bd:%p eqp:%d\n", | ||
| 495 | (unsigned long long)buf_add, req_len, bd, | ||
| 496 | ep->bd_list.eqp_bdi); | ||
| 497 | bd = bdi_to_bd(ep, ep->bd_list.eqp_bdi); | ||
| 498 | bd->offset[3] = cpu_to_le32(BD_SBF); | ||
| 499 | } | ||
| 500 | /* clear the STOP BD fetch bit from the first bd of this xfr */ | ||
| 501 | bd = bdi_to_bd(ep, bd_xfr->start_bdi); | ||
| 502 | bd->offset[3] &= cpu_to_le32(~BD_SBF); | ||
| 503 | /* the new eqp will be next hw dqp */ | ||
| 504 | bd_xfr->num_bds = num_bds; | ||
| 505 | bd_xfr->next_hwd_bdi = ep->bd_list.eqp_bdi; | ||
| 506 | /* everything is written correctly before notifying the HW */ | ||
| 507 | wmb(); | ||
| 508 | |||
| 509 | return 0; | ||
| 510 | } | ||
| 511 | |||
| 512 | /* Queue the xfr */ | ||
| 513 | static int bdc_queue_xfr(struct bdc *bdc, struct bdc_req *req) | ||
| 514 | { | ||
| 515 | int num_bds, bd_available; | ||
| 516 | struct bdc_ep *ep; | ||
| 517 | int ret; | ||
| 518 | |||
| 519 | ep = req->ep; | ||
| 520 | dev_dbg(bdc->dev, "%s req:%p\n", __func__, req); | ||
| 521 | dev_dbg(bdc->dev, "eqp_bdi:%d hwd_bdi:%d\n", | ||
| 522 | ep->bd_list.eqp_bdi, ep->bd_list.hwd_bdi); | ||
| 523 | |||
| 524 | num_bds = bd_needed_req(req); | ||
| 525 | bd_available = bd_available_ep(ep); | ||
| 526 | |||
| 527 | /* how many bd's are avaialble on ep */ | ||
| 528 | if (num_bds > bd_available) | ||
| 529 | return -ENOMEM; | ||
| 530 | |||
| 531 | ret = setup_bd_list_xfr(bdc, req, num_bds); | ||
| 532 | if (ret) | ||
| 533 | return ret; | ||
| 534 | list_add_tail(&req->queue, &ep->queue); | ||
| 535 | bdc_dbg_bd_list(bdc, ep); | ||
| 536 | bdc_notify_xfr(bdc, ep->ep_num); | ||
| 537 | |||
| 538 | return 0; | ||
| 539 | } | ||
| 540 | |||
| 541 | /* callback to gadget layer when xfr completes */ | ||
| 542 | static void bdc_req_complete(struct bdc_ep *ep, struct bdc_req *req, | ||
| 543 | int status) | ||
| 544 | { | ||
| 545 | struct bdc *bdc = ep->bdc; | ||
| 546 | |||
| 547 | if (req == NULL || &req->queue == NULL || &req->usb_req == NULL) | ||
| 548 | return; | ||
| 549 | |||
| 550 | dev_dbg(bdc->dev, "%s ep:%s status:%d\n", __func__, ep->name, status); | ||
| 551 | list_del(&req->queue); | ||
| 552 | req->usb_req.status = status; | ||
| 553 | usb_gadget_unmap_request(&bdc->gadget, &req->usb_req, ep->dir); | ||
| 554 | if (req->usb_req.complete) { | ||
| 555 | spin_unlock(&bdc->lock); | ||
| 556 | usb_gadget_giveback_request(&ep->usb_ep, &req->usb_req); | ||
| 557 | spin_lock(&bdc->lock); | ||
| 558 | } | ||
| 559 | } | ||
| 560 | |||
| 561 | /* Disable the endpoint */ | ||
| 562 | int bdc_ep_disable(struct bdc_ep *ep) | ||
| 563 | { | ||
| 564 | struct bdc_req *req; | ||
| 565 | struct bdc *bdc; | ||
| 566 | int ret; | ||
| 567 | |||
| 568 | ret = 0; | ||
| 569 | bdc = ep->bdc; | ||
| 570 | dev_dbg(bdc->dev, "%s() ep->ep_num=%d\n", __func__, ep->ep_num); | ||
| 571 | /* Stop the endpoint */ | ||
| 572 | ret = bdc_stop_ep(bdc, ep->ep_num); | ||
| 573 | |||
| 574 | /* | ||
| 575 | * Intentionally don't check the ret value of stop, it can fail in | ||
| 576 | * disconnect scenarios, continue with dconfig | ||
| 577 | */ | ||
| 578 | /* de-queue any pending requests */ | ||
| 579 | while (!list_empty(&ep->queue)) { | ||
| 580 | req = list_entry(ep->queue.next, struct bdc_req, | ||
| 581 | queue); | ||
| 582 | bdc_req_complete(ep, req, -ESHUTDOWN); | ||
| 583 | } | ||
| 584 | /* deconfigure the endpoint */ | ||
| 585 | ret = bdc_dconfig_ep(bdc, ep); | ||
| 586 | if (ret) | ||
| 587 | dev_warn(bdc->dev, | ||
| 588 | "dconfig fail but continue with memory free"); | ||
| 589 | |||
| 590 | ep->flags = 0; | ||
| 591 | /* ep0 memory is not freed, but reused on next connect sr */ | ||
| 592 | if (ep->ep_num == 1) | ||
| 593 | return 0; | ||
| 594 | |||
| 595 | /* Free the bdl memory */ | ||
| 596 | ep_bd_list_free(ep, ep->bd_list.num_tabs); | ||
| 597 | ep->desc = NULL; | ||
| 598 | ep->comp_desc = NULL; | ||
| 599 | ep->usb_ep.desc = NULL; | ||
| 600 | ep->ep_type = 0; | ||
| 601 | |||
| 602 | return ret; | ||
| 603 | } | ||
| 604 | |||
| 605 | /* Enable the ep */ | ||
| 606 | int bdc_ep_enable(struct bdc_ep *ep) | ||
| 607 | { | ||
| 608 | struct bdc *bdc; | ||
| 609 | int ret = 0; | ||
| 610 | |||
| 611 | bdc = ep->bdc; | ||
| 612 | dev_dbg(bdc->dev, "%s NUM_TABLES:%d %d\n", | ||
| 613 | __func__, NUM_TABLES, NUM_TABLES_ISOCH); | ||
| 614 | |||
| 615 | ret = ep_bd_list_alloc(ep); | ||
| 616 | if (ret) { | ||
| 617 | dev_err(bdc->dev, "ep bd list allocation failed:%d\n", ret); | ||
| 618 | return -ENOMEM; | ||
| 619 | } | ||
| 620 | bdc_dbg_bd_list(bdc, ep); | ||
| 621 | /* only for ep0: config ep is called for ep0 from connect event */ | ||
| 622 | ep->flags |= BDC_EP_ENABLED; | ||
| 623 | if (ep->ep_num == 1) | ||
| 624 | return ret; | ||
| 625 | |||
| 626 | /* Issue a configure endpoint command */ | ||
| 627 | ret = bdc_config_ep(bdc, ep); | ||
| 628 | if (ret) | ||
| 629 | return ret; | ||
| 630 | |||
| 631 | ep->usb_ep.maxpacket = usb_endpoint_maxp(ep->desc); | ||
| 632 | ep->usb_ep.desc = ep->desc; | ||
| 633 | ep->usb_ep.comp_desc = ep->comp_desc; | ||
| 634 | ep->ep_type = usb_endpoint_type(ep->desc); | ||
| 635 | ep->flags |= BDC_EP_ENABLED; | ||
| 636 | |||
| 637 | return 0; | ||
| 638 | } | ||
| 639 | |||
| 640 | /* EP0 related code */ | ||
| 641 | |||
| 642 | /* Queue a status stage BD */ | ||
| 643 | static int ep0_queue_status_stage(struct bdc *bdc) | ||
| 644 | { | ||
| 645 | struct bdc_req *status_req; | ||
| 646 | struct bdc_ep *ep; | ||
| 647 | |||
| 648 | status_req = &bdc->status_req; | ||
| 649 | ep = bdc->bdc_ep_array[1]; | ||
| 650 | status_req->ep = ep; | ||
| 651 | status_req->usb_req.length = 0; | ||
| 652 | status_req->usb_req.status = -EINPROGRESS; | ||
| 653 | status_req->usb_req.actual = 0; | ||
| 654 | status_req->usb_req.complete = NULL; | ||
| 655 | bdc_queue_xfr(bdc, status_req); | ||
| 656 | |||
| 657 | return 0; | ||
| 658 | } | ||
| 659 | |||
| 660 | /* Queue xfr on ep0 */ | ||
| 661 | static int ep0_queue(struct bdc_ep *ep, struct bdc_req *req) | ||
| 662 | { | ||
| 663 | struct bdc *bdc; | ||
| 664 | int ret; | ||
| 665 | |||
| 666 | bdc = ep->bdc; | ||
| 667 | dev_dbg(bdc->dev, "%s()\n", __func__); | ||
| 668 | req->usb_req.actual = 0; | ||
| 669 | req->usb_req.status = -EINPROGRESS; | ||
| 670 | req->epnum = ep->ep_num; | ||
| 671 | |||
| 672 | if (bdc->delayed_status) { | ||
| 673 | bdc->delayed_status = false; | ||
| 674 | /* if status stage was delayed? */ | ||
| 675 | if (bdc->ep0_state == WAIT_FOR_STATUS_START) { | ||
| 676 | /* Queue a status stage BD */ | ||
| 677 | ep0_queue_status_stage(bdc); | ||
| 678 | bdc->ep0_state = WAIT_FOR_STATUS_XMIT; | ||
| 679 | return 0; | ||
| 680 | } | ||
| 681 | } else { | ||
| 682 | /* | ||
| 683 | * if delayed status is false and 0 length transfer is requested | ||
| 684 | * i.e. for status stage of some setup request, then just | ||
| 685 | * return from here the status stage is queued independently | ||
| 686 | */ | ||
| 687 | if (req->usb_req.length == 0) | ||
| 688 | return 0; | ||
| 689 | |||
| 690 | } | ||
| 691 | ret = usb_gadget_map_request(&bdc->gadget, &req->usb_req, ep->dir); | ||
| 692 | if (ret) { | ||
| 693 | dev_err(bdc->dev, "dma mapping failed %s\n", ep->name); | ||
| 694 | return ret; | ||
| 695 | } | ||
| 696 | |||
| 697 | return bdc_queue_xfr(bdc, req); | ||
| 698 | } | ||
| 699 | |||
| 700 | /* Queue data stage */ | ||
| 701 | static int ep0_queue_data_stage(struct bdc *bdc) | ||
| 702 | { | ||
| 703 | struct usb_request *ep0_usb_req; | ||
| 704 | struct bdc_ep *ep; | ||
| 705 | |||
| 706 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 707 | ep0_usb_req = &bdc->ep0_req.usb_req; | ||
| 708 | ep = bdc->bdc_ep_array[1]; | ||
| 709 | bdc->ep0_req.ep = ep; | ||
| 710 | bdc->ep0_req.usb_req.complete = NULL; | ||
| 711 | |||
| 712 | return ep0_queue(ep, &bdc->ep0_req); | ||
| 713 | } | ||
| 714 | |||
| 715 | /* Queue req on ep */ | ||
| 716 | static int ep_queue(struct bdc_ep *ep, struct bdc_req *req) | ||
| 717 | { | ||
| 718 | struct bdc *bdc; | ||
| 719 | int ret = 0; | ||
| 720 | |||
| 721 | bdc = ep->bdc; | ||
| 722 | if (!req || !ep || !ep->usb_ep.desc) | ||
| 723 | return -EINVAL; | ||
| 724 | |||
| 725 | req->usb_req.actual = 0; | ||
| 726 | req->usb_req.status = -EINPROGRESS; | ||
| 727 | req->epnum = ep->ep_num; | ||
| 728 | |||
| 729 | ret = usb_gadget_map_request(&bdc->gadget, &req->usb_req, ep->dir); | ||
| 730 | if (ret) { | ||
| 731 | dev_err(bdc->dev, "dma mapping failed\n"); | ||
| 732 | return ret; | ||
| 733 | } | ||
| 734 | |||
| 735 | return bdc_queue_xfr(bdc, req); | ||
| 736 | } | ||
| 737 | |||
| 738 | /* Dequeue a request from ep */ | ||
| 739 | static int ep_dequeue(struct bdc_ep *ep, struct bdc_req *req) | ||
| 740 | { | ||
| 741 | int start_bdi, end_bdi, tbi, eqp_bdi, curr_hw_dqpi; | ||
| 742 | bool start_pending, end_pending; | ||
| 743 | bool first_remove = false; | ||
| 744 | struct bdc_req *first_req; | ||
| 745 | struct bdc_bd *bd_start; | ||
| 746 | struct bd_table *table; | ||
| 747 | dma_addr_t next_bd_dma; | ||
| 748 | u64 deq_ptr_64 = 0; | ||
| 749 | struct bdc *bdc; | ||
| 750 | u32 tmp_32; | ||
| 751 | int ret; | ||
| 752 | |||
| 753 | bdc = ep->bdc; | ||
| 754 | start_pending = end_pending = false; | ||
| 755 | eqp_bdi = ep->bd_list.eqp_bdi - 1; | ||
| 756 | |||
| 757 | if (eqp_bdi < 0) | ||
| 758 | eqp_bdi = ep->bd_list.max_bdi; | ||
| 759 | |||
| 760 | start_bdi = req->bd_xfr.start_bdi; | ||
| 761 | end_bdi = find_end_bdi(ep, req->bd_xfr.next_hwd_bdi); | ||
| 762 | |||
| 763 | dev_dbg(bdc->dev, "%s ep:%s start:%d end:%d\n", | ||
| 764 | __func__, ep->name, start_bdi, end_bdi); | ||
| 765 | dev_dbg(bdc->dev, "ep_dequeue ep=%p ep->desc=%p\n", | ||
| 766 | ep, (void *)ep->usb_ep.desc); | ||
| 767 | /* Stop the ep to see where the HW is ? */ | ||
| 768 | ret = bdc_stop_ep(bdc, ep->ep_num); | ||
| 769 | /* if there is an issue with stopping ep, then no need to go further */ | ||
| 770 | if (ret) | ||
| 771 | return 0; | ||
| 772 | |||
| 773 | /* | ||
| 774 | * After endpoint is stopped, there can be 3 cases, the request | ||
| 775 | * is processed, pending or in the middle of processing | ||
| 776 | */ | ||
| 777 | |||
| 778 | /* The current hw dequeue pointer */ | ||
| 779 | tmp_32 = bdc_readl(bdc->regs, BDC_EPSTS0(0)); | ||
| 780 | deq_ptr_64 = tmp_32; | ||
| 781 | tmp_32 = bdc_readl(bdc->regs, BDC_EPSTS0(1)); | ||
| 782 | deq_ptr_64 |= ((u64)tmp_32 << 32); | ||
| 783 | |||
| 784 | /* we have the dma addr of next bd that will be fetched by hardware */ | ||
| 785 | curr_hw_dqpi = bd_add_to_bdi(ep, deq_ptr_64); | ||
| 786 | if (curr_hw_dqpi < 0) | ||
| 787 | return curr_hw_dqpi; | ||
| 788 | |||
| 789 | /* | ||
| 790 | * curr_hw_dqpi points to actual dqp of HW and HW owns bd's from | ||
| 791 | * curr_hw_dqbdi..eqp_bdi. | ||
| 792 | */ | ||
| 793 | |||
| 794 | /* Check if start_bdi and end_bdi are in range of HW owned BD's */ | ||
| 795 | if (curr_hw_dqpi > eqp_bdi) { | ||
| 796 | /* there is a wrap from last to 0 */ | ||
| 797 | if (start_bdi >= curr_hw_dqpi || start_bdi <= eqp_bdi) { | ||
| 798 | start_pending = true; | ||
| 799 | end_pending = true; | ||
| 800 | } else if (end_bdi >= curr_hw_dqpi || end_bdi <= eqp_bdi) { | ||
| 801 | end_pending = true; | ||
| 802 | } | ||
| 803 | } else { | ||
| 804 | if (start_bdi >= curr_hw_dqpi) { | ||
| 805 | start_pending = true; | ||
| 806 | end_pending = true; | ||
| 807 | } else if (end_bdi >= curr_hw_dqpi) { | ||
| 808 | end_pending = true; | ||
| 809 | } | ||
| 810 | } | ||
| 811 | dev_dbg(bdc->dev, | ||
| 812 | "start_pending:%d end_pending:%d speed:%d\n", | ||
| 813 | start_pending, end_pending, bdc->gadget.speed); | ||
| 814 | |||
| 815 | /* If both start till end are processes, we cannot deq req */ | ||
| 816 | if (!start_pending && !end_pending) | ||
| 817 | return -EINVAL; | ||
| 818 | |||
| 819 | /* | ||
| 820 | * if ep_dequeue is called after disconnect then just return | ||
| 821 | * success from here | ||
| 822 | */ | ||
| 823 | if (bdc->gadget.speed == USB_SPEED_UNKNOWN) | ||
| 824 | return 0; | ||
| 825 | tbi = bdi_to_tbi(ep, req->bd_xfr.next_hwd_bdi); | ||
| 826 | table = ep->bd_list.bd_table_array[tbi]; | ||
| 827 | next_bd_dma = table->dma + | ||
| 828 | sizeof(struct bdc_bd)*(req->bd_xfr.next_hwd_bdi - | ||
| 829 | tbi * ep->bd_list.num_bds_table); | ||
| 830 | |||
| 831 | first_req = list_first_entry(&ep->queue, struct bdc_req, | ||
| 832 | queue); | ||
| 833 | |||
| 834 | if (req == first_req) | ||
| 835 | first_remove = true; | ||
| 836 | |||
| 837 | /* | ||
| 838 | * Due to HW limitation we need to bypadd chain bd's and issue ep_bla, | ||
| 839 | * incase if start is pending this is the first request in the list | ||
| 840 | * then issue ep_bla instead of marking as chain bd | ||
| 841 | */ | ||
| 842 | if (start_pending && !first_remove) { | ||
| 843 | /* | ||
| 844 | * Mark the start bd as Chain bd, and point the chain | ||
| 845 | * bd to next_bd_dma | ||
| 846 | */ | ||
| 847 | bd_start = bdi_to_bd(ep, start_bdi); | ||
| 848 | bd_start->offset[0] = cpu_to_le32(lower_32_bits(next_bd_dma)); | ||
| 849 | bd_start->offset[1] = cpu_to_le32(upper_32_bits(next_bd_dma)); | ||
| 850 | bd_start->offset[2] = 0x0; | ||
| 851 | bd_start->offset[3] = cpu_to_le32(MARK_CHAIN_BD); | ||
| 852 | bdc_dbg_bd_list(bdc, ep); | ||
| 853 | } else if (end_pending) { | ||
| 854 | /* | ||
| 855 | * The transfer is stopped in the middle, move the | ||
| 856 | * HW deq pointer to next_bd_dma | ||
| 857 | */ | ||
| 858 | ret = bdc_ep_bla(bdc, ep, next_bd_dma); | ||
| 859 | if (ret) { | ||
| 860 | dev_err(bdc->dev, "error in ep_bla:%d\n", ret); | ||
| 861 | return ret; | ||
| 862 | } | ||
| 863 | } | ||
| 864 | |||
| 865 | return 0; | ||
| 866 | } | ||
| 867 | |||
| 868 | /* Halt/Clear the ep based on value */ | ||
| 869 | static int ep_set_halt(struct bdc_ep *ep, u32 value) | ||
| 870 | { | ||
| 871 | struct bdc *bdc; | ||
| 872 | int ret; | ||
| 873 | |||
| 874 | bdc = ep->bdc; | ||
| 875 | dev_dbg(bdc->dev, "%s ep:%s value=%d\n", __func__, ep->name, value); | ||
| 876 | |||
| 877 | if (value) { | ||
| 878 | dev_dbg(bdc->dev, "Halt\n"); | ||
| 879 | if (ep->ep_num == 1) | ||
| 880 | bdc->ep0_state = WAIT_FOR_SETUP; | ||
| 881 | |||
| 882 | ret = bdc_ep_set_stall(bdc, ep->ep_num); | ||
| 883 | if (ret) | ||
| 884 | dev_err(bdc->dev, "failed to %s STALL on %s\n", | ||
| 885 | value ? "set" : "clear", ep->name); | ||
| 886 | else | ||
| 887 | ep->flags |= BDC_EP_STALL; | ||
| 888 | } else { | ||
| 889 | /* Clear */ | ||
| 890 | dev_dbg(bdc->dev, "Before Clear\n"); | ||
| 891 | ret = bdc_ep_clear_stall(bdc, ep->ep_num); | ||
| 892 | if (ret) | ||
| 893 | dev_err(bdc->dev, "failed to %s STALL on %s\n", | ||
| 894 | value ? "set" : "clear", ep->name); | ||
| 895 | else | ||
| 896 | ep->flags &= ~BDC_EP_STALL; | ||
| 897 | dev_dbg(bdc->dev, "After Clear\n"); | ||
| 898 | } | ||
| 899 | |||
| 900 | return ret; | ||
| 901 | } | ||
| 902 | |||
| 903 | /* Free all the ep */ | ||
| 904 | void bdc_free_ep(struct bdc *bdc) | ||
| 905 | { | ||
| 906 | struct bdc_ep *ep; | ||
| 907 | u8 epnum; | ||
| 908 | |||
| 909 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 910 | for (epnum = 1; epnum < bdc->num_eps; epnum++) { | ||
| 911 | ep = bdc->bdc_ep_array[epnum]; | ||
| 912 | if (!ep) | ||
| 913 | continue; | ||
| 914 | |||
| 915 | if (ep->flags & BDC_EP_ENABLED) | ||
| 916 | ep_bd_list_free(ep, ep->bd_list.num_tabs); | ||
| 917 | |||
| 918 | /* ep0 is not in this gadget list */ | ||
| 919 | if (epnum != 1) | ||
| 920 | list_del(&ep->usb_ep.ep_list); | ||
| 921 | |||
| 922 | kfree(ep); | ||
| 923 | } | ||
| 924 | } | ||
| 925 | |||
| 926 | /* USB2 spec, section 7.1.20 */ | ||
| 927 | static int bdc_set_test_mode(struct bdc *bdc) | ||
| 928 | { | ||
| 929 | u32 usb2_pm; | ||
| 930 | |||
| 931 | usb2_pm = bdc_readl(bdc->regs, BDC_USPPM2); | ||
| 932 | usb2_pm &= ~BDC_PTC_MASK; | ||
| 933 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 934 | switch (bdc->test_mode) { | ||
| 935 | case TEST_J: | ||
| 936 | case TEST_K: | ||
| 937 | case TEST_SE0_NAK: | ||
| 938 | case TEST_PACKET: | ||
| 939 | case TEST_FORCE_EN: | ||
| 940 | usb2_pm |= bdc->test_mode << 28; | ||
| 941 | break; | ||
| 942 | default: | ||
| 943 | return -EINVAL; | ||
| 944 | } | ||
| 945 | dev_dbg(bdc->dev, "usb2_pm=%08x", usb2_pm); | ||
| 946 | bdc_writel(bdc->regs, BDC_USPPM2, usb2_pm); | ||
| 947 | |||
| 948 | return 0; | ||
| 949 | } | ||
| 950 | |||
| 951 | /* | ||
| 952 | * Helper function to handle Transfer status report with status as either | ||
| 953 | * success or short | ||
| 954 | */ | ||
| 955 | static void handle_xsr_succ_status(struct bdc *bdc, struct bdc_ep *ep, | ||
| 956 | struct bdc_sr *sreport) | ||
| 957 | { | ||
| 958 | int short_bdi, start_bdi, end_bdi, max_len_bds, chain_bds; | ||
| 959 | struct bd_list *bd_list = &ep->bd_list; | ||
| 960 | int actual_length, length_short; | ||
| 961 | struct bd_transfer *bd_xfr; | ||
| 962 | struct bdc_bd *short_bd; | ||
| 963 | struct bdc_req *req; | ||
| 964 | u64 deq_ptr_64 = 0; | ||
| 965 | int status = 0; | ||
| 966 | int sr_status; | ||
| 967 | u32 tmp_32; | ||
| 968 | |||
| 969 | dev_dbg(bdc->dev, "%s ep:%p\n", __func__, ep); | ||
| 970 | bdc_dbg_srr(bdc, 0); | ||
| 971 | /* do not process thie sr if ignore flag is set */ | ||
| 972 | if (ep->ignore_next_sr) { | ||
| 973 | ep->ignore_next_sr = false; | ||
| 974 | return; | ||
| 975 | } | ||
| 976 | |||
| 977 | if (unlikely(list_empty(&ep->queue))) { | ||
| 978 | dev_warn(bdc->dev, "xfr srr with no BD's queued\n"); | ||
| 979 | return; | ||
| 980 | } | ||
| 981 | req = list_entry(ep->queue.next, struct bdc_req, | ||
| 982 | queue); | ||
| 983 | |||
| 984 | bd_xfr = &req->bd_xfr; | ||
| 985 | sr_status = XSF_STS(le32_to_cpu(sreport->offset[3])); | ||
| 986 | |||
| 987 | /* | ||
| 988 | * sr_status is short and this transfer has more than 1 bd then it needs | ||
| 989 | * special handling, this is only applicable for bulk and ctrl | ||
| 990 | */ | ||
| 991 | if (sr_status == XSF_SHORT && bd_xfr->num_bds > 1) { | ||
| 992 | /* | ||
| 993 | * This is multi bd xfr, lets see which bd | ||
| 994 | * caused short transfer and how many bytes have been | ||
| 995 | * transferred so far. | ||
| 996 | */ | ||
| 997 | tmp_32 = le32_to_cpu(sreport->offset[0]); | ||
| 998 | deq_ptr_64 = tmp_32; | ||
| 999 | tmp_32 = le32_to_cpu(sreport->offset[1]); | ||
| 1000 | deq_ptr_64 |= ((u64)tmp_32 << 32); | ||
| 1001 | short_bdi = bd_add_to_bdi(ep, deq_ptr_64); | ||
| 1002 | if (unlikely(short_bdi < 0)) | ||
| 1003 | dev_warn(bdc->dev, "bd doesn't exist?\n"); | ||
| 1004 | |||
| 1005 | start_bdi = bd_xfr->start_bdi; | ||
| 1006 | /* | ||
| 1007 | * We know the start_bdi and short_bdi, how many xfr | ||
| 1008 | * bds in between | ||
| 1009 | */ | ||
| 1010 | if (start_bdi <= short_bdi) { | ||
| 1011 | max_len_bds = short_bdi - start_bdi; | ||
| 1012 | if (max_len_bds <= bd_list->num_bds_table) { | ||
| 1013 | if (!(bdi_to_tbi(ep, start_bdi) == | ||
| 1014 | bdi_to_tbi(ep, short_bdi))) | ||
| 1015 | max_len_bds--; | ||
| 1016 | } else { | ||
| 1017 | chain_bds = max_len_bds/bd_list->num_bds_table; | ||
| 1018 | max_len_bds -= chain_bds; | ||
| 1019 | } | ||
| 1020 | } else { | ||
| 1021 | /* there is a wrap in the ring within a xfr */ | ||
| 1022 | chain_bds = (bd_list->max_bdi - start_bdi)/ | ||
| 1023 | bd_list->num_bds_table; | ||
| 1024 | chain_bds += short_bdi/bd_list->num_bds_table; | ||
| 1025 | max_len_bds = bd_list->max_bdi - start_bdi; | ||
| 1026 | max_len_bds += short_bdi; | ||
| 1027 | max_len_bds -= chain_bds; | ||
| 1028 | } | ||
| 1029 | /* max_len_bds is the number of full length bds */ | ||
| 1030 | end_bdi = find_end_bdi(ep, bd_xfr->next_hwd_bdi); | ||
| 1031 | if (!(end_bdi == short_bdi)) | ||
| 1032 | ep->ignore_next_sr = true; | ||
| 1033 | |||
| 1034 | actual_length = max_len_bds * BD_MAX_BUFF_SIZE; | ||
| 1035 | short_bd = bdi_to_bd(ep, short_bdi); | ||
| 1036 | /* length queued */ | ||
| 1037 | length_short = le32_to_cpu(short_bd->offset[2]) & 0x1FFFFF; | ||
| 1038 | /* actual length trensfered */ | ||
| 1039 | length_short -= SR_BD_LEN(le32_to_cpu(sreport->offset[2])); | ||
| 1040 | actual_length += length_short; | ||
| 1041 | req->usb_req.actual = actual_length; | ||
| 1042 | } else { | ||
| 1043 | req->usb_req.actual = req->usb_req.length - | ||
| 1044 | SR_BD_LEN(le32_to_cpu(sreport->offset[2])); | ||
| 1045 | dev_dbg(bdc->dev, | ||
| 1046 | "len=%d actual=%d bd_xfr->next_hwd_bdi:%d\n", | ||
| 1047 | req->usb_req.length, req->usb_req.actual, | ||
| 1048 | bd_xfr->next_hwd_bdi); | ||
| 1049 | } | ||
| 1050 | |||
| 1051 | /* Update the dequeue pointer */ | ||
| 1052 | ep->bd_list.hwd_bdi = bd_xfr->next_hwd_bdi; | ||
| 1053 | if (req->usb_req.actual < req->usb_req.length) { | ||
| 1054 | dev_dbg(bdc->dev, "short xfr on %d\n", ep->ep_num); | ||
| 1055 | if (req->usb_req.short_not_ok) | ||
| 1056 | status = -EREMOTEIO; | ||
| 1057 | } | ||
| 1058 | bdc_req_complete(ep, bd_xfr->req, status); | ||
| 1059 | } | ||
| 1060 | |||
| 1061 | /* EP0 setup related packet handlers */ | ||
| 1062 | |||
| 1063 | /* | ||
| 1064 | * Setup packet received, just store the packet and process on next DS or SS | ||
| 1065 | * started SR | ||
| 1066 | */ | ||
| 1067 | void bdc_xsf_ep0_setup_recv(struct bdc *bdc, struct bdc_sr *sreport) | ||
| 1068 | { | ||
| 1069 | struct usb_ctrlrequest *setup_pkt; | ||
| 1070 | u32 len; | ||
| 1071 | |||
| 1072 | dev_dbg(bdc->dev, | ||
| 1073 | "%s ep0_state:%s\n", | ||
| 1074 | __func__, ep0_state_string[bdc->ep0_state]); | ||
| 1075 | /* Store received setup packet */ | ||
| 1076 | setup_pkt = &bdc->setup_pkt; | ||
| 1077 | memcpy(setup_pkt, &sreport->offset[0], sizeof(*setup_pkt)); | ||
| 1078 | len = le16_to_cpu(setup_pkt->wLength); | ||
| 1079 | if (!len) | ||
| 1080 | bdc->ep0_state = WAIT_FOR_STATUS_START; | ||
| 1081 | else | ||
| 1082 | bdc->ep0_state = WAIT_FOR_DATA_START; | ||
| 1083 | |||
| 1084 | |||
| 1085 | dev_dbg(bdc->dev, | ||
| 1086 | "%s exit ep0_state:%s\n", | ||
| 1087 | __func__, ep0_state_string[bdc->ep0_state]); | ||
| 1088 | } | ||
| 1089 | |||
| 1090 | /* Stall ep0 */ | ||
| 1091 | static void ep0_stall(struct bdc *bdc) | ||
| 1092 | { | ||
| 1093 | struct bdc_ep *ep = bdc->bdc_ep_array[1]; | ||
| 1094 | struct bdc_req *req; | ||
| 1095 | |||
| 1096 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 1097 | bdc->delayed_status = false; | ||
| 1098 | ep_set_halt(ep, 1); | ||
| 1099 | |||
| 1100 | /* de-queue any pendig requests */ | ||
| 1101 | while (!list_empty(&ep->queue)) { | ||
| 1102 | req = list_entry(ep->queue.next, struct bdc_req, | ||
| 1103 | queue); | ||
| 1104 | bdc_req_complete(ep, req, -ESHUTDOWN); | ||
| 1105 | } | ||
| 1106 | } | ||
| 1107 | |||
| 1108 | /* SET_ADD handlers */ | ||
| 1109 | static int ep0_set_address(struct bdc *bdc, struct usb_ctrlrequest *ctrl) | ||
| 1110 | { | ||
| 1111 | enum usb_device_state state = bdc->gadget.state; | ||
| 1112 | int ret = 0; | ||
| 1113 | u32 addr; | ||
| 1114 | |||
| 1115 | addr = le16_to_cpu(ctrl->wValue); | ||
| 1116 | dev_dbg(bdc->dev, | ||
| 1117 | "%s addr:%d dev state:%d\n", | ||
| 1118 | __func__, addr, state); | ||
| 1119 | |||
| 1120 | if (addr > 127) | ||
| 1121 | return -EINVAL; | ||
| 1122 | |||
| 1123 | switch (state) { | ||
| 1124 | case USB_STATE_DEFAULT: | ||
| 1125 | case USB_STATE_ADDRESS: | ||
| 1126 | /* Issue Address device command */ | ||
| 1127 | ret = bdc_address_device(bdc, addr); | ||
| 1128 | if (ret) | ||
| 1129 | return ret; | ||
| 1130 | |||
| 1131 | if (addr) | ||
| 1132 | usb_gadget_set_state(&bdc->gadget, USB_STATE_ADDRESS); | ||
| 1133 | else | ||
| 1134 | usb_gadget_set_state(&bdc->gadget, USB_STATE_DEFAULT); | ||
| 1135 | |||
| 1136 | bdc->dev_addr = addr; | ||
| 1137 | break; | ||
| 1138 | default: | ||
| 1139 | dev_warn(bdc->dev, | ||
| 1140 | "SET Address in wrong device state %d\n", | ||
| 1141 | state); | ||
| 1142 | ret = -EINVAL; | ||
| 1143 | } | ||
| 1144 | |||
| 1145 | return ret; | ||
| 1146 | } | ||
| 1147 | |||
| 1148 | /* Handler for SET/CLEAR FEATURE requests for device */ | ||
| 1149 | static int ep0_handle_feature_dev(struct bdc *bdc, u16 wValue, | ||
| 1150 | u16 wIndex, bool set) | ||
| 1151 | { | ||
| 1152 | enum usb_device_state state = bdc->gadget.state; | ||
| 1153 | u32 usppms = 0; | ||
| 1154 | |||
| 1155 | dev_dbg(bdc->dev, "%s set:%d dev state:%d\n", | ||
| 1156 | __func__, set, state); | ||
| 1157 | switch (wValue) { | ||
| 1158 | case USB_DEVICE_REMOTE_WAKEUP: | ||
| 1159 | dev_dbg(bdc->dev, "USB_DEVICE_REMOTE_WAKEUP\n"); | ||
| 1160 | if (set) | ||
| 1161 | bdc->devstatus |= REMOTE_WAKE_ENABLE; | ||
| 1162 | else | ||
| 1163 | bdc->devstatus &= ~REMOTE_WAKE_ENABLE; | ||
| 1164 | break; | ||
| 1165 | |||
| 1166 | case USB_DEVICE_TEST_MODE: | ||
| 1167 | dev_dbg(bdc->dev, "USB_DEVICE_TEST_MODE\n"); | ||
| 1168 | if ((wIndex & 0xFF) || | ||
| 1169 | (bdc->gadget.speed != USB_SPEED_HIGH) || !set) | ||
| 1170 | return -EINVAL; | ||
| 1171 | |||
| 1172 | bdc->test_mode = wIndex >> 8; | ||
| 1173 | break; | ||
| 1174 | |||
| 1175 | case USB_DEVICE_U1_ENABLE: | ||
| 1176 | dev_dbg(bdc->dev, "USB_DEVICE_U1_ENABLE\n"); | ||
| 1177 | |||
| 1178 | if (bdc->gadget.speed != USB_SPEED_SUPER || | ||
| 1179 | state != USB_STATE_CONFIGURED) | ||
| 1180 | return -EINVAL; | ||
| 1181 | |||
| 1182 | usppms = bdc_readl(bdc->regs, BDC_USPPMS); | ||
| 1183 | if (set) { | ||
| 1184 | /* clear previous u1t */ | ||
| 1185 | usppms &= ~BDC_U1T(BDC_U1T_MASK); | ||
| 1186 | usppms |= BDC_U1T(U1_TIMEOUT); | ||
| 1187 | usppms |= BDC_U1E | BDC_PORT_W1S; | ||
| 1188 | bdc->devstatus |= (1 << USB_DEV_STAT_U1_ENABLED); | ||
| 1189 | } else { | ||
| 1190 | usppms &= ~BDC_U1E; | ||
| 1191 | usppms |= BDC_PORT_W1S; | ||
| 1192 | bdc->devstatus &= ~(1 << USB_DEV_STAT_U1_ENABLED); | ||
| 1193 | } | ||
| 1194 | bdc_writel(bdc->regs, BDC_USPPMS, usppms); | ||
| 1195 | break; | ||
| 1196 | |||
| 1197 | case USB_DEVICE_U2_ENABLE: | ||
| 1198 | dev_dbg(bdc->dev, "USB_DEVICE_U2_ENABLE\n"); | ||
| 1199 | |||
| 1200 | if (bdc->gadget.speed != USB_SPEED_SUPER || | ||
| 1201 | state != USB_STATE_CONFIGURED) | ||
| 1202 | return -EINVAL; | ||
| 1203 | |||
| 1204 | usppms = bdc_readl(bdc->regs, BDC_USPPMS); | ||
| 1205 | if (set) { | ||
| 1206 | usppms |= BDC_U2E; | ||
| 1207 | usppms |= BDC_U2A; | ||
| 1208 | bdc->devstatus |= (1 << USB_DEV_STAT_U2_ENABLED); | ||
| 1209 | } else { | ||
| 1210 | usppms &= ~BDC_U2E; | ||
| 1211 | usppms &= ~BDC_U2A; | ||
| 1212 | bdc->devstatus &= ~(1 << USB_DEV_STAT_U2_ENABLED); | ||
| 1213 | } | ||
| 1214 | bdc_writel(bdc->regs, BDC_USPPMS, usppms); | ||
| 1215 | break; | ||
| 1216 | |||
| 1217 | case USB_DEVICE_LTM_ENABLE: | ||
| 1218 | dev_dbg(bdc->dev, "USB_DEVICE_LTM_ENABLE?\n"); | ||
| 1219 | if (bdc->gadget.speed != USB_SPEED_SUPER || | ||
| 1220 | state != USB_STATE_CONFIGURED) | ||
| 1221 | return -EINVAL; | ||
| 1222 | break; | ||
| 1223 | default: | ||
| 1224 | dev_err(bdc->dev, "Unknown wValue:%d\n", wValue); | ||
| 1225 | return -EOPNOTSUPP; | ||
| 1226 | } /* USB_RECIP_DEVICE end */ | ||
| 1227 | |||
| 1228 | return 0; | ||
| 1229 | } | ||
| 1230 | |||
| 1231 | /* SET/CLEAR FEATURE handler */ | ||
| 1232 | static int ep0_handle_feature(struct bdc *bdc, | ||
| 1233 | struct usb_ctrlrequest *setup_pkt, bool set) | ||
| 1234 | { | ||
| 1235 | enum usb_device_state state = bdc->gadget.state; | ||
| 1236 | struct bdc_ep *ep; | ||
| 1237 | u16 wValue; | ||
| 1238 | u16 wIndex; | ||
| 1239 | int epnum; | ||
| 1240 | |||
| 1241 | wValue = le16_to_cpu(setup_pkt->wValue); | ||
| 1242 | wIndex = le16_to_cpu(setup_pkt->wIndex); | ||
| 1243 | |||
| 1244 | dev_dbg(bdc->dev, | ||
| 1245 | "%s wValue=%d wIndex=%d devstate=%08x speed=%d set=%d", | ||
| 1246 | __func__, wValue, wIndex, state, | ||
| 1247 | bdc->gadget.speed, set); | ||
| 1248 | |||
| 1249 | switch (setup_pkt->bRequestType & USB_RECIP_MASK) { | ||
| 1250 | case USB_RECIP_DEVICE: | ||
| 1251 | return ep0_handle_feature_dev(bdc, wValue, wIndex, set); | ||
| 1252 | case USB_RECIP_INTERFACE: | ||
| 1253 | dev_dbg(bdc->dev, "USB_RECIP_INTERFACE\n"); | ||
| 1254 | /* USB3 spec, sec 9.4.9 */ | ||
| 1255 | if (wValue != USB_INTRF_FUNC_SUSPEND) | ||
| 1256 | return -EINVAL; | ||
| 1257 | /* USB3 spec, Table 9-8 */ | ||
| 1258 | if (set) { | ||
| 1259 | if (wIndex & USB_INTRF_FUNC_SUSPEND_RW) { | ||
| 1260 | dev_dbg(bdc->dev, "SET REMOTE_WAKEUP\n"); | ||
| 1261 | bdc->devstatus |= REMOTE_WAKE_ENABLE; | ||
| 1262 | } else { | ||
| 1263 | dev_dbg(bdc->dev, "CLEAR REMOTE_WAKEUP\n"); | ||
| 1264 | bdc->devstatus &= ~REMOTE_WAKE_ENABLE; | ||
| 1265 | } | ||
| 1266 | } | ||
| 1267 | break; | ||
| 1268 | |||
| 1269 | case USB_RECIP_ENDPOINT: | ||
| 1270 | dev_dbg(bdc->dev, "USB_RECIP_ENDPOINT\n"); | ||
| 1271 | if (wValue != USB_ENDPOINT_HALT) | ||
| 1272 | return -EINVAL; | ||
| 1273 | |||
| 1274 | epnum = wIndex & USB_ENDPOINT_NUMBER_MASK; | ||
| 1275 | if (epnum) { | ||
| 1276 | if ((wIndex & USB_ENDPOINT_DIR_MASK) == USB_DIR_IN) | ||
| 1277 | epnum = epnum * 2 + 1; | ||
| 1278 | else | ||
| 1279 | epnum *= 2; | ||
| 1280 | } else { | ||
| 1281 | epnum = 1; /*EP0*/ | ||
| 1282 | } | ||
| 1283 | /* | ||
| 1284 | * If CLEAR_FEATURE on ep0 then don't do anything as the stall | ||
| 1285 | * condition on ep0 has already been cleared when SETUP packet | ||
| 1286 | * was received. | ||
| 1287 | */ | ||
| 1288 | if (epnum == 1 && !set) { | ||
| 1289 | dev_dbg(bdc->dev, "ep0 stall already cleared\n"); | ||
| 1290 | return 0; | ||
| 1291 | } | ||
| 1292 | dev_dbg(bdc->dev, "epnum=%d\n", epnum); | ||
| 1293 | ep = bdc->bdc_ep_array[epnum]; | ||
| 1294 | if (!ep) | ||
| 1295 | return -EINVAL; | ||
| 1296 | |||
| 1297 | return ep_set_halt(ep, set); | ||
| 1298 | default: | ||
| 1299 | dev_err(bdc->dev, "Unknown recipient\n"); | ||
| 1300 | return -EINVAL; | ||
| 1301 | } | ||
| 1302 | |||
| 1303 | return 0; | ||
| 1304 | } | ||
| 1305 | |||
| 1306 | /* GET_STATUS request handler */ | ||
| 1307 | static int ep0_handle_status(struct bdc *bdc, | ||
| 1308 | struct usb_ctrlrequest *setup_pkt) | ||
| 1309 | { | ||
| 1310 | enum usb_device_state state = bdc->gadget.state; | ||
| 1311 | struct bdc_ep *ep; | ||
| 1312 | u16 usb_status = 0; | ||
| 1313 | u32 epnum; | ||
| 1314 | u16 wIndex; | ||
| 1315 | |||
| 1316 | /* USB2.0 spec sec 9.4.5 */ | ||
| 1317 | if (state == USB_STATE_DEFAULT) | ||
| 1318 | return -EINVAL; | ||
| 1319 | wIndex = le16_to_cpu(setup_pkt->wIndex); | ||
| 1320 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 1321 | usb_status = bdc->devstatus; | ||
| 1322 | switch (setup_pkt->bRequestType & USB_RECIP_MASK) { | ||
| 1323 | case USB_RECIP_DEVICE: | ||
| 1324 | dev_dbg(bdc->dev, | ||
| 1325 | "USB_RECIP_DEVICE devstatus:%08x\n", | ||
| 1326 | bdc->devstatus); | ||
| 1327 | /* USB3 spec, sec 9.4.5 */ | ||
| 1328 | if (bdc->gadget.speed == USB_SPEED_SUPER) | ||
| 1329 | usb_status &= ~REMOTE_WAKE_ENABLE; | ||
| 1330 | break; | ||
| 1331 | |||
| 1332 | case USB_RECIP_INTERFACE: | ||
| 1333 | dev_dbg(bdc->dev, "USB_RECIP_INTERFACE\n"); | ||
| 1334 | if (bdc->gadget.speed == USB_SPEED_SUPER) { | ||
| 1335 | /* | ||
| 1336 | * This should come from func for Func remote wkup | ||
| 1337 | * usb_status |=1; | ||
| 1338 | */ | ||
| 1339 | if (bdc->devstatus & REMOTE_WAKE_ENABLE) | ||
| 1340 | usb_status |= REMOTE_WAKE_ENABLE; | ||
| 1341 | } else { | ||
| 1342 | usb_status = 0; | ||
| 1343 | } | ||
| 1344 | |||
| 1345 | break; | ||
| 1346 | |||
| 1347 | case USB_RECIP_ENDPOINT: | ||
| 1348 | dev_dbg(bdc->dev, "USB_RECIP_ENDPOINT\n"); | ||
| 1349 | epnum = wIndex & USB_ENDPOINT_NUMBER_MASK; | ||
| 1350 | if (epnum) { | ||
| 1351 | if ((wIndex & USB_ENDPOINT_DIR_MASK) == USB_DIR_IN) | ||
| 1352 | epnum = epnum*2 + 1; | ||
| 1353 | else | ||
| 1354 | epnum *= 2; | ||
| 1355 | } else { | ||
| 1356 | epnum = 1; /* EP0 */ | ||
| 1357 | } | ||
| 1358 | |||
| 1359 | ep = bdc->bdc_ep_array[epnum]; | ||
| 1360 | if (!ep) { | ||
| 1361 | dev_err(bdc->dev, "ISSUE, GET_STATUS for invalid EP ?"); | ||
| 1362 | return -EINVAL; | ||
| 1363 | } | ||
| 1364 | if (ep->flags & BDC_EP_STALL) | ||
| 1365 | usb_status |= 1 << USB_ENDPOINT_HALT; | ||
| 1366 | |||
| 1367 | break; | ||
| 1368 | default: | ||
| 1369 | dev_err(bdc->dev, "Unknown recipient for get_status\n"); | ||
| 1370 | return -EINVAL; | ||
| 1371 | } | ||
| 1372 | /* prepare a data stage for GET_STATUS */ | ||
| 1373 | dev_dbg(bdc->dev, "usb_status=%08x\n", usb_status); | ||
| 1374 | *(__le16 *)bdc->ep0_response_buff = cpu_to_le16(usb_status); | ||
| 1375 | bdc->ep0_req.usb_req.length = 2; | ||
| 1376 | bdc->ep0_req.usb_req.buf = &bdc->ep0_response_buff; | ||
| 1377 | ep0_queue_data_stage(bdc); | ||
| 1378 | |||
| 1379 | return 0; | ||
| 1380 | } | ||
| 1381 | |||
| 1382 | static void ep0_set_sel_cmpl(struct usb_ep *_ep, struct usb_request *_req) | ||
| 1383 | { | ||
| 1384 | /* ep0_set_sel_cmpl */ | ||
| 1385 | } | ||
| 1386 | |||
| 1387 | /* Queue data stage to handle 6 byte SET_SEL request */ | ||
| 1388 | static int ep0_set_sel(struct bdc *bdc, | ||
| 1389 | struct usb_ctrlrequest *setup_pkt) | ||
| 1390 | { | ||
| 1391 | struct bdc_ep *ep; | ||
| 1392 | u16 wLength; | ||
| 1393 | u16 wValue; | ||
| 1394 | |||
| 1395 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 1396 | wValue = le16_to_cpu(setup_pkt->wValue); | ||
| 1397 | wLength = le16_to_cpu(setup_pkt->wLength); | ||
| 1398 | if (unlikely(wLength != 6)) { | ||
| 1399 | dev_err(bdc->dev, "%s Wrong wLength:%d\n", __func__, wLength); | ||
| 1400 | return -EINVAL; | ||
| 1401 | } | ||
| 1402 | ep = bdc->bdc_ep_array[1]; | ||
| 1403 | bdc->ep0_req.ep = ep; | ||
| 1404 | bdc->ep0_req.usb_req.length = 6; | ||
| 1405 | bdc->ep0_req.usb_req.buf = bdc->ep0_response_buff; | ||
| 1406 | bdc->ep0_req.usb_req.complete = ep0_set_sel_cmpl; | ||
| 1407 | ep0_queue_data_stage(bdc); | ||
| 1408 | |||
| 1409 | return 0; | ||
| 1410 | } | ||
| 1411 | |||
| 1412 | /* | ||
| 1413 | * Queue a 0 byte bd only if wLength is more than the length and and length is | ||
| 1414 | * a multiple of MaxPacket then queue 0 byte BD | ||
| 1415 | */ | ||
| 1416 | static int ep0_queue_zlp(struct bdc *bdc) | ||
| 1417 | { | ||
| 1418 | int ret; | ||
| 1419 | |||
| 1420 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 1421 | bdc->ep0_req.ep = bdc->bdc_ep_array[1]; | ||
| 1422 | bdc->ep0_req.usb_req.length = 0; | ||
| 1423 | bdc->ep0_req.usb_req.complete = NULL; | ||
| 1424 | bdc->ep0_state = WAIT_FOR_DATA_START; | ||
| 1425 | ret = bdc_queue_xfr(bdc, &bdc->ep0_req); | ||
| 1426 | if (ret) { | ||
| 1427 | dev_err(bdc->dev, "err queueing zlp :%d\n", ret); | ||
| 1428 | return ret; | ||
| 1429 | } | ||
| 1430 | bdc->ep0_state = WAIT_FOR_DATA_XMIT; | ||
| 1431 | |||
| 1432 | return 0; | ||
| 1433 | } | ||
| 1434 | |||
| 1435 | /* Control request handler */ | ||
| 1436 | static int handle_control_request(struct bdc *bdc) | ||
| 1437 | { | ||
| 1438 | enum usb_device_state state = bdc->gadget.state; | ||
| 1439 | struct usb_ctrlrequest *setup_pkt; | ||
| 1440 | int delegate_setup = 0; | ||
| 1441 | int ret = 0; | ||
| 1442 | int config = 0; | ||
| 1443 | |||
| 1444 | setup_pkt = &bdc->setup_pkt; | ||
| 1445 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 1446 | if ((setup_pkt->bRequestType & USB_TYPE_MASK) == USB_TYPE_STANDARD) { | ||
| 1447 | switch (setup_pkt->bRequest) { | ||
| 1448 | case USB_REQ_SET_ADDRESS: | ||
| 1449 | dev_dbg(bdc->dev, "USB_REQ_SET_ADDRESS\n"); | ||
| 1450 | ret = ep0_set_address(bdc, setup_pkt); | ||
| 1451 | bdc->devstatus &= DEVSTATUS_CLEAR; | ||
| 1452 | break; | ||
| 1453 | |||
| 1454 | case USB_REQ_SET_CONFIGURATION: | ||
| 1455 | dev_dbg(bdc->dev, "USB_REQ_SET_CONFIGURATION\n"); | ||
| 1456 | if (state == USB_STATE_ADDRESS) { | ||
| 1457 | usb_gadget_set_state(&bdc->gadget, | ||
| 1458 | USB_STATE_CONFIGURED); | ||
| 1459 | } else if (state == USB_STATE_CONFIGURED) { | ||
| 1460 | /* | ||
| 1461 | * USB2 spec sec 9.4.7, if wValue is 0 then dev | ||
| 1462 | * is moved to addressed state | ||
| 1463 | */ | ||
| 1464 | config = le16_to_cpu(setup_pkt->wValue); | ||
| 1465 | if (!config) | ||
| 1466 | usb_gadget_set_state( | ||
| 1467 | &bdc->gadget, | ||
| 1468 | USB_STATE_ADDRESS); | ||
| 1469 | } | ||
| 1470 | delegate_setup = 1; | ||
| 1471 | break; | ||
| 1472 | |||
| 1473 | case USB_REQ_SET_FEATURE: | ||
| 1474 | dev_dbg(bdc->dev, "USB_REQ_SET_FEATURE\n"); | ||
| 1475 | ret = ep0_handle_feature(bdc, setup_pkt, 1); | ||
| 1476 | break; | ||
| 1477 | |||
| 1478 | case USB_REQ_CLEAR_FEATURE: | ||
| 1479 | dev_dbg(bdc->dev, "USB_REQ_CLEAR_FEATURE\n"); | ||
| 1480 | ret = ep0_handle_feature(bdc, setup_pkt, 0); | ||
| 1481 | break; | ||
| 1482 | |||
| 1483 | case USB_REQ_GET_STATUS: | ||
| 1484 | dev_dbg(bdc->dev, "USB_REQ_GET_STATUS\n"); | ||
| 1485 | ret = ep0_handle_status(bdc, setup_pkt); | ||
| 1486 | break; | ||
| 1487 | |||
| 1488 | case USB_REQ_SET_SEL: | ||
| 1489 | dev_dbg(bdc->dev, "USB_REQ_SET_SEL\n"); | ||
| 1490 | ret = ep0_set_sel(bdc, setup_pkt); | ||
| 1491 | break; | ||
| 1492 | |||
| 1493 | case USB_REQ_SET_ISOCH_DELAY: | ||
| 1494 | dev_warn(bdc->dev, | ||
| 1495 | "USB_REQ_SET_ISOCH_DELAY not handled\n"); | ||
| 1496 | ret = 0; | ||
| 1497 | break; | ||
| 1498 | default: | ||
| 1499 | delegate_setup = 1; | ||
| 1500 | } | ||
| 1501 | } else { | ||
| 1502 | delegate_setup = 1; | ||
| 1503 | } | ||
| 1504 | |||
| 1505 | if (delegate_setup) { | ||
| 1506 | spin_unlock(&bdc->lock); | ||
| 1507 | ret = bdc->gadget_driver->setup(&bdc->gadget, setup_pkt); | ||
| 1508 | spin_lock(&bdc->lock); | ||
| 1509 | } | ||
| 1510 | |||
| 1511 | return ret; | ||
| 1512 | } | ||
| 1513 | |||
| 1514 | /* EP0: Data stage started */ | ||
| 1515 | void bdc_xsf_ep0_data_start(struct bdc *bdc, struct bdc_sr *sreport) | ||
| 1516 | { | ||
| 1517 | struct bdc_ep *ep; | ||
| 1518 | int ret = 0; | ||
| 1519 | |||
| 1520 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 1521 | ep = bdc->bdc_ep_array[1]; | ||
| 1522 | /* If ep0 was stalled, the clear it first */ | ||
| 1523 | if (ep->flags & BDC_EP_STALL) { | ||
| 1524 | ret = ep_set_halt(ep, 0); | ||
| 1525 | if (ret) | ||
| 1526 | goto err; | ||
| 1527 | } | ||
| 1528 | if (bdc->ep0_state != WAIT_FOR_DATA_START) | ||
| 1529 | dev_warn(bdc->dev, | ||
| 1530 | "Data stage not expected ep0_state:%s\n", | ||
| 1531 | ep0_state_string[bdc->ep0_state]); | ||
| 1532 | |||
| 1533 | ret = handle_control_request(bdc); | ||
| 1534 | if (ret == USB_GADGET_DELAYED_STATUS) { | ||
| 1535 | /* | ||
| 1536 | * The ep0 state will remain WAIT_FOR_DATA_START till | ||
| 1537 | * we received ep_queue on ep0 | ||
| 1538 | */ | ||
| 1539 | bdc->delayed_status = true; | ||
| 1540 | return; | ||
| 1541 | } | ||
| 1542 | if (!ret) { | ||
| 1543 | bdc->ep0_state = WAIT_FOR_DATA_XMIT; | ||
| 1544 | dev_dbg(bdc->dev, | ||
| 1545 | "ep0_state:%s", ep0_state_string[bdc->ep0_state]); | ||
| 1546 | return; | ||
| 1547 | } | ||
| 1548 | err: | ||
| 1549 | ep0_stall(bdc); | ||
| 1550 | } | ||
| 1551 | |||
| 1552 | /* EP0: status stage started */ | ||
| 1553 | void bdc_xsf_ep0_status_start(struct bdc *bdc, struct bdc_sr *sreport) | ||
| 1554 | { | ||
| 1555 | struct usb_ctrlrequest *setup_pkt; | ||
| 1556 | struct bdc_ep *ep; | ||
| 1557 | int ret = 0; | ||
| 1558 | |||
| 1559 | dev_dbg(bdc->dev, | ||
| 1560 | "%s ep0_state:%s", | ||
| 1561 | __func__, ep0_state_string[bdc->ep0_state]); | ||
| 1562 | ep = bdc->bdc_ep_array[1]; | ||
| 1563 | |||
| 1564 | /* check if ZLP was queued? */ | ||
| 1565 | if (bdc->zlp_needed) | ||
| 1566 | bdc->zlp_needed = false; | ||
| 1567 | |||
| 1568 | if (ep->flags & BDC_EP_STALL) { | ||
| 1569 | ret = ep_set_halt(ep, 0); | ||
| 1570 | if (ret) | ||
| 1571 | goto err; | ||
| 1572 | } | ||
| 1573 | |||
| 1574 | if ((bdc->ep0_state != WAIT_FOR_STATUS_START) && | ||
| 1575 | (bdc->ep0_state != WAIT_FOR_DATA_XMIT)) | ||
| 1576 | dev_err(bdc->dev, | ||
| 1577 | "Status stage recv but ep0_state:%s\n", | ||
| 1578 | ep0_state_string[bdc->ep0_state]); | ||
| 1579 | |||
| 1580 | /* check if data stage is in progress ? */ | ||
| 1581 | if (bdc->ep0_state == WAIT_FOR_DATA_XMIT) { | ||
| 1582 | bdc->ep0_state = STATUS_PENDING; | ||
| 1583 | /* Status stage will be queued upon Data stage transmit event */ | ||
| 1584 | dev_dbg(bdc->dev, | ||
| 1585 | "status started but data not transmitted yet\n"); | ||
| 1586 | return; | ||
| 1587 | } | ||
| 1588 | setup_pkt = &bdc->setup_pkt; | ||
| 1589 | |||
| 1590 | /* | ||
| 1591 | * 2 stage setup then only process the setup, for 3 stage setup the date | ||
| 1592 | * stage is already handled | ||
| 1593 | */ | ||
| 1594 | if (!le16_to_cpu(setup_pkt->wLength)) { | ||
| 1595 | ret = handle_control_request(bdc); | ||
| 1596 | if (ret == USB_GADGET_DELAYED_STATUS) { | ||
| 1597 | bdc->delayed_status = true; | ||
| 1598 | /* ep0_state will remain WAIT_FOR_STATUS_START */ | ||
| 1599 | return; | ||
| 1600 | } | ||
| 1601 | } | ||
| 1602 | if (!ret) { | ||
| 1603 | /* Queue a status stage BD */ | ||
| 1604 | ep0_queue_status_stage(bdc); | ||
| 1605 | bdc->ep0_state = WAIT_FOR_STATUS_XMIT; | ||
| 1606 | dev_dbg(bdc->dev, | ||
| 1607 | "ep0_state:%s", ep0_state_string[bdc->ep0_state]); | ||
| 1608 | return; | ||
| 1609 | } | ||
| 1610 | err: | ||
| 1611 | ep0_stall(bdc); | ||
| 1612 | } | ||
| 1613 | |||
| 1614 | /* Helper function to update ep0 upon SR with xsf_succ or xsf_short */ | ||
| 1615 | static void ep0_xsf_complete(struct bdc *bdc, struct bdc_sr *sreport) | ||
| 1616 | { | ||
| 1617 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 1618 | switch (bdc->ep0_state) { | ||
| 1619 | case WAIT_FOR_DATA_XMIT: | ||
| 1620 | bdc->ep0_state = WAIT_FOR_STATUS_START; | ||
| 1621 | break; | ||
| 1622 | case WAIT_FOR_STATUS_XMIT: | ||
| 1623 | bdc->ep0_state = WAIT_FOR_SETUP; | ||
| 1624 | if (bdc->test_mode) { | ||
| 1625 | int ret; | ||
| 1626 | |||
| 1627 | dev_dbg(bdc->dev, "test_mode:%d\n", bdc->test_mode); | ||
| 1628 | ret = bdc_set_test_mode(bdc); | ||
| 1629 | if (ret < 0) { | ||
| 1630 | dev_err(bdc->dev, "Err in setting Test mode\n"); | ||
| 1631 | return; | ||
| 1632 | } | ||
| 1633 | bdc->test_mode = 0; | ||
| 1634 | } | ||
| 1635 | break; | ||
| 1636 | case STATUS_PENDING: | ||
| 1637 | bdc_xsf_ep0_status_start(bdc, sreport); | ||
| 1638 | break; | ||
| 1639 | |||
| 1640 | default: | ||
| 1641 | dev_err(bdc->dev, | ||
| 1642 | "Unknown ep0_state:%s\n", | ||
| 1643 | ep0_state_string[bdc->ep0_state]); | ||
| 1644 | |||
| 1645 | } | ||
| 1646 | } | ||
| 1647 | |||
| 1648 | /* xfr completion status report handler */ | ||
| 1649 | void bdc_sr_xsf(struct bdc *bdc, struct bdc_sr *sreport) | ||
| 1650 | { | ||
| 1651 | struct bdc_ep *ep; | ||
| 1652 | u32 sr_status; | ||
| 1653 | u8 ep_num; | ||
| 1654 | |||
| 1655 | ep_num = (le32_to_cpu(sreport->offset[3])>>4) & 0x1f; | ||
| 1656 | ep = bdc->bdc_ep_array[ep_num]; | ||
| 1657 | if (!ep || !(ep->flags & BDC_EP_ENABLED)) { | ||
| 1658 | dev_err(bdc->dev, "xsf for ep not enabled\n"); | ||
| 1659 | return; | ||
| 1660 | } | ||
| 1661 | /* | ||
| 1662 | * check if this transfer is after link went from U3->U0 due | ||
| 1663 | * to remote wakeup | ||
| 1664 | */ | ||
| 1665 | if (bdc->devstatus & FUNC_WAKE_ISSUED) { | ||
| 1666 | bdc->devstatus &= ~(FUNC_WAKE_ISSUED); | ||
| 1667 | dev_dbg(bdc->dev, "%s clearing FUNC_WAKE_ISSUED flag\n", | ||
| 1668 | __func__); | ||
| 1669 | } | ||
| 1670 | sr_status = XSF_STS(le32_to_cpu(sreport->offset[3])); | ||
| 1671 | dev_dbg_ratelimited(bdc->dev, "%s sr_status=%d ep:%s\n", | ||
| 1672 | __func__, sr_status, ep->name); | ||
| 1673 | |||
| 1674 | switch (sr_status) { | ||
| 1675 | case XSF_SUCC: | ||
| 1676 | case XSF_SHORT: | ||
| 1677 | handle_xsr_succ_status(bdc, ep, sreport); | ||
| 1678 | if (ep_num == 1) | ||
| 1679 | ep0_xsf_complete(bdc, sreport); | ||
| 1680 | break; | ||
| 1681 | |||
| 1682 | case XSF_SETUP_RECV: | ||
| 1683 | case XSF_DATA_START: | ||
| 1684 | case XSF_STATUS_START: | ||
| 1685 | if (ep_num != 1) { | ||
| 1686 | dev_err(bdc->dev, | ||
| 1687 | "ep0 related packets on non ep0 endpoint"); | ||
| 1688 | return; | ||
| 1689 | } | ||
| 1690 | bdc->sr_xsf_ep0[sr_status - XSF_SETUP_RECV](bdc, sreport); | ||
| 1691 | break; | ||
| 1692 | |||
| 1693 | case XSF_BABB: | ||
| 1694 | if (ep_num == 1) { | ||
| 1695 | dev_dbg(bdc->dev, "Babble on ep0 zlp_need:%d\n", | ||
| 1696 | bdc->zlp_needed); | ||
| 1697 | /* | ||
| 1698 | * If the last completed transfer had wLength >Data Len, | ||
| 1699 | * and Len is multiple of MaxPacket,then queue ZLP | ||
| 1700 | */ | ||
| 1701 | if (bdc->zlp_needed) { | ||
| 1702 | /* queue 0 length bd */ | ||
| 1703 | ep0_queue_zlp(bdc); | ||
| 1704 | return; | ||
| 1705 | } | ||
| 1706 | } | ||
| 1707 | dev_warn(bdc->dev, "Babble on ep not handled\n"); | ||
| 1708 | break; | ||
| 1709 | default: | ||
| 1710 | dev_warn(bdc->dev, "sr status not handled:%x\n", sr_status); | ||
| 1711 | break; | ||
| 1712 | } | ||
| 1713 | } | ||
| 1714 | |||
| 1715 | static int bdc_gadget_ep_queue(struct usb_ep *_ep, | ||
| 1716 | struct usb_request *_req, gfp_t gfp_flags) | ||
| 1717 | { | ||
| 1718 | struct bdc_req *req; | ||
| 1719 | unsigned long flags; | ||
| 1720 | struct bdc_ep *ep; | ||
| 1721 | struct bdc *bdc; | ||
| 1722 | int ret; | ||
| 1723 | |||
| 1724 | if (!_ep || !_ep->desc) | ||
| 1725 | return -ESHUTDOWN; | ||
| 1726 | |||
| 1727 | if (!_req || !_req->complete || !_req->buf) | ||
| 1728 | return -EINVAL; | ||
| 1729 | |||
| 1730 | ep = to_bdc_ep(_ep); | ||
| 1731 | req = to_bdc_req(_req); | ||
| 1732 | bdc = ep->bdc; | ||
| 1733 | dev_dbg(bdc->dev, "%s ep:%p req:%p\n", __func__, ep, req); | ||
| 1734 | dev_dbg(bdc->dev, "queuing request %p to %s length %d zero:%d\n", | ||
| 1735 | _req, ep->name, _req->length, _req->zero); | ||
| 1736 | |||
| 1737 | if (!ep->usb_ep.desc) { | ||
| 1738 | dev_warn(bdc->dev, | ||
| 1739 | "trying to queue req %p to disabled %s\n", | ||
| 1740 | _req, ep->name); | ||
| 1741 | return -ESHUTDOWN; | ||
| 1742 | } | ||
| 1743 | |||
| 1744 | if (_req->length > MAX_XFR_LEN) { | ||
| 1745 | dev_warn(bdc->dev, | ||
| 1746 | "req length > supported MAX:%d requested:%d\n", | ||
| 1747 | MAX_XFR_LEN, _req->length); | ||
| 1748 | return -EOPNOTSUPP; | ||
| 1749 | } | ||
| 1750 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 1751 | if (ep == bdc->bdc_ep_array[1]) | ||
| 1752 | ret = ep0_queue(ep, req); | ||
| 1753 | else | ||
| 1754 | ret = ep_queue(ep, req); | ||
| 1755 | |||
| 1756 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 1757 | |||
| 1758 | return ret; | ||
| 1759 | } | ||
| 1760 | |||
| 1761 | static int bdc_gadget_ep_dequeue(struct usb_ep *_ep, | ||
| 1762 | struct usb_request *_req) | ||
| 1763 | { | ||
| 1764 | struct bdc_req *req; | ||
| 1765 | unsigned long flags; | ||
| 1766 | struct bdc_ep *ep; | ||
| 1767 | struct bdc *bdc; | ||
| 1768 | int ret; | ||
| 1769 | |||
| 1770 | if (!_ep || !_req) | ||
| 1771 | return -EINVAL; | ||
| 1772 | |||
| 1773 | ep = to_bdc_ep(_ep); | ||
| 1774 | req = to_bdc_req(_req); | ||
| 1775 | bdc = ep->bdc; | ||
| 1776 | dev_dbg(bdc->dev, "%s ep:%s req:%p\n", __func__, ep->name, req); | ||
| 1777 | bdc_dbg_bd_list(bdc, ep); | ||
| 1778 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 1779 | /* make sure it's still queued on this endpoint */ | ||
| 1780 | list_for_each_entry(req, &ep->queue, queue) { | ||
| 1781 | if (&req->usb_req == _req) | ||
| 1782 | break; | ||
| 1783 | } | ||
| 1784 | if (&req->usb_req != _req) { | ||
| 1785 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 1786 | dev_err(bdc->dev, "usb_req !=req n"); | ||
| 1787 | return -EINVAL; | ||
| 1788 | } | ||
| 1789 | ret = ep_dequeue(ep, req); | ||
| 1790 | if (ret) { | ||
| 1791 | ret = -EOPNOTSUPP; | ||
| 1792 | goto err; | ||
| 1793 | } | ||
| 1794 | bdc_req_complete(ep, req, -ECONNRESET); | ||
| 1795 | |||
| 1796 | err: | ||
| 1797 | bdc_dbg_bd_list(bdc, ep); | ||
| 1798 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 1799 | |||
| 1800 | return ret; | ||
| 1801 | } | ||
| 1802 | |||
| 1803 | static int bdc_gadget_ep_set_halt(struct usb_ep *_ep, int value) | ||
| 1804 | { | ||
| 1805 | unsigned long flags; | ||
| 1806 | struct bdc_ep *ep; | ||
| 1807 | struct bdc *bdc; | ||
| 1808 | int ret; | ||
| 1809 | |||
| 1810 | ep = to_bdc_ep(_ep); | ||
| 1811 | bdc = ep->bdc; | ||
| 1812 | dev_dbg(bdc->dev, "%s ep:%s value=%d\n", __func__, ep->name, value); | ||
| 1813 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 1814 | if (usb_endpoint_xfer_isoc(ep->usb_ep.desc)) | ||
| 1815 | ret = -EINVAL; | ||
| 1816 | else if (!list_empty(&ep->queue)) | ||
| 1817 | ret = -EAGAIN; | ||
| 1818 | else | ||
| 1819 | ret = ep_set_halt(ep, value); | ||
| 1820 | |||
| 1821 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 1822 | |||
| 1823 | return ret; | ||
| 1824 | } | ||
| 1825 | |||
| 1826 | static struct usb_request *bdc_gadget_alloc_request(struct usb_ep *_ep, | ||
| 1827 | gfp_t gfp_flags) | ||
| 1828 | { | ||
| 1829 | struct bdc_req *req; | ||
| 1830 | struct bdc_ep *ep; | ||
| 1831 | |||
| 1832 | req = kzalloc(sizeof(*req), gfp_flags); | ||
| 1833 | if (!req) | ||
| 1834 | return NULL; | ||
| 1835 | |||
| 1836 | ep = to_bdc_ep(_ep); | ||
| 1837 | req->ep = ep; | ||
| 1838 | req->epnum = ep->ep_num; | ||
| 1839 | req->usb_req.dma = DMA_ADDR_INVALID; | ||
| 1840 | dev_dbg(ep->bdc->dev, "%s ep:%s req:%p\n", __func__, ep->name, req); | ||
| 1841 | |||
| 1842 | return &req->usb_req; | ||
| 1843 | } | ||
| 1844 | |||
| 1845 | static void bdc_gadget_free_request(struct usb_ep *_ep, | ||
| 1846 | struct usb_request *_req) | ||
| 1847 | { | ||
| 1848 | struct bdc_req *req; | ||
| 1849 | |||
| 1850 | req = to_bdc_req(_req); | ||
| 1851 | kfree(req); | ||
| 1852 | } | ||
| 1853 | |||
| 1854 | /* endpoint operations */ | ||
| 1855 | |||
| 1856 | /* configure endpoint and also allocate resources */ | ||
| 1857 | static int bdc_gadget_ep_enable(struct usb_ep *_ep, | ||
| 1858 | const struct usb_endpoint_descriptor *desc) | ||
| 1859 | { | ||
| 1860 | unsigned long flags; | ||
| 1861 | struct bdc_ep *ep; | ||
| 1862 | struct bdc *bdc; | ||
| 1863 | int ret; | ||
| 1864 | |||
| 1865 | if (!_ep || !desc || desc->bDescriptorType != USB_DT_ENDPOINT) { | ||
| 1866 | pr_debug("bdc_gadget_ep_enable invalid parameters\n"); | ||
| 1867 | return -EINVAL; | ||
| 1868 | } | ||
| 1869 | |||
| 1870 | if (!desc->wMaxPacketSize) { | ||
| 1871 | pr_debug("bdc_gadget_ep_enable missing wMaxPacketSize\n"); | ||
| 1872 | return -EINVAL; | ||
| 1873 | } | ||
| 1874 | |||
| 1875 | ep = to_bdc_ep(_ep); | ||
| 1876 | bdc = ep->bdc; | ||
| 1877 | |||
| 1878 | /* Sanity check, upper layer will not send enable for ep0 */ | ||
| 1879 | if (ep == bdc->bdc_ep_array[1]) | ||
| 1880 | return -EINVAL; | ||
| 1881 | |||
| 1882 | if (!bdc->gadget_driver | ||
| 1883 | || bdc->gadget.speed == USB_SPEED_UNKNOWN) { | ||
| 1884 | return -ESHUTDOWN; | ||
| 1885 | } | ||
| 1886 | |||
| 1887 | dev_dbg(bdc->dev, "%s Enabling %s\n", __func__, ep->name); | ||
| 1888 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 1889 | ep->desc = desc; | ||
| 1890 | ep->comp_desc = _ep->comp_desc; | ||
| 1891 | ret = bdc_ep_enable(ep); | ||
| 1892 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 1893 | |||
| 1894 | return ret; | ||
| 1895 | } | ||
| 1896 | |||
| 1897 | static int bdc_gadget_ep_disable(struct usb_ep *_ep) | ||
| 1898 | { | ||
| 1899 | unsigned long flags; | ||
| 1900 | struct bdc_ep *ep; | ||
| 1901 | struct bdc *bdc; | ||
| 1902 | int ret; | ||
| 1903 | |||
| 1904 | if (!_ep) { | ||
| 1905 | pr_debug("bdc: invalid parameters\n"); | ||
| 1906 | return -EINVAL; | ||
| 1907 | } | ||
| 1908 | ep = to_bdc_ep(_ep); | ||
| 1909 | bdc = ep->bdc; | ||
| 1910 | |||
| 1911 | /* Upper layer will not call this for ep0, but do a sanity check */ | ||
| 1912 | if (ep == bdc->bdc_ep_array[1]) { | ||
| 1913 | dev_warn(bdc->dev, "%s called for ep0\n", __func__); | ||
| 1914 | return -EINVAL; | ||
| 1915 | } | ||
| 1916 | dev_dbg(bdc->dev, | ||
| 1917 | "%s() ep:%s ep->flags:%08x\n", | ||
| 1918 | __func__, ep->name, ep->flags); | ||
| 1919 | |||
| 1920 | if (!(ep->flags & BDC_EP_ENABLED)) { | ||
| 1921 | dev_warn(bdc->dev, "%s is already disabled\n", ep->name); | ||
| 1922 | return 0; | ||
| 1923 | } | ||
| 1924 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 1925 | ret = bdc_ep_disable(ep); | ||
| 1926 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 1927 | |||
| 1928 | return ret; | ||
| 1929 | } | ||
| 1930 | |||
| 1931 | static const struct usb_ep_ops bdc_gadget_ep_ops = { | ||
| 1932 | .enable = bdc_gadget_ep_enable, | ||
| 1933 | .disable = bdc_gadget_ep_disable, | ||
| 1934 | .alloc_request = bdc_gadget_alloc_request, | ||
| 1935 | .free_request = bdc_gadget_free_request, | ||
| 1936 | .queue = bdc_gadget_ep_queue, | ||
| 1937 | .dequeue = bdc_gadget_ep_dequeue, | ||
| 1938 | .set_halt = bdc_gadget_ep_set_halt | ||
| 1939 | }; | ||
| 1940 | |||
| 1941 | /* dir = 1 is IN */ | ||
| 1942 | static int init_ep(struct bdc *bdc, u32 epnum, u32 dir) | ||
| 1943 | { | ||
| 1944 | struct bdc_ep *ep; | ||
| 1945 | |||
| 1946 | dev_dbg(bdc->dev, "%s epnum=%d dir=%d\n", __func__, epnum, dir); | ||
| 1947 | ep = kzalloc(sizeof(*ep), GFP_KERNEL); | ||
| 1948 | if (!ep) | ||
| 1949 | return -ENOMEM; | ||
| 1950 | |||
| 1951 | ep->bdc = bdc; | ||
| 1952 | ep->dir = dir; | ||
| 1953 | |||
| 1954 | /* ep->ep_num is the index inside bdc_ep */ | ||
| 1955 | if (epnum == 1) { | ||
| 1956 | ep->ep_num = 1; | ||
| 1957 | bdc->bdc_ep_array[ep->ep_num] = ep; | ||
| 1958 | snprintf(ep->name, sizeof(ep->name), "ep%d", epnum - 1); | ||
| 1959 | usb_ep_set_maxpacket_limit(&ep->usb_ep, EP0_MAX_PKT_SIZE); | ||
| 1960 | ep->comp_desc = NULL; | ||
| 1961 | bdc->gadget.ep0 = &ep->usb_ep; | ||
| 1962 | } else { | ||
| 1963 | if (dir) | ||
| 1964 | ep->ep_num = epnum * 2 - 1; | ||
| 1965 | else | ||
| 1966 | ep->ep_num = epnum * 2 - 2; | ||
| 1967 | |||
| 1968 | bdc->bdc_ep_array[ep->ep_num] = ep; | ||
| 1969 | snprintf(ep->name, sizeof(ep->name), "ep%d%s", epnum - 1, | ||
| 1970 | dir & 1 ? "in" : "out"); | ||
| 1971 | |||
| 1972 | usb_ep_set_maxpacket_limit(&ep->usb_ep, 1024); | ||
| 1973 | ep->usb_ep.max_streams = 0; | ||
| 1974 | list_add_tail(&ep->usb_ep.ep_list, &bdc->gadget.ep_list); | ||
| 1975 | } | ||
| 1976 | ep->usb_ep.ops = &bdc_gadget_ep_ops; | ||
| 1977 | ep->usb_ep.name = ep->name; | ||
| 1978 | ep->flags = 0; | ||
| 1979 | ep->ignore_next_sr = false; | ||
| 1980 | dev_dbg(bdc->dev, "ep=%p ep->usb_ep.name=%s epnum=%d ep->epnum=%d\n", | ||
| 1981 | ep, ep->usb_ep.name, epnum, ep->ep_num); | ||
| 1982 | |||
| 1983 | INIT_LIST_HEAD(&ep->queue); | ||
| 1984 | |||
| 1985 | return 0; | ||
| 1986 | } | ||
| 1987 | |||
| 1988 | /* Init all ep */ | ||
| 1989 | int bdc_init_ep(struct bdc *bdc) | ||
| 1990 | { | ||
| 1991 | u8 epnum; | ||
| 1992 | int ret; | ||
| 1993 | |||
| 1994 | dev_dbg(bdc->dev, "%s()\n", __func__); | ||
| 1995 | INIT_LIST_HEAD(&bdc->gadget.ep_list); | ||
| 1996 | /* init ep0 */ | ||
| 1997 | ret = init_ep(bdc, 1, 0); | ||
| 1998 | if (ret) { | ||
| 1999 | dev_err(bdc->dev, "init ep ep0 fail %d\n", ret); | ||
| 2000 | return ret; | ||
| 2001 | } | ||
| 2002 | |||
| 2003 | for (epnum = 2; epnum <= bdc->num_eps / 2; epnum++) { | ||
| 2004 | /* OUT */ | ||
| 2005 | ret = init_ep(bdc, epnum, 0); | ||
| 2006 | if (ret) { | ||
| 2007 | dev_err(bdc->dev, | ||
| 2008 | "init ep failed for:%d error: %d\n", | ||
| 2009 | epnum, ret); | ||
| 2010 | return ret; | ||
| 2011 | } | ||
| 2012 | |||
| 2013 | /* IN */ | ||
| 2014 | ret = init_ep(bdc, epnum, 1); | ||
| 2015 | if (ret) { | ||
| 2016 | dev_err(bdc->dev, | ||
| 2017 | "init ep failed for:%d error: %d\n", | ||
| 2018 | epnum, ret); | ||
| 2019 | return ret; | ||
| 2020 | } | ||
| 2021 | } | ||
| 2022 | |||
| 2023 | return 0; | ||
| 2024 | } | ||
diff --git a/drivers/usb/gadget/udc/bdc/bdc_ep.h b/drivers/usb/gadget/udc/bdc/bdc_ep.h new file mode 100644 index 000000000000..8a6b36cbf2ea --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/bdc_ep.h | |||
| @@ -0,0 +1,22 @@ | |||
| 1 | /* | ||
| 2 | * bdc_ep.h - header for the BDC debug functions | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Broadcom Corporation | ||
| 5 | * | ||
| 6 | * Author: Ashwini Pahuja | ||
| 7 | * | ||
| 8 | * This program is free software; you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | * | ||
| 13 | */ | ||
| 14 | #ifndef __LINUX_BDC_EP_H__ | ||
| 15 | #define __LINUX_BDC_EP_H__ | ||
| 16 | |||
| 17 | int bdc_init_ep(struct bdc *); | ||
| 18 | int bdc_ep_disable(struct bdc_ep *); | ||
| 19 | int bdc_ep_enable(struct bdc_ep *); | ||
| 20 | void bdc_free_ep(struct bdc *); | ||
| 21 | |||
| 22 | #endif /* __LINUX_BDC_EP_H__ */ | ||
diff --git a/drivers/usb/gadget/udc/bdc/bdc_pci.c b/drivers/usb/gadget/udc/bdc/bdc_pci.c new file mode 100644 index 000000000000..02968842b359 --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/bdc_pci.c | |||
| @@ -0,0 +1,132 @@ | |||
| 1 | /* | ||
| 2 | * bdc_pci.c - BRCM BDC USB3.0 device controller PCI interface file. | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Broadcom Corporation | ||
| 5 | * | ||
| 6 | * Author: Ashwini Pahuja | ||
| 7 | * | ||
| 8 | * Based on drivers under drivers/usb/ | ||
| 9 | * | ||
| 10 | * This program is free software; you can redistribute it and/or modify it | ||
| 11 | * under the terms of the GNU General Public License as published by the | ||
| 12 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 13 | * option) any later version. | ||
| 14 | * | ||
| 15 | */ | ||
| 16 | |||
| 17 | #include <linux/kernel.h> | ||
| 18 | #include <linux/module.h> | ||
| 19 | #include <linux/slab.h> | ||
| 20 | #include <linux/pci.h> | ||
| 21 | #include <linux/pci_ids.h> | ||
| 22 | #include <linux/platform_device.h> | ||
| 23 | |||
| 24 | #include "bdc.h" | ||
| 25 | |||
| 26 | #define BDC_PCI_PID 0x1570 | ||
| 27 | |||
| 28 | struct bdc_pci { | ||
| 29 | struct device *dev; | ||
| 30 | struct platform_device *bdc; | ||
| 31 | }; | ||
| 32 | |||
| 33 | static int bdc_setup_msi(struct pci_dev *pci) | ||
| 34 | { | ||
| 35 | int ret; | ||
| 36 | |||
| 37 | ret = pci_enable_msi(pci); | ||
| 38 | if (ret) { | ||
| 39 | pr_err("failed to allocate MSI entry\n"); | ||
| 40 | return ret; | ||
| 41 | } | ||
| 42 | |||
| 43 | return ret; | ||
| 44 | } | ||
| 45 | |||
| 46 | static int bdc_pci_probe(struct pci_dev *pci, const struct pci_device_id *id) | ||
| 47 | { | ||
| 48 | struct resource res[2]; | ||
| 49 | struct platform_device *bdc; | ||
| 50 | struct bdc_pci *glue; | ||
| 51 | int ret = -ENOMEM; | ||
| 52 | |||
| 53 | glue = devm_kzalloc(&pci->dev, sizeof(*glue), GFP_KERNEL); | ||
| 54 | if (!glue) | ||
| 55 | return -ENOMEM; | ||
| 56 | |||
| 57 | glue->dev = &pci->dev; | ||
| 58 | ret = pci_enable_device(pci); | ||
| 59 | if (ret) { | ||
| 60 | dev_err(&pci->dev, "failed to enable pci device\n"); | ||
| 61 | return -ENODEV; | ||
| 62 | } | ||
| 63 | pci_set_master(pci); | ||
| 64 | |||
| 65 | bdc = platform_device_alloc(BRCM_BDC_NAME, PLATFORM_DEVID_AUTO); | ||
| 66 | if (!bdc) | ||
| 67 | return -ENOMEM; | ||
| 68 | |||
| 69 | memset(res, 0x00, sizeof(struct resource) * ARRAY_SIZE(res)); | ||
| 70 | bdc_setup_msi(pci); | ||
| 71 | |||
| 72 | res[0].start = pci_resource_start(pci, 0); | ||
| 73 | res[0].end = pci_resource_end(pci, 0); | ||
| 74 | res[0].name = BRCM_BDC_NAME; | ||
| 75 | res[0].flags = IORESOURCE_MEM; | ||
| 76 | |||
| 77 | res[1].start = pci->irq; | ||
| 78 | res[1].name = BRCM_BDC_NAME; | ||
| 79 | res[1].flags = IORESOURCE_IRQ; | ||
| 80 | |||
| 81 | ret = platform_device_add_resources(bdc, res, ARRAY_SIZE(res)); | ||
| 82 | if (ret) { | ||
| 83 | dev_err(&pci->dev, | ||
| 84 | "couldn't add resources to bdc device\n"); | ||
| 85 | return ret; | ||
| 86 | } | ||
| 87 | |||
| 88 | pci_set_drvdata(pci, glue); | ||
| 89 | |||
| 90 | dma_set_coherent_mask(&bdc->dev, pci->dev.coherent_dma_mask); | ||
| 91 | |||
| 92 | bdc->dev.dma_mask = pci->dev.dma_mask; | ||
| 93 | bdc->dev.dma_parms = pci->dev.dma_parms; | ||
| 94 | bdc->dev.parent = &pci->dev; | ||
| 95 | glue->bdc = bdc; | ||
| 96 | |||
| 97 | ret = platform_device_add(bdc); | ||
| 98 | if (ret) { | ||
| 99 | dev_err(&pci->dev, "failed to register bdc device\n"); | ||
| 100 | platform_device_put(bdc); | ||
| 101 | return ret; | ||
| 102 | } | ||
| 103 | |||
| 104 | return 0; | ||
| 105 | } | ||
| 106 | |||
| 107 | static void bdc_pci_remove(struct pci_dev *pci) | ||
| 108 | { | ||
| 109 | struct bdc_pci *glue = pci_get_drvdata(pci); | ||
| 110 | |||
| 111 | platform_device_unregister(glue->bdc); | ||
| 112 | pci_disable_msi(pci); | ||
| 113 | } | ||
| 114 | |||
| 115 | static struct pci_device_id bdc_pci_id_table[] = { | ||
| 116 | { PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BDC_PCI_PID), }, | ||
| 117 | {} /* Terminating Entry */ | ||
| 118 | }; | ||
| 119 | |||
| 120 | MODULE_DEVICE_TABLE(pci, bdc_pci_id_table); | ||
| 121 | |||
| 122 | static struct pci_driver bdc_pci_driver = { | ||
| 123 | .name = "bdc-pci", | ||
| 124 | .id_table = bdc_pci_id_table, | ||
| 125 | .probe = bdc_pci_probe, | ||
| 126 | .remove = bdc_pci_remove, | ||
| 127 | }; | ||
| 128 | |||
| 129 | MODULE_AUTHOR("Ashwini Pahuja <ashwini.linux@gmail.com>"); | ||
| 130 | MODULE_LICENSE("GPL"); | ||
| 131 | MODULE_DESCRIPTION("BRCM BDC USB3 PCI Glue layer"); | ||
| 132 | module_pci_driver(bdc_pci_driver); | ||
diff --git a/drivers/usb/gadget/udc/bdc/bdc_udc.c b/drivers/usb/gadget/udc/bdc/bdc_udc.c new file mode 100644 index 000000000000..3700ce70b0be --- /dev/null +++ b/drivers/usb/gadget/udc/bdc/bdc_udc.c | |||
| @@ -0,0 +1,587 @@ | |||
| 1 | /* | ||
| 2 | * bdc_udc.c - BRCM BDC USB3.0 device controller gagdet ops | ||
| 3 | * | ||
| 4 | * Copyright (C) 2014 Broadcom Corporation | ||
| 5 | * | ||
| 6 | * Author: Ashwini Pahuja | ||
| 7 | * | ||
| 8 | * Based on drivers under drivers/usb/gadget/udc/ | ||
| 9 | * | ||
| 10 | * This program is free software; you can redistribute it and/or modify it | ||
| 11 | * under the terms of the GNU General Public License as published by the | ||
| 12 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 13 | * option) any later version. | ||
| 14 | * | ||
| 15 | */ | ||
| 16 | #include <linux/module.h> | ||
| 17 | #include <linux/pci.h> | ||
| 18 | #include <linux/dma-mapping.h> | ||
| 19 | #include <linux/kernel.h> | ||
| 20 | #include <linux/delay.h> | ||
| 21 | #include <linux/ioport.h> | ||
| 22 | #include <linux/sched.h> | ||
| 23 | #include <linux/slab.h> | ||
| 24 | #include <linux/errno.h> | ||
| 25 | #include <linux/init.h> | ||
| 26 | #include <linux/timer.h> | ||
| 27 | #include <linux/list.h> | ||
| 28 | #include <linux/interrupt.h> | ||
| 29 | #include <linux/moduleparam.h> | ||
| 30 | #include <linux/device.h> | ||
| 31 | #include <linux/usb/ch9.h> | ||
| 32 | #include <linux/usb/gadget.h> | ||
| 33 | #include <linux/usb/otg.h> | ||
| 34 | #include <linux/pm.h> | ||
| 35 | #include <linux/io.h> | ||
| 36 | #include <linux/irq.h> | ||
| 37 | #include <asm/unaligned.h> | ||
| 38 | #include <linux/platform_device.h> | ||
| 39 | |||
| 40 | #include "bdc.h" | ||
| 41 | #include "bdc_ep.h" | ||
| 42 | #include "bdc_cmd.h" | ||
| 43 | #include "bdc_dbg.h" | ||
| 44 | |||
| 45 | static const struct usb_gadget_ops bdc_gadget_ops; | ||
| 46 | |||
| 47 | static const char * const conn_speed_str[] = { | ||
| 48 | "Not connected", | ||
| 49 | "Full Speed", | ||
| 50 | "Low Speed", | ||
| 51 | "High Speed", | ||
| 52 | "Super Speed", | ||
| 53 | }; | ||
| 54 | |||
| 55 | /* EP0 initial descripror */ | ||
| 56 | static struct usb_endpoint_descriptor bdc_gadget_ep0_desc = { | ||
| 57 | .bLength = USB_DT_ENDPOINT_SIZE, | ||
| 58 | .bDescriptorType = USB_DT_ENDPOINT, | ||
| 59 | .bmAttributes = USB_ENDPOINT_XFER_CONTROL, | ||
| 60 | .bEndpointAddress = 0, | ||
| 61 | .wMaxPacketSize = cpu_to_le16(EP0_MAX_PKT_SIZE), | ||
| 62 | }; | ||
| 63 | |||
| 64 | /* Advance the srr dqp maintained by SW */ | ||
| 65 | static void srr_dqp_index_advc(struct bdc *bdc, u32 srr_num) | ||
| 66 | { | ||
| 67 | struct srr *srr; | ||
| 68 | |||
| 69 | srr = &bdc->srr; | ||
| 70 | dev_dbg_ratelimited(bdc->dev, "srr->dqp_index:%d\n", srr->dqp_index); | ||
| 71 | srr->dqp_index++; | ||
| 72 | /* rollback to 0 if we are past the last */ | ||
| 73 | if (srr->dqp_index == NUM_SR_ENTRIES) | ||
| 74 | srr->dqp_index = 0; | ||
| 75 | } | ||
| 76 | |||
| 77 | /* connect sr */ | ||
| 78 | static void bdc_uspc_connected(struct bdc *bdc) | ||
| 79 | { | ||
| 80 | u32 speed, temp; | ||
| 81 | u32 usppms; | ||
| 82 | int ret; | ||
| 83 | |||
| 84 | temp = bdc_readl(bdc->regs, BDC_USPC); | ||
| 85 | speed = BDC_PSP(temp); | ||
| 86 | dev_dbg(bdc->dev, "%s speed=%x\n", __func__, speed); | ||
| 87 | switch (speed) { | ||
| 88 | case BDC_SPEED_SS: | ||
| 89 | bdc_gadget_ep0_desc.wMaxPacketSize = | ||
| 90 | cpu_to_le16(EP0_MAX_PKT_SIZE); | ||
| 91 | bdc->gadget.ep0->maxpacket = EP0_MAX_PKT_SIZE; | ||
| 92 | bdc->gadget.speed = USB_SPEED_SUPER; | ||
| 93 | /* Enable U1T in SS mode */ | ||
| 94 | usppms = bdc_readl(bdc->regs, BDC_USPPMS); | ||
| 95 | usppms &= ~BDC_U1T(0xff); | ||
| 96 | usppms |= BDC_U1T(U1_TIMEOUT); | ||
| 97 | usppms |= BDC_PORT_W1S; | ||
| 98 | bdc_writel(bdc->regs, BDC_USPPMS, usppms); | ||
| 99 | break; | ||
| 100 | |||
| 101 | case BDC_SPEED_HS: | ||
| 102 | bdc_gadget_ep0_desc.wMaxPacketSize = cpu_to_le16(64); | ||
| 103 | bdc->gadget.ep0->maxpacket = 64; | ||
| 104 | bdc->gadget.speed = USB_SPEED_HIGH; | ||
| 105 | break; | ||
| 106 | |||
| 107 | case BDC_SPEED_FS: | ||
| 108 | bdc_gadget_ep0_desc.wMaxPacketSize = cpu_to_le16(64); | ||
| 109 | bdc->gadget.ep0->maxpacket = 64; | ||
| 110 | bdc->gadget.speed = USB_SPEED_FULL; | ||
| 111 | break; | ||
| 112 | |||
| 113 | case BDC_SPEED_LS: | ||
| 114 | bdc_gadget_ep0_desc.wMaxPacketSize = cpu_to_le16(8); | ||
| 115 | bdc->gadget.ep0->maxpacket = 8; | ||
| 116 | bdc->gadget.speed = USB_SPEED_LOW; | ||
| 117 | break; | ||
| 118 | default: | ||
| 119 | dev_err(bdc->dev, "UNDEFINED SPEED\n"); | ||
| 120 | return; | ||
| 121 | } | ||
| 122 | dev_dbg(bdc->dev, "connected at %s\n", conn_speed_str[speed]); | ||
| 123 | /* Now we know the speed, configure ep0 */ | ||
| 124 | bdc->bdc_ep_array[1]->desc = &bdc_gadget_ep0_desc; | ||
| 125 | ret = bdc_config_ep(bdc, bdc->bdc_ep_array[1]); | ||
| 126 | if (ret) | ||
| 127 | dev_err(bdc->dev, "EP0 config failed\n"); | ||
| 128 | bdc->bdc_ep_array[1]->usb_ep.desc = &bdc_gadget_ep0_desc; | ||
| 129 | bdc->bdc_ep_array[1]->flags |= BDC_EP_ENABLED; | ||
| 130 | usb_gadget_set_state(&bdc->gadget, USB_STATE_DEFAULT); | ||
| 131 | } | ||
| 132 | |||
| 133 | /* device got disconnected */ | ||
| 134 | static void bdc_uspc_disconnected(struct bdc *bdc, bool reinit) | ||
| 135 | { | ||
| 136 | struct bdc_ep *ep; | ||
| 137 | |||
| 138 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 139 | /* | ||
| 140 | * Only stop ep0 from here, rest of the endpoints will be disabled | ||
| 141 | * from gadget_disconnect | ||
| 142 | */ | ||
| 143 | ep = bdc->bdc_ep_array[1]; | ||
| 144 | if (ep && (ep->flags & BDC_EP_ENABLED)) | ||
| 145 | /* if enabled then stop and remove requests */ | ||
| 146 | bdc_ep_disable(ep); | ||
| 147 | |||
| 148 | if (bdc->gadget_driver && bdc->gadget_driver->disconnect) { | ||
| 149 | spin_unlock(&bdc->lock); | ||
| 150 | bdc->gadget_driver->disconnect(&bdc->gadget); | ||
| 151 | spin_lock(&bdc->lock); | ||
| 152 | } | ||
| 153 | /* Set Unknown speed */ | ||
| 154 | bdc->gadget.speed = USB_SPEED_UNKNOWN; | ||
| 155 | bdc->devstatus &= DEVSTATUS_CLEAR; | ||
| 156 | bdc->delayed_status = false; | ||
| 157 | bdc->reinit = reinit; | ||
| 158 | bdc->test_mode = false; | ||
| 159 | } | ||
| 160 | |||
| 161 | /* TNotify wkaeup timer */ | ||
| 162 | static void bdc_func_wake_timer(struct work_struct *work) | ||
| 163 | { | ||
| 164 | struct bdc *bdc = container_of(work, struct bdc, func_wake_notify.work); | ||
| 165 | unsigned long flags; | ||
| 166 | |||
| 167 | dev_dbg(bdc->dev, "%s\n", __func__); | ||
| 168 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 169 | /* | ||
| 170 | * Check if host has started transferring on endpoints | ||
| 171 | * FUNC_WAKE_ISSUED is cleared when transfer has started after resume | ||
| 172 | */ | ||
| 173 | if (bdc->devstatus & FUNC_WAKE_ISSUED) { | ||
| 174 | dev_dbg(bdc->dev, "FUNC_WAKE_ISSUED FLAG IS STILL SET\n"); | ||
| 175 | /* flag is still set, so again send func wake */ | ||
| 176 | bdc_function_wake_fh(bdc, 0); | ||
| 177 | schedule_delayed_work(&bdc->func_wake_notify, | ||
| 178 | msecs_to_jiffies(BDC_TNOTIFY)); | ||
| 179 | } | ||
| 180 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 181 | } | ||
| 182 | |||
| 183 | /* handler for Link state change condition */ | ||
| 184 | static void handle_link_state_change(struct bdc *bdc, u32 uspc) | ||
| 185 | { | ||
| 186 | u32 link_state; | ||
| 187 | |||
| 188 | dev_dbg(bdc->dev, "Link state change"); | ||
| 189 | link_state = BDC_PST(uspc); | ||
| 190 | switch (link_state) { | ||
| 191 | case BDC_LINK_STATE_U3: | ||
| 192 | if ((bdc->gadget.speed != USB_SPEED_UNKNOWN) && | ||
| 193 | bdc->gadget_driver->suspend) { | ||
| 194 | dev_dbg(bdc->dev, "Entered Suspend mode\n"); | ||
| 195 | spin_unlock(&bdc->lock); | ||
| 196 | bdc->devstatus |= DEVICE_SUSPENDED; | ||
| 197 | bdc->gadget_driver->suspend(&bdc->gadget); | ||
| 198 | spin_lock(&bdc->lock); | ||
| 199 | } | ||
| 200 | break; | ||
| 201 | case BDC_LINK_STATE_U0: | ||
| 202 | if (bdc->devstatus & REMOTE_WAKEUP_ISSUED) { | ||
| 203 | bdc->devstatus &= ~REMOTE_WAKEUP_ISSUED; | ||
| 204 | if (bdc->gadget.speed == USB_SPEED_SUPER) { | ||
| 205 | bdc_function_wake_fh(bdc, 0); | ||
| 206 | bdc->devstatus |= FUNC_WAKE_ISSUED; | ||
| 207 | /* | ||
| 208 | * Start a Notification timer and check if the | ||
| 209 | * Host transferred anything on any of the EPs, | ||
| 210 | * if not then send function wake again every | ||
| 211 | * TNotification secs until host initiates | ||
| 212 | * transfer to BDC, USB3 spec Table 8.13 | ||
| 213 | */ | ||
| 214 | schedule_delayed_work( | ||
| 215 | &bdc->func_wake_notify, | ||
| 216 | msecs_to_jiffies(BDC_TNOTIFY)); | ||
| 217 | dev_dbg(bdc->dev, "sched func_wake_notify\n"); | ||
| 218 | } | ||
| 219 | } | ||
| 220 | break; | ||
| 221 | |||
| 222 | case BDC_LINK_STATE_RESUME: | ||
| 223 | dev_dbg(bdc->dev, "Resumed from Suspend\n"); | ||
| 224 | if (bdc->devstatus & DEVICE_SUSPENDED) { | ||
| 225 | bdc->gadget_driver->resume(&bdc->gadget); | ||
| 226 | bdc->devstatus &= ~DEVICE_SUSPENDED; | ||
| 227 | } | ||
| 228 | break; | ||
| 229 | default: | ||
| 230 | dev_dbg(bdc->dev, "link state:%d\n", link_state); | ||
| 231 | } | ||
| 232 | } | ||
| 233 | |||
| 234 | /* something changes on upstream port, handle it here */ | ||
| 235 | void bdc_sr_uspc(struct bdc *bdc, struct bdc_sr *sreport) | ||
| 236 | { | ||
| 237 | u32 clear_flags = 0; | ||
| 238 | u32 uspc; | ||
| 239 | bool connected = false; | ||
| 240 | bool disconn = false; | ||
| 241 | |||
| 242 | uspc = bdc_readl(bdc->regs, BDC_USPC); | ||
| 243 | dev_dbg(bdc->dev, "%s uspc=0x%08x\n", __func__, uspc); | ||
| 244 | |||
| 245 | /* Port connect changed */ | ||
| 246 | if (uspc & BDC_PCC) { | ||
| 247 | /* Vbus not present, and not connected to Downstream port */ | ||
| 248 | if ((uspc & BDC_VBC) && !(uspc & BDC_VBS) && !(uspc & BDC_PCS)) | ||
| 249 | disconn = true; | ||
| 250 | else if ((uspc & BDC_PCS) && !BDC_PST(uspc)) | ||
| 251 | connected = true; | ||
| 252 | } | ||
| 253 | |||
| 254 | /* Change in VBus and VBus is present */ | ||
| 255 | if ((uspc & BDC_VBC) && (uspc & BDC_VBS)) { | ||
| 256 | if (bdc->pullup) { | ||
| 257 | dev_dbg(bdc->dev, "Do a softconnect\n"); | ||
| 258 | /* Attached state, do a softconnect */ | ||
| 259 | bdc_softconn(bdc); | ||
| 260 | usb_gadget_set_state(&bdc->gadget, USB_STATE_POWERED); | ||
| 261 | } | ||
| 262 | clear_flags = BDC_VBC; | ||
| 263 | } else if ((uspc & BDC_PRS) || (uspc & BDC_PRC) || disconn) { | ||
| 264 | /* Hot reset, warm reset, 2.0 bus reset or disconn */ | ||
| 265 | dev_dbg(bdc->dev, "Port reset or disconn\n"); | ||
| 266 | bdc_uspc_disconnected(bdc, disconn); | ||
| 267 | clear_flags = BDC_PCC|BDC_PCS|BDC_PRS|BDC_PRC; | ||
| 268 | } else if ((uspc & BDC_PSC) && (uspc & BDC_PCS)) { | ||
| 269 | /* Change in Link state */ | ||
| 270 | handle_link_state_change(bdc, uspc); | ||
| 271 | clear_flags = BDC_PSC|BDC_PCS; | ||
| 272 | } | ||
| 273 | |||
| 274 | /* | ||
| 275 | * In SS we might not have PRC bit set before connection, but in 2.0 | ||
| 276 | * the PRC bit is set before connection, so moving this condition out | ||
| 277 | * of bus reset to handle both SS/2.0 speeds. | ||
| 278 | */ | ||
| 279 | if (connected) { | ||
| 280 | /* This is the connect event for U0/L0 */ | ||
| 281 | dev_dbg(bdc->dev, "Connected\n"); | ||
| 282 | bdc_uspc_connected(bdc); | ||
| 283 | bdc->devstatus &= ~(DEVICE_SUSPENDED); | ||
| 284 | } | ||
| 285 | uspc = bdc_readl(bdc->regs, BDC_USPC); | ||
| 286 | uspc &= (~BDC_USPSC_RW); | ||
| 287 | dev_dbg(bdc->dev, "uspc=%x\n", uspc); | ||
| 288 | bdc_writel(bdc->regs, BDC_USPC, clear_flags); | ||
| 289 | } | ||
| 290 | |||
| 291 | /* Main interrupt handler for bdc */ | ||
| 292 | static irqreturn_t bdc_udc_interrupt(int irq, void *_bdc) | ||
| 293 | { | ||
| 294 | u32 eqp_index, dqp_index, sr_type, srr_int; | ||
| 295 | struct bdc_sr *sreport; | ||
| 296 | struct bdc *bdc = _bdc; | ||
| 297 | u32 status; | ||
| 298 | int ret; | ||
| 299 | |||
| 300 | spin_lock(&bdc->lock); | ||
| 301 | status = bdc_readl(bdc->regs, BDC_BDCSC); | ||
| 302 | if (!(status & BDC_GIP)) { | ||
| 303 | spin_unlock(&bdc->lock); | ||
| 304 | return IRQ_NONE; | ||
| 305 | } | ||
| 306 | srr_int = bdc_readl(bdc->regs, BDC_SRRINT(0)); | ||
| 307 | /* Check if the SRR IP bit it set? */ | ||
| 308 | if (!(srr_int & BDC_SRR_IP)) { | ||
| 309 | dev_warn(bdc->dev, "Global irq pending but SRR IP is 0\n"); | ||
| 310 | spin_unlock(&bdc->lock); | ||
| 311 | return IRQ_NONE; | ||
| 312 | } | ||
| 313 | eqp_index = BDC_SRR_EPI(srr_int); | ||
| 314 | dqp_index = BDC_SRR_DPI(srr_int); | ||
| 315 | dev_dbg(bdc->dev, | ||
| 316 | "%s eqp_index=%d dqp_index=%d srr.dqp_index=%d\n\n", | ||
| 317 | __func__, eqp_index, dqp_index, bdc->srr.dqp_index); | ||
| 318 | |||
| 319 | /* check for ring empty condition */ | ||
| 320 | if (eqp_index == dqp_index) { | ||
| 321 | dev_dbg(bdc->dev, "SRR empty?\n"); | ||
| 322 | spin_unlock(&bdc->lock); | ||
| 323 | return IRQ_HANDLED; | ||
| 324 | } | ||
| 325 | |||
| 326 | while (bdc->srr.dqp_index != eqp_index) { | ||
| 327 | sreport = &bdc->srr.sr_bds[bdc->srr.dqp_index]; | ||
| 328 | /* sreport is read before using it */ | ||
| 329 | rmb(); | ||
| 330 | sr_type = le32_to_cpu(sreport->offset[3]) & BD_TYPE_BITMASK; | ||
| 331 | dev_dbg_ratelimited(bdc->dev, "sr_type=%d\n", sr_type); | ||
| 332 | switch (sr_type) { | ||
| 333 | case SR_XSF: | ||
| 334 | bdc->sr_handler[0](bdc, sreport); | ||
| 335 | break; | ||
| 336 | |||
| 337 | case SR_USPC: | ||
| 338 | bdc->sr_handler[1](bdc, sreport); | ||
| 339 | break; | ||
| 340 | default: | ||
| 341 | dev_warn(bdc->dev, "SR:%d not handled\n", sr_type); | ||
| 342 | } | ||
| 343 | /* Advance the srr dqp index */ | ||
| 344 | srr_dqp_index_advc(bdc, 0); | ||
| 345 | } | ||
| 346 | /* update the hw dequeue pointer */ | ||
| 347 | srr_int = bdc_readl(bdc->regs, BDC_SRRINT(0)); | ||
| 348 | srr_int &= ~BDC_SRR_DPI_MASK; | ||
| 349 | srr_int &= ~(BDC_SRR_RWS|BDC_SRR_RST|BDC_SRR_ISR); | ||
| 350 | srr_int |= ((bdc->srr.dqp_index) << 16); | ||
| 351 | srr_int |= BDC_SRR_IP; | ||
| 352 | bdc_writel(bdc->regs, BDC_SRRINT(0), srr_int); | ||
| 353 | srr_int = bdc_readl(bdc->regs, BDC_SRRINT(0)); | ||
| 354 | if (bdc->reinit) { | ||
| 355 | ret = bdc_reinit(bdc); | ||
| 356 | if (ret) | ||
| 357 | dev_err(bdc->dev, "err in bdc reinit\n"); | ||
| 358 | } | ||
| 359 | |||
| 360 | spin_unlock(&bdc->lock); | ||
| 361 | |||
| 362 | return IRQ_HANDLED; | ||
| 363 | } | ||
| 364 | |||
| 365 | /* Gadget ops */ | ||
| 366 | static int bdc_udc_start(struct usb_gadget *gadget, | ||
| 367 | struct usb_gadget_driver *driver) | ||
| 368 | { | ||
| 369 | struct bdc *bdc = gadget_to_bdc(gadget); | ||
| 370 | unsigned long flags; | ||
| 371 | int ret = 0; | ||
| 372 | |||
| 373 | dev_dbg(bdc->dev, "%s()\n", __func__); | ||
| 374 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 375 | if (bdc->gadget_driver) { | ||
| 376 | dev_err(bdc->dev, "%s is already bound to %s\n", | ||
| 377 | bdc->gadget.name, | ||
| 378 | bdc->gadget_driver->driver.name); | ||
| 379 | ret = -EBUSY; | ||
| 380 | goto err; | ||
| 381 | } | ||
| 382 | /* | ||
| 383 | * Run the controller from here and when BDC is connected to | ||
| 384 | * Host then driver will receive a USPC SR with VBUS present | ||
| 385 | * and then driver will do a softconnect. | ||
| 386 | */ | ||
| 387 | ret = bdc_run(bdc); | ||
| 388 | if (ret) { | ||
| 389 | dev_err(bdc->dev, "%s bdc run fail\n", __func__); | ||
| 390 | goto err; | ||
| 391 | } | ||
| 392 | bdc->gadget_driver = driver; | ||
| 393 | bdc->gadget.dev.driver = &driver->driver; | ||
| 394 | err: | ||
| 395 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 396 | |||
| 397 | return ret; | ||
| 398 | } | ||
| 399 | |||
| 400 | static int bdc_udc_stop(struct usb_gadget *gadget) | ||
| 401 | { | ||
| 402 | struct bdc *bdc = gadget_to_bdc(gadget); | ||
| 403 | unsigned long flags; | ||
| 404 | |||
| 405 | dev_dbg(bdc->dev, "%s()\n", __func__); | ||
| 406 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 407 | bdc_stop(bdc); | ||
| 408 | bdc->gadget_driver = NULL; | ||
| 409 | bdc->gadget.dev.driver = NULL; | ||
| 410 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 411 | |||
| 412 | return 0; | ||
| 413 | } | ||
| 414 | |||
| 415 | static int bdc_udc_pullup(struct usb_gadget *gadget, int is_on) | ||
| 416 | { | ||
| 417 | struct bdc *bdc = gadget_to_bdc(gadget); | ||
| 418 | unsigned long flags; | ||
| 419 | u32 uspc; | ||
| 420 | |||
| 421 | dev_dbg(bdc->dev, "%s() is_on:%d\n", __func__, is_on); | ||
| 422 | if (!gadget) | ||
| 423 | return -EINVAL; | ||
| 424 | |||
| 425 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 426 | if (!is_on) { | ||
| 427 | bdc_softdisconn(bdc); | ||
| 428 | bdc->pullup = false; | ||
| 429 | } else { | ||
| 430 | /* | ||
| 431 | * For a self powered device, we need to wait till we receive | ||
| 432 | * a VBUS change and Vbus present event, then if pullup flag | ||
| 433 | * is set, then only we present the Termintation. | ||
| 434 | */ | ||
| 435 | bdc->pullup = true; | ||
| 436 | /* | ||
| 437 | * Check if BDC is already connected to Host i.e Vbus=1, | ||
| 438 | * if yes, then present TERM now, this is typical for bus | ||
| 439 | * powered devices. | ||
| 440 | */ | ||
| 441 | uspc = bdc_readl(bdc->regs, BDC_USPC); | ||
| 442 | if (uspc & BDC_VBS) | ||
| 443 | bdc_softconn(bdc); | ||
| 444 | } | ||
| 445 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 446 | |||
| 447 | return 0; | ||
| 448 | } | ||
| 449 | |||
| 450 | static int bdc_udc_set_selfpowered(struct usb_gadget *gadget, | ||
| 451 | int is_self) | ||
| 452 | { | ||
| 453 | struct bdc *bdc = gadget_to_bdc(gadget); | ||
| 454 | unsigned long flags; | ||
| 455 | |||
| 456 | dev_dbg(bdc->dev, "%s()\n", __func__); | ||
| 457 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 458 | if (!is_self) | ||
| 459 | bdc->devstatus |= 1 << USB_DEVICE_SELF_POWERED; | ||
| 460 | else | ||
| 461 | bdc->devstatus &= ~(1 << USB_DEVICE_SELF_POWERED); | ||
| 462 | |||
| 463 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 464 | |||
| 465 | return 0; | ||
| 466 | } | ||
| 467 | |||
| 468 | static int bdc_udc_wakeup(struct usb_gadget *gadget) | ||
| 469 | { | ||
| 470 | struct bdc *bdc = gadget_to_bdc(gadget); | ||
| 471 | unsigned long flags; | ||
| 472 | u8 link_state; | ||
| 473 | u32 uspc; | ||
| 474 | int ret = 0; | ||
| 475 | |||
| 476 | dev_dbg(bdc->dev, | ||
| 477 | "%s() bdc->devstatus=%08x\n", | ||
| 478 | __func__, bdc->devstatus); | ||
| 479 | |||
| 480 | if (!(bdc->devstatus & REMOTE_WAKE_ENABLE)) | ||
| 481 | return -EOPNOTSUPP; | ||
| 482 | |||
| 483 | spin_lock_irqsave(&bdc->lock, flags); | ||
| 484 | uspc = bdc_readl(bdc->regs, BDC_USPC); | ||
| 485 | link_state = BDC_PST(uspc); | ||
| 486 | dev_dbg(bdc->dev, "link_state =%d portsc=%x", link_state, uspc); | ||
| 487 | if (link_state != BDC_LINK_STATE_U3) { | ||
| 488 | dev_warn(bdc->dev, | ||
| 489 | "can't wakeup from link state %d\n", | ||
| 490 | link_state); | ||
| 491 | ret = -EINVAL; | ||
| 492 | goto out; | ||
| 493 | } | ||
| 494 | if (bdc->gadget.speed == USB_SPEED_SUPER) | ||
| 495 | bdc->devstatus |= REMOTE_WAKEUP_ISSUED; | ||
| 496 | |||
| 497 | uspc &= ~BDC_PST_MASK; | ||
| 498 | uspc &= (~BDC_USPSC_RW); | ||
| 499 | uspc |= BDC_PST(BDC_LINK_STATE_U0); | ||
| 500 | uspc |= BDC_SWS; | ||
| 501 | bdc_writel(bdc->regs, BDC_USPC, uspc); | ||
| 502 | uspc = bdc_readl(bdc->regs, BDC_USPC); | ||
| 503 | link_state = BDC_PST(uspc); | ||
| 504 | dev_dbg(bdc->dev, "link_state =%d portsc=%x", link_state, uspc); | ||
| 505 | out: | ||
| 506 | spin_unlock_irqrestore(&bdc->lock, flags); | ||
| 507 | |||
| 508 | return ret; | ||
| 509 | } | ||
| 510 | |||
| 511 | static const struct usb_gadget_ops bdc_gadget_ops = { | ||
| 512 | .wakeup = bdc_udc_wakeup, | ||
| 513 | .set_selfpowered = bdc_udc_set_selfpowered, | ||
| 514 | .pullup = bdc_udc_pullup, | ||
| 515 | .udc_start = bdc_udc_start, | ||
| 516 | .udc_stop = bdc_udc_stop, | ||
| 517 | }; | ||
| 518 | |||
| 519 | /* Init the gadget interface and register the udc */ | ||
| 520 | int bdc_udc_init(struct bdc *bdc) | ||
| 521 | { | ||
| 522 | u32 temp; | ||
| 523 | int ret; | ||
| 524 | |||
| 525 | dev_dbg(bdc->dev, "%s()\n", __func__); | ||
| 526 | bdc->gadget.ops = &bdc_gadget_ops; | ||
| 527 | bdc->gadget.max_speed = USB_SPEED_SUPER; | ||
| 528 | bdc->gadget.speed = USB_SPEED_UNKNOWN; | ||
| 529 | bdc->gadget.dev.parent = bdc->dev; | ||
| 530 | |||
| 531 | bdc->gadget.sg_supported = false; | ||
| 532 | |||
| 533 | |||
| 534 | bdc->gadget.name = BRCM_BDC_NAME; | ||
| 535 | ret = devm_request_irq(bdc->dev, bdc->irq, bdc_udc_interrupt, | ||
| 536 | IRQF_SHARED , BRCM_BDC_NAME, bdc); | ||
| 537 | if (ret) { | ||
| 538 | dev_err(bdc->dev, | ||
| 539 | "failed to request irq #%d %d\n", | ||
| 540 | bdc->irq, ret); | ||
| 541 | return ret; | ||
| 542 | } | ||
| 543 | |||
| 544 | ret = bdc_init_ep(bdc); | ||
| 545 | if (ret) { | ||
| 546 | dev_err(bdc->dev, "bdc init ep fail: %d\n", ret); | ||
| 547 | return ret; | ||
| 548 | } | ||
| 549 | |||
| 550 | ret = usb_add_gadget_udc(bdc->dev, &bdc->gadget); | ||
| 551 | if (ret) { | ||
| 552 | dev_err(bdc->dev, "failed to register udc\n"); | ||
| 553 | goto err0; | ||
| 554 | } | ||
| 555 | usb_gadget_set_state(&bdc->gadget, USB_STATE_NOTATTACHED); | ||
| 556 | bdc->bdc_ep_array[1]->desc = &bdc_gadget_ep0_desc; | ||
| 557 | /* | ||
| 558 | * Allocate bd list for ep0 only, ep0 will be enabled on connect | ||
| 559 | * status report when the speed is known | ||
| 560 | */ | ||
| 561 | ret = bdc_ep_enable(bdc->bdc_ep_array[1]); | ||
| 562 | if (ret) { | ||
| 563 | dev_err(bdc->dev, "fail to enable %s\n", | ||
| 564 | bdc->bdc_ep_array[1]->name); | ||
| 565 | goto err1; | ||
| 566 | } | ||
| 567 | INIT_DELAYED_WORK(&bdc->func_wake_notify, bdc_func_wake_timer); | ||
| 568 | /* Enable Interrupts */ | ||
| 569 | temp = bdc_readl(bdc->regs, BDC_BDCSC); | ||
| 570 | temp |= BDC_GIE; | ||
| 571 | bdc_writel(bdc->regs, BDC_BDCSC, temp); | ||
| 572 | return 0; | ||
| 573 | err1: | ||
| 574 | usb_del_gadget_udc(&bdc->gadget); | ||
| 575 | err0: | ||
| 576 | bdc_free_ep(bdc); | ||
| 577 | |||
| 578 | return ret; | ||
| 579 | } | ||
| 580 | |||
| 581 | void bdc_udc_exit(struct bdc *bdc) | ||
| 582 | { | ||
| 583 | dev_dbg(bdc->dev, "%s()\n", __func__); | ||
| 584 | bdc_ep_disable(bdc->bdc_ep_array[1]); | ||
| 585 | usb_del_gadget_udc(&bdc->gadget); | ||
| 586 | bdc_free_ep(bdc); | ||
| 587 | } | ||
diff --git a/drivers/usb/gadget/udc/dummy_hcd.c b/drivers/usb/gadget/udc/dummy_hcd.c index 81dc5959e36b..1c69c760408e 100644 --- a/drivers/usb/gadget/udc/dummy_hcd.c +++ b/drivers/usb/gadget/udc/dummy_hcd.c | |||
| @@ -367,19 +367,22 @@ static void set_link_state(struct dummy_hcd *dum_hcd) | |||
| 367 | dum_hcd->active) | 367 | dum_hcd->active) |
| 368 | dum_hcd->resuming = 0; | 368 | dum_hcd->resuming = 0; |
| 369 | 369 | ||
| 370 | /* if !connected or reset */ | 370 | /* Currently !connected or in reset */ |
| 371 | if ((dum_hcd->port_status & USB_PORT_STAT_CONNECTION) == 0 || | 371 | if ((dum_hcd->port_status & USB_PORT_STAT_CONNECTION) == 0 || |
| 372 | (dum_hcd->port_status & USB_PORT_STAT_RESET) != 0) { | 372 | (dum_hcd->port_status & USB_PORT_STAT_RESET) != 0) { |
| 373 | /* | 373 | unsigned disconnect = USB_PORT_STAT_CONNECTION & |
| 374 | * We're connected and not reset (reset occurred now), | 374 | dum_hcd->old_status & (~dum_hcd->port_status); |
| 375 | * and driver attached - disconnect! | 375 | unsigned reset = USB_PORT_STAT_RESET & |
| 376 | */ | 376 | (~dum_hcd->old_status) & dum_hcd->port_status; |
| 377 | if ((dum_hcd->old_status & USB_PORT_STAT_CONNECTION) != 0 && | 377 | |
| 378 | (dum_hcd->old_status & USB_PORT_STAT_RESET) == 0 && | 378 | /* Report reset and disconnect events to the driver */ |
| 379 | dum->driver) { | 379 | if (dum->driver && (disconnect || reset)) { |
| 380 | stop_activity(dum); | 380 | stop_activity(dum); |
| 381 | spin_unlock(&dum->lock); | 381 | spin_unlock(&dum->lock); |
| 382 | dum->driver->disconnect(&dum->gadget); | 382 | if (reset) |
| 383 | usb_gadget_udc_reset(&dum->gadget, dum->driver); | ||
| 384 | else | ||
| 385 | dum->driver->disconnect(&dum->gadget); | ||
| 383 | spin_lock(&dum->lock); | 386 | spin_lock(&dum->lock); |
| 384 | } | 387 | } |
| 385 | } else if (dum_hcd->active != dum_hcd->old_active) { | 388 | } else if (dum_hcd->active != dum_hcd->old_active) { |
| @@ -851,8 +854,7 @@ static int dummy_pullup(struct usb_gadget *_gadget, int value) | |||
| 851 | 854 | ||
| 852 | static int dummy_udc_start(struct usb_gadget *g, | 855 | static int dummy_udc_start(struct usb_gadget *g, |
| 853 | struct usb_gadget_driver *driver); | 856 | struct usb_gadget_driver *driver); |
| 854 | static int dummy_udc_stop(struct usb_gadget *g, | 857 | static int dummy_udc_stop(struct usb_gadget *g); |
| 855 | struct usb_gadget_driver *driver); | ||
| 856 | 858 | ||
| 857 | static const struct usb_gadget_ops dummy_ops = { | 859 | static const struct usb_gadget_ops dummy_ops = { |
| 858 | .get_frame = dummy_g_get_frame, | 860 | .get_frame = dummy_g_get_frame, |
| @@ -908,23 +910,16 @@ static int dummy_udc_start(struct usb_gadget *g, | |||
| 908 | */ | 910 | */ |
| 909 | 911 | ||
| 910 | dum->devstatus = 0; | 912 | dum->devstatus = 0; |
| 911 | |||
| 912 | dum->driver = driver; | 913 | dum->driver = driver; |
| 913 | dev_dbg(udc_dev(dum), "binding gadget driver '%s'\n", | 914 | |
| 914 | driver->driver.name); | ||
| 915 | return 0; | 915 | return 0; |
| 916 | } | 916 | } |
| 917 | 917 | ||
| 918 | static int dummy_udc_stop(struct usb_gadget *g, | 918 | static int dummy_udc_stop(struct usb_gadget *g) |
| 919 | struct usb_gadget_driver *driver) | ||
| 920 | { | 919 | { |
| 921 | struct dummy_hcd *dum_hcd = gadget_to_dummy_hcd(g); | 920 | struct dummy_hcd *dum_hcd = gadget_to_dummy_hcd(g); |
| 922 | struct dummy *dum = dum_hcd->dum; | 921 | struct dummy *dum = dum_hcd->dum; |
| 923 | 922 | ||
| 924 | if (driver) | ||
| 925 | dev_dbg(udc_dev(dum), "unregister gadget driver '%s'\n", | ||
| 926 | driver->driver.name); | ||
| 927 | |||
| 928 | dum->driver = NULL; | 923 | dum->driver = NULL; |
| 929 | 924 | ||
| 930 | return 0; | 925 | return 0; |
| @@ -2370,7 +2365,6 @@ static void dummy_stop(struct usb_hcd *hcd) | |||
| 2370 | 2365 | ||
| 2371 | dum = hcd_to_dummy_hcd(hcd)->dum; | 2366 | dum = hcd_to_dummy_hcd(hcd)->dum; |
| 2372 | device_remove_file(dummy_dev(hcd_to_dummy_hcd(hcd)), &dev_attr_urbs); | 2367 | device_remove_file(dummy_dev(hcd_to_dummy_hcd(hcd)), &dev_attr_urbs); |
| 2373 | usb_gadget_unregister_driver(dum->driver); | ||
| 2374 | dev_info(dummy_dev(hcd_to_dummy_hcd(hcd)), "stopped\n"); | 2368 | dev_info(dummy_dev(hcd_to_dummy_hcd(hcd)), "stopped\n"); |
| 2375 | } | 2369 | } |
| 2376 | 2370 | ||
diff --git a/drivers/usb/gadget/udc/fotg210-udc.c b/drivers/usb/gadget/udc/fotg210-udc.c index 1d315921bf34..1ca52e11eb98 100644 --- a/drivers/usb/gadget/udc/fotg210-udc.c +++ b/drivers/usb/gadget/udc/fotg210-udc.c | |||
| @@ -1053,8 +1053,7 @@ static void fotg210_init(struct fotg210_udc *fotg210) | |||
| 1053 | iowrite32(value, fotg210->reg + FOTG210_DMISGR0); | 1053 | iowrite32(value, fotg210->reg + FOTG210_DMISGR0); |
| 1054 | } | 1054 | } |
| 1055 | 1055 | ||
| 1056 | static int fotg210_udc_stop(struct usb_gadget *g, | 1056 | static int fotg210_udc_stop(struct usb_gadget *g) |
| 1057 | struct usb_gadget_driver *driver) | ||
| 1058 | { | 1057 | { |
| 1059 | struct fotg210_udc *fotg210 = gadget_to_fotg210(g); | 1058 | struct fotg210_udc *fotg210 = gadget_to_fotg210(g); |
| 1060 | unsigned long flags; | 1059 | unsigned long flags; |
diff --git a/drivers/usb/gadget/udc/fsl_qe_udc.c b/drivers/usb/gadget/udc/fsl_qe_udc.c index dd18ea38e391..d201f9a89ce3 100644 --- a/drivers/usb/gadget/udc/fsl_qe_udc.c +++ b/drivers/usb/gadget/udc/fsl_qe_udc.c | |||
| @@ -1887,8 +1887,7 @@ static int qe_get_frame(struct usb_gadget *gadget) | |||
| 1887 | 1887 | ||
| 1888 | static int fsl_qe_start(struct usb_gadget *gadget, | 1888 | static int fsl_qe_start(struct usb_gadget *gadget, |
| 1889 | struct usb_gadget_driver *driver); | 1889 | struct usb_gadget_driver *driver); |
| 1890 | static int fsl_qe_stop(struct usb_gadget *gadget, | 1890 | static int fsl_qe_stop(struct usb_gadget *gadget); |
| 1891 | struct usb_gadget_driver *driver); | ||
| 1892 | 1891 | ||
| 1893 | /* defined in usb_gadget.h */ | 1892 | /* defined in usb_gadget.h */ |
| 1894 | static const struct usb_gadget_ops qe_gadget_ops = { | 1893 | static const struct usb_gadget_ops qe_gadget_ops = { |
| @@ -1918,7 +1917,7 @@ static int reset_queues(struct qe_udc *udc) | |||
| 1918 | 1917 | ||
| 1919 | /* report disconnect; the driver is already quiesced */ | 1918 | /* report disconnect; the driver is already quiesced */ |
| 1920 | spin_unlock(&udc->lock); | 1919 | spin_unlock(&udc->lock); |
| 1921 | udc->driver->disconnect(&udc->gadget); | 1920 | usb_gadget_udc_reset(&udc->gadget, udc->driver); |
| 1922 | spin_lock(&udc->lock); | 1921 | spin_lock(&udc->lock); |
| 1923 | 1922 | ||
| 1924 | return 0; | 1923 | return 0; |
| @@ -2305,13 +2304,10 @@ static int fsl_qe_start(struct usb_gadget *gadget, | |||
| 2305 | udc->ep0_dir = USB_DIR_OUT; | 2304 | udc->ep0_dir = USB_DIR_OUT; |
| 2306 | spin_unlock_irqrestore(&udc->lock, flags); | 2305 | spin_unlock_irqrestore(&udc->lock, flags); |
| 2307 | 2306 | ||
| 2308 | dev_info(udc->dev, "%s bind to driver %s\n", udc->gadget.name, | ||
| 2309 | driver->driver.name); | ||
| 2310 | return 0; | 2307 | return 0; |
| 2311 | } | 2308 | } |
| 2312 | 2309 | ||
| 2313 | static int fsl_qe_stop(struct usb_gadget *gadget, | 2310 | static int fsl_qe_stop(struct usb_gadget *gadget) |
| 2314 | struct usb_gadget_driver *driver) | ||
| 2315 | { | 2311 | { |
| 2316 | struct qe_udc *udc; | 2312 | struct qe_udc *udc; |
| 2317 | struct qe_ep *loop_ep; | 2313 | struct qe_ep *loop_ep; |
| @@ -2336,8 +2332,6 @@ static int fsl_qe_stop(struct usb_gadget *gadget, | |||
| 2336 | 2332 | ||
| 2337 | udc->driver = NULL; | 2333 | udc->driver = NULL; |
| 2338 | 2334 | ||
| 2339 | dev_info(udc->dev, "unregistered gadget driver '%s'\r\n", | ||
| 2340 | driver->driver.name); | ||
| 2341 | return 0; | 2335 | return 0; |
| 2342 | } | 2336 | } |
| 2343 | 2337 | ||
| @@ -2538,7 +2532,6 @@ static int qe_udc_probe(struct platform_device *ofdev) | |||
| 2538 | /* create a buf for ZLP send, need to remain zeroed */ | 2532 | /* create a buf for ZLP send, need to remain zeroed */ |
| 2539 | udc->nullbuf = devm_kzalloc(&ofdev->dev, 256, GFP_KERNEL); | 2533 | udc->nullbuf = devm_kzalloc(&ofdev->dev, 256, GFP_KERNEL); |
| 2540 | if (udc->nullbuf == NULL) { | 2534 | if (udc->nullbuf == NULL) { |
| 2541 | dev_err(udc->dev, "cannot alloc nullbuf\n"); | ||
| 2542 | ret = -ENOMEM; | 2535 | ret = -ENOMEM; |
| 2543 | goto err3; | 2536 | goto err3; |
| 2544 | } | 2537 | } |
diff --git a/drivers/usb/gadget/udc/fsl_udc_core.c b/drivers/usb/gadget/udc/fsl_udc_core.c index c3620791a315..f340181da23c 100644 --- a/drivers/usb/gadget/udc/fsl_udc_core.c +++ b/drivers/usb/gadget/udc/fsl_udc_core.c | |||
| @@ -1236,9 +1236,8 @@ static int fsl_pullup(struct usb_gadget *gadget, int is_on) | |||
| 1236 | 1236 | ||
| 1237 | static int fsl_udc_start(struct usb_gadget *g, | 1237 | static int fsl_udc_start(struct usb_gadget *g, |
| 1238 | struct usb_gadget_driver *driver); | 1238 | struct usb_gadget_driver *driver); |
| 1239 | static int fsl_udc_stop(struct usb_gadget *g, | 1239 | static int fsl_udc_stop(struct usb_gadget *g); |
| 1240 | struct usb_gadget_driver *driver); | 1240 | |
| 1241 | /* defined in gadget.h */ | ||
| 1242 | static const struct usb_gadget_ops fsl_gadget_ops = { | 1241 | static const struct usb_gadget_ops fsl_gadget_ops = { |
| 1243 | .get_frame = fsl_get_frame, | 1242 | .get_frame = fsl_get_frame, |
| 1244 | .wakeup = fsl_wakeup, | 1243 | .wakeup = fsl_wakeup, |
| @@ -1772,7 +1771,7 @@ static void bus_resume(struct fsl_udc *udc) | |||
| 1772 | } | 1771 | } |
| 1773 | 1772 | ||
| 1774 | /* Clear up all ep queues */ | 1773 | /* Clear up all ep queues */ |
| 1775 | static int reset_queues(struct fsl_udc *udc) | 1774 | static int reset_queues(struct fsl_udc *udc, bool bus_reset) |
| 1776 | { | 1775 | { |
| 1777 | u8 pipe; | 1776 | u8 pipe; |
| 1778 | 1777 | ||
| @@ -1781,7 +1780,10 @@ static int reset_queues(struct fsl_udc *udc) | |||
| 1781 | 1780 | ||
| 1782 | /* report disconnect; the driver is already quiesced */ | 1781 | /* report disconnect; the driver is already quiesced */ |
| 1783 | spin_unlock(&udc->lock); | 1782 | spin_unlock(&udc->lock); |
| 1784 | udc->driver->disconnect(&udc->gadget); | 1783 | if (bus_reset) |
| 1784 | usb_gadget_udc_reset(&udc->gadget, udc->driver); | ||
| 1785 | else | ||
| 1786 | udc->driver->disconnect(&udc->gadget); | ||
| 1785 | spin_lock(&udc->lock); | 1787 | spin_lock(&udc->lock); |
| 1786 | 1788 | ||
| 1787 | return 0; | 1789 | return 0; |
| @@ -1835,7 +1837,7 @@ static void reset_irq(struct fsl_udc *udc) | |||
| 1835 | udc->bus_reset = 1; | 1837 | udc->bus_reset = 1; |
| 1836 | /* Reset all the queues, include XD, dTD, EP queue | 1838 | /* Reset all the queues, include XD, dTD, EP queue |
| 1837 | * head and TR Queue */ | 1839 | * head and TR Queue */ |
| 1838 | reset_queues(udc); | 1840 | reset_queues(udc, true); |
| 1839 | udc->usb_state = USB_STATE_DEFAULT; | 1841 | udc->usb_state = USB_STATE_DEFAULT; |
| 1840 | } else { | 1842 | } else { |
| 1841 | VDBG("Controller reset"); | 1843 | VDBG("Controller reset"); |
| @@ -1844,7 +1846,7 @@ static void reset_irq(struct fsl_udc *udc) | |||
| 1844 | dr_controller_setup(udc); | 1846 | dr_controller_setup(udc); |
| 1845 | 1847 | ||
| 1846 | /* Reset all internal used Queues */ | 1848 | /* Reset all internal used Queues */ |
| 1847 | reset_queues(udc); | 1849 | reset_queues(udc, false); |
| 1848 | 1850 | ||
| 1849 | ep0_setup(udc); | 1851 | ep0_setup(udc); |
| 1850 | 1852 | ||
| @@ -1975,8 +1977,7 @@ static int fsl_udc_start(struct usb_gadget *g, | |||
| 1975 | } | 1977 | } |
| 1976 | 1978 | ||
| 1977 | /* Disconnect from gadget driver */ | 1979 | /* Disconnect from gadget driver */ |
| 1978 | static int fsl_udc_stop(struct usb_gadget *g, | 1980 | static int fsl_udc_stop(struct usb_gadget *g) |
| 1979 | struct usb_gadget_driver *driver) | ||
| 1980 | { | 1981 | { |
| 1981 | struct fsl_ep *loop_ep; | 1982 | struct fsl_ep *loop_ep; |
| 1982 | unsigned long flags; | 1983 | unsigned long flags; |
diff --git a/drivers/usb/gadget/udc/fusb300_udc.c b/drivers/usb/gadget/udc/fusb300_udc.c index 8286df72add4..a1b33f534b52 100644 --- a/drivers/usb/gadget/udc/fusb300_udc.c +++ b/drivers/usb/gadget/udc/fusb300_udc.c | |||
| @@ -1320,8 +1320,7 @@ static int fusb300_udc_start(struct usb_gadget *g, | |||
| 1320 | return 0; | 1320 | return 0; |
| 1321 | } | 1321 | } |
| 1322 | 1322 | ||
| 1323 | static int fusb300_udc_stop(struct usb_gadget *g, | 1323 | static int fusb300_udc_stop(struct usb_gadget *g) |
| 1324 | struct usb_gadget_driver *driver) | ||
| 1325 | { | 1324 | { |
| 1326 | struct fusb300 *fusb300 = to_fusb300(g); | 1325 | struct fusb300 *fusb300 = to_fusb300(g); |
| 1327 | 1326 | ||
diff --git a/drivers/usb/gadget/udc/goku_udc.c b/drivers/usb/gadget/udc/goku_udc.c index bf9c5ef8b56b..5b9176e7202a 100644 --- a/drivers/usb/gadget/udc/goku_udc.c +++ b/drivers/usb/gadget/udc/goku_udc.c | |||
| @@ -992,8 +992,7 @@ static int goku_get_frame(struct usb_gadget *_gadget) | |||
| 992 | 992 | ||
| 993 | static int goku_udc_start(struct usb_gadget *g, | 993 | static int goku_udc_start(struct usb_gadget *g, |
| 994 | struct usb_gadget_driver *driver); | 994 | struct usb_gadget_driver *driver); |
| 995 | static int goku_udc_stop(struct usb_gadget *g, | 995 | static int goku_udc_stop(struct usb_gadget *g); |
| 996 | struct usb_gadget_driver *driver); | ||
| 997 | 996 | ||
| 998 | static const struct usb_gadget_ops goku_ops = { | 997 | static const struct usb_gadget_ops goku_ops = { |
| 999 | .get_frame = goku_get_frame, | 998 | .get_frame = goku_get_frame, |
| @@ -1364,8 +1363,7 @@ static void stop_activity(struct goku_udc *dev) | |||
| 1364 | udc_enable(dev); | 1363 | udc_enable(dev); |
| 1365 | } | 1364 | } |
| 1366 | 1365 | ||
| 1367 | static int goku_udc_stop(struct usb_gadget *g, | 1366 | static int goku_udc_stop(struct usb_gadget *g) |
| 1368 | struct usb_gadget_driver *driver) | ||
| 1369 | { | 1367 | { |
| 1370 | struct goku_udc *dev = to_goku_udc(g); | 1368 | struct goku_udc *dev = to_goku_udc(g); |
| 1371 | unsigned long flags; | 1369 | unsigned long flags; |
diff --git a/drivers/usb/gadget/udc/gr_udc.c b/drivers/usb/gadget/udc/gr_udc.c index 1b3048a6a2a3..320df9a250ff 100644 --- a/drivers/usb/gadget/udc/gr_udc.c +++ b/drivers/usb/gadget/udc/gr_udc.c | |||
| @@ -1932,14 +1932,10 @@ static int gr_udc_start(struct usb_gadget *gadget, | |||
| 1932 | 1932 | ||
| 1933 | spin_unlock(&dev->lock); | 1933 | spin_unlock(&dev->lock); |
| 1934 | 1934 | ||
| 1935 | dev_info(dev->dev, "Started with gadget driver '%s'\n", | ||
| 1936 | driver->driver.name); | ||
| 1937 | |||
| 1938 | return 0; | 1935 | return 0; |
| 1939 | } | 1936 | } |
| 1940 | 1937 | ||
| 1941 | static int gr_udc_stop(struct usb_gadget *gadget, | 1938 | static int gr_udc_stop(struct usb_gadget *gadget) |
| 1942 | struct usb_gadget_driver *driver) | ||
| 1943 | { | 1939 | { |
| 1944 | struct gr_udc *dev = to_gr_udc(gadget); | 1940 | struct gr_udc *dev = to_gr_udc(gadget); |
| 1945 | unsigned long flags; | 1941 | unsigned long flags; |
| @@ -1951,8 +1947,6 @@ static int gr_udc_stop(struct usb_gadget *gadget, | |||
| 1951 | 1947 | ||
| 1952 | spin_unlock_irqrestore(&dev->lock, flags); | 1948 | spin_unlock_irqrestore(&dev->lock, flags); |
| 1953 | 1949 | ||
| 1954 | dev_info(dev->dev, "Stopped\n"); | ||
| 1955 | |||
| 1956 | return 0; | 1950 | return 0; |
| 1957 | } | 1951 | } |
| 1958 | 1952 | ||
diff --git a/drivers/usb/gadget/udc/lpc32xx_udc.c b/drivers/usb/gadget/udc/lpc32xx_udc.c index feab0bac8fdc..976529631c19 100644 --- a/drivers/usb/gadget/udc/lpc32xx_udc.c +++ b/drivers/usb/gadget/udc/lpc32xx_udc.c | |||
| @@ -582,8 +582,7 @@ static void create_debug_file(struct lpc32xx_udc *udc) | |||
| 582 | 582 | ||
| 583 | static void remove_debug_file(struct lpc32xx_udc *udc) | 583 | static void remove_debug_file(struct lpc32xx_udc *udc) |
| 584 | { | 584 | { |
| 585 | if (udc->pde) | 585 | debugfs_remove(udc->pde); |
| 586 | debugfs_remove(udc->pde); | ||
| 587 | } | 586 | } |
| 588 | 587 | ||
| 589 | #else | 588 | #else |
| @@ -2559,7 +2558,7 @@ static int lpc32xx_pullup(struct usb_gadget *gadget, int is_on) | |||
| 2559 | } | 2558 | } |
| 2560 | 2559 | ||
| 2561 | static int lpc32xx_start(struct usb_gadget *, struct usb_gadget_driver *); | 2560 | static int lpc32xx_start(struct usb_gadget *, struct usb_gadget_driver *); |
| 2562 | static int lpc32xx_stop(struct usb_gadget *, struct usb_gadget_driver *); | 2561 | static int lpc32xx_stop(struct usb_gadget *); |
| 2563 | 2562 | ||
| 2564 | static const struct usb_gadget_ops lpc32xx_udc_ops = { | 2563 | static const struct usb_gadget_ops lpc32xx_udc_ops = { |
| 2565 | .get_frame = lpc32xx_get_frame, | 2564 | .get_frame = lpc32xx_get_frame, |
| @@ -2961,15 +2960,11 @@ static int lpc32xx_start(struct usb_gadget *gadget, | |||
| 2961 | return 0; | 2960 | return 0; |
| 2962 | } | 2961 | } |
| 2963 | 2962 | ||
| 2964 | static int lpc32xx_stop(struct usb_gadget *gadget, | 2963 | static int lpc32xx_stop(struct usb_gadget *gadget) |
| 2965 | struct usb_gadget_driver *driver) | ||
| 2966 | { | 2964 | { |
| 2967 | int i; | 2965 | int i; |
| 2968 | struct lpc32xx_udc *udc = to_udc(gadget); | 2966 | struct lpc32xx_udc *udc = to_udc(gadget); |
| 2969 | 2967 | ||
| 2970 | if (!driver || driver != udc->driver) | ||
| 2971 | return -EINVAL; | ||
| 2972 | |||
| 2973 | for (i = IRQ_USB_LP; i <= IRQ_USB_ATX; i++) | 2968 | for (i = IRQ_USB_LP; i <= IRQ_USB_ATX; i++) |
| 2974 | disable_irq(udc->udp_irq[i]); | 2969 | disable_irq(udc->udp_irq[i]); |
| 2975 | 2970 | ||
diff --git a/drivers/usb/gadget/udc/m66592-udc.c b/drivers/usb/gadget/udc/m66592-udc.c index 898565687a8c..ef3f73dd9099 100644 --- a/drivers/usb/gadget/udc/m66592-udc.c +++ b/drivers/usb/gadget/udc/m66592-udc.c | |||
| @@ -1142,7 +1142,7 @@ static void irq_device_state(struct m66592 *m66592) | |||
| 1142 | m66592_write(m66592, ~M66592_DVST, M66592_INTSTS0); | 1142 | m66592_write(m66592, ~M66592_DVST, M66592_INTSTS0); |
| 1143 | 1143 | ||
| 1144 | if (dvsq == M66592_DS_DFLT) { /* bus reset */ | 1144 | if (dvsq == M66592_DS_DFLT) { /* bus reset */ |
| 1145 | m66592->driver->disconnect(&m66592->gadget); | 1145 | usb_gadget_udc_reset(&m66592->gadget, m66592->driver); |
| 1146 | m66592_update_usb_speed(m66592); | 1146 | m66592_update_usb_speed(m66592); |
| 1147 | } | 1147 | } |
| 1148 | if (m66592->old_dvsq == M66592_DS_CNFG && dvsq != M66592_DS_CNFG) | 1148 | if (m66592->old_dvsq == M66592_DS_CNFG && dvsq != M66592_DS_CNFG) |
| @@ -1485,8 +1485,7 @@ static int m66592_udc_start(struct usb_gadget *g, | |||
| 1485 | return 0; | 1485 | return 0; |
| 1486 | } | 1486 | } |
| 1487 | 1487 | ||
| 1488 | static int m66592_udc_stop(struct usb_gadget *g, | 1488 | static int m66592_udc_stop(struct usb_gadget *g) |
| 1489 | struct usb_gadget_driver *driver) | ||
| 1490 | { | 1489 | { |
| 1491 | struct m66592 *m66592 = to_m66592(g); | 1490 | struct m66592 *m66592 = to_m66592(g); |
| 1492 | 1491 | ||
diff --git a/drivers/usb/gadget/udc/mv_u3d_core.c b/drivers/usb/gadget/udc/mv_u3d_core.c index 046a1f808b0d..ea422ac79990 100644 --- a/drivers/usb/gadget/udc/mv_u3d_core.c +++ b/drivers/usb/gadget/udc/mv_u3d_core.c | |||
| @@ -1266,8 +1266,7 @@ static int mv_u3d_start(struct usb_gadget *g, | |||
| 1266 | return 0; | 1266 | return 0; |
| 1267 | } | 1267 | } |
| 1268 | 1268 | ||
| 1269 | static int mv_u3d_stop(struct usb_gadget *g, | 1269 | static int mv_u3d_stop(struct usb_gadget *g) |
| 1270 | struct usb_gadget_driver *driver) | ||
| 1271 | { | 1270 | { |
| 1272 | struct mv_u3d *u3d = container_of(g, struct mv_u3d, gadget); | 1271 | struct mv_u3d *u3d = container_of(g, struct mv_u3d, gadget); |
| 1273 | struct mv_usb_platform_data *pdata = dev_get_platdata(u3d->dev); | 1272 | struct mv_usb_platform_data *pdata = dev_get_platdata(u3d->dev); |
| @@ -1284,7 +1283,7 @@ static int mv_u3d_stop(struct usb_gadget *g, | |||
| 1284 | mv_u3d_controller_stop(u3d); | 1283 | mv_u3d_controller_stop(u3d); |
| 1285 | /* stop all usb activities */ | 1284 | /* stop all usb activities */ |
| 1286 | u3d->gadget.speed = USB_SPEED_UNKNOWN; | 1285 | u3d->gadget.speed = USB_SPEED_UNKNOWN; |
| 1287 | mv_u3d_stop_activity(u3d, driver); | 1286 | mv_u3d_stop_activity(u3d, NULL); |
| 1288 | mv_u3d_disable(u3d); | 1287 | mv_u3d_disable(u3d); |
| 1289 | 1288 | ||
| 1290 | if (pdata->phy_deinit) | 1289 | if (pdata->phy_deinit) |
diff --git a/drivers/usb/gadget/udc/mv_udc_core.c b/drivers/usb/gadget/udc/mv_udc_core.c index 3c5db80ae325..d4edd763e963 100644 --- a/drivers/usb/gadget/udc/mv_udc_core.c +++ b/drivers/usb/gadget/udc/mv_udc_core.c | |||
| @@ -1223,7 +1223,7 @@ static int mv_udc_pullup(struct usb_gadget *gadget, int is_on) | |||
| 1223 | } | 1223 | } |
| 1224 | 1224 | ||
| 1225 | static int mv_udc_start(struct usb_gadget *, struct usb_gadget_driver *); | 1225 | static int mv_udc_start(struct usb_gadget *, struct usb_gadget_driver *); |
| 1226 | static int mv_udc_stop(struct usb_gadget *, struct usb_gadget_driver *); | 1226 | static int mv_udc_stop(struct usb_gadget *); |
| 1227 | /* device controller usb_gadget_ops structure */ | 1227 | /* device controller usb_gadget_ops structure */ |
| 1228 | static const struct usb_gadget_ops mv_ops = { | 1228 | static const struct usb_gadget_ops mv_ops = { |
| 1229 | 1229 | ||
| @@ -1307,6 +1307,23 @@ static void nuke(struct mv_ep *ep, int status) | |||
| 1307 | } | 1307 | } |
| 1308 | } | 1308 | } |
| 1309 | 1309 | ||
| 1310 | static void gadget_reset(struct mv_udc *udc, struct usb_gadget_driver *driver) | ||
| 1311 | { | ||
| 1312 | struct mv_ep *ep; | ||
| 1313 | |||
| 1314 | nuke(&udc->eps[0], -ESHUTDOWN); | ||
| 1315 | |||
| 1316 | list_for_each_entry(ep, &udc->gadget.ep_list, ep.ep_list) { | ||
| 1317 | nuke(ep, -ESHUTDOWN); | ||
| 1318 | } | ||
| 1319 | |||
| 1320 | /* report reset; the driver is already quiesced */ | ||
| 1321 | if (driver) { | ||
| 1322 | spin_unlock(&udc->lock); | ||
| 1323 | usb_gadget_udc_reset(&udc->gadget, driver); | ||
| 1324 | spin_lock(&udc->lock); | ||
| 1325 | } | ||
| 1326 | } | ||
| 1310 | /* stop all USB activities */ | 1327 | /* stop all USB activities */ |
| 1311 | static void stop_activity(struct mv_udc *udc, struct usb_gadget_driver *driver) | 1328 | static void stop_activity(struct mv_udc *udc, struct usb_gadget_driver *driver) |
| 1312 | { | 1329 | { |
| @@ -1371,8 +1388,7 @@ static int mv_udc_start(struct usb_gadget *gadget, | |||
| 1371 | return 0; | 1388 | return 0; |
| 1372 | } | 1389 | } |
| 1373 | 1390 | ||
| 1374 | static int mv_udc_stop(struct usb_gadget *gadget, | 1391 | static int mv_udc_stop(struct usb_gadget *gadget) |
| 1375 | struct usb_gadget_driver *driver) | ||
| 1376 | { | 1392 | { |
| 1377 | struct mv_udc *udc; | 1393 | struct mv_udc *udc; |
| 1378 | unsigned long flags; | 1394 | unsigned long flags; |
| @@ -1386,7 +1402,7 @@ static int mv_udc_stop(struct usb_gadget *gadget, | |||
| 1386 | 1402 | ||
| 1387 | /* stop all usb activities */ | 1403 | /* stop all usb activities */ |
| 1388 | udc->gadget.speed = USB_SPEED_UNKNOWN; | 1404 | udc->gadget.speed = USB_SPEED_UNKNOWN; |
| 1389 | stop_activity(udc, driver); | 1405 | stop_activity(udc, NULL); |
| 1390 | mv_udc_disable(udc); | 1406 | mv_udc_disable(udc); |
| 1391 | 1407 | ||
| 1392 | spin_unlock_irqrestore(&udc->lock, flags); | 1408 | spin_unlock_irqrestore(&udc->lock, flags); |
| @@ -1882,7 +1898,7 @@ static void irq_process_reset(struct mv_udc *udc) | |||
| 1882 | dev_info(&udc->dev->dev, "usb bus reset\n"); | 1898 | dev_info(&udc->dev->dev, "usb bus reset\n"); |
| 1883 | udc->usb_state = USB_STATE_DEFAULT; | 1899 | udc->usb_state = USB_STATE_DEFAULT; |
| 1884 | /* reset all the queues, stop all USB activities */ | 1900 | /* reset all the queues, stop all USB activities */ |
| 1885 | stop_activity(udc, udc->driver); | 1901 | gadget_reset(udc, udc->driver); |
| 1886 | } else { | 1902 | } else { |
| 1887 | dev_info(&udc->dev->dev, "USB reset portsc 0x%x\n", | 1903 | dev_info(&udc->dev->dev, "USB reset portsc 0x%x\n", |
| 1888 | readl(&udc->op_regs->portsc)); | 1904 | readl(&udc->op_regs->portsc)); |
| @@ -2107,10 +2123,8 @@ static int mv_udc_probe(struct platform_device *pdev) | |||
| 2107 | } | 2123 | } |
| 2108 | 2124 | ||
| 2109 | udc = devm_kzalloc(&pdev->dev, sizeof(*udc), GFP_KERNEL); | 2125 | udc = devm_kzalloc(&pdev->dev, sizeof(*udc), GFP_KERNEL); |
| 2110 | if (udc == NULL) { | 2126 | if (udc == NULL) |
| 2111 | dev_err(&pdev->dev, "failed to allocate memory for udc\n"); | ||
| 2112 | return -ENOMEM; | 2127 | return -ENOMEM; |
| 2113 | } | ||
| 2114 | 2128 | ||
| 2115 | udc->done = &release_done; | 2129 | udc->done = &release_done; |
| 2116 | udc->pdata = dev_get_platdata(&pdev->dev); | 2130 | udc->pdata = dev_get_platdata(&pdev->dev); |
| @@ -2207,7 +2221,6 @@ static int mv_udc_probe(struct platform_device *pdev) | |||
| 2207 | size = udc->max_eps * sizeof(struct mv_ep) *2; | 2221 | size = udc->max_eps * sizeof(struct mv_ep) *2; |
| 2208 | udc->eps = devm_kzalloc(&pdev->dev, size, GFP_KERNEL); | 2222 | udc->eps = devm_kzalloc(&pdev->dev, size, GFP_KERNEL); |
| 2209 | if (udc->eps == NULL) { | 2223 | if (udc->eps == NULL) { |
| 2210 | dev_err(&pdev->dev, "allocate ep memory failed\n"); | ||
| 2211 | retval = -ENOMEM; | 2224 | retval = -ENOMEM; |
| 2212 | goto err_destroy_dma; | 2225 | goto err_destroy_dma; |
| 2213 | } | 2226 | } |
| @@ -2216,7 +2229,6 @@ static int mv_udc_probe(struct platform_device *pdev) | |||
| 2216 | udc->status_req = devm_kzalloc(&pdev->dev, sizeof(struct mv_req), | 2229 | udc->status_req = devm_kzalloc(&pdev->dev, sizeof(struct mv_req), |
| 2217 | GFP_KERNEL); | 2230 | GFP_KERNEL); |
| 2218 | if (!udc->status_req) { | 2231 | if (!udc->status_req) { |
| 2219 | dev_err(&pdev->dev, "allocate status_req memory failed\n"); | ||
| 2220 | retval = -ENOMEM; | 2232 | retval = -ENOMEM; |
| 2221 | goto err_destroy_dma; | 2233 | goto err_destroy_dma; |
| 2222 | } | 2234 | } |
diff --git a/drivers/usb/gadget/udc/net2272.c b/drivers/usb/gadget/udc/net2272.c index 84d7162a8022..3a90856625f2 100644 --- a/drivers/usb/gadget/udc/net2272.c +++ b/drivers/usb/gadget/udc/net2272.c | |||
| @@ -1169,8 +1169,7 @@ net2272_pullup(struct usb_gadget *_gadget, int is_on) | |||
| 1169 | 1169 | ||
| 1170 | static int net2272_start(struct usb_gadget *_gadget, | 1170 | static int net2272_start(struct usb_gadget *_gadget, |
| 1171 | struct usb_gadget_driver *driver); | 1171 | struct usb_gadget_driver *driver); |
| 1172 | static int net2272_stop(struct usb_gadget *_gadget, | 1172 | static int net2272_stop(struct usb_gadget *_gadget); |
| 1173 | struct usb_gadget_driver *driver); | ||
| 1174 | 1173 | ||
| 1175 | static const struct usb_gadget_ops net2272_ops = { | 1174 | static const struct usb_gadget_ops net2272_ops = { |
| 1176 | .get_frame = net2272_get_frame, | 1175 | .get_frame = net2272_get_frame, |
| @@ -1471,8 +1470,6 @@ static int net2272_start(struct usb_gadget *_gadget, | |||
| 1471 | */ | 1470 | */ |
| 1472 | net2272_ep0_start(dev); | 1471 | net2272_ep0_start(dev); |
| 1473 | 1472 | ||
| 1474 | dev_dbg(dev->dev, "%s ready\n", driver->driver.name); | ||
| 1475 | |||
| 1476 | return 0; | 1473 | return 0; |
| 1477 | } | 1474 | } |
| 1478 | 1475 | ||
| @@ -1502,8 +1499,7 @@ stop_activity(struct net2272 *dev, struct usb_gadget_driver *driver) | |||
| 1502 | net2272_usb_reinit(dev); | 1499 | net2272_usb_reinit(dev); |
| 1503 | } | 1500 | } |
| 1504 | 1501 | ||
| 1505 | static int net2272_stop(struct usb_gadget *_gadget, | 1502 | static int net2272_stop(struct usb_gadget *_gadget) |
| 1506 | struct usb_gadget_driver *driver) | ||
| 1507 | { | 1503 | { |
| 1508 | struct net2272 *dev; | 1504 | struct net2272 *dev; |
| 1509 | unsigned long flags; | 1505 | unsigned long flags; |
| @@ -1511,12 +1507,11 @@ static int net2272_stop(struct usb_gadget *_gadget, | |||
| 1511 | dev = container_of(_gadget, struct net2272, gadget); | 1507 | dev = container_of(_gadget, struct net2272, gadget); |
| 1512 | 1508 | ||
| 1513 | spin_lock_irqsave(&dev->lock, flags); | 1509 | spin_lock_irqsave(&dev->lock, flags); |
| 1514 | stop_activity(dev, driver); | 1510 | stop_activity(dev, NULL); |
| 1515 | spin_unlock_irqrestore(&dev->lock, flags); | 1511 | spin_unlock_irqrestore(&dev->lock, flags); |
| 1516 | 1512 | ||
| 1517 | dev->driver = NULL; | 1513 | dev->driver = NULL; |
| 1518 | 1514 | ||
| 1519 | dev_dbg(dev->dev, "unregistered driver '%s'\n", driver->driver.name); | ||
| 1520 | return 0; | 1515 | return 0; |
| 1521 | } | 1516 | } |
| 1522 | 1517 | ||
| @@ -1987,17 +1982,42 @@ net2272_handle_stat1_irqs(struct net2272 *dev, u8 stat) | |||
| 1987 | mask = (1 << USB_HIGH_SPEED) | (1 << USB_FULL_SPEED); | 1982 | mask = (1 << USB_HIGH_SPEED) | (1 << USB_FULL_SPEED); |
| 1988 | 1983 | ||
| 1989 | if (stat & tmp) { | 1984 | if (stat & tmp) { |
| 1985 | bool reset = false; | ||
| 1986 | bool disconnect = false; | ||
| 1987 | |||
| 1988 | /* | ||
| 1989 | * Ignore disconnects and resets if the speed hasn't been set. | ||
| 1990 | * VBUS can bounce and there's always an initial reset. | ||
| 1991 | */ | ||
| 1990 | net2272_write(dev, IRQSTAT1, tmp); | 1992 | net2272_write(dev, IRQSTAT1, tmp); |
| 1991 | if ((((stat & (1 << ROOT_PORT_RESET_INTERRUPT)) && | 1993 | if (dev->gadget.speed != USB_SPEED_UNKNOWN) { |
| 1992 | ((net2272_read(dev, USBCTL1) & mask) == 0)) | 1994 | if ((stat & (1 << VBUS_INTERRUPT)) && |
| 1993 | || ((net2272_read(dev, USBCTL1) & (1 << VBUS_PIN)) | 1995 | (net2272_read(dev, USBCTL1) & |
| 1994 | == 0)) | 1996 | (1 << VBUS_PIN)) == 0) { |
| 1995 | && (dev->gadget.speed != USB_SPEED_UNKNOWN)) { | 1997 | disconnect = true; |
| 1996 | dev_dbg(dev->dev, "disconnect %s\n", | 1998 | dev_dbg(dev->dev, "disconnect %s\n", |
| 1997 | dev->driver->driver.name); | 1999 | dev->driver->driver.name); |
| 1998 | stop_activity(dev, dev->driver); | 2000 | } else if ((stat & (1 << ROOT_PORT_RESET_INTERRUPT)) && |
| 1999 | net2272_ep0_start(dev); | 2001 | (net2272_read(dev, USBCTL1) & mask) |
| 2000 | return; | 2002 | == 0) { |
| 2003 | reset = true; | ||
| 2004 | dev_dbg(dev->dev, "reset %s\n", | ||
| 2005 | dev->driver->driver.name); | ||
| 2006 | } | ||
| 2007 | |||
| 2008 | if (disconnect || reset) { | ||
| 2009 | stop_activity(dev, dev->driver); | ||
| 2010 | net2272_ep0_start(dev); | ||
| 2011 | spin_unlock(&dev->lock); | ||
| 2012 | if (reset) | ||
| 2013 | usb_gadget_udc_reset | ||
| 2014 | (&dev->gadget, dev->driver); | ||
| 2015 | else | ||
| 2016 | (dev->driver->disconnect) | ||
| 2017 | (&dev->gadget); | ||
| 2018 | spin_lock(&dev->lock); | ||
| 2019 | return; | ||
| 2020 | } | ||
| 2001 | } | 2021 | } |
| 2002 | stat &= ~tmp; | 2022 | stat &= ~tmp; |
| 2003 | 2023 | ||
| @@ -2200,18 +2220,8 @@ static void | |||
| 2200 | net2272_remove(struct net2272 *dev) | 2220 | net2272_remove(struct net2272 *dev) |
| 2201 | { | 2221 | { |
| 2202 | usb_del_gadget_udc(&dev->gadget); | 2222 | usb_del_gadget_udc(&dev->gadget); |
| 2203 | |||
| 2204 | /* start with the driver above us */ | ||
| 2205 | if (dev->driver) { | ||
| 2206 | /* should have been done already by driver model core */ | ||
| 2207 | dev_warn(dev->dev, "pci remove, driver '%s' is still registered\n", | ||
| 2208 | dev->driver->driver.name); | ||
| 2209 | usb_gadget_unregister_driver(dev->driver); | ||
| 2210 | } | ||
| 2211 | |||
| 2212 | free_irq(dev->irq, dev); | 2223 | free_irq(dev->irq, dev); |
| 2213 | iounmap(dev->base_addr); | 2224 | iounmap(dev->base_addr); |
| 2214 | |||
| 2215 | device_remove_file(dev->dev, &dev_attr_registers); | 2225 | device_remove_file(dev->dev, &dev_attr_registers); |
| 2216 | 2226 | ||
| 2217 | dev_info(dev->dev, "unbind\n"); | 2227 | dev_info(dev->dev, "unbind\n"); |
diff --git a/drivers/usb/gadget/udc/net2280.c b/drivers/usb/gadget/udc/net2280.c index 8d13337e2dde..d6411e0a8e03 100644 --- a/drivers/usb/gadget/udc/net2280.c +++ b/drivers/usb/gadget/udc/net2280.c | |||
| @@ -1118,10 +1118,10 @@ static void scan_dma_completions(struct net2280_ep *ep) | |||
| 1118 | break; | 1118 | break; |
| 1119 | } else if (!ep->is_in && | 1119 | } else if (!ep->is_in && |
| 1120 | (req->req.length % ep->ep.maxpacket) != 0) { | 1120 | (req->req.length % ep->ep.maxpacket) != 0) { |
| 1121 | tmp = readl(&ep->regs->ep_stat); | ||
| 1122 | if (ep->dev->quirks & PLX_SUPERSPEED) | 1121 | if (ep->dev->quirks & PLX_SUPERSPEED) |
| 1123 | return dma_done(ep, req, tmp, 0); | 1122 | return dma_done(ep, req, tmp, 0); |
| 1124 | 1123 | ||
| 1124 | tmp = readl(&ep->regs->ep_stat); | ||
| 1125 | /* AVOID TROUBLE HERE by not issuing short reads from | 1125 | /* AVOID TROUBLE HERE by not issuing short reads from |
| 1126 | * your gadget driver. That helps avoids errata 0121, | 1126 | * your gadget driver. That helps avoids errata 0121, |
| 1127 | * 0122, and 0124; not all cases trigger the warning. | 1127 | * 0122, and 0124; not all cases trigger the warning. |
| @@ -1548,8 +1548,7 @@ static int net2280_pullup(struct usb_gadget *_gadget, int is_on) | |||
| 1548 | 1548 | ||
| 1549 | static int net2280_start(struct usb_gadget *_gadget, | 1549 | static int net2280_start(struct usb_gadget *_gadget, |
| 1550 | struct usb_gadget_driver *driver); | 1550 | struct usb_gadget_driver *driver); |
| 1551 | static int net2280_stop(struct usb_gadget *_gadget, | 1551 | static int net2280_stop(struct usb_gadget *_gadget); |
| 1552 | struct usb_gadget_driver *driver); | ||
| 1553 | 1552 | ||
| 1554 | static const struct usb_gadget_ops net2280_ops = { | 1553 | static const struct usb_gadget_ops net2280_ops = { |
| 1555 | .get_frame = net2280_get_frame, | 1554 | .get_frame = net2280_get_frame, |
| @@ -2397,11 +2396,6 @@ static int net2280_start(struct usb_gadget *_gadget, | |||
| 2397 | 2396 | ||
| 2398 | ep0_start(dev); | 2397 | ep0_start(dev); |
| 2399 | 2398 | ||
| 2400 | ep_dbg(dev, "%s ready, usbctl %08x stdrsp %08x\n", | ||
| 2401 | driver->driver.name, | ||
| 2402 | readl(&dev->usb->usbctl), | ||
| 2403 | readl(&dev->usb->stdrsp)); | ||
| 2404 | |||
| 2405 | /* pci writes may still be posted */ | 2399 | /* pci writes may still be posted */ |
| 2406 | return 0; | 2400 | return 0; |
| 2407 | 2401 | ||
| @@ -2437,8 +2431,7 @@ static void stop_activity(struct net2280 *dev, struct usb_gadget_driver *driver) | |||
| 2437 | usb_reinit(dev); | 2431 | usb_reinit(dev); |
| 2438 | } | 2432 | } |
| 2439 | 2433 | ||
| 2440 | static int net2280_stop(struct usb_gadget *_gadget, | 2434 | static int net2280_stop(struct usb_gadget *_gadget) |
| 2441 | struct usb_gadget_driver *driver) | ||
| 2442 | { | 2435 | { |
| 2443 | struct net2280 *dev; | 2436 | struct net2280 *dev; |
| 2444 | unsigned long flags; | 2437 | unsigned long flags; |
| @@ -2446,11 +2439,9 @@ static int net2280_stop(struct usb_gadget *_gadget, | |||
| 2446 | dev = container_of(_gadget, struct net2280, gadget); | 2439 | dev = container_of(_gadget, struct net2280, gadget); |
| 2447 | 2440 | ||
| 2448 | spin_lock_irqsave(&dev->lock, flags); | 2441 | spin_lock_irqsave(&dev->lock, flags); |
| 2449 | stop_activity(dev, driver); | 2442 | stop_activity(dev, NULL); |
| 2450 | spin_unlock_irqrestore(&dev->lock, flags); | 2443 | spin_unlock_irqrestore(&dev->lock, flags); |
| 2451 | 2444 | ||
| 2452 | dev->driver = NULL; | ||
| 2453 | |||
| 2454 | net2280_led_active(dev, 0); | 2445 | net2280_led_active(dev, 0); |
| 2455 | 2446 | ||
| 2456 | /* Disable full-speed test mode */ | 2447 | /* Disable full-speed test mode */ |
| @@ -2460,8 +2451,7 @@ static int net2280_stop(struct usb_gadget *_gadget, | |||
| 2460 | device_remove_file(&dev->pdev->dev, &dev_attr_function); | 2451 | device_remove_file(&dev->pdev->dev, &dev_attr_function); |
| 2461 | device_remove_file(&dev->pdev->dev, &dev_attr_queues); | 2452 | device_remove_file(&dev->pdev->dev, &dev_attr_queues); |
| 2462 | 2453 | ||
| 2463 | ep_dbg(dev, "unregistered driver '%s'\n", | 2454 | dev->driver = NULL; |
| 2464 | driver ? driver->driver.name : ""); | ||
| 2465 | 2455 | ||
| 2466 | return 0; | 2456 | return 0; |
| 2467 | } | 2457 | } |
| @@ -3318,17 +3308,42 @@ static void handle_stat1_irqs(struct net2280 *dev, u32 stat) | |||
| 3318 | * only indicates a change in the reset state). | 3308 | * only indicates a change in the reset state). |
| 3319 | */ | 3309 | */ |
| 3320 | if (stat & tmp) { | 3310 | if (stat & tmp) { |
| 3311 | bool reset = false; | ||
| 3312 | bool disconnect = false; | ||
| 3313 | |||
| 3314 | /* | ||
| 3315 | * Ignore disconnects and resets if the speed hasn't been set. | ||
| 3316 | * VBUS can bounce and there's always an initial reset. | ||
| 3317 | */ | ||
| 3321 | writel(tmp, &dev->regs->irqstat1); | 3318 | writel(tmp, &dev->regs->irqstat1); |
| 3322 | if ((((stat & BIT(ROOT_PORT_RESET_INTERRUPT)) && | 3319 | if (dev->gadget.speed != USB_SPEED_UNKNOWN) { |
| 3323 | ((readl(&dev->usb->usbstat) & mask) == 0)) || | 3320 | if ((stat & BIT(VBUS_INTERRUPT)) && |
| 3324 | ((readl(&dev->usb->usbctl) & | 3321 | (readl(&dev->usb->usbctl) & |
| 3325 | BIT(VBUS_PIN)) == 0)) && | 3322 | BIT(VBUS_PIN)) == 0) { |
| 3326 | (dev->gadget.speed != USB_SPEED_UNKNOWN)) { | 3323 | disconnect = true; |
| 3327 | ep_dbg(dev, "disconnect %s\n", | 3324 | ep_dbg(dev, "disconnect %s\n", |
| 3328 | dev->driver->driver.name); | 3325 | dev->driver->driver.name); |
| 3329 | stop_activity(dev, dev->driver); | 3326 | } else if ((stat & BIT(ROOT_PORT_RESET_INTERRUPT)) && |
| 3330 | ep0_start(dev); | 3327 | (readl(&dev->usb->usbstat) & mask) |
| 3331 | return; | 3328 | == 0) { |
| 3329 | reset = true; | ||
| 3330 | ep_dbg(dev, "reset %s\n", | ||
| 3331 | dev->driver->driver.name); | ||
| 3332 | } | ||
| 3333 | |||
| 3334 | if (disconnect || reset) { | ||
| 3335 | stop_activity(dev, dev->driver); | ||
| 3336 | ep0_start(dev); | ||
| 3337 | spin_unlock(&dev->lock); | ||
| 3338 | if (reset) | ||
| 3339 | usb_gadget_udc_reset | ||
| 3340 | (&dev->gadget, dev->driver); | ||
| 3341 | else | ||
| 3342 | (dev->driver->disconnect) | ||
| 3343 | (&dev->gadget); | ||
| 3344 | spin_lock(&dev->lock); | ||
| 3345 | return; | ||
| 3346 | } | ||
| 3332 | } | 3347 | } |
| 3333 | stat &= ~tmp; | 3348 | stat &= ~tmp; |
| 3334 | 3349 | ||
diff --git a/drivers/usb/gadget/udc/omap_udc.c b/drivers/usb/gadget/udc/omap_udc.c index dcdfea46003b..534b85c07feb 100644 --- a/drivers/usb/gadget/udc/omap_udc.c +++ b/drivers/usb/gadget/udc/omap_udc.c | |||
| @@ -1311,8 +1311,7 @@ static int omap_pullup(struct usb_gadget *gadget, int is_on) | |||
| 1311 | 1311 | ||
| 1312 | static int omap_udc_start(struct usb_gadget *g, | 1312 | static int omap_udc_start(struct usb_gadget *g, |
| 1313 | struct usb_gadget_driver *driver); | 1313 | struct usb_gadget_driver *driver); |
| 1314 | static int omap_udc_stop(struct usb_gadget *g, | 1314 | static int omap_udc_stop(struct usb_gadget *g); |
| 1315 | struct usb_gadget_driver *driver); | ||
| 1316 | 1315 | ||
| 1317 | static const struct usb_gadget_ops omap_gadget_ops = { | 1316 | static const struct usb_gadget_ops omap_gadget_ops = { |
| 1318 | .get_frame = omap_get_frame, | 1317 | .get_frame = omap_get_frame, |
| @@ -2102,8 +2101,7 @@ done: | |||
| 2102 | return status; | 2101 | return status; |
| 2103 | } | 2102 | } |
| 2104 | 2103 | ||
| 2105 | static int omap_udc_stop(struct usb_gadget *g, | 2104 | static int omap_udc_stop(struct usb_gadget *g) |
| 2106 | struct usb_gadget_driver *driver) | ||
| 2107 | { | 2105 | { |
| 2108 | unsigned long flags; | 2106 | unsigned long flags; |
| 2109 | int status = -ENODEV; | 2107 | int status = -ENODEV; |
diff --git a/drivers/usb/gadget/udc/pch_udc.c b/drivers/usb/gadget/udc/pch_udc.c index ccbe3d4a2a50..1c7379ac2379 100644 --- a/drivers/usb/gadget/udc/pch_udc.c +++ b/drivers/usb/gadget/udc/pch_udc.c | |||
| @@ -1240,8 +1240,8 @@ static int pch_udc_pcd_vbus_draw(struct usb_gadget *gadget, unsigned int mA) | |||
| 1240 | 1240 | ||
| 1241 | static int pch_udc_start(struct usb_gadget *g, | 1241 | static int pch_udc_start(struct usb_gadget *g, |
| 1242 | struct usb_gadget_driver *driver); | 1242 | struct usb_gadget_driver *driver); |
| 1243 | static int pch_udc_stop(struct usb_gadget *g, | 1243 | static int pch_udc_stop(struct usb_gadget *g); |
| 1244 | struct usb_gadget_driver *driver); | 1244 | |
| 1245 | static const struct usb_gadget_ops pch_udc_ops = { | 1245 | static const struct usb_gadget_ops pch_udc_ops = { |
| 1246 | .get_frame = pch_udc_pcd_get_frame, | 1246 | .get_frame = pch_udc_pcd_get_frame, |
| 1247 | .wakeup = pch_udc_pcd_wakeup, | 1247 | .wakeup = pch_udc_pcd_wakeup, |
| @@ -2592,9 +2592,9 @@ static void pch_udc_svc_ur_interrupt(struct pch_udc_dev *dev) | |||
| 2592 | /* Complete request queue */ | 2592 | /* Complete request queue */ |
| 2593 | empty_req_queue(ep); | 2593 | empty_req_queue(ep); |
| 2594 | } | 2594 | } |
| 2595 | if (dev->driver && dev->driver->disconnect) { | 2595 | if (dev->driver) { |
| 2596 | spin_unlock(&dev->lock); | 2596 | spin_unlock(&dev->lock); |
| 2597 | dev->driver->disconnect(&dev->gadget); | 2597 | usb_gadget_udc_reset(&dev->gadget, dev->driver); |
| 2598 | spin_lock(&dev->lock); | 2598 | spin_lock(&dev->lock); |
| 2599 | } | 2599 | } |
| 2600 | } | 2600 | } |
| @@ -3008,8 +3008,7 @@ static int pch_udc_start(struct usb_gadget *g, | |||
| 3008 | return 0; | 3008 | return 0; |
| 3009 | } | 3009 | } |
| 3010 | 3010 | ||
| 3011 | static int pch_udc_stop(struct usb_gadget *g, | 3011 | static int pch_udc_stop(struct usb_gadget *g) |
| 3012 | struct usb_gadget_driver *driver) | ||
| 3013 | { | 3012 | { |
| 3014 | struct pch_udc_dev *dev = to_pch_udc(g); | 3013 | struct pch_udc_dev *dev = to_pch_udc(g); |
| 3015 | 3014 | ||
diff --git a/drivers/usb/gadget/udc/pxa25x_udc.c b/drivers/usb/gadget/udc/pxa25x_udc.c index 42f7eeb8ff6f..347a05b5afc1 100644 --- a/drivers/usb/gadget/udc/pxa25x_udc.c +++ b/drivers/usb/gadget/udc/pxa25x_udc.c | |||
| @@ -998,8 +998,7 @@ static int pxa25x_udc_vbus_draw(struct usb_gadget *_gadget, unsigned mA) | |||
| 998 | 998 | ||
| 999 | static int pxa25x_udc_start(struct usb_gadget *g, | 999 | static int pxa25x_udc_start(struct usb_gadget *g, |
| 1000 | struct usb_gadget_driver *driver); | 1000 | struct usb_gadget_driver *driver); |
| 1001 | static int pxa25x_udc_stop(struct usb_gadget *g, | 1001 | static int pxa25x_udc_stop(struct usb_gadget *g); |
| 1002 | struct usb_gadget_driver *driver); | ||
| 1003 | 1002 | ||
| 1004 | static const struct usb_gadget_ops pxa25x_udc_ops = { | 1003 | static const struct usb_gadget_ops pxa25x_udc_ops = { |
| 1005 | .get_frame = pxa25x_udc_get_frame, | 1004 | .get_frame = pxa25x_udc_get_frame, |
| @@ -1135,11 +1134,7 @@ static const struct file_operations debug_fops = { | |||
| 1135 | dev->debugfs_udc = debugfs_create_file(dev->gadget.name, \ | 1134 | dev->debugfs_udc = debugfs_create_file(dev->gadget.name, \ |
| 1136 | S_IRUGO, NULL, dev, &debug_fops); \ | 1135 | S_IRUGO, NULL, dev, &debug_fops); \ |
| 1137 | } while (0) | 1136 | } while (0) |
| 1138 | #define remove_debug_files(dev) \ | 1137 | #define remove_debug_files(dev) debugfs_remove(dev->debugfs_udc) |
| 1139 | do { \ | ||
| 1140 | if (dev->debugfs_udc) \ | ||
| 1141 | debugfs_remove(dev->debugfs_udc); \ | ||
| 1142 | } while (0) | ||
| 1143 | 1138 | ||
| 1144 | #else /* !CONFIG_USB_GADGET_DEBUG_FILES */ | 1139 | #else /* !CONFIG_USB_GADGET_DEBUG_FILES */ |
| 1145 | 1140 | ||
| @@ -1285,6 +1280,33 @@ bind_fail: | |||
| 1285 | } | 1280 | } |
| 1286 | 1281 | ||
| 1287 | static void | 1282 | static void |
| 1283 | reset_gadget(struct pxa25x_udc *dev, struct usb_gadget_driver *driver) | ||
| 1284 | { | ||
| 1285 | int i; | ||
| 1286 | |||
| 1287 | /* don't disconnect drivers more than once */ | ||
| 1288 | if (dev->gadget.speed == USB_SPEED_UNKNOWN) | ||
| 1289 | driver = NULL; | ||
| 1290 | dev->gadget.speed = USB_SPEED_UNKNOWN; | ||
| 1291 | |||
| 1292 | /* prevent new request submissions, kill any outstanding requests */ | ||
| 1293 | for (i = 0; i < PXA_UDC_NUM_ENDPOINTS; i++) { | ||
| 1294 | struct pxa25x_ep *ep = &dev->ep[i]; | ||
| 1295 | |||
| 1296 | ep->stopped = 1; | ||
| 1297 | nuke(ep, -ESHUTDOWN); | ||
| 1298 | } | ||
| 1299 | del_timer_sync(&dev->timer); | ||
| 1300 | |||
| 1301 | /* report reset; the driver is already quiesced */ | ||
| 1302 | if (driver) | ||
| 1303 | usb_gadget_udc_reset(&dev->gadget, driver); | ||
| 1304 | |||
| 1305 | /* re-init driver-visible data structures */ | ||
| 1306 | udc_reinit(dev); | ||
| 1307 | } | ||
| 1308 | |||
| 1309 | static void | ||
| 1288 | stop_activity(struct pxa25x_udc *dev, struct usb_gadget_driver *driver) | 1310 | stop_activity(struct pxa25x_udc *dev, struct usb_gadget_driver *driver) |
| 1289 | { | 1311 | { |
| 1290 | int i; | 1312 | int i; |
| @@ -1311,15 +1333,14 @@ stop_activity(struct pxa25x_udc *dev, struct usb_gadget_driver *driver) | |||
| 1311 | udc_reinit(dev); | 1333 | udc_reinit(dev); |
| 1312 | } | 1334 | } |
| 1313 | 1335 | ||
| 1314 | static int pxa25x_udc_stop(struct usb_gadget*g, | 1336 | static int pxa25x_udc_stop(struct usb_gadget*g) |
| 1315 | struct usb_gadget_driver *driver) | ||
| 1316 | { | 1337 | { |
| 1317 | struct pxa25x_udc *dev = to_pxa25x(g); | 1338 | struct pxa25x_udc *dev = to_pxa25x(g); |
| 1318 | 1339 | ||
| 1319 | local_irq_disable(); | 1340 | local_irq_disable(); |
| 1320 | dev->pullup = 0; | 1341 | dev->pullup = 0; |
| 1321 | pullup(dev); | 1342 | pullup(dev); |
| 1322 | stop_activity(dev, driver); | 1343 | stop_activity(dev, NULL); |
| 1323 | local_irq_enable(); | 1344 | local_irq_enable(); |
| 1324 | 1345 | ||
| 1325 | if (!IS_ERR_OR_NULL(dev->transceiver)) | 1346 | if (!IS_ERR_OR_NULL(dev->transceiver)) |
| @@ -1723,7 +1744,7 @@ pxa25x_udc_irq(int irq, void *_dev) | |||
| 1723 | /* reset driver and endpoints, | 1744 | /* reset driver and endpoints, |
| 1724 | * in case that's not yet done | 1745 | * in case that's not yet done |
| 1725 | */ | 1746 | */ |
| 1726 | stop_activity (dev, dev->driver); | 1747 | reset_gadget(dev, dev->driver); |
| 1727 | 1748 | ||
| 1728 | } else { | 1749 | } else { |
| 1729 | DBG(DBG_VERBOSE, "USB reset end\n"); | 1750 | DBG(DBG_VERBOSE, "USB reset end\n"); |
diff --git a/drivers/usb/gadget/udc/pxa27x_udc.c b/drivers/usb/gadget/udc/pxa27x_udc.c index 4868369eeec6..9b03fab13707 100644 --- a/drivers/usb/gadget/udc/pxa27x_udc.c +++ b/drivers/usb/gadget/udc/pxa27x_udc.c | |||
| @@ -22,10 +22,13 @@ | |||
| 22 | #include <linux/clk.h> | 22 | #include <linux/clk.h> |
| 23 | #include <linux/irq.h> | 23 | #include <linux/irq.h> |
| 24 | #include <linux/gpio.h> | 24 | #include <linux/gpio.h> |
| 25 | #include <linux/gpio/consumer.h> | ||
| 25 | #include <linux/slab.h> | 26 | #include <linux/slab.h> |
| 26 | #include <linux/prefetch.h> | 27 | #include <linux/prefetch.h> |
| 27 | #include <linux/byteorder/generic.h> | 28 | #include <linux/byteorder/generic.h> |
| 28 | #include <linux/platform_data/pxa2xx_udc.h> | 29 | #include <linux/platform_data/pxa2xx_udc.h> |
| 30 | #include <linux/of_device.h> | ||
| 31 | #include <linux/of_gpio.h> | ||
| 29 | 32 | ||
| 30 | #include <linux/usb.h> | 33 | #include <linux/usb.h> |
| 31 | #include <linux/usb/ch9.h> | 34 | #include <linux/usb/ch9.h> |
| @@ -1507,18 +1510,13 @@ static struct usb_ep_ops pxa_ep_ops = { | |||
| 1507 | */ | 1510 | */ |
| 1508 | static void dplus_pullup(struct pxa_udc *udc, int on) | 1511 | static void dplus_pullup(struct pxa_udc *udc, int on) |
| 1509 | { | 1512 | { |
| 1510 | if (on) { | 1513 | if (udc->gpiod) { |
| 1511 | if (gpio_is_valid(udc->mach->gpio_pullup)) | 1514 | gpiod_set_value(udc->gpiod, on); |
| 1512 | gpio_set_value(udc->mach->gpio_pullup, | 1515 | } else if (udc->udc_command) { |
| 1513 | !udc->mach->gpio_pullup_inverted); | 1516 | if (on) |
| 1514 | if (udc->mach->udc_command) | 1517 | udc->udc_command(PXA2XX_UDC_CMD_CONNECT); |
| 1515 | udc->mach->udc_command(PXA2XX_UDC_CMD_CONNECT); | 1518 | else |
| 1516 | } else { | 1519 | udc->udc_command(PXA2XX_UDC_CMD_DISCONNECT); |
| 1517 | if (gpio_is_valid(udc->mach->gpio_pullup)) | ||
| 1518 | gpio_set_value(udc->mach->gpio_pullup, | ||
| 1519 | udc->mach->gpio_pullup_inverted); | ||
| 1520 | if (udc->mach->udc_command) | ||
| 1521 | udc->mach->udc_command(PXA2XX_UDC_CMD_DISCONNECT); | ||
| 1522 | } | 1520 | } |
| 1523 | udc->pullup_on = on; | 1521 | udc->pullup_on = on; |
| 1524 | } | 1522 | } |
| @@ -1609,7 +1607,7 @@ static int pxa_udc_pullup(struct usb_gadget *_gadget, int is_active) | |||
| 1609 | { | 1607 | { |
| 1610 | struct pxa_udc *udc = to_gadget_udc(_gadget); | 1608 | struct pxa_udc *udc = to_gadget_udc(_gadget); |
| 1611 | 1609 | ||
| 1612 | if (!gpio_is_valid(udc->mach->gpio_pullup) && !udc->mach->udc_command) | 1610 | if (!udc->gpiod && !udc->udc_command) |
| 1613 | return -EOPNOTSUPP; | 1611 | return -EOPNOTSUPP; |
| 1614 | 1612 | ||
| 1615 | dplus_pullup(udc, is_active); | 1613 | dplus_pullup(udc, is_active); |
| @@ -1671,8 +1669,7 @@ static int pxa_udc_vbus_draw(struct usb_gadget *_gadget, unsigned mA) | |||
| 1671 | 1669 | ||
| 1672 | static int pxa27x_udc_start(struct usb_gadget *g, | 1670 | static int pxa27x_udc_start(struct usb_gadget *g, |
| 1673 | struct usb_gadget_driver *driver); | 1671 | struct usb_gadget_driver *driver); |
| 1674 | static int pxa27x_udc_stop(struct usb_gadget *g, | 1672 | static int pxa27x_udc_stop(struct usb_gadget *g); |
| 1675 | struct usb_gadget_driver *driver); | ||
| 1676 | 1673 | ||
| 1677 | static const struct usb_gadget_ops pxa_udc_ops = { | 1674 | static const struct usb_gadget_ops pxa_udc_ops = { |
| 1678 | .get_frame = pxa_udc_get_frame, | 1675 | .get_frame = pxa_udc_get_frame, |
| @@ -1701,10 +1698,10 @@ static void udc_disable(struct pxa_udc *udc) | |||
| 1701 | udc_writel(udc, UDCICR1, 0); | 1698 | udc_writel(udc, UDCICR1, 0); |
| 1702 | 1699 | ||
| 1703 | udc_clear_mask_UDCCR(udc, UDCCR_UDE); | 1700 | udc_clear_mask_UDCCR(udc, UDCCR_UDE); |
| 1704 | clk_disable(udc->clk); | ||
| 1705 | 1701 | ||
| 1706 | ep0_idle(udc); | 1702 | ep0_idle(udc); |
| 1707 | udc->gadget.speed = USB_SPEED_UNKNOWN; | 1703 | udc->gadget.speed = USB_SPEED_UNKNOWN; |
| 1704 | clk_disable(udc->clk); | ||
| 1708 | 1705 | ||
| 1709 | udc->enabled = 0; | 1706 | udc->enabled = 0; |
| 1710 | } | 1707 | } |
| @@ -1757,16 +1754,16 @@ static void udc_enable(struct pxa_udc *udc) | |||
| 1757 | if (udc->enabled) | 1754 | if (udc->enabled) |
| 1758 | return; | 1755 | return; |
| 1759 | 1756 | ||
| 1757 | clk_enable(udc->clk); | ||
| 1760 | udc_writel(udc, UDCICR0, 0); | 1758 | udc_writel(udc, UDCICR0, 0); |
| 1761 | udc_writel(udc, UDCICR1, 0); | 1759 | udc_writel(udc, UDCICR1, 0); |
| 1762 | udc_clear_mask_UDCCR(udc, UDCCR_UDE); | 1760 | udc_clear_mask_UDCCR(udc, UDCCR_UDE); |
| 1763 | 1761 | ||
| 1764 | clk_enable(udc->clk); | ||
| 1765 | |||
| 1766 | ep0_idle(udc); | 1762 | ep0_idle(udc); |
| 1767 | udc->gadget.speed = USB_SPEED_FULL; | 1763 | udc->gadget.speed = USB_SPEED_FULL; |
| 1768 | memset(&udc->stats, 0, sizeof(udc->stats)); | 1764 | memset(&udc->stats, 0, sizeof(udc->stats)); |
| 1769 | 1765 | ||
| 1766 | pxa_eps_setup(udc); | ||
| 1770 | udc_set_mask_UDCCR(udc, UDCCR_UDE); | 1767 | udc_set_mask_UDCCR(udc, UDCCR_UDE); |
| 1771 | ep_write_UDCCSR(&udc->pxa_ep[0], UDCCSR0_ACM); | 1768 | ep_write_UDCCSR(&udc->pxa_ep[0], UDCCSR0_ACM); |
| 1772 | udelay(2); | 1769 | udelay(2); |
| @@ -1859,12 +1856,11 @@ static void stop_activity(struct pxa_udc *udc, struct usb_gadget_driver *driver) | |||
| 1859 | * | 1856 | * |
| 1860 | * Returns 0 if no error, -ENODEV, -EINVAL otherwise | 1857 | * Returns 0 if no error, -ENODEV, -EINVAL otherwise |
| 1861 | */ | 1858 | */ |
| 1862 | static int pxa27x_udc_stop(struct usb_gadget *g, | 1859 | static int pxa27x_udc_stop(struct usb_gadget *g) |
| 1863 | struct usb_gadget_driver *driver) | ||
| 1864 | { | 1860 | { |
| 1865 | struct pxa_udc *udc = to_pxa(g); | 1861 | struct pxa_udc *udc = to_pxa(g); |
| 1866 | 1862 | ||
| 1867 | stop_activity(udc, driver); | 1863 | stop_activity(udc, NULL); |
| 1868 | udc_disable(udc); | 1864 | udc_disable(udc); |
| 1869 | dplus_pullup(udc, 0); | 1865 | dplus_pullup(udc, 0); |
| 1870 | 1866 | ||
| @@ -2404,6 +2400,14 @@ static struct pxa_udc memory = { | |||
| 2404 | } | 2400 | } |
| 2405 | }; | 2401 | }; |
| 2406 | 2402 | ||
| 2403 | #if defined(CONFIG_OF) | ||
| 2404 | static struct of_device_id udc_pxa_dt_ids[] = { | ||
| 2405 | { .compatible = "marvell,pxa270-udc" }, | ||
| 2406 | {} | ||
| 2407 | }; | ||
| 2408 | MODULE_DEVICE_TABLE(of, udc_pxa_dt_ids); | ||
| 2409 | #endif | ||
| 2410 | |||
| 2407 | /** | 2411 | /** |
| 2408 | * pxa_udc_probe - probes the udc device | 2412 | * pxa_udc_probe - probes the udc device |
| 2409 | * @_dev: platform device | 2413 | * @_dev: platform device |
| @@ -2416,81 +2420,77 @@ static int pxa_udc_probe(struct platform_device *pdev) | |||
| 2416 | struct resource *regs; | 2420 | struct resource *regs; |
| 2417 | struct pxa_udc *udc = &memory; | 2421 | struct pxa_udc *udc = &memory; |
| 2418 | int retval = 0, gpio; | 2422 | int retval = 0, gpio; |
| 2423 | struct pxa2xx_udc_mach_info *mach = dev_get_platdata(&pdev->dev); | ||
| 2424 | unsigned long gpio_flags; | ||
| 2425 | |||
| 2426 | if (mach) { | ||
| 2427 | gpio_flags = mach->gpio_pullup_inverted ? GPIOF_ACTIVE_LOW : 0; | ||
| 2428 | gpio = mach->gpio_pullup; | ||
| 2429 | if (gpio_is_valid(gpio)) { | ||
| 2430 | retval = devm_gpio_request_one(&pdev->dev, gpio, | ||
| 2431 | gpio_flags, | ||
| 2432 | "USB D+ pullup"); | ||
| 2433 | if (retval) | ||
| 2434 | return retval; | ||
| 2435 | udc->gpiod = gpio_to_desc(mach->gpio_pullup); | ||
| 2436 | } | ||
| 2437 | udc->udc_command = mach->udc_command; | ||
| 2438 | } else { | ||
| 2439 | udc->gpiod = devm_gpiod_get(&pdev->dev, NULL); | ||
| 2440 | } | ||
| 2419 | 2441 | ||
| 2420 | regs = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 2442 | regs = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 2421 | if (!regs) | 2443 | udc->regs = devm_ioremap_resource(&pdev->dev, regs); |
| 2422 | return -ENXIO; | 2444 | if (IS_ERR(udc->regs)) |
| 2445 | return PTR_ERR(udc->regs); | ||
| 2423 | udc->irq = platform_get_irq(pdev, 0); | 2446 | udc->irq = platform_get_irq(pdev, 0); |
| 2424 | if (udc->irq < 0) | 2447 | if (udc->irq < 0) |
| 2425 | return udc->irq; | 2448 | return udc->irq; |
| 2426 | 2449 | ||
| 2427 | udc->dev = &pdev->dev; | 2450 | udc->dev = &pdev->dev; |
| 2428 | udc->mach = dev_get_platdata(&pdev->dev); | ||
| 2429 | udc->transceiver = usb_get_phy(USB_PHY_TYPE_USB2); | 2451 | udc->transceiver = usb_get_phy(USB_PHY_TYPE_USB2); |
| 2430 | 2452 | ||
| 2431 | gpio = udc->mach->gpio_pullup; | 2453 | if (IS_ERR(udc->gpiod)) { |
| 2432 | if (gpio_is_valid(gpio)) { | 2454 | dev_err(&pdev->dev, "Couldn't find or request D+ gpio : %ld\n", |
| 2433 | retval = gpio_request(gpio, "USB D+ pullup"); | 2455 | PTR_ERR(udc->gpiod)); |
| 2434 | if (retval == 0) | 2456 | return PTR_ERR(udc->gpiod); |
| 2435 | gpio_direction_output(gpio, | ||
| 2436 | udc->mach->gpio_pullup_inverted); | ||
| 2437 | } | ||
| 2438 | if (retval) { | ||
| 2439 | dev_err(&pdev->dev, "Couldn't request gpio %d : %d\n", | ||
| 2440 | gpio, retval); | ||
| 2441 | return retval; | ||
| 2442 | } | 2457 | } |
| 2458 | if (udc->gpiod) | ||
| 2459 | gpiod_direction_output(udc->gpiod, 0); | ||
| 2460 | |||
| 2461 | udc->clk = devm_clk_get(&pdev->dev, NULL); | ||
| 2462 | if (IS_ERR(udc->clk)) | ||
| 2463 | return PTR_ERR(udc->clk); | ||
| 2443 | 2464 | ||
| 2444 | udc->clk = clk_get(&pdev->dev, NULL); | ||
| 2445 | if (IS_ERR(udc->clk)) { | ||
| 2446 | retval = PTR_ERR(udc->clk); | ||
| 2447 | goto err_clk; | ||
| 2448 | } | ||
| 2449 | retval = clk_prepare(udc->clk); | 2465 | retval = clk_prepare(udc->clk); |
| 2450 | if (retval) | 2466 | if (retval) |
| 2451 | goto err_clk_prepare; | 2467 | return retval; |
| 2452 | |||
| 2453 | retval = -ENOMEM; | ||
| 2454 | udc->regs = ioremap(regs->start, resource_size(regs)); | ||
| 2455 | if (!udc->regs) { | ||
| 2456 | dev_err(&pdev->dev, "Unable to map UDC I/O memory\n"); | ||
| 2457 | goto err_map; | ||
| 2458 | } | ||
| 2459 | 2468 | ||
| 2460 | udc->vbus_sensed = 0; | 2469 | udc->vbus_sensed = 0; |
| 2461 | 2470 | ||
| 2462 | the_controller = udc; | 2471 | the_controller = udc; |
| 2463 | platform_set_drvdata(pdev, udc); | 2472 | platform_set_drvdata(pdev, udc); |
| 2464 | udc_init_data(udc); | 2473 | udc_init_data(udc); |
| 2465 | pxa_eps_setup(udc); | ||
| 2466 | 2474 | ||
| 2467 | /* irq setup after old hardware state is cleaned up */ | 2475 | /* irq setup after old hardware state is cleaned up */ |
| 2468 | retval = request_irq(udc->irq, pxa_udc_irq, | 2476 | retval = devm_request_irq(&pdev->dev, udc->irq, pxa_udc_irq, |
| 2469 | IRQF_SHARED, driver_name, udc); | 2477 | IRQF_SHARED, driver_name, udc); |
| 2470 | if (retval != 0) { | 2478 | if (retval != 0) { |
| 2471 | dev_err(udc->dev, "%s: can't get irq %i, err %d\n", | 2479 | dev_err(udc->dev, "%s: can't get irq %i, err %d\n", |
| 2472 | driver_name, udc->irq, retval); | 2480 | driver_name, udc->irq, retval); |
| 2473 | goto err_irq; | 2481 | goto err; |
| 2474 | } | 2482 | } |
| 2475 | 2483 | ||
| 2476 | retval = usb_add_gadget_udc(&pdev->dev, &udc->gadget); | 2484 | retval = usb_add_gadget_udc(&pdev->dev, &udc->gadget); |
| 2477 | if (retval) | 2485 | if (retval) |
| 2478 | goto err_add_udc; | 2486 | goto err; |
| 2479 | 2487 | ||
| 2480 | pxa_init_debugfs(udc); | 2488 | pxa_init_debugfs(udc); |
| 2481 | 2489 | if (should_enable_udc(udc)) | |
| 2490 | udc_enable(udc); | ||
| 2482 | return 0; | 2491 | return 0; |
| 2483 | 2492 | err: | |
| 2484 | err_add_udc: | ||
| 2485 | free_irq(udc->irq, udc); | ||
| 2486 | err_irq: | ||
| 2487 | iounmap(udc->regs); | ||
| 2488 | err_map: | ||
| 2489 | clk_unprepare(udc->clk); | 2493 | clk_unprepare(udc->clk); |
| 2490 | err_clk_prepare: | ||
| 2491 | clk_put(udc->clk); | ||
| 2492 | udc->clk = NULL; | ||
| 2493 | err_clk: | ||
| 2494 | return retval; | 2494 | return retval; |
| 2495 | } | 2495 | } |
| 2496 | 2496 | ||
| @@ -2501,22 +2501,15 @@ err_clk: | |||
| 2501 | static int pxa_udc_remove(struct platform_device *_dev) | 2501 | static int pxa_udc_remove(struct platform_device *_dev) |
| 2502 | { | 2502 | { |
| 2503 | struct pxa_udc *udc = platform_get_drvdata(_dev); | 2503 | struct pxa_udc *udc = platform_get_drvdata(_dev); |
| 2504 | int gpio = udc->mach->gpio_pullup; | ||
| 2505 | 2504 | ||
| 2506 | usb_del_gadget_udc(&udc->gadget); | 2505 | usb_del_gadget_udc(&udc->gadget); |
| 2507 | usb_gadget_unregister_driver(udc->driver); | ||
| 2508 | free_irq(udc->irq, udc); | ||
| 2509 | pxa_cleanup_debugfs(udc); | 2506 | pxa_cleanup_debugfs(udc); |
| 2510 | if (gpio_is_valid(gpio)) | ||
| 2511 | gpio_free(gpio); | ||
| 2512 | 2507 | ||
| 2513 | usb_put_phy(udc->transceiver); | 2508 | usb_put_phy(udc->transceiver); |
| 2514 | 2509 | ||
| 2515 | udc->transceiver = NULL; | 2510 | udc->transceiver = NULL; |
| 2516 | the_controller = NULL; | 2511 | the_controller = NULL; |
| 2517 | clk_unprepare(udc->clk); | 2512 | clk_unprepare(udc->clk); |
| 2518 | clk_put(udc->clk); | ||
| 2519 | iounmap(udc->regs); | ||
| 2520 | 2513 | ||
| 2521 | return 0; | 2514 | return 0; |
| 2522 | } | 2515 | } |
| @@ -2546,19 +2539,11 @@ extern void pxa27x_clear_otgph(void); | |||
| 2546 | */ | 2539 | */ |
| 2547 | static int pxa_udc_suspend(struct platform_device *_dev, pm_message_t state) | 2540 | static int pxa_udc_suspend(struct platform_device *_dev, pm_message_t state) |
| 2548 | { | 2541 | { |
| 2549 | int i; | ||
| 2550 | struct pxa_udc *udc = platform_get_drvdata(_dev); | 2542 | struct pxa_udc *udc = platform_get_drvdata(_dev); |
| 2551 | struct pxa_ep *ep; | 2543 | struct pxa_ep *ep; |
| 2552 | 2544 | ||
| 2553 | ep = &udc->pxa_ep[0]; | 2545 | ep = &udc->pxa_ep[0]; |
| 2554 | udc->udccsr0 = udc_ep_readl(ep, UDCCSR); | 2546 | udc->udccsr0 = udc_ep_readl(ep, UDCCSR); |
| 2555 | for (i = 1; i < NR_PXA_ENDPOINTS; i++) { | ||
| 2556 | ep = &udc->pxa_ep[i]; | ||
| 2557 | ep->udccsr_value = udc_ep_readl(ep, UDCCSR); | ||
| 2558 | ep->udccr_value = udc_ep_readl(ep, UDCCR); | ||
| 2559 | ep_dbg(ep, "udccsr:0x%03x, udccr:0x%x\n", | ||
| 2560 | ep->udccsr_value, ep->udccr_value); | ||
| 2561 | } | ||
| 2562 | 2547 | ||
| 2563 | udc_disable(udc); | 2548 | udc_disable(udc); |
| 2564 | udc->pullup_resume = udc->pullup_on; | 2549 | udc->pullup_resume = udc->pullup_on; |
| @@ -2576,19 +2561,11 @@ static int pxa_udc_suspend(struct platform_device *_dev, pm_message_t state) | |||
| 2576 | */ | 2561 | */ |
| 2577 | static int pxa_udc_resume(struct platform_device *_dev) | 2562 | static int pxa_udc_resume(struct platform_device *_dev) |
| 2578 | { | 2563 | { |
| 2579 | int i; | ||
| 2580 | struct pxa_udc *udc = platform_get_drvdata(_dev); | 2564 | struct pxa_udc *udc = platform_get_drvdata(_dev); |
| 2581 | struct pxa_ep *ep; | 2565 | struct pxa_ep *ep; |
| 2582 | 2566 | ||
| 2583 | ep = &udc->pxa_ep[0]; | 2567 | ep = &udc->pxa_ep[0]; |
| 2584 | udc_ep_writel(ep, UDCCSR, udc->udccsr0 & (UDCCSR0_FST | UDCCSR0_DME)); | 2568 | udc_ep_writel(ep, UDCCSR, udc->udccsr0 & (UDCCSR0_FST | UDCCSR0_DME)); |
| 2585 | for (i = 1; i < NR_PXA_ENDPOINTS; i++) { | ||
| 2586 | ep = &udc->pxa_ep[i]; | ||
| 2587 | udc_ep_writel(ep, UDCCSR, ep->udccsr_value); | ||
| 2588 | udc_ep_writel(ep, UDCCR, ep->udccr_value); | ||
| 2589 | ep_dbg(ep, "udccsr:0x%03x, udccr:0x%x\n", | ||
| 2590 | ep->udccsr_value, ep->udccr_value); | ||
| 2591 | } | ||
| 2592 | 2569 | ||
| 2593 | dplus_pullup(udc, udc->pullup_resume); | 2570 | dplus_pullup(udc, udc->pullup_resume); |
| 2594 | if (should_enable_udc(udc)) | 2571 | if (should_enable_udc(udc)) |
| @@ -2615,6 +2592,7 @@ static struct platform_driver udc_driver = { | |||
| 2615 | .driver = { | 2592 | .driver = { |
| 2616 | .name = "pxa27x-udc", | 2593 | .name = "pxa27x-udc", |
| 2617 | .owner = THIS_MODULE, | 2594 | .owner = THIS_MODULE, |
| 2595 | .of_match_table = of_match_ptr(udc_pxa_dt_ids), | ||
| 2618 | }, | 2596 | }, |
| 2619 | .probe = pxa_udc_probe, | 2597 | .probe = pxa_udc_probe, |
| 2620 | .remove = pxa_udc_remove, | 2598 | .remove = pxa_udc_remove, |
diff --git a/drivers/usb/gadget/udc/pxa27x_udc.h b/drivers/usb/gadget/udc/pxa27x_udc.h index 28f2b53530f5..11e14232794b 100644 --- a/drivers/usb/gadget/udc/pxa27x_udc.h +++ b/drivers/usb/gadget/udc/pxa27x_udc.h | |||
| @@ -420,7 +420,8 @@ struct udc_stats { | |||
| 420 | * @usb_gadget: udc gadget structure | 420 | * @usb_gadget: udc gadget structure |
| 421 | * @driver: bound gadget (zero, g_ether, g_mass_storage, ...) | 421 | * @driver: bound gadget (zero, g_ether, g_mass_storage, ...) |
| 422 | * @dev: device | 422 | * @dev: device |
| 423 | * @mach: machine info, used to activate specific GPIO | 423 | * @udc_command: machine specific function to activate D+ pullup |
| 424 | * @gpiod: gpio descriptor of gpio for D+ pullup (or NULL if none) | ||
| 424 | * @transceiver: external transceiver to handle vbus sense and D+ pullup | 425 | * @transceiver: external transceiver to handle vbus sense and D+ pullup |
| 425 | * @ep0state: control endpoint state machine state | 426 | * @ep0state: control endpoint state machine state |
| 426 | * @stats: statistics on udc usage | 427 | * @stats: statistics on udc usage |
| @@ -446,7 +447,8 @@ struct pxa_udc { | |||
| 446 | struct usb_gadget gadget; | 447 | struct usb_gadget gadget; |
| 447 | struct usb_gadget_driver *driver; | 448 | struct usb_gadget_driver *driver; |
| 448 | struct device *dev; | 449 | struct device *dev; |
| 449 | struct pxa2xx_udc_mach_info *mach; | 450 | void (*udc_command)(int); |
| 451 | struct gpio_desc *gpiod; | ||
| 450 | struct usb_phy *transceiver; | 452 | struct usb_phy *transceiver; |
| 451 | 453 | ||
| 452 | enum ep0_state ep0state; | 454 | enum ep0_state ep0state; |
diff --git a/drivers/usb/gadget/udc/r8a66597-udc.c b/drivers/usb/gadget/udc/r8a66597-udc.c index f8186613b53e..06870da0b988 100644 --- a/drivers/usb/gadget/udc/r8a66597-udc.c +++ b/drivers/usb/gadget/udc/r8a66597-udc.c | |||
| @@ -1345,7 +1345,7 @@ static void irq_device_state(struct r8a66597 *r8a66597) | |||
| 1345 | if (dvsq == DS_DFLT) { | 1345 | if (dvsq == DS_DFLT) { |
| 1346 | /* bus reset */ | 1346 | /* bus reset */ |
| 1347 | spin_unlock(&r8a66597->lock); | 1347 | spin_unlock(&r8a66597->lock); |
| 1348 | r8a66597->driver->disconnect(&r8a66597->gadget); | 1348 | usb_gadget_udc_reset(&r8a66597->gadget, r8a66597->driver); |
| 1349 | spin_lock(&r8a66597->lock); | 1349 | spin_lock(&r8a66597->lock); |
| 1350 | r8a66597_update_usb_speed(r8a66597); | 1350 | r8a66597_update_usb_speed(r8a66597); |
| 1351 | } | 1351 | } |
| @@ -1763,8 +1763,7 @@ static int r8a66597_start(struct usb_gadget *gadget, | |||
| 1763 | return 0; | 1763 | return 0; |
| 1764 | } | 1764 | } |
| 1765 | 1765 | ||
| 1766 | static int r8a66597_stop(struct usb_gadget *gadget, | 1766 | static int r8a66597_stop(struct usb_gadget *gadget) |
| 1767 | struct usb_gadget_driver *driver) | ||
| 1768 | { | 1767 | { |
| 1769 | struct r8a66597 *r8a66597 = gadget_to_r8a66597(gadget); | 1768 | struct r8a66597 *r8a66597 = gadget_to_r8a66597(gadget); |
| 1770 | unsigned long flags; | 1769 | unsigned long flags; |
| @@ -1846,10 +1845,7 @@ static int r8a66597_sudmac_ioremap(struct r8a66597 *r8a66597, | |||
| 1846 | 1845 | ||
| 1847 | res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "sudmac"); | 1846 | res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "sudmac"); |
| 1848 | r8a66597->sudmac_reg = devm_ioremap_resource(&pdev->dev, res); | 1847 | r8a66597->sudmac_reg = devm_ioremap_resource(&pdev->dev, res); |
| 1849 | if (IS_ERR(r8a66597->sudmac_reg)) | 1848 | return PTR_ERR_OR_ZERO(r8a66597->sudmac_reg); |
| 1850 | return PTR_ERR(r8a66597->sudmac_reg); | ||
| 1851 | |||
| 1852 | return 0; | ||
| 1853 | } | 1849 | } |
| 1854 | 1850 | ||
| 1855 | static int r8a66597_probe(struct platform_device *pdev) | 1851 | static int r8a66597_probe(struct platform_device *pdev) |
diff --git a/drivers/usb/gadget/udc/s3c-hsudc.c b/drivers/usb/gadget/udc/s3c-hsudc.c index dfbf55797360..97d3a9144381 100644 --- a/drivers/usb/gadget/udc/s3c-hsudc.c +++ b/drivers/usb/gadget/udc/s3c-hsudc.c | |||
| @@ -1172,8 +1172,6 @@ static int s3c_hsudc_start(struct usb_gadget *gadget, | |||
| 1172 | } | 1172 | } |
| 1173 | 1173 | ||
| 1174 | enable_irq(hsudc->irq); | 1174 | enable_irq(hsudc->irq); |
| 1175 | dev_info(hsudc->dev, "bound driver %s\n", driver->driver.name); | ||
| 1176 | |||
| 1177 | s3c_hsudc_reconfig(hsudc); | 1175 | s3c_hsudc_reconfig(hsudc); |
| 1178 | 1176 | ||
| 1179 | pm_runtime_get_sync(hsudc->dev); | 1177 | pm_runtime_get_sync(hsudc->dev); |
| @@ -1190,8 +1188,7 @@ err_supplies: | |||
| 1190 | return ret; | 1188 | return ret; |
| 1191 | } | 1189 | } |
| 1192 | 1190 | ||
| 1193 | static int s3c_hsudc_stop(struct usb_gadget *gadget, | 1191 | static int s3c_hsudc_stop(struct usb_gadget *gadget) |
| 1194 | struct usb_gadget_driver *driver) | ||
| 1195 | { | 1192 | { |
| 1196 | struct s3c_hsudc *hsudc = to_hsudc(gadget); | 1193 | struct s3c_hsudc *hsudc = to_hsudc(gadget); |
| 1197 | unsigned long flags; | 1194 | unsigned long flags; |
| @@ -1199,11 +1196,7 @@ static int s3c_hsudc_stop(struct usb_gadget *gadget, | |||
| 1199 | if (!hsudc) | 1196 | if (!hsudc) |
| 1200 | return -ENODEV; | 1197 | return -ENODEV; |
| 1201 | 1198 | ||
| 1202 | if (!driver || driver != hsudc->driver) | ||
| 1203 | return -EINVAL; | ||
| 1204 | |||
| 1205 | spin_lock_irqsave(&hsudc->lock, flags); | 1199 | spin_lock_irqsave(&hsudc->lock, flags); |
| 1206 | hsudc->driver = NULL; | ||
| 1207 | hsudc->gadget.speed = USB_SPEED_UNKNOWN; | 1200 | hsudc->gadget.speed = USB_SPEED_UNKNOWN; |
| 1208 | s3c_hsudc_uninit_phy(); | 1201 | s3c_hsudc_uninit_phy(); |
| 1209 | 1202 | ||
| @@ -1220,9 +1213,8 @@ static int s3c_hsudc_stop(struct usb_gadget *gadget, | |||
| 1220 | disable_irq(hsudc->irq); | 1213 | disable_irq(hsudc->irq); |
| 1221 | 1214 | ||
| 1222 | regulator_bulk_disable(ARRAY_SIZE(hsudc->supplies), hsudc->supplies); | 1215 | regulator_bulk_disable(ARRAY_SIZE(hsudc->supplies), hsudc->supplies); |
| 1216 | hsudc->driver = NULL; | ||
| 1223 | 1217 | ||
| 1224 | dev_info(hsudc->dev, "unregistered gadget driver '%s'\n", | ||
| 1225 | driver->driver.name); | ||
| 1226 | return 0; | 1218 | return 0; |
| 1227 | } | 1219 | } |
| 1228 | 1220 | ||
| @@ -1267,10 +1259,8 @@ static int s3c_hsudc_probe(struct platform_device *pdev) | |||
| 1267 | hsudc = devm_kzalloc(&pdev->dev, sizeof(struct s3c_hsudc) + | 1259 | hsudc = devm_kzalloc(&pdev->dev, sizeof(struct s3c_hsudc) + |
| 1268 | sizeof(struct s3c_hsudc_ep) * pd->epnum, | 1260 | sizeof(struct s3c_hsudc_ep) * pd->epnum, |
| 1269 | GFP_KERNEL); | 1261 | GFP_KERNEL); |
| 1270 | if (!hsudc) { | 1262 | if (!hsudc) |
| 1271 | dev_err(dev, "cannot allocate memory\n"); | ||
| 1272 | return -ENOMEM; | 1263 | return -ENOMEM; |
| 1273 | } | ||
| 1274 | 1264 | ||
| 1275 | platform_set_drvdata(pdev, dev); | 1265 | platform_set_drvdata(pdev, dev); |
| 1276 | hsudc->dev = dev; | 1266 | hsudc->dev = dev; |
diff --git a/drivers/usb/gadget/udc/s3c2410_udc.c b/drivers/usb/gadget/udc/s3c2410_udc.c index ff423d15beff..2a8e36d31488 100644 --- a/drivers/usb/gadget/udc/s3c2410_udc.c +++ b/drivers/usb/gadget/udc/s3c2410_udc.c | |||
| @@ -1541,8 +1541,7 @@ static int s3c2410_vbus_draw(struct usb_gadget *_gadget, unsigned ma) | |||
| 1541 | 1541 | ||
| 1542 | static int s3c2410_udc_start(struct usb_gadget *g, | 1542 | static int s3c2410_udc_start(struct usb_gadget *g, |
| 1543 | struct usb_gadget_driver *driver); | 1543 | struct usb_gadget_driver *driver); |
| 1544 | static int s3c2410_udc_stop(struct usb_gadget *g, | 1544 | static int s3c2410_udc_stop(struct usb_gadget *g); |
| 1545 | struct usb_gadget_driver *driver); | ||
| 1546 | 1545 | ||
| 1547 | static const struct usb_gadget_ops s3c2410_ops = { | 1546 | static const struct usb_gadget_ops s3c2410_ops = { |
| 1548 | .get_frame = s3c2410_udc_get_frame, | 1547 | .get_frame = s3c2410_udc_get_frame, |
| @@ -1683,8 +1682,7 @@ static int s3c2410_udc_start(struct usb_gadget *g, | |||
| 1683 | return 0; | 1682 | return 0; |
| 1684 | } | 1683 | } |
| 1685 | 1684 | ||
| 1686 | static int s3c2410_udc_stop(struct usb_gadget *g, | 1685 | static int s3c2410_udc_stop(struct usb_gadget *g) |
| 1687 | struct usb_gadget_driver *driver) | ||
| 1688 | { | 1686 | { |
| 1689 | struct s3c2410_udc *udc = to_s3c2410(g); | 1687 | struct s3c2410_udc *udc = to_s3c2410(g); |
| 1690 | 1688 | ||
diff --git a/drivers/usb/gadget/udc/udc-core.c b/drivers/usb/gadget/udc/udc-core.c index f2054659f25b..e31d574d8860 100644 --- a/drivers/usb/gadget/udc/udc-core.c +++ b/drivers/usb/gadget/udc/udc-core.c | |||
| @@ -174,8 +174,7 @@ EXPORT_SYMBOL_GPL(usb_gadget_udc_reset); | |||
| 174 | 174 | ||
| 175 | /** | 175 | /** |
| 176 | * usb_gadget_udc_start - tells usb device controller to start up | 176 | * usb_gadget_udc_start - tells usb device controller to start up |
| 177 | * @gadget: The gadget we want to get started | 177 | * @udc: The UDC to be started |
| 178 | * @driver: The driver we want to bind to @gadget | ||
| 179 | * | 178 | * |
| 180 | * This call is issued by the UDC Class driver when it's about | 179 | * This call is issued by the UDC Class driver when it's about |
| 181 | * to register a gadget driver to the device controller, before | 180 | * to register a gadget driver to the device controller, before |
| @@ -186,10 +185,9 @@ EXPORT_SYMBOL_GPL(usb_gadget_udc_reset); | |||
| 186 | * | 185 | * |
| 187 | * Returns zero on success, else negative errno. | 186 | * Returns zero on success, else negative errno. |
| 188 | */ | 187 | */ |
| 189 | static inline int usb_gadget_udc_start(struct usb_gadget *gadget, | 188 | static inline int usb_gadget_udc_start(struct usb_udc *udc) |
| 190 | struct usb_gadget_driver *driver) | ||
| 191 | { | 189 | { |
| 192 | return gadget->ops->udc_start(gadget, driver); | 190 | return udc->gadget->ops->udc_start(udc->gadget, udc->driver); |
| 193 | } | 191 | } |
| 194 | 192 | ||
| 195 | /** | 193 | /** |
| @@ -204,10 +202,9 @@ static inline int usb_gadget_udc_start(struct usb_gadget *gadget, | |||
| 204 | * far as powering off UDC completely and disable its data | 202 | * far as powering off UDC completely and disable its data |
| 205 | * line pullups. | 203 | * line pullups. |
| 206 | */ | 204 | */ |
| 207 | static inline void usb_gadget_udc_stop(struct usb_gadget *gadget, | 205 | static inline void usb_gadget_udc_stop(struct usb_udc *udc) |
| 208 | struct usb_gadget_driver *driver) | ||
| 209 | { | 206 | { |
| 210 | gadget->ops->udc_stop(gadget, driver); | 207 | udc->gadget->ops->udc_stop(udc->gadget); |
| 211 | } | 208 | } |
| 212 | 209 | ||
| 213 | /** | 210 | /** |
| @@ -328,14 +325,14 @@ EXPORT_SYMBOL_GPL(usb_add_gadget_udc); | |||
| 328 | static void usb_gadget_remove_driver(struct usb_udc *udc) | 325 | static void usb_gadget_remove_driver(struct usb_udc *udc) |
| 329 | { | 326 | { |
| 330 | dev_dbg(&udc->dev, "unregistering UDC driver [%s]\n", | 327 | dev_dbg(&udc->dev, "unregistering UDC driver [%s]\n", |
| 331 | udc->gadget->name); | 328 | udc->driver->function); |
| 332 | 329 | ||
| 333 | kobject_uevent(&udc->dev.kobj, KOBJ_CHANGE); | 330 | kobject_uevent(&udc->dev.kobj, KOBJ_CHANGE); |
| 334 | 331 | ||
| 335 | usb_gadget_disconnect(udc->gadget); | 332 | usb_gadget_disconnect(udc->gadget); |
| 336 | udc->driver->disconnect(udc->gadget); | 333 | udc->driver->disconnect(udc->gadget); |
| 337 | udc->driver->unbind(udc->gadget); | 334 | udc->driver->unbind(udc->gadget); |
| 338 | usb_gadget_udc_stop(udc->gadget, NULL); | 335 | usb_gadget_udc_stop(udc); |
| 339 | 336 | ||
| 340 | udc->driver = NULL; | 337 | udc->driver = NULL; |
| 341 | udc->dev.driver = NULL; | 338 | udc->dev.driver = NULL; |
| @@ -395,7 +392,7 @@ static int udc_bind_to_driver(struct usb_udc *udc, struct usb_gadget_driver *dri | |||
| 395 | ret = driver->bind(udc->gadget, driver); | 392 | ret = driver->bind(udc->gadget, driver); |
| 396 | if (ret) | 393 | if (ret) |
| 397 | goto err1; | 394 | goto err1; |
| 398 | ret = usb_gadget_udc_start(udc->gadget, driver); | 395 | ret = usb_gadget_udc_start(udc); |
| 399 | if (ret) { | 396 | if (ret) { |
| 400 | driver->unbind(udc->gadget); | 397 | driver->unbind(udc->gadget); |
| 401 | goto err1; | 398 | goto err1; |
| @@ -414,7 +411,7 @@ err1: | |||
| 414 | return ret; | 411 | return ret; |
| 415 | } | 412 | } |
| 416 | 413 | ||
| 417 | int udc_attach_driver(const char *name, struct usb_gadget_driver *driver) | 414 | int usb_udc_attach_driver(const char *name, struct usb_gadget_driver *driver) |
| 418 | { | 415 | { |
| 419 | struct usb_udc *udc = NULL; | 416 | struct usb_udc *udc = NULL; |
| 420 | int ret = -ENODEV; | 417 | int ret = -ENODEV; |
| @@ -438,7 +435,7 @@ out: | |||
| 438 | mutex_unlock(&udc_lock); | 435 | mutex_unlock(&udc_lock); |
| 439 | return ret; | 436 | return ret; |
| 440 | } | 437 | } |
| 441 | EXPORT_SYMBOL_GPL(udc_attach_driver); | 438 | EXPORT_SYMBOL_GPL(usb_udc_attach_driver); |
| 442 | 439 | ||
| 443 | int usb_gadget_probe_driver(struct usb_gadget_driver *driver) | 440 | int usb_gadget_probe_driver(struct usb_gadget_driver *driver) |
| 444 | { | 441 | { |
| @@ -513,11 +510,12 @@ static ssize_t usb_udc_softconn_store(struct device *dev, | |||
| 513 | } | 510 | } |
| 514 | 511 | ||
| 515 | if (sysfs_streq(buf, "connect")) { | 512 | if (sysfs_streq(buf, "connect")) { |
| 516 | usb_gadget_udc_start(udc->gadget, udc->driver); | 513 | usb_gadget_udc_start(udc); |
| 517 | usb_gadget_connect(udc->gadget); | 514 | usb_gadget_connect(udc->gadget); |
| 518 | } else if (sysfs_streq(buf, "disconnect")) { | 515 | } else if (sysfs_streq(buf, "disconnect")) { |
| 519 | usb_gadget_disconnect(udc->gadget); | 516 | usb_gadget_disconnect(udc->gadget); |
| 520 | usb_gadget_udc_stop(udc->gadget, udc->driver); | 517 | udc->driver->disconnect(udc->gadget); |
| 518 | usb_gadget_udc_stop(udc); | ||
| 521 | } else { | 519 | } else { |
| 522 | dev_err(dev, "unsupported command '%s'\n", buf); | 520 | dev_err(dev, "unsupported command '%s'\n", buf); |
| 523 | return -EINVAL; | 521 | return -EINVAL; |
diff --git a/drivers/usb/gadget/udc/udc-xilinx.c b/drivers/usb/gadget/udc/udc-xilinx.c index ed27e1687a4e..1eac56fc384d 100644 --- a/drivers/usb/gadget/udc/udc-xilinx.c +++ b/drivers/usb/gadget/udc/udc-xilinx.c | |||
| @@ -1403,8 +1403,7 @@ err: | |||
| 1403 | * | 1403 | * |
| 1404 | * Return: zero always | 1404 | * Return: zero always |
| 1405 | */ | 1405 | */ |
| 1406 | static int xudc_stop(struct usb_gadget *gadget, | 1406 | static int xudc_stop(struct usb_gadget *gadget) |
| 1407 | struct usb_gadget_driver *driver) | ||
| 1408 | { | 1407 | { |
| 1409 | struct xusb_udc *udc = to_udc(gadget); | 1408 | struct xusb_udc *udc = to_udc(gadget); |
| 1410 | unsigned long flags; | 1409 | unsigned long flags; |
diff --git a/drivers/usb/host/Kconfig b/drivers/usb/host/Kconfig index a3ca1375dd52..fafc628480e0 100644 --- a/drivers/usb/host/Kconfig +++ b/drivers/usb/host/Kconfig | |||
| @@ -292,11 +292,15 @@ config USB_EHCI_HCD_PLATFORM | |||
| 292 | If unsure, say N. | 292 | If unsure, say N. |
| 293 | 293 | ||
| 294 | config USB_OCTEON_EHCI | 294 | config USB_OCTEON_EHCI |
| 295 | bool "Octeon on-chip EHCI support" | 295 | bool "Octeon on-chip EHCI support (DEPRECATED)" |
| 296 | depends on CAVIUM_OCTEON_SOC | 296 | depends on CAVIUM_OCTEON_SOC |
| 297 | default n | 297 | default n |
| 298 | select USB_EHCI_BIG_ENDIAN_MMIO | 298 | select USB_EHCI_BIG_ENDIAN_MMIO |
| 299 | select USB_EHCI_HCD_PLATFORM | ||
| 299 | help | 300 | help |
| 301 | This option is deprecated now and the driver was removed, use | ||
| 302 | USB_EHCI_HCD_PLATFORM instead. | ||
| 303 | |||
| 300 | Enable support for the Octeon II SOC's on-chip EHCI | 304 | Enable support for the Octeon II SOC's on-chip EHCI |
| 301 | controller. It is needed for high-speed (480Mbit/sec) | 305 | controller. It is needed for high-speed (480Mbit/sec) |
| 302 | USB 2.0 device support. All CN6XXX based chips with USB are | 306 | USB 2.0 device support. All CN6XXX based chips with USB are |
| @@ -575,12 +579,16 @@ config USB_OHCI_HCD_PLATFORM | |||
| 575 | If unsure, say N. | 579 | If unsure, say N. |
| 576 | 580 | ||
| 577 | config USB_OCTEON_OHCI | 581 | config USB_OCTEON_OHCI |
| 578 | bool "Octeon on-chip OHCI support" | 582 | bool "Octeon on-chip OHCI support (DEPRECATED)" |
| 579 | depends on CAVIUM_OCTEON_SOC | 583 | depends on CAVIUM_OCTEON_SOC |
| 580 | default USB_OCTEON_EHCI | 584 | default USB_OCTEON_EHCI |
| 581 | select USB_OHCI_BIG_ENDIAN_MMIO | 585 | select USB_OHCI_BIG_ENDIAN_MMIO |
| 582 | select USB_OHCI_LITTLE_ENDIAN | 586 | select USB_OHCI_LITTLE_ENDIAN |
| 587 | select USB_OHCI_HCD_PLATFORM | ||
| 583 | help | 588 | help |
| 589 | This option is deprecated now and the driver was removed, use | ||
| 590 | USB_OHCI_HCD_PLATFORM instead. | ||
| 591 | |||
| 584 | Enable support for the Octeon II SOC's on-chip OHCI | 592 | Enable support for the Octeon II SOC's on-chip OHCI |
| 585 | controller. It is needed for low-speed USB 1.0 device | 593 | controller. It is needed for low-speed USB 1.0 device |
| 586 | support. All CN6XXX based chips with USB are supported. | 594 | support. All CN6XXX based chips with USB are supported. |
| @@ -754,12 +762,6 @@ config USB_IMX21_HCD | |||
| 754 | To compile this driver as a module, choose M here: the | 762 | To compile this driver as a module, choose M here: the |
| 755 | module will be called "imx21-hcd". | 763 | module will be called "imx21-hcd". |
| 756 | 764 | ||
| 757 | |||
| 758 | |||
| 759 | config USB_OCTEON2_COMMON | ||
| 760 | bool | ||
| 761 | default y if USB_OCTEON_EHCI || USB_OCTEON_OHCI | ||
| 762 | |||
| 763 | config USB_HCD_BCMA | 765 | config USB_HCD_BCMA |
| 764 | tristate "BCMA usb host driver" | 766 | tristate "BCMA usb host driver" |
| 765 | depends on BCMA | 767 | depends on BCMA |
diff --git a/drivers/usb/host/Makefile b/drivers/usb/host/Makefile index 348c24321562..d6216a493bab 100644 --- a/drivers/usb/host/Makefile +++ b/drivers/usb/host/Makefile | |||
| @@ -73,7 +73,6 @@ obj-$(CONFIG_USB_ISP1760_HCD) += isp1760.o | |||
| 73 | obj-$(CONFIG_USB_HWA_HCD) += hwa-hc.o | 73 | obj-$(CONFIG_USB_HWA_HCD) += hwa-hc.o |
| 74 | obj-$(CONFIG_USB_IMX21_HCD) += imx21-hcd.o | 74 | obj-$(CONFIG_USB_IMX21_HCD) += imx21-hcd.o |
| 75 | obj-$(CONFIG_USB_FSL_MPH_DR_OF) += fsl-mph-dr-of.o | 75 | obj-$(CONFIG_USB_FSL_MPH_DR_OF) += fsl-mph-dr-of.o |
| 76 | obj-$(CONFIG_USB_OCTEON2_COMMON) += octeon2-common.o | ||
| 77 | obj-$(CONFIG_USB_HCD_BCMA) += bcma-hcd.o | 76 | obj-$(CONFIG_USB_HCD_BCMA) += bcma-hcd.o |
| 78 | obj-$(CONFIG_USB_HCD_SSB) += ssb-hcd.o | 77 | obj-$(CONFIG_USB_HCD_SSB) += ssb-hcd.o |
| 79 | obj-$(CONFIG_USB_FUSBH200_HCD) += fusbh200-hcd.o | 78 | obj-$(CONFIG_USB_FUSBH200_HCD) += fusbh200-hcd.o |
diff --git a/drivers/usb/host/ehci-atmel.c b/drivers/usb/host/ehci-atmel.c index ec9f7b75d497..56a88506febe 100644 --- a/drivers/usb/host/ehci-atmel.c +++ b/drivers/usb/host/ehci-atmel.c | |||
| @@ -107,22 +107,15 @@ static int ehci_atmel_drv_probe(struct platform_device *pdev) | |||
| 107 | } | 107 | } |
| 108 | 108 | ||
| 109 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 109 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 110 | if (!res) { | ||
| 111 | dev_err(&pdev->dev, | ||
| 112 | "Found HC with no register addr. Check %s setup!\n", | ||
| 113 | dev_name(&pdev->dev)); | ||
| 114 | retval = -ENODEV; | ||
| 115 | goto fail_request_resource; | ||
| 116 | } | ||
| 117 | hcd->rsrc_start = res->start; | ||
| 118 | hcd->rsrc_len = resource_size(res); | ||
| 119 | |||
| 120 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 110 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 121 | if (IS_ERR(hcd->regs)) { | 111 | if (IS_ERR(hcd->regs)) { |
| 122 | retval = PTR_ERR(hcd->regs); | 112 | retval = PTR_ERR(hcd->regs); |
| 123 | goto fail_request_resource; | 113 | goto fail_request_resource; |
| 124 | } | 114 | } |
| 125 | 115 | ||
| 116 | hcd->rsrc_start = res->start; | ||
| 117 | hcd->rsrc_len = resource_size(res); | ||
| 118 | |||
| 126 | iclk = devm_clk_get(&pdev->dev, "ehci_clk"); | 119 | iclk = devm_clk_get(&pdev->dev, "ehci_clk"); |
| 127 | if (IS_ERR(iclk)) { | 120 | if (IS_ERR(iclk)) { |
| 128 | dev_err(&pdev->dev, "Error getting interface clock\n"); | 121 | dev_err(&pdev->dev, "Error getting interface clock\n"); |
diff --git a/drivers/usb/host/ehci-exynos.c b/drivers/usb/host/ehci-exynos.c index 7189f2e32ac2..f58c9750e3e4 100644 --- a/drivers/usb/host/ehci-exynos.c +++ b/drivers/usb/host/ehci-exynos.c | |||
| @@ -74,7 +74,6 @@ static int exynos_ehci_get_phy(struct device *dev, | |||
| 74 | 74 | ||
| 75 | phy = devm_of_phy_get(dev, child, NULL); | 75 | phy = devm_of_phy_get(dev, child, NULL); |
| 76 | exynos_ehci->phy[phy_number] = phy; | 76 | exynos_ehci->phy[phy_number] = phy; |
| 77 | of_node_put(child); | ||
| 78 | if (IS_ERR(phy)) { | 77 | if (IS_ERR(phy)) { |
| 79 | ret = PTR_ERR(phy); | 78 | ret = PTR_ERR(phy); |
| 80 | if (ret == -EPROBE_DEFER) { | 79 | if (ret == -EPROBE_DEFER) { |
| @@ -188,20 +187,15 @@ skip_phy: | |||
| 188 | goto fail_clk; | 187 | goto fail_clk; |
| 189 | 188 | ||
| 190 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 189 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 191 | if (!res) { | ||
| 192 | dev_err(&pdev->dev, "Failed to get I/O memory\n"); | ||
| 193 | err = -ENXIO; | ||
| 194 | goto fail_io; | ||
| 195 | } | ||
| 196 | |||
| 197 | hcd->rsrc_start = res->start; | ||
| 198 | hcd->rsrc_len = resource_size(res); | ||
| 199 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 190 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 200 | if (IS_ERR(hcd->regs)) { | 191 | if (IS_ERR(hcd->regs)) { |
| 201 | err = PTR_ERR(hcd->regs); | 192 | err = PTR_ERR(hcd->regs); |
| 202 | goto fail_io; | 193 | goto fail_io; |
| 203 | } | 194 | } |
| 204 | 195 | ||
| 196 | hcd->rsrc_start = res->start; | ||
| 197 | hcd->rsrc_len = resource_size(res); | ||
| 198 | |||
| 205 | irq = platform_get_irq(pdev, 0); | 199 | irq = platform_get_irq(pdev, 0); |
| 206 | if (!irq) { | 200 | if (!irq) { |
| 207 | dev_err(&pdev->dev, "Failed to get IRQ\n"); | 201 | dev_err(&pdev->dev, "Failed to get IRQ\n"); |
diff --git a/drivers/usb/host/ehci-fsl.c b/drivers/usb/host/ehci-fsl.c index 2d2ae8db439e..fb7bd0c7dc15 100644 --- a/drivers/usb/host/ehci-fsl.c +++ b/drivers/usb/host/ehci-fsl.c | |||
| @@ -93,21 +93,15 @@ static int usb_hcd_fsl_probe(const struct hc_driver *driver, | |||
| 93 | } | 93 | } |
| 94 | 94 | ||
| 95 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 95 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 96 | if (!res) { | ||
| 97 | dev_err(&pdev->dev, | ||
| 98 | "Found HC with no register addr. Check %s setup!\n", | ||
| 99 | dev_name(&pdev->dev)); | ||
| 100 | retval = -ENODEV; | ||
| 101 | goto err2; | ||
| 102 | } | ||
| 103 | hcd->rsrc_start = res->start; | ||
| 104 | hcd->rsrc_len = resource_size(res); | ||
| 105 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 96 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 106 | if (IS_ERR(hcd->regs)) { | 97 | if (IS_ERR(hcd->regs)) { |
| 107 | retval = PTR_ERR(hcd->regs); | 98 | retval = PTR_ERR(hcd->regs); |
| 108 | goto err2; | 99 | goto err2; |
| 109 | } | 100 | } |
| 110 | 101 | ||
| 102 | hcd->rsrc_start = res->start; | ||
| 103 | hcd->rsrc_len = resource_size(res); | ||
| 104 | |||
| 111 | pdata->regs = hcd->regs; | 105 | pdata->regs = hcd->regs; |
| 112 | 106 | ||
| 113 | if (pdata->power_budget) | 107 | if (pdata->power_budget) |
diff --git a/drivers/usb/host/ehci-hcd.c b/drivers/usb/host/ehci-hcd.c index 15feaf924b71..38bfeedae1d0 100644 --- a/drivers/usb/host/ehci-hcd.c +++ b/drivers/usb/host/ehci-hcd.c | |||
| @@ -311,6 +311,7 @@ static void unlink_empty_async_suspended(struct ehci_hcd *ehci); | |||
| 311 | static void ehci_work(struct ehci_hcd *ehci); | 311 | static void ehci_work(struct ehci_hcd *ehci); |
| 312 | static void start_unlink_intr(struct ehci_hcd *ehci, struct ehci_qh *qh); | 312 | static void start_unlink_intr(struct ehci_hcd *ehci, struct ehci_qh *qh); |
| 313 | static void end_unlink_intr(struct ehci_hcd *ehci, struct ehci_qh *qh); | 313 | static void end_unlink_intr(struct ehci_hcd *ehci, struct ehci_qh *qh); |
| 314 | static int ehci_port_power(struct ehci_hcd *ehci, int portnum, bool enable); | ||
| 314 | 315 | ||
| 315 | #include "ehci-timer.c" | 316 | #include "ehci-timer.c" |
| 316 | #include "ehci-hub.c" | 317 | #include "ehci-hub.c" |
| @@ -329,9 +330,13 @@ static void ehci_turn_off_all_ports(struct ehci_hcd *ehci) | |||
| 329 | { | 330 | { |
| 330 | int port = HCS_N_PORTS(ehci->hcs_params); | 331 | int port = HCS_N_PORTS(ehci->hcs_params); |
| 331 | 332 | ||
| 332 | while (port--) | 333 | while (port--) { |
| 333 | ehci_writel(ehci, PORT_RWC_BITS, | 334 | ehci_writel(ehci, PORT_RWC_BITS, |
| 334 | &ehci->regs->port_status[port]); | 335 | &ehci->regs->port_status[port]); |
| 336 | spin_unlock_irq(&ehci->lock); | ||
| 337 | ehci_port_power(ehci, port, false); | ||
| 338 | spin_lock_irq(&ehci->lock); | ||
| 339 | } | ||
| 335 | } | 340 | } |
| 336 | 341 | ||
| 337 | /* | 342 | /* |
| @@ -1233,6 +1238,8 @@ void ehci_init_driver(struct hc_driver *drv, | |||
| 1233 | drv->hcd_priv_size += over->extra_priv_size; | 1238 | drv->hcd_priv_size += over->extra_priv_size; |
| 1234 | if (over->reset) | 1239 | if (over->reset) |
| 1235 | drv->reset = over->reset; | 1240 | drv->reset = over->reset; |
| 1241 | if (over->port_power) | ||
| 1242 | drv->port_power = over->port_power; | ||
| 1236 | } | 1243 | } |
| 1237 | } | 1244 | } |
| 1238 | EXPORT_SYMBOL_GPL(ehci_init_driver); | 1245 | EXPORT_SYMBOL_GPL(ehci_init_driver); |
| @@ -1268,11 +1275,6 @@ MODULE_LICENSE ("GPL"); | |||
| 1268 | #define XILINX_OF_PLATFORM_DRIVER ehci_hcd_xilinx_of_driver | 1275 | #define XILINX_OF_PLATFORM_DRIVER ehci_hcd_xilinx_of_driver |
| 1269 | #endif | 1276 | #endif |
| 1270 | 1277 | ||
| 1271 | #ifdef CONFIG_USB_OCTEON_EHCI | ||
| 1272 | #include "ehci-octeon.c" | ||
| 1273 | #define PLATFORM_DRIVER ehci_octeon_driver | ||
| 1274 | #endif | ||
| 1275 | |||
| 1276 | #ifdef CONFIG_TILE_USB | 1278 | #ifdef CONFIG_TILE_USB |
| 1277 | #include "ehci-tilegx.c" | 1279 | #include "ehci-tilegx.c" |
| 1278 | #define PLATFORM_DRIVER ehci_hcd_tilegx_driver | 1280 | #define PLATFORM_DRIVER ehci_hcd_tilegx_driver |
diff --git a/drivers/usb/host/ehci-hub.c b/drivers/usb/host/ehci-hub.c index 5728829cf6ef..118edb7bdca2 100644 --- a/drivers/usb/host/ehci-hub.c +++ b/drivers/usb/host/ehci-hub.c | |||
| @@ -69,10 +69,8 @@ static void ehci_handover_companion_ports(struct ehci_hcd *ehci) | |||
| 69 | if (test_bit(port, &ehci->owned_ports)) { | 69 | if (test_bit(port, &ehci->owned_ports)) { |
| 70 | reg = &ehci->regs->port_status[port]; | 70 | reg = &ehci->regs->port_status[port]; |
| 71 | status = ehci_readl(ehci, reg) & ~PORT_RWC_BITS; | 71 | status = ehci_readl(ehci, reg) & ~PORT_RWC_BITS; |
| 72 | if (!(status & PORT_POWER)) { | 72 | if (!(status & PORT_POWER)) |
| 73 | status |= PORT_POWER; | 73 | ehci_port_power(ehci, port, true); |
| 74 | ehci_writel(ehci, status, reg); | ||
| 75 | } | ||
| 76 | } | 74 | } |
| 77 | } | 75 | } |
| 78 | 76 | ||
| @@ -952,9 +950,11 @@ int ehci_hub_control( | |||
| 952 | clear_bit(wIndex, &ehci->port_c_suspend); | 950 | clear_bit(wIndex, &ehci->port_c_suspend); |
| 953 | break; | 951 | break; |
| 954 | case USB_PORT_FEAT_POWER: | 952 | case USB_PORT_FEAT_POWER: |
| 955 | if (HCS_PPC (ehci->hcs_params)) | 953 | if (HCS_PPC(ehci->hcs_params)) { |
| 956 | ehci_writel(ehci, temp & ~PORT_POWER, | 954 | spin_unlock_irqrestore(&ehci->lock, flags); |
| 957 | status_reg); | 955 | ehci_port_power(ehci, wIndex, false); |
| 956 | spin_lock_irqsave(&ehci->lock, flags); | ||
| 957 | } | ||
| 958 | break; | 958 | break; |
| 959 | case USB_PORT_FEAT_C_CONNECTION: | 959 | case USB_PORT_FEAT_C_CONNECTION: |
| 960 | ehci_writel(ehci, temp | PORT_CSC, status_reg); | 960 | ehci_writel(ehci, temp | PORT_CSC, status_reg); |
| @@ -1004,9 +1004,9 @@ int ehci_hub_control( | |||
| 1004 | */ | 1004 | */ |
| 1005 | if (((temp & PORT_OC) || (ehci->need_oc_pp_cycle)) | 1005 | if (((temp & PORT_OC) || (ehci->need_oc_pp_cycle)) |
| 1006 | && HCS_PPC(ehci->hcs_params)) { | 1006 | && HCS_PPC(ehci->hcs_params)) { |
| 1007 | ehci_writel(ehci, | 1007 | spin_unlock_irqrestore(&ehci->lock, flags); |
| 1008 | temp & ~(PORT_RWC_BITS | PORT_POWER), | 1008 | ehci_port_power(ehci, wIndex, false); |
| 1009 | status_reg); | 1009 | spin_lock_irqsave(&ehci->lock, flags); |
| 1010 | temp = ehci_readl(ehci, status_reg); | 1010 | temp = ehci_readl(ehci, status_reg); |
| 1011 | } | 1011 | } |
| 1012 | } | 1012 | } |
| @@ -1187,9 +1187,11 @@ int ehci_hub_control( | |||
| 1187 | set_bit(wIndex, &ehci->suspended_ports); | 1187 | set_bit(wIndex, &ehci->suspended_ports); |
| 1188 | break; | 1188 | break; |
| 1189 | case USB_PORT_FEAT_POWER: | 1189 | case USB_PORT_FEAT_POWER: |
| 1190 | if (HCS_PPC (ehci->hcs_params)) | 1190 | if (HCS_PPC(ehci->hcs_params)) { |
| 1191 | ehci_writel(ehci, temp | PORT_POWER, | 1191 | spin_unlock_irqrestore(&ehci->lock, flags); |
| 1192 | status_reg); | 1192 | ehci_port_power(ehci, wIndex, true); |
| 1193 | spin_lock_irqsave(&ehci->lock, flags); | ||
| 1194 | } | ||
| 1193 | break; | 1195 | break; |
| 1194 | case USB_PORT_FEAT_RESET: | 1196 | case USB_PORT_FEAT_RESET: |
| 1195 | if (temp & (PORT_SUSPEND|PORT_RESUME)) | 1197 | if (temp & (PORT_SUSPEND|PORT_RESUME)) |
| @@ -1297,3 +1299,20 @@ static int ehci_port_handed_over(struct usb_hcd *hcd, int portnum) | |||
| 1297 | reg = &ehci->regs->port_status[portnum - 1]; | 1299 | reg = &ehci->regs->port_status[portnum - 1]; |
| 1298 | return ehci_readl(ehci, reg) & PORT_OWNER; | 1300 | return ehci_readl(ehci, reg) & PORT_OWNER; |
| 1299 | } | 1301 | } |
| 1302 | |||
| 1303 | static int ehci_port_power(struct ehci_hcd *ehci, int portnum, bool enable) | ||
| 1304 | { | ||
| 1305 | struct usb_hcd *hcd = ehci_to_hcd(ehci); | ||
| 1306 | u32 __iomem *status_reg = &ehci->regs->port_status[portnum]; | ||
| 1307 | u32 temp = ehci_readl(ehci, status_reg) & ~PORT_RWC_BITS; | ||
| 1308 | |||
| 1309 | if (enable) | ||
| 1310 | ehci_writel(ehci, temp | PORT_POWER, status_reg); | ||
| 1311 | else | ||
| 1312 | ehci_writel(ehci, temp & ~PORT_POWER, status_reg); | ||
| 1313 | |||
| 1314 | if (hcd->driver->port_power) | ||
| 1315 | hcd->driver->port_power(hcd, portnum, enable); | ||
| 1316 | |||
| 1317 | return 0; | ||
| 1318 | } | ||
diff --git a/drivers/usb/host/ehci-msm.c b/drivers/usb/host/ehci-msm.c index 9dc2118ae808..9db74ca7e5b9 100644 --- a/drivers/usb/host/ehci-msm.c +++ b/drivers/usb/host/ehci-msm.c | |||
| @@ -88,19 +88,13 @@ static int ehci_msm_probe(struct platform_device *pdev) | |||
| 88 | } | 88 | } |
| 89 | 89 | ||
| 90 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 90 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 91 | if (!res) { | ||
| 92 | dev_err(&pdev->dev, "Unable to get memory resource\n"); | ||
| 93 | ret = -ENODEV; | ||
| 94 | goto put_hcd; | ||
| 95 | } | ||
| 96 | |||
| 97 | hcd->rsrc_start = res->start; | ||
| 98 | hcd->rsrc_len = resource_size(res); | ||
| 99 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 91 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 100 | if (IS_ERR(hcd->regs)) { | 92 | if (IS_ERR(hcd->regs)) { |
| 101 | ret = PTR_ERR(hcd->regs); | 93 | ret = PTR_ERR(hcd->regs); |
| 102 | goto put_hcd; | 94 | goto put_hcd; |
| 103 | } | 95 | } |
| 96 | hcd->rsrc_start = res->start; | ||
| 97 | hcd->rsrc_len = resource_size(res); | ||
| 104 | 98 | ||
| 105 | /* | 99 | /* |
| 106 | * OTG driver takes care of PHY initialization, clock management, | 100 | * OTG driver takes care of PHY initialization, clock management, |
diff --git a/drivers/usb/host/ehci-mv.c b/drivers/usb/host/ehci-mv.c index 08147c35f836..849806a75f1c 100644 --- a/drivers/usb/host/ehci-mv.c +++ b/drivers/usb/host/ehci-mv.c | |||
| @@ -153,7 +153,6 @@ static int mv_ehci_probe(struct platform_device *pdev) | |||
| 153 | 153 | ||
| 154 | ehci_mv = devm_kzalloc(&pdev->dev, sizeof(*ehci_mv), GFP_KERNEL); | 154 | ehci_mv = devm_kzalloc(&pdev->dev, sizeof(*ehci_mv), GFP_KERNEL); |
| 155 | if (ehci_mv == NULL) { | 155 | if (ehci_mv == NULL) { |
| 156 | dev_err(&pdev->dev, "cannot allocate ehci_hcd_mv\n"); | ||
| 157 | retval = -ENOMEM; | 156 | retval = -ENOMEM; |
| 158 | goto err_put_hcd; | 157 | goto err_put_hcd; |
| 159 | } | 158 | } |
| @@ -170,12 +169,6 @@ static int mv_ehci_probe(struct platform_device *pdev) | |||
| 170 | } | 169 | } |
| 171 | 170 | ||
| 172 | r = platform_get_resource_byname(pdev, IORESOURCE_MEM, "phyregs"); | 171 | r = platform_get_resource_byname(pdev, IORESOURCE_MEM, "phyregs"); |
| 173 | if (r == NULL) { | ||
| 174 | dev_err(&pdev->dev, "no phy I/O memory resource defined\n"); | ||
| 175 | retval = -ENODEV; | ||
| 176 | goto err_put_hcd; | ||
| 177 | } | ||
| 178 | |||
| 179 | ehci_mv->phy_regs = devm_ioremap_resource(&pdev->dev, r); | 172 | ehci_mv->phy_regs = devm_ioremap_resource(&pdev->dev, r); |
| 180 | if (IS_ERR(ehci_mv->phy_regs)) { | 173 | if (IS_ERR(ehci_mv->phy_regs)) { |
| 181 | retval = PTR_ERR(ehci_mv->phy_regs); | 174 | retval = PTR_ERR(ehci_mv->phy_regs); |
| @@ -183,12 +176,6 @@ static int mv_ehci_probe(struct platform_device *pdev) | |||
| 183 | } | 176 | } |
| 184 | 177 | ||
| 185 | r = platform_get_resource_byname(pdev, IORESOURCE_MEM, "capregs"); | 178 | r = platform_get_resource_byname(pdev, IORESOURCE_MEM, "capregs"); |
| 186 | if (!r) { | ||
| 187 | dev_err(&pdev->dev, "no I/O memory resource defined\n"); | ||
| 188 | retval = -ENODEV; | ||
| 189 | goto err_put_hcd; | ||
| 190 | } | ||
| 191 | |||
| 192 | ehci_mv->cap_regs = devm_ioremap_resource(&pdev->dev, r); | 179 | ehci_mv->cap_regs = devm_ioremap_resource(&pdev->dev, r); |
| 193 | if (IS_ERR(ehci_mv->cap_regs)) { | 180 | if (IS_ERR(ehci_mv->cap_regs)) { |
| 194 | retval = PTR_ERR(ehci_mv->cap_regs); | 181 | retval = PTR_ERR(ehci_mv->cap_regs); |
diff --git a/drivers/usb/host/ehci-mxc.c b/drivers/usb/host/ehci-mxc.c index dbe5e4eea08d..c7a9b31eeaef 100644 --- a/drivers/usb/host/ehci-mxc.c +++ b/drivers/usb/host/ehci-mxc.c | |||
| @@ -69,20 +69,13 @@ static int ehci_mxc_drv_probe(struct platform_device *pdev) | |||
| 69 | return -ENOMEM; | 69 | return -ENOMEM; |
| 70 | 70 | ||
| 71 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 71 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 72 | if (!res) { | ||
| 73 | dev_err(dev, "Found HC with no register addr. Check setup!\n"); | ||
| 74 | ret = -ENODEV; | ||
| 75 | goto err_alloc; | ||
| 76 | } | ||
| 77 | |||
| 78 | hcd->rsrc_start = res->start; | ||
| 79 | hcd->rsrc_len = resource_size(res); | ||
| 80 | |||
| 81 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 72 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 82 | if (IS_ERR(hcd->regs)) { | 73 | if (IS_ERR(hcd->regs)) { |
| 83 | ret = PTR_ERR(hcd->regs); | 74 | ret = PTR_ERR(hcd->regs); |
| 84 | goto err_alloc; | 75 | goto err_alloc; |
| 85 | } | 76 | } |
| 77 | hcd->rsrc_start = res->start; | ||
| 78 | hcd->rsrc_len = resource_size(res); | ||
| 86 | 79 | ||
| 87 | hcd->has_tt = 1; | 80 | hcd->has_tt = 1; |
| 88 | ehci = hcd_to_ehci(hcd); | 81 | ehci = hcd_to_ehci(hcd); |
diff --git a/drivers/usb/host/ehci-octeon.c b/drivers/usb/host/ehci-octeon.c deleted file mode 100644 index 9051439039a7..000000000000 --- a/drivers/usb/host/ehci-octeon.c +++ /dev/null | |||
| @@ -1,188 +0,0 @@ | |||
| 1 | /* | ||
| 2 | * EHCI HCD glue for Cavium Octeon II SOCs. | ||
| 3 | * | ||
| 4 | * Loosely based on ehci-au1xxx.c | ||
| 5 | * | ||
| 6 | * This file is subject to the terms and conditions of the GNU General Public | ||
| 7 | * License. See the file "COPYING" in the main directory of this archive | ||
| 8 | * for more details. | ||
| 9 | * | ||
| 10 | * Copyright (C) 2010 Cavium Networks | ||
| 11 | * | ||
| 12 | */ | ||
| 13 | |||
| 14 | #include <linux/platform_device.h> | ||
| 15 | |||
| 16 | #include <asm/octeon/octeon.h> | ||
| 17 | #include <asm/octeon/cvmx-uctlx-defs.h> | ||
| 18 | |||
| 19 | #define OCTEON_EHCI_HCD_NAME "octeon-ehci" | ||
| 20 | |||
| 21 | /* Common clock init code. */ | ||
| 22 | void octeon2_usb_clocks_start(void); | ||
| 23 | void octeon2_usb_clocks_stop(void); | ||
| 24 | |||
| 25 | static void ehci_octeon_start(void) | ||
| 26 | { | ||
| 27 | union cvmx_uctlx_ehci_ctl ehci_ctl; | ||
| 28 | |||
| 29 | octeon2_usb_clocks_start(); | ||
| 30 | |||
| 31 | ehci_ctl.u64 = cvmx_read_csr(CVMX_UCTLX_EHCI_CTL(0)); | ||
| 32 | /* Use 64-bit addressing. */ | ||
| 33 | ehci_ctl.s.ehci_64b_addr_en = 1; | ||
| 34 | ehci_ctl.s.l2c_addr_msb = 0; | ||
| 35 | ehci_ctl.s.l2c_buff_emod = 1; /* Byte swapped. */ | ||
| 36 | ehci_ctl.s.l2c_desc_emod = 1; /* Byte swapped. */ | ||
| 37 | cvmx_write_csr(CVMX_UCTLX_EHCI_CTL(0), ehci_ctl.u64); | ||
| 38 | } | ||
| 39 | |||
| 40 | static void ehci_octeon_stop(void) | ||
| 41 | { | ||
| 42 | octeon2_usb_clocks_stop(); | ||
| 43 | } | ||
| 44 | |||
| 45 | static const struct hc_driver ehci_octeon_hc_driver = { | ||
| 46 | .description = hcd_name, | ||
| 47 | .product_desc = "Octeon EHCI", | ||
| 48 | .hcd_priv_size = sizeof(struct ehci_hcd), | ||
| 49 | |||
| 50 | /* | ||
| 51 | * generic hardware linkage | ||
| 52 | */ | ||
| 53 | .irq = ehci_irq, | ||
| 54 | .flags = HCD_MEMORY | HCD_USB2 | HCD_BH, | ||
| 55 | |||
| 56 | /* | ||
| 57 | * basic lifecycle operations | ||
| 58 | */ | ||
| 59 | .reset = ehci_setup, | ||
| 60 | .start = ehci_run, | ||
| 61 | .stop = ehci_stop, | ||
| 62 | .shutdown = ehci_shutdown, | ||
| 63 | |||
| 64 | /* | ||
| 65 | * managing i/o requests and associated device resources | ||
| 66 | */ | ||
| 67 | .urb_enqueue = ehci_urb_enqueue, | ||
| 68 | .urb_dequeue = ehci_urb_dequeue, | ||
| 69 | .endpoint_disable = ehci_endpoint_disable, | ||
| 70 | .endpoint_reset = ehci_endpoint_reset, | ||
| 71 | |||
| 72 | /* | ||
| 73 | * scheduling support | ||
| 74 | */ | ||
| 75 | .get_frame_number = ehci_get_frame, | ||
| 76 | |||
| 77 | /* | ||
| 78 | * root hub support | ||
| 79 | */ | ||
| 80 | .hub_status_data = ehci_hub_status_data, | ||
| 81 | .hub_control = ehci_hub_control, | ||
| 82 | .bus_suspend = ehci_bus_suspend, | ||
| 83 | .bus_resume = ehci_bus_resume, | ||
| 84 | .relinquish_port = ehci_relinquish_port, | ||
| 85 | .port_handed_over = ehci_port_handed_over, | ||
| 86 | |||
| 87 | .clear_tt_buffer_complete = ehci_clear_tt_buffer_complete, | ||
| 88 | }; | ||
| 89 | |||
| 90 | static u64 ehci_octeon_dma_mask = DMA_BIT_MASK(64); | ||
| 91 | |||
| 92 | static int ehci_octeon_drv_probe(struct platform_device *pdev) | ||
| 93 | { | ||
| 94 | struct usb_hcd *hcd; | ||
| 95 | struct ehci_hcd *ehci; | ||
| 96 | struct resource *res_mem; | ||
| 97 | int irq; | ||
| 98 | int ret; | ||
| 99 | |||
| 100 | if (usb_disabled()) | ||
| 101 | return -ENODEV; | ||
| 102 | |||
| 103 | irq = platform_get_irq(pdev, 0); | ||
| 104 | if (irq < 0) { | ||
| 105 | dev_err(&pdev->dev, "No irq assigned\n"); | ||
| 106 | return -ENODEV; | ||
| 107 | } | ||
| 108 | |||
| 109 | res_mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 110 | if (res_mem == NULL) { | ||
| 111 | dev_err(&pdev->dev, "No register space assigned\n"); | ||
| 112 | return -ENODEV; | ||
| 113 | } | ||
| 114 | |||
| 115 | /* | ||
| 116 | * We can DMA from anywhere. But the descriptors must be in | ||
| 117 | * the lower 4GB. | ||
| 118 | */ | ||
| 119 | pdev->dev.dma_mask = &ehci_octeon_dma_mask; | ||
| 120 | ret = dma_set_coherent_mask(&pdev->dev, DMA_BIT_MASK(32)); | ||
| 121 | if (ret) | ||
| 122 | return ret; | ||
| 123 | |||
| 124 | hcd = usb_create_hcd(&ehci_octeon_hc_driver, &pdev->dev, "octeon"); | ||
| 125 | if (!hcd) | ||
| 126 | return -ENOMEM; | ||
| 127 | |||
| 128 | hcd->rsrc_start = res_mem->start; | ||
| 129 | hcd->rsrc_len = resource_size(res_mem); | ||
| 130 | |||
| 131 | hcd->regs = devm_ioremap_resource(&pdev->dev, res_mem); | ||
| 132 | if (IS_ERR(hcd->regs)) { | ||
| 133 | ret = PTR_ERR(hcd->regs); | ||
| 134 | goto err1; | ||
| 135 | } | ||
| 136 | |||
| 137 | ehci_octeon_start(); | ||
| 138 | |||
| 139 | ehci = hcd_to_ehci(hcd); | ||
| 140 | |||
| 141 | /* Octeon EHCI matches CPU endianness. */ | ||
| 142 | #ifdef __BIG_ENDIAN | ||
| 143 | ehci->big_endian_mmio = 1; | ||
| 144 | #endif | ||
| 145 | |||
| 146 | ehci->caps = hcd->regs; | ||
| 147 | |||
| 148 | ret = usb_add_hcd(hcd, irq, IRQF_SHARED); | ||
| 149 | if (ret) { | ||
| 150 | dev_dbg(&pdev->dev, "failed to add hcd with err %d\n", ret); | ||
| 151 | goto err2; | ||
| 152 | } | ||
| 153 | device_wakeup_enable(hcd->self.controller); | ||
| 154 | |||
| 155 | platform_set_drvdata(pdev, hcd); | ||
| 156 | |||
| 157 | return 0; | ||
| 158 | err2: | ||
| 159 | ehci_octeon_stop(); | ||
| 160 | |||
| 161 | err1: | ||
| 162 | usb_put_hcd(hcd); | ||
| 163 | return ret; | ||
| 164 | } | ||
| 165 | |||
| 166 | static int ehci_octeon_drv_remove(struct platform_device *pdev) | ||
| 167 | { | ||
| 168 | struct usb_hcd *hcd = platform_get_drvdata(pdev); | ||
| 169 | |||
| 170 | usb_remove_hcd(hcd); | ||
| 171 | |||
| 172 | ehci_octeon_stop(); | ||
| 173 | usb_put_hcd(hcd); | ||
| 174 | |||
| 175 | return 0; | ||
| 176 | } | ||
| 177 | |||
| 178 | static struct platform_driver ehci_octeon_driver = { | ||
| 179 | .probe = ehci_octeon_drv_probe, | ||
| 180 | .remove = ehci_octeon_drv_remove, | ||
| 181 | .shutdown = usb_hcd_platform_shutdown, | ||
| 182 | .driver = { | ||
| 183 | .name = OCTEON_EHCI_HCD_NAME, | ||
| 184 | .owner = THIS_MODULE, | ||
| 185 | } | ||
| 186 | }; | ||
| 187 | |||
| 188 | MODULE_ALIAS("platform:" OCTEON_EHCI_HCD_NAME); | ||
diff --git a/drivers/usb/host/ehci-orion.c b/drivers/usb/host/ehci-orion.c index 22e15cab8ea5..3c76489ea61a 100644 --- a/drivers/usb/host/ehci-orion.c +++ b/drivers/usb/host/ehci-orion.c | |||
| @@ -25,8 +25,8 @@ | |||
| 25 | 25 | ||
| 26 | #include "ehci.h" | 26 | #include "ehci.h" |
| 27 | 27 | ||
| 28 | #define rdl(off) __raw_readl(hcd->regs + (off)) | 28 | #define rdl(off) readl_relaxed(hcd->regs + (off)) |
| 29 | #define wrl(off, val) __raw_writel((val), hcd->regs + (off)) | 29 | #define wrl(off, val) writel_relaxed((val), hcd->regs + (off)) |
| 30 | 30 | ||
| 31 | #define USB_CMD 0x140 | 31 | #define USB_CMD 0x140 |
| 32 | #define USB_MODE 0x1a8 | 32 | #define USB_MODE 0x1a8 |
| @@ -175,15 +175,6 @@ static int ehci_orion_drv_probe(struct platform_device *pdev) | |||
| 175 | goto err; | 175 | goto err; |
| 176 | } | 176 | } |
| 177 | 177 | ||
| 178 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 179 | if (!res) { | ||
| 180 | dev_err(&pdev->dev, | ||
| 181 | "Found HC with no register addr. Check %s setup!\n", | ||
| 182 | dev_name(&pdev->dev)); | ||
| 183 | err = -ENODEV; | ||
| 184 | goto err; | ||
| 185 | } | ||
| 186 | |||
| 187 | /* | 178 | /* |
| 188 | * Right now device-tree probed devices don't get dma_mask | 179 | * Right now device-tree probed devices don't get dma_mask |
| 189 | * set. Since shared usb code relies on it, set it here for | 180 | * set. Since shared usb code relies on it, set it here for |
| @@ -193,6 +184,7 @@ static int ehci_orion_drv_probe(struct platform_device *pdev) | |||
| 193 | if (err) | 184 | if (err) |
| 194 | goto err; | 185 | goto err; |
| 195 | 186 | ||
| 187 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 196 | regs = devm_ioremap_resource(&pdev->dev, res); | 188 | regs = devm_ioremap_resource(&pdev->dev, res); |
| 197 | if (IS_ERR(regs)) { | 189 | if (IS_ERR(regs)) { |
| 198 | err = PTR_ERR(regs); | 190 | err = PTR_ERR(regs); |
diff --git a/drivers/usb/host/ehci-platform.c b/drivers/usb/host/ehci-platform.c index 2f5b9ce3e042..35a9aeda0168 100644 --- a/drivers/usb/host/ehci-platform.c +++ b/drivers/usb/host/ehci-platform.c | |||
| @@ -164,11 +164,6 @@ static int ehci_platform_probe(struct platform_device *dev) | |||
| 164 | dev_err(&dev->dev, "no irq provided"); | 164 | dev_err(&dev->dev, "no irq provided"); |
| 165 | return irq; | 165 | return irq; |
| 166 | } | 166 | } |
| 167 | res_mem = platform_get_resource(dev, IORESOURCE_MEM, 0); | ||
| 168 | if (!res_mem) { | ||
| 169 | dev_err(&dev->dev, "no memory resource provided"); | ||
| 170 | return -ENXIO; | ||
| 171 | } | ||
| 172 | 167 | ||
| 173 | hcd = usb_create_hcd(&ehci_platform_hc_driver, &dev->dev, | 168 | hcd = usb_create_hcd(&ehci_platform_hc_driver, &dev->dev, |
| 174 | dev_name(&dev->dev)); | 169 | dev_name(&dev->dev)); |
| @@ -250,14 +245,15 @@ static int ehci_platform_probe(struct platform_device *dev) | |||
| 250 | goto err_reset; | 245 | goto err_reset; |
| 251 | } | 246 | } |
| 252 | 247 | ||
| 253 | hcd->rsrc_start = res_mem->start; | 248 | res_mem = platform_get_resource(dev, IORESOURCE_MEM, 0); |
| 254 | hcd->rsrc_len = resource_size(res_mem); | ||
| 255 | |||
| 256 | hcd->regs = devm_ioremap_resource(&dev->dev, res_mem); | 249 | hcd->regs = devm_ioremap_resource(&dev->dev, res_mem); |
| 257 | if (IS_ERR(hcd->regs)) { | 250 | if (IS_ERR(hcd->regs)) { |
| 258 | err = PTR_ERR(hcd->regs); | 251 | err = PTR_ERR(hcd->regs); |
| 259 | goto err_power; | 252 | goto err_power; |
| 260 | } | 253 | } |
| 254 | hcd->rsrc_start = res_mem->start; | ||
| 255 | hcd->rsrc_len = resource_size(res_mem); | ||
| 256 | |||
| 261 | err = usb_add_hcd(hcd, irq, IRQF_SHARED); | 257 | err = usb_add_hcd(hcd, irq, IRQF_SHARED); |
| 262 | if (err) | 258 | if (err) |
| 263 | goto err_power; | 259 | goto err_power; |
| @@ -311,8 +307,7 @@ static int ehci_platform_remove(struct platform_device *dev) | |||
| 311 | return 0; | 307 | return 0; |
| 312 | } | 308 | } |
| 313 | 309 | ||
| 314 | #ifdef CONFIG_PM | 310 | #ifdef CONFIG_PM_SLEEP |
| 315 | |||
| 316 | static int ehci_platform_suspend(struct device *dev) | 311 | static int ehci_platform_suspend(struct device *dev) |
| 317 | { | 312 | { |
| 318 | struct usb_hcd *hcd = dev_get_drvdata(dev); | 313 | struct usb_hcd *hcd = dev_get_drvdata(dev); |
| @@ -348,11 +343,7 @@ static int ehci_platform_resume(struct device *dev) | |||
| 348 | ehci_resume(hcd, false); | 343 | ehci_resume(hcd, false); |
| 349 | return 0; | 344 | return 0; |
| 350 | } | 345 | } |
| 351 | 346 | #endif /* CONFIG_PM_SLEEP */ | |
| 352 | #else /* !CONFIG_PM */ | ||
| 353 | #define ehci_platform_suspend NULL | ||
| 354 | #define ehci_platform_resume NULL | ||
| 355 | #endif /* CONFIG_PM */ | ||
| 356 | 347 | ||
| 357 | static const struct of_device_id vt8500_ehci_ids[] = { | 348 | static const struct of_device_id vt8500_ehci_ids[] = { |
| 358 | { .compatible = "via,vt8500-ehci", }, | 349 | { .compatible = "via,vt8500-ehci", }, |
| @@ -368,10 +359,8 @@ static const struct platform_device_id ehci_platform_table[] = { | |||
| 368 | }; | 359 | }; |
| 369 | MODULE_DEVICE_TABLE(platform, ehci_platform_table); | 360 | MODULE_DEVICE_TABLE(platform, ehci_platform_table); |
| 370 | 361 | ||
| 371 | static const struct dev_pm_ops ehci_platform_pm_ops = { | 362 | static SIMPLE_DEV_PM_OPS(ehci_platform_pm_ops, ehci_platform_suspend, |
| 372 | .suspend = ehci_platform_suspend, | 363 | ehci_platform_resume); |
| 373 | .resume = ehci_platform_resume, | ||
| 374 | }; | ||
| 375 | 364 | ||
| 376 | static struct platform_driver ehci_platform_driver = { | 365 | static struct platform_driver ehci_platform_driver = { |
| 377 | .id_table = ehci_platform_table, | 366 | .id_table = ehci_platform_table, |
diff --git a/drivers/usb/host/ehci-sead3.c b/drivers/usb/host/ehci-sead3.c index cf1267673868..9b6e8d0eac43 100644 --- a/drivers/usb/host/ehci-sead3.c +++ b/drivers/usb/host/ehci-sead3.c | |||
| @@ -110,14 +110,13 @@ static int ehci_hcd_sead3_drv_probe(struct platform_device *pdev) | |||
| 110 | return -ENOMEM; | 110 | return -ENOMEM; |
| 111 | 111 | ||
| 112 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 112 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 113 | hcd->rsrc_start = res->start; | ||
| 114 | hcd->rsrc_len = resource_size(res); | ||
| 115 | |||
| 116 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 113 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 117 | if (IS_ERR(hcd->regs)) { | 114 | if (IS_ERR(hcd->regs)) { |
| 118 | ret = PTR_ERR(hcd->regs); | 115 | ret = PTR_ERR(hcd->regs); |
| 119 | goto err1; | 116 | goto err1; |
| 120 | } | 117 | } |
| 118 | hcd->rsrc_start = res->start; | ||
| 119 | hcd->rsrc_len = resource_size(res); | ||
| 121 | 120 | ||
| 122 | /* Root hub has integrated TT. */ | 121 | /* Root hub has integrated TT. */ |
| 123 | hcd->has_tt = 1; | 122 | hcd->has_tt = 1; |
diff --git a/drivers/usb/host/ehci-sh.c b/drivers/usb/host/ehci-sh.c index 9b9b9f5b016e..0e0ce684aff3 100644 --- a/drivers/usb/host/ehci-sh.c +++ b/drivers/usb/host/ehci-sh.c | |||
| @@ -86,15 +86,6 @@ static int ehci_hcd_sh_probe(struct platform_device *pdev) | |||
| 86 | if (usb_disabled()) | 86 | if (usb_disabled()) |
| 87 | return -ENODEV; | 87 | return -ENODEV; |
| 88 | 88 | ||
| 89 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 90 | if (!res) { | ||
| 91 | dev_err(&pdev->dev, | ||
| 92 | "Found HC with no register addr. Check %s setup!\n", | ||
| 93 | dev_name(&pdev->dev)); | ||
| 94 | ret = -ENODEV; | ||
| 95 | goto fail_create_hcd; | ||
| 96 | } | ||
| 97 | |||
| 98 | irq = platform_get_irq(pdev, 0); | 89 | irq = platform_get_irq(pdev, 0); |
| 99 | if (irq <= 0) { | 90 | if (irq <= 0) { |
| 100 | dev_err(&pdev->dev, | 91 | dev_err(&pdev->dev, |
| @@ -114,19 +105,18 @@ static int ehci_hcd_sh_probe(struct platform_device *pdev) | |||
| 114 | goto fail_create_hcd; | 105 | goto fail_create_hcd; |
| 115 | } | 106 | } |
| 116 | 107 | ||
| 117 | hcd->rsrc_start = res->start; | 108 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 118 | hcd->rsrc_len = resource_size(res); | ||
| 119 | |||
| 120 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 109 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 121 | if (IS_ERR(hcd->regs)) { | 110 | if (IS_ERR(hcd->regs)) { |
| 122 | ret = PTR_ERR(hcd->regs); | 111 | ret = PTR_ERR(hcd->regs); |
| 123 | goto fail_request_resource; | 112 | goto fail_request_resource; |
| 124 | } | 113 | } |
| 114 | hcd->rsrc_start = res->start; | ||
| 115 | hcd->rsrc_len = resource_size(res); | ||
| 125 | 116 | ||
| 126 | priv = devm_kzalloc(&pdev->dev, sizeof(struct ehci_sh_priv), | 117 | priv = devm_kzalloc(&pdev->dev, sizeof(struct ehci_sh_priv), |
| 127 | GFP_KERNEL); | 118 | GFP_KERNEL); |
| 128 | if (!priv) { | 119 | if (!priv) { |
| 129 | dev_dbg(&pdev->dev, "error allocating priv data\n"); | ||
| 130 | ret = -ENOMEM; | 120 | ret = -ENOMEM; |
| 131 | goto fail_request_resource; | 121 | goto fail_request_resource; |
| 132 | } | 122 | } |
diff --git a/drivers/usb/host/ehci-spear.c b/drivers/usb/host/ehci-spear.c index 1355ff0946b9..34e14746b92e 100644 --- a/drivers/usb/host/ehci-spear.c +++ b/drivers/usb/host/ehci-spear.c | |||
| @@ -99,18 +99,13 @@ static int spear_ehci_hcd_drv_probe(struct platform_device *pdev) | |||
| 99 | } | 99 | } |
| 100 | 100 | ||
| 101 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 101 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 102 | if (!res) { | ||
| 103 | retval = -ENODEV; | ||
| 104 | goto err_put_hcd; | ||
| 105 | } | ||
| 106 | |||
| 107 | hcd->rsrc_start = res->start; | ||
| 108 | hcd->rsrc_len = resource_size(res); | ||
| 109 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 102 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 110 | if (IS_ERR(hcd->regs)) { | 103 | if (IS_ERR(hcd->regs)) { |
| 111 | retval = PTR_ERR(hcd->regs); | 104 | retval = PTR_ERR(hcd->regs); |
| 112 | goto err_put_hcd; | 105 | goto err_put_hcd; |
| 113 | } | 106 | } |
| 107 | hcd->rsrc_start = res->start; | ||
| 108 | hcd->rsrc_len = resource_size(res); | ||
| 114 | 109 | ||
| 115 | sehci = to_spear_ehci(hcd); | 110 | sehci = to_spear_ehci(hcd); |
| 116 | sehci->clk = usbh_clk; | 111 | sehci->clk = usbh_clk; |
diff --git a/drivers/usb/host/ehci-tegra.c b/drivers/usb/host/ehci-tegra.c index aaa01971efe9..19a9af1b4d74 100644 --- a/drivers/usb/host/ehci-tegra.c +++ b/drivers/usb/host/ehci-tegra.c | |||
| @@ -460,18 +460,14 @@ static int tegra_ehci_probe(struct platform_device *pdev) | |||
| 460 | "nvidia,needs-double-reset"); | 460 | "nvidia,needs-double-reset"); |
| 461 | 461 | ||
| 462 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 462 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 463 | if (!res) { | ||
| 464 | dev_err(&pdev->dev, "Failed to get I/O memory\n"); | ||
| 465 | err = -ENXIO; | ||
| 466 | goto cleanup_clk_en; | ||
| 467 | } | ||
| 468 | hcd->rsrc_start = res->start; | ||
| 469 | hcd->rsrc_len = resource_size(res); | ||
| 470 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 463 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 471 | if (IS_ERR(hcd->regs)) { | 464 | if (IS_ERR(hcd->regs)) { |
| 472 | err = PTR_ERR(hcd->regs); | 465 | err = PTR_ERR(hcd->regs); |
| 473 | goto cleanup_clk_en; | 466 | goto cleanup_clk_en; |
| 474 | } | 467 | } |
| 468 | hcd->rsrc_start = res->start; | ||
| 469 | hcd->rsrc_len = resource_size(res); | ||
| 470 | |||
| 475 | ehci->caps = hcd->regs + 0x100; | 471 | ehci->caps = hcd->regs + 0x100; |
| 476 | ehci->has_hostpc = soc_config->has_hostpc; | 472 | ehci->has_hostpc = soc_config->has_hostpc; |
| 477 | 473 | ||
| @@ -484,7 +480,6 @@ static int tegra_ehci_probe(struct platform_device *pdev) | |||
| 484 | u_phy->otg = devm_kzalloc(&pdev->dev, sizeof(struct usb_otg), | 480 | u_phy->otg = devm_kzalloc(&pdev->dev, sizeof(struct usb_otg), |
| 485 | GFP_KERNEL); | 481 | GFP_KERNEL); |
| 486 | if (!u_phy->otg) { | 482 | if (!u_phy->otg) { |
| 487 | dev_err(&pdev->dev, "Failed to alloc memory for otg\n"); | ||
| 488 | err = -ENOMEM; | 483 | err = -ENOMEM; |
| 489 | goto cleanup_phy; | 484 | goto cleanup_phy; |
| 490 | } | 485 | } |
diff --git a/drivers/usb/host/ehci-w90x900.c b/drivers/usb/host/ehci-w90x900.c index a9303aff125e..c305732e8634 100644 --- a/drivers/usb/host/ehci-w90x900.c +++ b/drivers/usb/host/ehci-w90x900.c | |||
| @@ -42,27 +42,20 @@ static int usb_w90x900_probe(const struct hc_driver *driver, | |||
| 42 | int retval = 0, irq; | 42 | int retval = 0, irq; |
| 43 | unsigned long val; | 43 | unsigned long val; |
| 44 | 44 | ||
| 45 | |||
| 46 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 47 | if (!res) { | ||
| 48 | retval = -ENXIO; | ||
| 49 | goto err1; | ||
| 50 | } | ||
| 51 | |||
| 52 | hcd = usb_create_hcd(driver, &pdev->dev, "w90x900 EHCI"); | 45 | hcd = usb_create_hcd(driver, &pdev->dev, "w90x900 EHCI"); |
| 53 | if (!hcd) { | 46 | if (!hcd) { |
| 54 | retval = -ENOMEM; | 47 | retval = -ENOMEM; |
| 55 | goto err1; | 48 | goto err1; |
| 56 | } | 49 | } |
| 57 | 50 | ||
| 58 | hcd->rsrc_start = res->start; | 51 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 59 | hcd->rsrc_len = resource_size(res); | ||
| 60 | |||
| 61 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 52 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 62 | if (IS_ERR(hcd->regs)) { | 53 | if (IS_ERR(hcd->regs)) { |
| 63 | retval = PTR_ERR(hcd->regs); | 54 | retval = PTR_ERR(hcd->regs); |
| 64 | goto err2; | 55 | goto err2; |
| 65 | } | 56 | } |
| 57 | hcd->rsrc_start = res->start; | ||
| 58 | hcd->rsrc_len = resource_size(res); | ||
| 66 | 59 | ||
| 67 | ehci = hcd_to_ehci(hcd); | 60 | ehci = hcd_to_ehci(hcd); |
| 68 | ehci->caps = hcd->regs; | 61 | ehci->caps = hcd->regs; |
| @@ -82,8 +75,10 @@ static int usb_w90x900_probe(const struct hc_driver *driver, | |||
| 82 | __raw_writel(val, ehci->regs+PHY1_CTR); | 75 | __raw_writel(val, ehci->regs+PHY1_CTR); |
| 83 | 76 | ||
| 84 | irq = platform_get_irq(pdev, 0); | 77 | irq = platform_get_irq(pdev, 0); |
| 85 | if (irq < 0) | 78 | if (irq < 0) { |
| 79 | retval = irq; | ||
| 86 | goto err2; | 80 | goto err2; |
| 81 | } | ||
| 87 | 82 | ||
| 88 | retval = usb_add_hcd(hcd, irq, IRQF_SHARED); | 83 | retval = usb_add_hcd(hcd, irq, IRQF_SHARED); |
| 89 | if (retval != 0) | 84 | if (retval != 0) |
diff --git a/drivers/usb/host/ehci.h b/drivers/usb/host/ehci.h index eee228a26a0e..6f0577b0a5ae 100644 --- a/drivers/usb/host/ehci.h +++ b/drivers/usb/host/ehci.h | |||
| @@ -859,6 +859,8 @@ static inline u32 hc32_to_cpup (const struct ehci_hcd *ehci, const __hc32 *x) | |||
| 859 | struct ehci_driver_overrides { | 859 | struct ehci_driver_overrides { |
| 860 | size_t extra_priv_size; | 860 | size_t extra_priv_size; |
| 861 | int (*reset)(struct usb_hcd *hcd); | 861 | int (*reset)(struct usb_hcd *hcd); |
| 862 | int (*port_power)(struct usb_hcd *hcd, | ||
| 863 | int portnum, bool enable); | ||
| 862 | }; | 864 | }; |
| 863 | 865 | ||
| 864 | extern void ehci_init_driver(struct hc_driver *drv, | 866 | extern void ehci_init_driver(struct hc_driver *drv, |
diff --git a/drivers/usb/host/fotg210.h b/drivers/usb/host/fotg210.h index ac6cd1bfd208..3bad17859cd7 100644 --- a/drivers/usb/host/fotg210.h +++ b/drivers/usb/host/fotg210.h | |||
| @@ -1,6 +1,8 @@ | |||
| 1 | #ifndef __LINUX_FOTG210_H | 1 | #ifndef __LINUX_FOTG210_H |
| 2 | #define __LINUX_FOTG210_H | 2 | #define __LINUX_FOTG210_H |
| 3 | 3 | ||
| 4 | #include <linux/usb/ehci-dbgp.h> | ||
| 5 | |||
| 4 | /* definitions used for the EHCI driver */ | 6 | /* definitions used for the EHCI driver */ |
| 5 | 7 | ||
| 6 | /* | 8 | /* |
| @@ -84,7 +86,7 @@ struct fotg210_hcd { /* one per controller */ | |||
| 84 | /* glue to PCI and HCD framework */ | 86 | /* glue to PCI and HCD framework */ |
| 85 | struct fotg210_caps __iomem *caps; | 87 | struct fotg210_caps __iomem *caps; |
| 86 | struct fotg210_regs __iomem *regs; | 88 | struct fotg210_regs __iomem *regs; |
| 87 | struct fotg210_dbg_port __iomem *debug; | 89 | struct ehci_dbg_port __iomem *debug; |
| 88 | 90 | ||
| 89 | __u32 hcs_params; /* cached register copy */ | 91 | __u32 hcs_params; /* cached register copy */ |
| 90 | spinlock_t lock; | 92 | spinlock_t lock; |
| @@ -293,64 +295,6 @@ struct fotg210_regs { | |||
| 293 | #define GMIR_MDEV_INT (1 << 0) | 295 | #define GMIR_MDEV_INT (1 << 0) |
| 294 | }; | 296 | }; |
| 295 | 297 | ||
| 296 | /* Appendix C, Debug port ... intended for use with special "debug devices" | ||
| 297 | * that can help if there's no serial console. (nonstandard enumeration.) | ||
| 298 | */ | ||
| 299 | struct fotg210_dbg_port { | ||
| 300 | u32 control; | ||
| 301 | #define DBGP_OWNER (1<<30) | ||
| 302 | #define DBGP_ENABLED (1<<28) | ||
| 303 | #define DBGP_DONE (1<<16) | ||
| 304 | #define DBGP_INUSE (1<<10) | ||
| 305 | #define DBGP_ERRCODE(x) (((x)>>7)&0x07) | ||
| 306 | # define DBGP_ERR_BAD 1 | ||
| 307 | # define DBGP_ERR_SIGNAL 2 | ||
| 308 | #define DBGP_ERROR (1<<6) | ||
| 309 | #define DBGP_GO (1<<5) | ||
| 310 | #define DBGP_OUT (1<<4) | ||
| 311 | #define DBGP_LEN(x) (((x)>>0)&0x0f) | ||
| 312 | u32 pids; | ||
| 313 | #define DBGP_PID_GET(x) (((x)>>16)&0xff) | ||
| 314 | #define DBGP_PID_SET(data, tok) (((data)<<8)|(tok)) | ||
| 315 | u32 data03; | ||
| 316 | u32 data47; | ||
| 317 | u32 address; | ||
| 318 | #define DBGP_EPADDR(dev, ep) (((dev)<<8)|(ep)) | ||
| 319 | }; | ||
| 320 | |||
| 321 | #ifdef CONFIG_EARLY_PRINTK_DBGP | ||
| 322 | #include <linux/init.h> | ||
| 323 | extern int __init early_dbgp_init(char *s); | ||
| 324 | extern struct console early_dbgp_console; | ||
| 325 | #endif /* CONFIG_EARLY_PRINTK_DBGP */ | ||
| 326 | |||
| 327 | struct usb_hcd; | ||
| 328 | |||
| 329 | static inline int xen_dbgp_reset_prep(struct usb_hcd *hcd) | ||
| 330 | { | ||
| 331 | return 1; /* Shouldn't this be 0? */ | ||
| 332 | } | ||
| 333 | |||
| 334 | static inline int xen_dbgp_external_startup(struct usb_hcd *hcd) | ||
| 335 | { | ||
| 336 | return -1; | ||
| 337 | } | ||
| 338 | |||
| 339 | #ifdef CONFIG_EARLY_PRINTK_DBGP | ||
| 340 | /* Call backs from fotg210 host driver to fotg210 debug driver */ | ||
| 341 | extern int dbgp_external_startup(struct usb_hcd *); | ||
| 342 | extern int dbgp_reset_prep(struct usb_hcd *hcd); | ||
| 343 | #else | ||
| 344 | static inline int dbgp_reset_prep(struct usb_hcd *hcd) | ||
| 345 | { | ||
| 346 | return xen_dbgp_reset_prep(hcd); | ||
| 347 | } | ||
| 348 | static inline int dbgp_external_startup(struct usb_hcd *hcd) | ||
| 349 | { | ||
| 350 | return xen_dbgp_external_startup(hcd); | ||
| 351 | } | ||
| 352 | #endif | ||
| 353 | |||
| 354 | /*-------------------------------------------------------------------------*/ | 298 | /*-------------------------------------------------------------------------*/ |
| 355 | 299 | ||
| 356 | #define QTD_NEXT(fotg210, dma) cpu_to_hc32(fotg210, (u32)dma) | 300 | #define QTD_NEXT(fotg210, dma) cpu_to_hc32(fotg210, (u32)dma) |
diff --git a/drivers/usb/host/fusbh200.h b/drivers/usb/host/fusbh200.h index 6b719e066c3f..d6e5b3d4aa68 100644 --- a/drivers/usb/host/fusbh200.h +++ b/drivers/usb/host/fusbh200.h | |||
| @@ -1,6 +1,8 @@ | |||
| 1 | #ifndef __LINUX_FUSBH200_H | 1 | #ifndef __LINUX_FUSBH200_H |
| 2 | #define __LINUX_FUSBH200_H | 2 | #define __LINUX_FUSBH200_H |
| 3 | 3 | ||
| 4 | #include <linux/usb/ehci-dbgp.h> | ||
| 5 | |||
| 4 | /* definitions used for the EHCI driver */ | 6 | /* definitions used for the EHCI driver */ |
| 5 | 7 | ||
| 6 | /* | 8 | /* |
| @@ -84,7 +86,7 @@ struct fusbh200_hcd { /* one per controller */ | |||
| 84 | /* glue to PCI and HCD framework */ | 86 | /* glue to PCI and HCD framework */ |
| 85 | struct fusbh200_caps __iomem *caps; | 87 | struct fusbh200_caps __iomem *caps; |
| 86 | struct fusbh200_regs __iomem *regs; | 88 | struct fusbh200_regs __iomem *regs; |
| 87 | struct fusbh200_dbg_port __iomem *debug; | 89 | struct ehci_dbg_port __iomem *debug; |
| 88 | 90 | ||
| 89 | __u32 hcs_params; /* cached register copy */ | 91 | __u32 hcs_params; /* cached register copy */ |
| 90 | spinlock_t lock; | 92 | spinlock_t lock; |
| @@ -285,64 +287,6 @@ struct fusbh200_regs { | |||
| 285 | #define BMIER_VBUS_ERR_EN (1<<0) | 287 | #define BMIER_VBUS_ERR_EN (1<<0) |
| 286 | }; | 288 | }; |
| 287 | 289 | ||
| 288 | /* Appendix C, Debug port ... intended for use with special "debug devices" | ||
| 289 | * that can help if there's no serial console. (nonstandard enumeration.) | ||
| 290 | */ | ||
| 291 | struct fusbh200_dbg_port { | ||
| 292 | u32 control; | ||
| 293 | #define DBGP_OWNER (1<<30) | ||
| 294 | #define DBGP_ENABLED (1<<28) | ||
| 295 | #define DBGP_DONE (1<<16) | ||
| 296 | #define DBGP_INUSE (1<<10) | ||
| 297 | #define DBGP_ERRCODE(x) (((x)>>7)&0x07) | ||
| 298 | # define DBGP_ERR_BAD 1 | ||
| 299 | # define DBGP_ERR_SIGNAL 2 | ||
| 300 | #define DBGP_ERROR (1<<6) | ||
| 301 | #define DBGP_GO (1<<5) | ||
| 302 | #define DBGP_OUT (1<<4) | ||
| 303 | #define DBGP_LEN(x) (((x)>>0)&0x0f) | ||
| 304 | u32 pids; | ||
| 305 | #define DBGP_PID_GET(x) (((x)>>16)&0xff) | ||
| 306 | #define DBGP_PID_SET(data, tok) (((data)<<8)|(tok)) | ||
| 307 | u32 data03; | ||
| 308 | u32 data47; | ||
| 309 | u32 address; | ||
| 310 | #define DBGP_EPADDR(dev, ep) (((dev)<<8)|(ep)) | ||
| 311 | }; | ||
| 312 | |||
| 313 | #ifdef CONFIG_EARLY_PRINTK_DBGP | ||
| 314 | #include <linux/init.h> | ||
| 315 | extern int __init early_dbgp_init(char *s); | ||
| 316 | extern struct console early_dbgp_console; | ||
| 317 | #endif /* CONFIG_EARLY_PRINTK_DBGP */ | ||
| 318 | |||
| 319 | struct usb_hcd; | ||
| 320 | |||
| 321 | static inline int xen_dbgp_reset_prep(struct usb_hcd *hcd) | ||
| 322 | { | ||
| 323 | return 1; /* Shouldn't this be 0? */ | ||
| 324 | } | ||
| 325 | |||
| 326 | static inline int xen_dbgp_external_startup(struct usb_hcd *hcd) | ||
| 327 | { | ||
| 328 | return -1; | ||
| 329 | } | ||
| 330 | |||
| 331 | #ifdef CONFIG_EARLY_PRINTK_DBGP | ||
| 332 | /* Call backs from fusbh200 host driver to fusbh200 debug driver */ | ||
| 333 | extern int dbgp_external_startup(struct usb_hcd *); | ||
| 334 | extern int dbgp_reset_prep(struct usb_hcd *hcd); | ||
| 335 | #else | ||
| 336 | static inline int dbgp_reset_prep(struct usb_hcd *hcd) | ||
| 337 | { | ||
| 338 | return xen_dbgp_reset_prep(hcd); | ||
| 339 | } | ||
| 340 | static inline int dbgp_external_startup(struct usb_hcd *hcd) | ||
| 341 | { | ||
| 342 | return xen_dbgp_external_startup(hcd); | ||
| 343 | } | ||
| 344 | #endif | ||
| 345 | |||
| 346 | /*-------------------------------------------------------------------------*/ | 290 | /*-------------------------------------------------------------------------*/ |
| 347 | 291 | ||
| 348 | #define QTD_NEXT(fusbh200, dma) cpu_to_hc32(fusbh200, (u32)dma) | 292 | #define QTD_NEXT(fusbh200, dma) cpu_to_hc32(fusbh200, (u32)dma) |
diff --git a/drivers/usb/host/imx21-hcd.c b/drivers/usb/host/imx21-hcd.c index 207bad99301f..eb4efba9f1ad 100644 --- a/drivers/usb/host/imx21-hcd.c +++ b/drivers/usb/host/imx21-hcd.c | |||
| @@ -1174,11 +1174,11 @@ static int imx21_hc_urb_enqueue(struct usb_hcd *hcd, | |||
| 1174 | 1174 | ||
| 1175 | dev_vdbg(imx21->dev, | 1175 | dev_vdbg(imx21->dev, |
| 1176 | "enqueue urb=%p ep=%p len=%d " | 1176 | "enqueue urb=%p ep=%p len=%d " |
| 1177 | "buffer=%p dma=%08X setupBuf=%p setupDma=%08X\n", | 1177 | "buffer=%p dma=%pad setupBuf=%p setupDma=%pad\n", |
| 1178 | urb, ep, | 1178 | urb, ep, |
| 1179 | urb->transfer_buffer_length, | 1179 | urb->transfer_buffer_length, |
| 1180 | urb->transfer_buffer, urb->transfer_dma, | 1180 | urb->transfer_buffer, &urb->transfer_dma, |
| 1181 | urb->setup_packet, urb->setup_dma); | 1181 | urb->setup_packet, &urb->setup_dma); |
| 1182 | 1182 | ||
| 1183 | if (usb_pipeisoc(urb->pipe)) | 1183 | if (usb_pipeisoc(urb->pipe)) |
| 1184 | return imx21_hc_urb_enqueue_isoc(hcd, ep, urb, mem_flags); | 1184 | return imx21_hc_urb_enqueue_isoc(hcd, ep, urb, mem_flags); |
diff --git a/drivers/usb/host/octeon2-common.c b/drivers/usb/host/octeon2-common.c deleted file mode 100644 index d9df423f3d12..000000000000 --- a/drivers/usb/host/octeon2-common.c +++ /dev/null | |||
| @@ -1,200 +0,0 @@ | |||
| 1 | /* | ||
| 2 | * This file is subject to the terms and conditions of the GNU General Public | ||
| 3 | * License. See the file "COPYING" in the main directory of this archive | ||
| 4 | * for more details. | ||
| 5 | * | ||
| 6 | * Copyright (C) 2010, 2011 Cavium Networks | ||
| 7 | */ | ||
| 8 | |||
| 9 | #include <linux/module.h> | ||
| 10 | #include <linux/mutex.h> | ||
| 11 | #include <linux/delay.h> | ||
| 12 | |||
| 13 | #include <asm/octeon/octeon.h> | ||
| 14 | #include <asm/octeon/cvmx-uctlx-defs.h> | ||
| 15 | |||
| 16 | static DEFINE_MUTEX(octeon2_usb_clocks_mutex); | ||
| 17 | |||
| 18 | static int octeon2_usb_clock_start_cnt; | ||
| 19 | |||
| 20 | void octeon2_usb_clocks_start(void) | ||
| 21 | { | ||
| 22 | u64 div; | ||
| 23 | union cvmx_uctlx_if_ena if_ena; | ||
| 24 | union cvmx_uctlx_clk_rst_ctl clk_rst_ctl; | ||
| 25 | union cvmx_uctlx_uphy_ctl_status uphy_ctl_status; | ||
| 26 | union cvmx_uctlx_uphy_portx_ctl_status port_ctl_status; | ||
| 27 | int i; | ||
| 28 | unsigned long io_clk_64_to_ns; | ||
| 29 | |||
| 30 | |||
| 31 | mutex_lock(&octeon2_usb_clocks_mutex); | ||
| 32 | |||
| 33 | octeon2_usb_clock_start_cnt++; | ||
| 34 | if (octeon2_usb_clock_start_cnt != 1) | ||
| 35 | goto exit; | ||
| 36 | |||
| 37 | io_clk_64_to_ns = 64000000000ull / octeon_get_io_clock_rate(); | ||
| 38 | |||
| 39 | /* | ||
| 40 | * Step 1: Wait for voltages stable. That surely happened | ||
| 41 | * before starting the kernel. | ||
| 42 | * | ||
| 43 | * Step 2: Enable SCLK of UCTL by writing UCTL0_IF_ENA[EN] = 1 | ||
| 44 | */ | ||
| 45 | if_ena.u64 = 0; | ||
| 46 | if_ena.s.en = 1; | ||
| 47 | cvmx_write_csr(CVMX_UCTLX_IF_ENA(0), if_ena.u64); | ||
| 48 | |||
| 49 | /* Step 3: Configure the reference clock, PHY, and HCLK */ | ||
| 50 | clk_rst_ctl.u64 = cvmx_read_csr(CVMX_UCTLX_CLK_RST_CTL(0)); | ||
| 51 | |||
| 52 | /* | ||
| 53 | * If the UCTL looks like it has already been started, skip | ||
| 54 | * the initialization, otherwise bus errors are obtained. | ||
| 55 | */ | ||
| 56 | if (clk_rst_ctl.s.hrst) | ||
| 57 | goto end_clock; | ||
| 58 | /* 3a */ | ||
| 59 | clk_rst_ctl.s.p_por = 1; | ||
| 60 | clk_rst_ctl.s.hrst = 0; | ||
| 61 | clk_rst_ctl.s.p_prst = 0; | ||
| 62 | clk_rst_ctl.s.h_clkdiv_rst = 0; | ||
| 63 | clk_rst_ctl.s.o_clkdiv_rst = 0; | ||
| 64 | clk_rst_ctl.s.h_clkdiv_en = 0; | ||
| 65 | clk_rst_ctl.s.o_clkdiv_en = 0; | ||
| 66 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 67 | |||
| 68 | /* 3b */ | ||
| 69 | /* 12MHz crystal. */ | ||
| 70 | clk_rst_ctl.s.p_refclk_sel = 0; | ||
| 71 | clk_rst_ctl.s.p_refclk_div = 0; | ||
| 72 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 73 | |||
| 74 | /* 3c */ | ||
| 75 | div = octeon_get_io_clock_rate() / 130000000ull; | ||
| 76 | |||
| 77 | switch (div) { | ||
| 78 | case 0: | ||
| 79 | div = 1; | ||
| 80 | break; | ||
| 81 | case 1: | ||
| 82 | case 2: | ||
| 83 | case 3: | ||
| 84 | case 4: | ||
| 85 | break; | ||
| 86 | case 5: | ||
| 87 | div = 4; | ||
| 88 | break; | ||
| 89 | case 6: | ||
| 90 | case 7: | ||
| 91 | div = 6; | ||
| 92 | break; | ||
| 93 | case 8: | ||
| 94 | case 9: | ||
| 95 | case 10: | ||
| 96 | case 11: | ||
| 97 | div = 8; | ||
| 98 | break; | ||
| 99 | default: | ||
| 100 | div = 12; | ||
| 101 | break; | ||
| 102 | } | ||
| 103 | clk_rst_ctl.s.h_div = div; | ||
| 104 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 105 | /* Read it back, */ | ||
| 106 | clk_rst_ctl.u64 = cvmx_read_csr(CVMX_UCTLX_CLK_RST_CTL(0)); | ||
| 107 | clk_rst_ctl.s.h_clkdiv_en = 1; | ||
| 108 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 109 | /* 3d */ | ||
| 110 | clk_rst_ctl.s.h_clkdiv_rst = 1; | ||
| 111 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 112 | |||
| 113 | /* 3e: delay 64 io clocks */ | ||
| 114 | ndelay(io_clk_64_to_ns); | ||
| 115 | |||
| 116 | /* | ||
| 117 | * Step 4: Program the power-on reset field in the UCTL | ||
| 118 | * clock-reset-control register. | ||
| 119 | */ | ||
| 120 | clk_rst_ctl.s.p_por = 0; | ||
| 121 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 122 | |||
| 123 | /* Step 5: Wait 1 ms for the PHY clock to start. */ | ||
| 124 | mdelay(1); | ||
| 125 | |||
| 126 | /* | ||
| 127 | * Step 6: Program the reset input from automatic test | ||
| 128 | * equipment field in the UPHY CSR | ||
| 129 | */ | ||
| 130 | uphy_ctl_status.u64 = cvmx_read_csr(CVMX_UCTLX_UPHY_CTL_STATUS(0)); | ||
| 131 | uphy_ctl_status.s.ate_reset = 1; | ||
| 132 | cvmx_write_csr(CVMX_UCTLX_UPHY_CTL_STATUS(0), uphy_ctl_status.u64); | ||
| 133 | |||
| 134 | /* Step 7: Wait for at least 10ns. */ | ||
| 135 | ndelay(10); | ||
| 136 | |||
| 137 | /* Step 8: Clear the ATE_RESET field in the UPHY CSR. */ | ||
| 138 | uphy_ctl_status.s.ate_reset = 0; | ||
| 139 | cvmx_write_csr(CVMX_UCTLX_UPHY_CTL_STATUS(0), uphy_ctl_status.u64); | ||
| 140 | |||
| 141 | /* | ||
| 142 | * Step 9: Wait for at least 20ns for UPHY to output PHY clock | ||
| 143 | * signals and OHCI_CLK48 | ||
| 144 | */ | ||
| 145 | ndelay(20); | ||
| 146 | |||
| 147 | /* Step 10: Configure the OHCI_CLK48 and OHCI_CLK12 clocks. */ | ||
| 148 | /* 10a */ | ||
| 149 | clk_rst_ctl.s.o_clkdiv_rst = 1; | ||
| 150 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 151 | |||
| 152 | /* 10b */ | ||
| 153 | clk_rst_ctl.s.o_clkdiv_en = 1; | ||
| 154 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 155 | |||
| 156 | /* 10c */ | ||
| 157 | ndelay(io_clk_64_to_ns); | ||
| 158 | |||
| 159 | /* | ||
| 160 | * Step 11: Program the PHY reset field: | ||
| 161 | * UCTL0_CLK_RST_CTL[P_PRST] = 1 | ||
| 162 | */ | ||
| 163 | clk_rst_ctl.s.p_prst = 1; | ||
| 164 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 165 | |||
| 166 | /* Step 12: Wait 1 uS. */ | ||
| 167 | udelay(1); | ||
| 168 | |||
| 169 | /* Step 13: Program the HRESET_N field: UCTL0_CLK_RST_CTL[HRST] = 1 */ | ||
| 170 | clk_rst_ctl.s.hrst = 1; | ||
| 171 | cvmx_write_csr(CVMX_UCTLX_CLK_RST_CTL(0), clk_rst_ctl.u64); | ||
| 172 | |||
| 173 | end_clock: | ||
| 174 | /* Now we can set some other registers. */ | ||
| 175 | |||
| 176 | for (i = 0; i <= 1; i++) { | ||
| 177 | port_ctl_status.u64 = | ||
| 178 | cvmx_read_csr(CVMX_UCTLX_UPHY_PORTX_CTL_STATUS(i, 0)); | ||
| 179 | /* Set txvreftune to 15 to obtain compliant 'eye' diagram. */ | ||
| 180 | port_ctl_status.s.txvreftune = 15; | ||
| 181 | port_ctl_status.s.txrisetune = 1; | ||
| 182 | port_ctl_status.s.txpreemphasistune = 1; | ||
| 183 | cvmx_write_csr(CVMX_UCTLX_UPHY_PORTX_CTL_STATUS(i, 0), | ||
| 184 | port_ctl_status.u64); | ||
| 185 | } | ||
| 186 | |||
| 187 | /* Set uSOF cycle period to 60,000 bits. */ | ||
| 188 | cvmx_write_csr(CVMX_UCTLX_EHCI_FLA(0), 0x20ull); | ||
| 189 | exit: | ||
| 190 | mutex_unlock(&octeon2_usb_clocks_mutex); | ||
| 191 | } | ||
| 192 | EXPORT_SYMBOL(octeon2_usb_clocks_start); | ||
| 193 | |||
| 194 | void octeon2_usb_clocks_stop(void) | ||
| 195 | { | ||
| 196 | mutex_lock(&octeon2_usb_clocks_mutex); | ||
| 197 | octeon2_usb_clock_start_cnt--; | ||
| 198 | mutex_unlock(&octeon2_usb_clocks_mutex); | ||
| 199 | } | ||
| 200 | EXPORT_SYMBOL(octeon2_usb_clocks_stop); | ||
diff --git a/drivers/usb/host/ohci-at91.c b/drivers/usb/host/ohci-at91.c index e49eb4f90f5d..39406607e53a 100644 --- a/drivers/usb/host/ohci-at91.c +++ b/drivers/usb/host/ohci-at91.c | |||
| @@ -24,12 +24,8 @@ | |||
| 24 | #include <linux/usb.h> | 24 | #include <linux/usb.h> |
| 25 | #include <linux/usb/hcd.h> | 25 | #include <linux/usb/hcd.h> |
| 26 | 26 | ||
| 27 | #include <mach/hardware.h> | ||
| 28 | #include <asm/gpio.h> | 27 | #include <asm/gpio.h> |
| 29 | 28 | ||
| 30 | #include <mach/cpu.h> | ||
| 31 | |||
| 32 | |||
| 33 | #include "ohci.h" | 29 | #include "ohci.h" |
| 34 | 30 | ||
| 35 | #define valid_port(index) ((index) >= 0 && (index) < AT91_MAX_USBH_PORTS) | 31 | #define valid_port(index) ((index) >= 0 && (index) < AT91_MAX_USBH_PORTS) |
| @@ -137,12 +133,6 @@ static int usb_hcd_at91_probe(const struct hc_driver *driver, | |||
| 137 | struct resource *res; | 133 | struct resource *res; |
| 138 | int irq; | 134 | int irq; |
| 139 | 135 | ||
| 140 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 141 | if (!res) { | ||
| 142 | dev_dbg(dev, "hcd probe: missing memory resource\n"); | ||
| 143 | return -ENXIO; | ||
| 144 | } | ||
| 145 | |||
| 146 | irq = platform_get_irq(pdev, 0); | 136 | irq = platform_get_irq(pdev, 0); |
| 147 | if (irq < 0) { | 137 | if (irq < 0) { |
| 148 | dev_dbg(dev, "hcd probe: missing irq resource\n"); | 138 | dev_dbg(dev, "hcd probe: missing irq resource\n"); |
| @@ -152,14 +142,15 @@ static int usb_hcd_at91_probe(const struct hc_driver *driver, | |||
| 152 | hcd = usb_create_hcd(driver, dev, "at91"); | 142 | hcd = usb_create_hcd(driver, dev, "at91"); |
| 153 | if (!hcd) | 143 | if (!hcd) |
| 154 | return -ENOMEM; | 144 | return -ENOMEM; |
| 155 | hcd->rsrc_start = res->start; | ||
| 156 | hcd->rsrc_len = resource_size(res); | ||
| 157 | 145 | ||
| 146 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 158 | hcd->regs = devm_ioremap_resource(dev, res); | 147 | hcd->regs = devm_ioremap_resource(dev, res); |
| 159 | if (IS_ERR(hcd->regs)) { | 148 | if (IS_ERR(hcd->regs)) { |
| 160 | retval = PTR_ERR(hcd->regs); | 149 | retval = PTR_ERR(hcd->regs); |
| 161 | goto err; | 150 | goto err; |
| 162 | } | 151 | } |
| 152 | hcd->rsrc_start = res->start; | ||
| 153 | hcd->rsrc_len = resource_size(res); | ||
| 163 | 154 | ||
| 164 | iclk = devm_clk_get(dev, "ohci_clk"); | 155 | iclk = devm_clk_get(dev, "ohci_clk"); |
| 165 | if (IS_ERR(iclk)) { | 156 | if (IS_ERR(iclk)) { |
diff --git a/drivers/usb/host/ohci-da8xx.c b/drivers/usb/host/ohci-da8xx.c index df06be6b47f5..1c76999b2184 100644 --- a/drivers/usb/host/ohci-da8xx.c +++ b/drivers/usb/host/ohci-da8xx.c | |||
| @@ -313,16 +313,13 @@ static int usb_hcd_da8xx_probe(const struct hc_driver *driver, | |||
| 313 | return -ENOMEM; | 313 | return -ENOMEM; |
| 314 | 314 | ||
| 315 | mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 315 | mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 316 | if (!mem) | ||
| 317 | return -ENODEV; | ||
| 318 | hcd->rsrc_start = mem->start; | ||
| 319 | hcd->rsrc_len = resource_size(mem); | ||
| 320 | |||
| 321 | hcd->regs = devm_ioremap_resource(&pdev->dev, mem); | 316 | hcd->regs = devm_ioremap_resource(&pdev->dev, mem); |
| 322 | if (IS_ERR(hcd->regs)) { | 317 | if (IS_ERR(hcd->regs)) { |
| 323 | error = PTR_ERR(hcd->regs); | 318 | error = PTR_ERR(hcd->regs); |
| 324 | goto err; | 319 | goto err; |
| 325 | } | 320 | } |
| 321 | hcd->rsrc_start = mem->start; | ||
| 322 | hcd->rsrc_len = resource_size(mem); | ||
| 326 | 323 | ||
| 327 | ohci_hcd_init(hcd_to_ohci(hcd)); | 324 | ohci_hcd_init(hcd_to_ohci(hcd)); |
| 328 | 325 | ||
diff --git a/drivers/usb/host/ohci-exynos.c b/drivers/usb/host/ohci-exynos.c index d28b6583ba02..035a8a85a867 100644 --- a/drivers/usb/host/ohci-exynos.c +++ b/drivers/usb/host/ohci-exynos.c | |||
| @@ -63,7 +63,6 @@ static int exynos_ohci_get_phy(struct device *dev, | |||
| 63 | 63 | ||
| 64 | phy = devm_of_phy_get(dev, child, NULL); | 64 | phy = devm_of_phy_get(dev, child, NULL); |
| 65 | exynos_ohci->phy[phy_number] = phy; | 65 | exynos_ohci->phy[phy_number] = phy; |
| 66 | of_node_put(child); | ||
| 67 | if (IS_ERR(phy)) { | 66 | if (IS_ERR(phy)) { |
| 68 | ret = PTR_ERR(phy); | 67 | ret = PTR_ERR(phy); |
| 69 | if (ret == -EPROBE_DEFER) { | 68 | if (ret == -EPROBE_DEFER) { |
| @@ -156,19 +155,13 @@ skip_phy: | |||
| 156 | goto fail_clk; | 155 | goto fail_clk; |
| 157 | 156 | ||
| 158 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 157 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 159 | if (!res) { | ||
| 160 | dev_err(&pdev->dev, "Failed to get I/O memory\n"); | ||
| 161 | err = -ENXIO; | ||
| 162 | goto fail_io; | ||
| 163 | } | ||
| 164 | |||
| 165 | hcd->rsrc_start = res->start; | ||
| 166 | hcd->rsrc_len = resource_size(res); | ||
| 167 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 158 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 168 | if (IS_ERR(hcd->regs)) { | 159 | if (IS_ERR(hcd->regs)) { |
| 169 | err = PTR_ERR(hcd->regs); | 160 | err = PTR_ERR(hcd->regs); |
| 170 | goto fail_io; | 161 | goto fail_io; |
| 171 | } | 162 | } |
| 163 | hcd->rsrc_start = res->start; | ||
| 164 | hcd->rsrc_len = resource_size(res); | ||
| 172 | 165 | ||
| 173 | irq = platform_get_irq(pdev, 0); | 166 | irq = platform_get_irq(pdev, 0); |
| 174 | if (!irq) { | 167 | if (!irq) { |
diff --git a/drivers/usb/host/ohci-hcd.c b/drivers/usb/host/ohci-hcd.c index d664edabf14e..1dab9dfbca6a 100644 --- a/drivers/usb/host/ohci-hcd.c +++ b/drivers/usb/host/ohci-hcd.c | |||
| @@ -1249,11 +1249,6 @@ MODULE_LICENSE ("GPL"); | |||
| 1249 | #define PLATFORM_DRIVER ohci_hcd_jz4740_driver | 1249 | #define PLATFORM_DRIVER ohci_hcd_jz4740_driver |
| 1250 | #endif | 1250 | #endif |
| 1251 | 1251 | ||
| 1252 | #ifdef CONFIG_USB_OCTEON_OHCI | ||
| 1253 | #include "ohci-octeon.c" | ||
| 1254 | #define PLATFORM_DRIVER ohci_octeon_driver | ||
| 1255 | #endif | ||
| 1256 | |||
| 1257 | #ifdef CONFIG_TILE_USB | 1252 | #ifdef CONFIG_TILE_USB |
| 1258 | #include "ohci-tilegx.c" | 1253 | #include "ohci-tilegx.c" |
| 1259 | #define PLATFORM_DRIVER ohci_hcd_tilegx_driver | 1254 | #define PLATFORM_DRIVER ohci_hcd_tilegx_driver |
diff --git a/drivers/usb/host/ohci-jz4740.c b/drivers/usb/host/ohci-jz4740.c index c2c221a332eb..8ddd8f5470cb 100644 --- a/drivers/usb/host/ohci-jz4740.c +++ b/drivers/usb/host/ohci-jz4740.c | |||
| @@ -153,13 +153,6 @@ static int jz4740_ohci_probe(struct platform_device *pdev) | |||
| 153 | struct resource *res; | 153 | struct resource *res; |
| 154 | int irq; | 154 | int irq; |
| 155 | 155 | ||
| 156 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 157 | |||
| 158 | if (!res) { | ||
| 159 | dev_err(&pdev->dev, "Failed to get platform resource\n"); | ||
| 160 | return -ENOENT; | ||
| 161 | } | ||
| 162 | |||
| 163 | irq = platform_get_irq(pdev, 0); | 156 | irq = platform_get_irq(pdev, 0); |
| 164 | if (irq < 0) { | 157 | if (irq < 0) { |
| 165 | dev_err(&pdev->dev, "Failed to get platform irq\n"); | 158 | dev_err(&pdev->dev, "Failed to get platform irq\n"); |
| @@ -174,14 +167,14 @@ static int jz4740_ohci_probe(struct platform_device *pdev) | |||
| 174 | 167 | ||
| 175 | jz4740_ohci = hcd_to_jz4740_hcd(hcd); | 168 | jz4740_ohci = hcd_to_jz4740_hcd(hcd); |
| 176 | 169 | ||
| 177 | hcd->rsrc_start = res->start; | 170 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 178 | hcd->rsrc_len = resource_size(res); | ||
| 179 | |||
| 180 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 171 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 181 | if (IS_ERR(hcd->regs)) { | 172 | if (IS_ERR(hcd->regs)) { |
| 182 | ret = PTR_ERR(hcd->regs); | 173 | ret = PTR_ERR(hcd->regs); |
| 183 | goto err_free; | 174 | goto err_free; |
| 184 | } | 175 | } |
| 176 | hcd->rsrc_start = res->start; | ||
| 177 | hcd->rsrc_len = resource_size(res); | ||
| 185 | 178 | ||
| 186 | jz4740_ohci->clk = devm_clk_get(&pdev->dev, "uhc"); | 179 | jz4740_ohci->clk = devm_clk_get(&pdev->dev, "uhc"); |
| 187 | if (IS_ERR(jz4740_ohci->clk)) { | 180 | if (IS_ERR(jz4740_ohci->clk)) { |
diff --git a/drivers/usb/host/ohci-octeon.c b/drivers/usb/host/ohci-octeon.c deleted file mode 100644 index 15af8954085e..000000000000 --- a/drivers/usb/host/ohci-octeon.c +++ /dev/null | |||
| @@ -1,202 +0,0 @@ | |||
| 1 | /* | ||
| 2 | * EHCI HCD glue for Cavium Octeon II SOCs. | ||
| 3 | * | ||
| 4 | * Loosely based on ehci-au1xxx.c | ||
| 5 | * | ||
| 6 | * This file is subject to the terms and conditions of the GNU General Public | ||
| 7 | * License. See the file "COPYING" in the main directory of this archive | ||
| 8 | * for more details. | ||
| 9 | * | ||
| 10 | * Copyright (C) 2010 Cavium Networks | ||
| 11 | * | ||
| 12 | */ | ||
| 13 | |||
| 14 | #include <linux/platform_device.h> | ||
| 15 | |||
| 16 | #include <asm/octeon/octeon.h> | ||
| 17 | #include <asm/octeon/cvmx-uctlx-defs.h> | ||
| 18 | |||
| 19 | #define OCTEON_OHCI_HCD_NAME "octeon-ohci" | ||
| 20 | |||
| 21 | /* Common clock init code. */ | ||
| 22 | void octeon2_usb_clocks_start(void); | ||
| 23 | void octeon2_usb_clocks_stop(void); | ||
| 24 | |||
| 25 | static void ohci_octeon_hw_start(void) | ||
| 26 | { | ||
| 27 | union cvmx_uctlx_ohci_ctl ohci_ctl; | ||
| 28 | |||
| 29 | octeon2_usb_clocks_start(); | ||
| 30 | |||
| 31 | ohci_ctl.u64 = cvmx_read_csr(CVMX_UCTLX_OHCI_CTL(0)); | ||
| 32 | ohci_ctl.s.l2c_addr_msb = 0; | ||
| 33 | ohci_ctl.s.l2c_buff_emod = 1; /* Byte swapped. */ | ||
| 34 | ohci_ctl.s.l2c_desc_emod = 1; /* Byte swapped. */ | ||
| 35 | cvmx_write_csr(CVMX_UCTLX_OHCI_CTL(0), ohci_ctl.u64); | ||
| 36 | |||
| 37 | } | ||
| 38 | |||
| 39 | static void ohci_octeon_hw_stop(void) | ||
| 40 | { | ||
| 41 | /* Undo ohci_octeon_start() */ | ||
| 42 | octeon2_usb_clocks_stop(); | ||
| 43 | } | ||
| 44 | |||
| 45 | static int ohci_octeon_start(struct usb_hcd *hcd) | ||
| 46 | { | ||
| 47 | struct ohci_hcd *ohci = hcd_to_ohci(hcd); | ||
| 48 | int ret; | ||
| 49 | |||
| 50 | ret = ohci_init(ohci); | ||
| 51 | |||
| 52 | if (ret < 0) | ||
| 53 | return ret; | ||
| 54 | |||
| 55 | ret = ohci_run(ohci); | ||
| 56 | |||
| 57 | if (ret < 0) { | ||
| 58 | ohci_err(ohci, "can't start %s", hcd->self.bus_name); | ||
| 59 | ohci_stop(hcd); | ||
| 60 | return ret; | ||
| 61 | } | ||
| 62 | |||
| 63 | return 0; | ||
| 64 | } | ||
| 65 | |||
| 66 | static const struct hc_driver ohci_octeon_hc_driver = { | ||
| 67 | .description = hcd_name, | ||
| 68 | .product_desc = "Octeon OHCI", | ||
| 69 | .hcd_priv_size = sizeof(struct ohci_hcd), | ||
| 70 | |||
| 71 | /* | ||
| 72 | * generic hardware linkage | ||
| 73 | */ | ||
| 74 | .irq = ohci_irq, | ||
| 75 | .flags = HCD_USB11 | HCD_MEMORY, | ||
| 76 | |||
| 77 | /* | ||
| 78 | * basic lifecycle operations | ||
| 79 | */ | ||
| 80 | .start = ohci_octeon_start, | ||
| 81 | .stop = ohci_stop, | ||
| 82 | .shutdown = ohci_shutdown, | ||
| 83 | |||
| 84 | /* | ||
| 85 | * managing i/o requests and associated device resources | ||
| 86 | */ | ||
| 87 | .urb_enqueue = ohci_urb_enqueue, | ||
| 88 | .urb_dequeue = ohci_urb_dequeue, | ||
| 89 | .endpoint_disable = ohci_endpoint_disable, | ||
| 90 | |||
| 91 | /* | ||
| 92 | * scheduling support | ||
| 93 | */ | ||
| 94 | .get_frame_number = ohci_get_frame, | ||
| 95 | |||
| 96 | /* | ||
| 97 | * root hub support | ||
| 98 | */ | ||
| 99 | .hub_status_data = ohci_hub_status_data, | ||
| 100 | .hub_control = ohci_hub_control, | ||
| 101 | |||
| 102 | .start_port_reset = ohci_start_port_reset, | ||
| 103 | }; | ||
| 104 | |||
| 105 | static int ohci_octeon_drv_probe(struct platform_device *pdev) | ||
| 106 | { | ||
| 107 | struct usb_hcd *hcd; | ||
| 108 | struct ohci_hcd *ohci; | ||
| 109 | void *reg_base; | ||
| 110 | struct resource *res_mem; | ||
| 111 | int irq; | ||
| 112 | int ret; | ||
| 113 | |||
| 114 | if (usb_disabled()) | ||
| 115 | return -ENODEV; | ||
| 116 | |||
| 117 | irq = platform_get_irq(pdev, 0); | ||
| 118 | if (irq < 0) { | ||
| 119 | dev_err(&pdev->dev, "No irq assigned\n"); | ||
| 120 | return -ENODEV; | ||
| 121 | } | ||
| 122 | |||
| 123 | res_mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 124 | if (res_mem == NULL) { | ||
| 125 | dev_err(&pdev->dev, "No register space assigned\n"); | ||
| 126 | return -ENODEV; | ||
| 127 | } | ||
| 128 | |||
| 129 | /* Ohci is a 32-bit device. */ | ||
| 130 | ret = dma_coerce_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(32)); | ||
| 131 | if (ret) | ||
| 132 | return ret; | ||
| 133 | |||
| 134 | hcd = usb_create_hcd(&ohci_octeon_hc_driver, &pdev->dev, "octeon"); | ||
| 135 | if (!hcd) | ||
| 136 | return -ENOMEM; | ||
| 137 | |||
| 138 | hcd->rsrc_start = res_mem->start; | ||
| 139 | hcd->rsrc_len = resource_size(res_mem); | ||
| 140 | |||
| 141 | reg_base = devm_ioremap_resource(&pdev->dev, res_mem); | ||
| 142 | if (IS_ERR(reg_base)) { | ||
| 143 | ret = PTR_ERR(reg_base); | ||
| 144 | goto err1; | ||
| 145 | } | ||
| 146 | |||
| 147 | ohci_octeon_hw_start(); | ||
| 148 | |||
| 149 | hcd->regs = reg_base; | ||
| 150 | |||
| 151 | ohci = hcd_to_ohci(hcd); | ||
| 152 | |||
| 153 | /* Octeon OHCI matches CPU endianness. */ | ||
| 154 | #ifdef __BIG_ENDIAN | ||
| 155 | ohci->flags |= OHCI_QUIRK_BE_MMIO; | ||
| 156 | #endif | ||
| 157 | |||
| 158 | ohci_hcd_init(ohci); | ||
| 159 | |||
| 160 | ret = usb_add_hcd(hcd, irq, IRQF_SHARED); | ||
| 161 | if (ret) { | ||
| 162 | dev_dbg(&pdev->dev, "failed to add hcd with err %d\n", ret); | ||
| 163 | goto err2; | ||
| 164 | } | ||
| 165 | |||
| 166 | device_wakeup_enable(hcd->self.controller); | ||
| 167 | |||
| 168 | platform_set_drvdata(pdev, hcd); | ||
| 169 | |||
| 170 | return 0; | ||
| 171 | |||
| 172 | err2: | ||
| 173 | ohci_octeon_hw_stop(); | ||
| 174 | |||
| 175 | err1: | ||
| 176 | usb_put_hcd(hcd); | ||
| 177 | return ret; | ||
| 178 | } | ||
| 179 | |||
| 180 | static int ohci_octeon_drv_remove(struct platform_device *pdev) | ||
| 181 | { | ||
| 182 | struct usb_hcd *hcd = platform_get_drvdata(pdev); | ||
| 183 | |||
| 184 | usb_remove_hcd(hcd); | ||
| 185 | |||
| 186 | ohci_octeon_hw_stop(); | ||
| 187 | usb_put_hcd(hcd); | ||
| 188 | |||
| 189 | return 0; | ||
| 190 | } | ||
| 191 | |||
| 192 | static struct platform_driver ohci_octeon_driver = { | ||
| 193 | .probe = ohci_octeon_drv_probe, | ||
| 194 | .remove = ohci_octeon_drv_remove, | ||
| 195 | .shutdown = usb_hcd_platform_shutdown, | ||
| 196 | .driver = { | ||
| 197 | .name = OCTEON_OHCI_HCD_NAME, | ||
| 198 | .owner = THIS_MODULE, | ||
| 199 | } | ||
| 200 | }; | ||
| 201 | |||
| 202 | MODULE_ALIAS("platform:" OCTEON_OHCI_HCD_NAME); | ||
diff --git a/drivers/usb/host/ohci-omap.c b/drivers/usb/host/ohci-omap.c index 0231606d47c2..3e5df5af3740 100644 --- a/drivers/usb/host/ohci-omap.c +++ b/drivers/usb/host/ohci-omap.c | |||
| @@ -183,7 +183,7 @@ static void start_hnp(struct ohci_hcd *ohci) | |||
| 183 | otg_start_hnp(hcd->usb_phy->otg); | 183 | otg_start_hnp(hcd->usb_phy->otg); |
| 184 | 184 | ||
| 185 | local_irq_save(flags); | 185 | local_irq_save(flags); |
| 186 | hcd->usb_phy->state = OTG_STATE_A_SUSPEND; | 186 | hcd->usb_phy->otg->state = OTG_STATE_A_SUSPEND; |
| 187 | writel (RH_PS_PSS, &ohci->regs->roothub.portstatus [port]); | 187 | writel (RH_PS_PSS, &ohci->regs->roothub.portstatus [port]); |
| 188 | l = omap_readl(OTG_CTRL); | 188 | l = omap_readl(OTG_CTRL); |
| 189 | l &= ~OTG_A_BUSREQ; | 189 | l &= ~OTG_A_BUSREQ; |
diff --git a/drivers/usb/host/ohci-platform.c b/drivers/usb/host/ohci-platform.c index 4369299064c7..9434c1d54495 100644 --- a/drivers/usb/host/ohci-platform.c +++ b/drivers/usb/host/ohci-platform.c | |||
| @@ -43,20 +43,6 @@ struct ohci_platform_priv { | |||
| 43 | 43 | ||
| 44 | static const char hcd_name[] = "ohci-platform"; | 44 | static const char hcd_name[] = "ohci-platform"; |
| 45 | 45 | ||
| 46 | static int ohci_platform_reset(struct usb_hcd *hcd) | ||
| 47 | { | ||
| 48 | struct platform_device *pdev = to_platform_device(hcd->self.controller); | ||
| 49 | struct usb_ohci_pdata *pdata = dev_get_platdata(&pdev->dev); | ||
| 50 | struct ohci_hcd *ohci = hcd_to_ohci(hcd); | ||
| 51 | |||
| 52 | if (pdata->no_big_frame_no) | ||
| 53 | ohci->flags |= OHCI_QUIRK_FRAME_NO; | ||
| 54 | if (pdata->num_ports) | ||
| 55 | ohci->num_ports = pdata->num_ports; | ||
| 56 | |||
| 57 | return ohci_setup(hcd); | ||
| 58 | } | ||
| 59 | |||
| 60 | static int ohci_platform_power_on(struct platform_device *dev) | 46 | static int ohci_platform_power_on(struct platform_device *dev) |
| 61 | { | 47 | { |
| 62 | struct usb_hcd *hcd = platform_get_drvdata(dev); | 48 | struct usb_hcd *hcd = platform_get_drvdata(dev); |
| @@ -110,7 +96,6 @@ static struct hc_driver __read_mostly ohci_platform_hc_driver; | |||
| 110 | 96 | ||
| 111 | static const struct ohci_driver_overrides platform_overrides __initconst = { | 97 | static const struct ohci_driver_overrides platform_overrides __initconst = { |
| 112 | .product_desc = "Generic Platform OHCI controller", | 98 | .product_desc = "Generic Platform OHCI controller", |
| 113 | .reset = ohci_platform_reset, | ||
| 114 | .extra_priv_size = sizeof(struct ohci_platform_priv), | 99 | .extra_priv_size = sizeof(struct ohci_platform_priv), |
| 115 | }; | 100 | }; |
| 116 | 101 | ||
| @@ -149,12 +134,6 @@ static int ohci_platform_probe(struct platform_device *dev) | |||
| 149 | return irq; | 134 | return irq; |
| 150 | } | 135 | } |
| 151 | 136 | ||
| 152 | res_mem = platform_get_resource(dev, IORESOURCE_MEM, 0); | ||
| 153 | if (!res_mem) { | ||
| 154 | dev_err(&dev->dev, "no memory resource provided"); | ||
| 155 | return -ENXIO; | ||
| 156 | } | ||
| 157 | |||
| 158 | hcd = usb_create_hcd(&ohci_platform_hc_driver, &dev->dev, | 137 | hcd = usb_create_hcd(&ohci_platform_hc_driver, &dev->dev, |
| 159 | dev_name(&dev->dev)); | 138 | dev_name(&dev->dev)); |
| 160 | if (!hcd) | 139 | if (!hcd) |
| @@ -175,6 +154,12 @@ static int ohci_platform_probe(struct platform_device *dev) | |||
| 175 | if (of_property_read_bool(dev->dev.of_node, "big-endian")) | 154 | if (of_property_read_bool(dev->dev.of_node, "big-endian")) |
| 176 | ohci->flags |= OHCI_QUIRK_BE_MMIO | OHCI_QUIRK_BE_DESC; | 155 | ohci->flags |= OHCI_QUIRK_BE_MMIO | OHCI_QUIRK_BE_DESC; |
| 177 | 156 | ||
| 157 | if (of_property_read_bool(dev->dev.of_node, "no-big-frame-no")) | ||
| 158 | ohci->flags |= OHCI_QUIRK_FRAME_NO; | ||
| 159 | |||
| 160 | of_property_read_u32(dev->dev.of_node, "num-ports", | ||
| 161 | &ohci->num_ports); | ||
| 162 | |||
| 178 | priv->phy = devm_phy_get(&dev->dev, "usb"); | 163 | priv->phy = devm_phy_get(&dev->dev, "usb"); |
| 179 | if (IS_ERR(priv->phy)) { | 164 | if (IS_ERR(priv->phy)) { |
| 180 | err = PTR_ERR(priv->phy); | 165 | err = PTR_ERR(priv->phy); |
| @@ -212,6 +197,10 @@ static int ohci_platform_probe(struct platform_device *dev) | |||
| 212 | ohci->flags |= OHCI_QUIRK_BE_DESC; | 197 | ohci->flags |= OHCI_QUIRK_BE_DESC; |
| 213 | if (pdata->big_endian_mmio) | 198 | if (pdata->big_endian_mmio) |
| 214 | ohci->flags |= OHCI_QUIRK_BE_MMIO; | 199 | ohci->flags |= OHCI_QUIRK_BE_MMIO; |
| 200 | if (pdata->no_big_frame_no) | ||
| 201 | ohci->flags |= OHCI_QUIRK_FRAME_NO; | ||
| 202 | if (pdata->num_ports) | ||
| 203 | ohci->num_ports = pdata->num_ports; | ||
| 215 | 204 | ||
| 216 | #ifndef CONFIG_USB_OHCI_BIG_ENDIAN_MMIO | 205 | #ifndef CONFIG_USB_OHCI_BIG_ENDIAN_MMIO |
| 217 | if (ohci->flags & OHCI_QUIRK_BE_MMIO) { | 206 | if (ohci->flags & OHCI_QUIRK_BE_MMIO) { |
| @@ -236,14 +225,15 @@ static int ohci_platform_probe(struct platform_device *dev) | |||
| 236 | goto err_reset; | 225 | goto err_reset; |
| 237 | } | 226 | } |
| 238 | 227 | ||
| 239 | hcd->rsrc_start = res_mem->start; | 228 | res_mem = platform_get_resource(dev, IORESOURCE_MEM, 0); |
| 240 | hcd->rsrc_len = resource_size(res_mem); | ||
| 241 | |||
| 242 | hcd->regs = devm_ioremap_resource(&dev->dev, res_mem); | 229 | hcd->regs = devm_ioremap_resource(&dev->dev, res_mem); |
| 243 | if (IS_ERR(hcd->regs)) { | 230 | if (IS_ERR(hcd->regs)) { |
| 244 | err = PTR_ERR(hcd->regs); | 231 | err = PTR_ERR(hcd->regs); |
| 245 | goto err_power; | 232 | goto err_power; |
| 246 | } | 233 | } |
| 234 | hcd->rsrc_start = res_mem->start; | ||
| 235 | hcd->rsrc_len = resource_size(res_mem); | ||
| 236 | |||
| 247 | err = usb_add_hcd(hcd, irq, IRQF_SHARED); | 237 | err = usb_add_hcd(hcd, irq, IRQF_SHARED); |
| 248 | if (err) | 238 | if (err) |
| 249 | goto err_power; | 239 | goto err_power; |
| @@ -298,8 +288,7 @@ static int ohci_platform_remove(struct platform_device *dev) | |||
| 298 | return 0; | 288 | return 0; |
| 299 | } | 289 | } |
| 300 | 290 | ||
| 301 | #ifdef CONFIG_PM | 291 | #ifdef CONFIG_PM_SLEEP |
| 302 | |||
| 303 | static int ohci_platform_suspend(struct device *dev) | 292 | static int ohci_platform_suspend(struct device *dev) |
| 304 | { | 293 | { |
| 305 | struct usb_hcd *hcd = dev_get_drvdata(dev); | 294 | struct usb_hcd *hcd = dev_get_drvdata(dev); |
| @@ -335,11 +324,7 @@ static int ohci_platform_resume(struct device *dev) | |||
| 335 | ohci_resume(hcd, false); | 324 | ohci_resume(hcd, false); |
| 336 | return 0; | 325 | return 0; |
| 337 | } | 326 | } |
| 338 | 327 | #endif /* CONFIG_PM_SLEEP */ | |
| 339 | #else /* !CONFIG_PM */ | ||
| 340 | #define ohci_platform_suspend NULL | ||
| 341 | #define ohci_platform_resume NULL | ||
| 342 | #endif /* CONFIG_PM */ | ||
| 343 | 328 | ||
| 344 | static const struct of_device_id ohci_platform_ids[] = { | 329 | static const struct of_device_id ohci_platform_ids[] = { |
| 345 | { .compatible = "generic-ohci", }, | 330 | { .compatible = "generic-ohci", }, |
| @@ -353,10 +338,8 @@ static const struct platform_device_id ohci_platform_table[] = { | |||
| 353 | }; | 338 | }; |
| 354 | MODULE_DEVICE_TABLE(platform, ohci_platform_table); | 339 | MODULE_DEVICE_TABLE(platform, ohci_platform_table); |
| 355 | 340 | ||
| 356 | static const struct dev_pm_ops ohci_platform_pm_ops = { | 341 | static SIMPLE_DEV_PM_OPS(ohci_platform_pm_ops, ohci_platform_suspend, |
| 357 | .suspend = ohci_platform_suspend, | 342 | ohci_platform_resume); |
| 358 | .resume = ohci_platform_resume, | ||
| 359 | }; | ||
| 360 | 343 | ||
| 361 | static struct platform_driver ohci_platform_driver = { | 344 | static struct platform_driver ohci_platform_driver = { |
| 362 | .id_table = ohci_platform_table, | 345 | .id_table = ohci_platform_table, |
diff --git a/drivers/usb/host/ohci-pxa27x.c b/drivers/usb/host/ohci-pxa27x.c index e68f3d02cd1a..13399814ef5f 100644 --- a/drivers/usb/host/ohci-pxa27x.c +++ b/drivers/usb/host/ohci-pxa27x.c | |||
| @@ -447,20 +447,13 @@ int usb_hcd_pxa27x_probe (const struct hc_driver *driver, struct platform_device | |||
| 447 | return -ENOMEM; | 447 | return -ENOMEM; |
| 448 | 448 | ||
| 449 | r = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 449 | r = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 450 | if (!r) { | ||
| 451 | pr_err("no resource of IORESOURCE_MEM"); | ||
| 452 | retval = -ENXIO; | ||
| 453 | goto err; | ||
| 454 | } | ||
| 455 | |||
| 456 | hcd->rsrc_start = r->start; | ||
| 457 | hcd->rsrc_len = resource_size(r); | ||
| 458 | |||
| 459 | hcd->regs = devm_ioremap_resource(&pdev->dev, r); | 450 | hcd->regs = devm_ioremap_resource(&pdev->dev, r); |
| 460 | if (IS_ERR(hcd->regs)) { | 451 | if (IS_ERR(hcd->regs)) { |
| 461 | retval = PTR_ERR(hcd->regs); | 452 | retval = PTR_ERR(hcd->regs); |
| 462 | goto err; | 453 | goto err; |
| 463 | } | 454 | } |
| 455 | hcd->rsrc_start = r->start; | ||
| 456 | hcd->rsrc_len = resource_size(r); | ||
| 464 | 457 | ||
| 465 | /* initialize "struct pxa27x_ohci" */ | 458 | /* initialize "struct pxa27x_ohci" */ |
| 466 | pxa_ohci = to_pxa27x_ohci(hcd); | 459 | pxa_ohci = to_pxa27x_ohci(hcd); |
diff --git a/drivers/usb/host/ohci-spear.c b/drivers/usb/host/ohci-spear.c index 8d5876692e7c..4a54f9d73136 100644 --- a/drivers/usb/host/ohci-spear.c +++ b/drivers/usb/host/ohci-spear.c | |||
| @@ -74,20 +74,15 @@ static int spear_ohci_hcd_drv_probe(struct platform_device *pdev) | |||
| 74 | } | 74 | } |
| 75 | 75 | ||
| 76 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 76 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 77 | if (!res) { | ||
| 78 | retval = -ENODEV; | ||
| 79 | goto err_put_hcd; | ||
| 80 | } | ||
| 81 | |||
| 82 | hcd->rsrc_start = pdev->resource[0].start; | ||
| 83 | hcd->rsrc_len = resource_size(res); | ||
| 84 | |||
| 85 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 77 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 86 | if (IS_ERR(hcd->regs)) { | 78 | if (IS_ERR(hcd->regs)) { |
| 87 | retval = PTR_ERR(hcd->regs); | 79 | retval = PTR_ERR(hcd->regs); |
| 88 | goto err_put_hcd; | 80 | goto err_put_hcd; |
| 89 | } | 81 | } |
| 90 | 82 | ||
| 83 | hcd->rsrc_start = pdev->resource[0].start; | ||
| 84 | hcd->rsrc_len = resource_size(res); | ||
| 85 | |||
| 91 | sohci_p = to_spear_ohci(hcd); | 86 | sohci_p = to_spear_ohci(hcd); |
| 92 | sohci_p->clk = usbh_clk; | 87 | sohci_p->clk = usbh_clk; |
| 93 | 88 | ||
diff --git a/drivers/usb/host/ohci.h b/drivers/usb/host/ohci.h index 59f424567a8d..bc462288cfb0 100644 --- a/drivers/usb/host/ohci.h +++ b/drivers/usb/host/ohci.h | |||
| @@ -647,23 +647,22 @@ static inline u32 hc32_to_cpup (const struct ohci_hcd *ohci, const __hc32 *x) | |||
| 647 | 647 | ||
| 648 | /*-------------------------------------------------------------------------*/ | 648 | /*-------------------------------------------------------------------------*/ |
| 649 | 649 | ||
| 650 | /* HCCA frame number is 16 bits, but is accessed as 32 bits since not all | 650 | /* |
| 651 | * hardware handles 16 bit reads. That creates a different confusion on | 651 | * The HCCA frame number is 16 bits, but is accessed as 32 bits since not all |
| 652 | * some big-endian SOC implementations. Same thing happens with PSW access. | 652 | * hardware handles 16 bit reads. Depending on the SoC implementation, the |
| 653 | * frame number can wind up in either bits [31:16] (default) or | ||
| 654 | * [15:0] (OHCI_QUIRK_FRAME_NO) on big endian hosts. | ||
| 655 | * | ||
| 656 | * Somewhat similarly, the 16-bit PSW fields in a transfer descriptor are | ||
| 657 | * reordered on BE. | ||
| 653 | */ | 658 | */ |
| 654 | 659 | ||
| 655 | #ifdef CONFIG_PPC_MPC52xx | ||
| 656 | #define big_endian_frame_no_quirk(ohci) (ohci->flags & OHCI_QUIRK_FRAME_NO) | ||
| 657 | #else | ||
| 658 | #define big_endian_frame_no_quirk(ohci) 0 | ||
| 659 | #endif | ||
| 660 | |||
| 661 | static inline u16 ohci_frame_no(const struct ohci_hcd *ohci) | 660 | static inline u16 ohci_frame_no(const struct ohci_hcd *ohci) |
| 662 | { | 661 | { |
| 663 | u32 tmp; | 662 | u32 tmp; |
| 664 | if (big_endian_desc(ohci)) { | 663 | if (big_endian_desc(ohci)) { |
| 665 | tmp = be32_to_cpup((__force __be32 *)&ohci->hcca->frame_no); | 664 | tmp = be32_to_cpup((__force __be32 *)&ohci->hcca->frame_no); |
| 666 | if (!big_endian_frame_no_quirk(ohci)) | 665 | if (!(ohci->flags & OHCI_QUIRK_FRAME_NO)) |
| 667 | tmp >>= 16; | 666 | tmp >>= 16; |
| 668 | } else | 667 | } else |
| 669 | tmp = le32_to_cpup((__force __le32 *)&ohci->hcca->frame_no); | 668 | tmp = le32_to_cpup((__force __le32 *)&ohci->hcca->frame_no); |
diff --git a/drivers/usb/host/oxu210hp-hcd.c b/drivers/usb/host/oxu210hp-hcd.c index 4fe79a2d71a9..75811dd5a9d7 100644 --- a/drivers/usb/host/oxu210hp-hcd.c +++ b/drivers/usb/host/oxu210hp-hcd.c | |||
| @@ -3846,7 +3846,6 @@ static int oxu_drv_probe(struct platform_device *pdev) | |||
| 3846 | */ | 3846 | */ |
| 3847 | info = devm_kzalloc(&pdev->dev, sizeof(struct oxu_info), GFP_KERNEL); | 3847 | info = devm_kzalloc(&pdev->dev, sizeof(struct oxu_info), GFP_KERNEL); |
| 3848 | if (!info) { | 3848 | if (!info) { |
| 3849 | dev_dbg(&pdev->dev, "error allocating memory\n"); | ||
| 3850 | ret = -EFAULT; | 3849 | ret = -EFAULT; |
| 3851 | goto error; | 3850 | goto error; |
| 3852 | } | 3851 | } |
diff --git a/drivers/usb/host/pci-quirks.c b/drivers/usb/host/pci-quirks.c index 2f3acebb577a..dd483c13565b 100644 --- a/drivers/usb/host/pci-quirks.c +++ b/drivers/usb/host/pci-quirks.c | |||
| @@ -233,10 +233,8 @@ commit: | |||
| 233 | 233 | ||
| 234 | spin_unlock_irqrestore(&amd_lock, flags); | 234 | spin_unlock_irqrestore(&amd_lock, flags); |
| 235 | 235 | ||
| 236 | if (info.nb_dev) | 236 | pci_dev_put(info.nb_dev); |
| 237 | pci_dev_put(info.nb_dev); | 237 | pci_dev_put(info.smbus_dev); |
| 238 | if (info.smbus_dev) | ||
| 239 | pci_dev_put(info.smbus_dev); | ||
| 240 | 238 | ||
| 241 | } else { | 239 | } else { |
| 242 | /* no race - commit the result */ | 240 | /* no race - commit the result */ |
| @@ -447,10 +445,8 @@ void usb_amd_dev_put(void) | |||
| 447 | 445 | ||
| 448 | spin_unlock_irqrestore(&amd_lock, flags); | 446 | spin_unlock_irqrestore(&amd_lock, flags); |
| 449 | 447 | ||
| 450 | if (nb) | 448 | pci_dev_put(nb); |
| 451 | pci_dev_put(nb); | 449 | pci_dev_put(smbus); |
| 452 | if (smbus) | ||
| 453 | pci_dev_put(smbus); | ||
| 454 | } | 450 | } |
| 455 | EXPORT_SYMBOL_GPL(usb_amd_dev_put); | 451 | EXPORT_SYMBOL_GPL(usb_amd_dev_put); |
| 456 | 452 | ||
diff --git a/drivers/usb/host/uhci-platform.c b/drivers/usb/host/uhci-platform.c index b987f1d10058..cf8f46003f62 100644 --- a/drivers/usb/host/uhci-platform.c +++ b/drivers/usb/host/uhci-platform.c | |||
| @@ -86,14 +86,14 @@ static int uhci_hcd_platform_probe(struct platform_device *pdev) | |||
| 86 | return -ENOMEM; | 86 | return -ENOMEM; |
| 87 | 87 | ||
| 88 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 88 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 89 | hcd->rsrc_start = res->start; | ||
| 90 | hcd->rsrc_len = resource_size(res); | ||
| 91 | |||
| 92 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 89 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 93 | if (IS_ERR(hcd->regs)) { | 90 | if (IS_ERR(hcd->regs)) { |
| 94 | ret = PTR_ERR(hcd->regs); | 91 | ret = PTR_ERR(hcd->regs); |
| 95 | goto err_rmr; | 92 | goto err_rmr; |
| 96 | } | 93 | } |
| 94 | hcd->rsrc_start = res->start; | ||
| 95 | hcd->rsrc_len = resource_size(res); | ||
| 96 | |||
| 97 | uhci = hcd_to_uhci(hcd); | 97 | uhci = hcd_to_uhci(hcd); |
| 98 | 98 | ||
| 99 | uhci->regs = hcd->regs; | 99 | uhci->regs = hcd->regs; |
diff --git a/drivers/usb/host/xhci-plat.c b/drivers/usb/host/xhci-plat.c index 646300cbe5f7..08d402b15482 100644 --- a/drivers/usb/host/xhci-plat.c +++ b/drivers/usb/host/xhci-plat.c | |||
| @@ -83,9 +83,6 @@ static int xhci_plat_probe(struct platform_device *pdev) | |||
| 83 | if (irq < 0) | 83 | if (irq < 0) |
| 84 | return -ENODEV; | 84 | return -ENODEV; |
| 85 | 85 | ||
| 86 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 87 | if (!res) | ||
| 88 | return -ENODEV; | ||
| 89 | 86 | ||
| 90 | if (of_device_is_compatible(pdev->dev.of_node, | 87 | if (of_device_is_compatible(pdev->dev.of_node, |
| 91 | "marvell,armada-375-xhci") || | 88 | "marvell,armada-375-xhci") || |
| @@ -109,15 +106,16 @@ static int xhci_plat_probe(struct platform_device *pdev) | |||
| 109 | if (!hcd) | 106 | if (!hcd) |
| 110 | return -ENOMEM; | 107 | return -ENOMEM; |
| 111 | 108 | ||
| 112 | hcd->rsrc_start = res->start; | 109 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| 113 | hcd->rsrc_len = resource_size(res); | ||
| 114 | |||
| 115 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); | 110 | hcd->regs = devm_ioremap_resource(&pdev->dev, res); |
| 116 | if (IS_ERR(hcd->regs)) { | 111 | if (IS_ERR(hcd->regs)) { |
| 117 | ret = PTR_ERR(hcd->regs); | 112 | ret = PTR_ERR(hcd->regs); |
| 118 | goto put_hcd; | 113 | goto put_hcd; |
| 119 | } | 114 | } |
| 120 | 115 | ||
| 116 | hcd->rsrc_start = res->start; | ||
| 117 | hcd->rsrc_len = resource_size(res); | ||
| 118 | |||
| 121 | /* | 119 | /* |
| 122 | * Not all platforms have a clk so it is not an error if the | 120 | * Not all platforms have a clk so it is not an error if the |
| 123 | * clock does not exists. | 121 | * clock does not exists. |
diff --git a/drivers/usb/host/xhci-ring.c b/drivers/usb/host/xhci-ring.c index 06433aec81d7..e692e769c50c 100644 --- a/drivers/usb/host/xhci-ring.c +++ b/drivers/usb/host/xhci-ring.c | |||
| @@ -716,9 +716,7 @@ remove_finished_td: | |||
| 716 | ring_doorbell_for_active_rings(xhci, slot_id, ep_index); | 716 | ring_doorbell_for_active_rings(xhci, slot_id, ep_index); |
| 717 | } | 717 | } |
| 718 | 718 | ||
| 719 | /* Clear stopped_td if endpoint is not halted */ | 719 | ep->stopped_td = NULL; |
| 720 | if (!(ep->ep_state & EP_HALTED)) | ||
| 721 | ep->stopped_td = NULL; | ||
| 722 | 720 | ||
| 723 | /* | 721 | /* |
| 724 | * Drop the lock and complete the URBs in the cancelled TD list. | 722 | * Drop the lock and complete the URBs in the cancelled TD list. |
| @@ -1732,13 +1730,11 @@ static void xhci_cleanup_halted_endpoint(struct xhci_hcd *xhci, | |||
| 1732 | return; | 1730 | return; |
| 1733 | 1731 | ||
| 1734 | ep->ep_state |= EP_HALTED; | 1732 | ep->ep_state |= EP_HALTED; |
| 1735 | ep->stopped_td = td; | ||
| 1736 | ep->stopped_stream = stream_id; | 1733 | ep->stopped_stream = stream_id; |
| 1737 | 1734 | ||
| 1738 | xhci_queue_reset_ep(xhci, command, slot_id, ep_index); | 1735 | xhci_queue_reset_ep(xhci, command, slot_id, ep_index); |
| 1739 | xhci_cleanup_stalled_ring(xhci, td->urb->dev, ep_index); | 1736 | xhci_cleanup_stalled_ring(xhci, ep_index, td); |
| 1740 | 1737 | ||
| 1741 | ep->stopped_td = NULL; | ||
| 1742 | ep->stopped_stream = 0; | 1738 | ep->stopped_stream = 0; |
| 1743 | 1739 | ||
| 1744 | xhci_ring_cmd_db(xhci); | 1740 | xhci_ring_cmd_db(xhci); |
| @@ -1813,72 +1809,65 @@ static int finish_td(struct xhci_hcd *xhci, struct xhci_td *td, | |||
| 1813 | if (skip) | 1809 | if (skip) |
| 1814 | goto td_cleanup; | 1810 | goto td_cleanup; |
| 1815 | 1811 | ||
| 1816 | if (trb_comp_code == COMP_STOP_INVAL || | 1812 | if (trb_comp_code == COMP_STOP_INVAL || trb_comp_code == COMP_STOP) { |
| 1817 | trb_comp_code == COMP_STOP) { | ||
| 1818 | /* The Endpoint Stop Command completion will take care of any | 1813 | /* The Endpoint Stop Command completion will take care of any |
| 1819 | * stopped TDs. A stopped TD may be restarted, so don't update | 1814 | * stopped TDs. A stopped TD may be restarted, so don't update |
| 1820 | * the ring dequeue pointer or take this TD off any lists yet. | 1815 | * the ring dequeue pointer or take this TD off any lists yet. |
| 1821 | */ | 1816 | */ |
| 1822 | ep->stopped_td = td; | 1817 | ep->stopped_td = td; |
| 1823 | return 0; | 1818 | return 0; |
| 1819 | } | ||
| 1820 | if (trb_comp_code == COMP_STALL || | ||
| 1821 | xhci_requires_manual_halt_cleanup(xhci, ep_ctx, | ||
| 1822 | trb_comp_code)) { | ||
| 1823 | /* Issue a reset endpoint command to clear the host side | ||
| 1824 | * halt, followed by a set dequeue command to move the | ||
| 1825 | * dequeue pointer past the TD. | ||
| 1826 | * The class driver clears the device side halt later. | ||
| 1827 | */ | ||
| 1828 | xhci_cleanup_halted_endpoint(xhci, slot_id, ep_index, | ||
| 1829 | ep_ring->stream_id, td, event_trb); | ||
| 1824 | } else { | 1830 | } else { |
| 1825 | if (trb_comp_code == COMP_STALL || | 1831 | /* Update ring dequeue pointer */ |
| 1826 | xhci_requires_manual_halt_cleanup(xhci, ep_ctx, | 1832 | while (ep_ring->dequeue != td->last_trb) |
| 1827 | trb_comp_code)) { | ||
| 1828 | /* Issue a reset endpoint command to clear the host side | ||
| 1829 | * halt, followed by a set dequeue command to move the | ||
| 1830 | * dequeue pointer past the TD. | ||
| 1831 | * The class driver clears the device side halt later. | ||
| 1832 | */ | ||
| 1833 | xhci_cleanup_halted_endpoint(xhci, | ||
| 1834 | slot_id, ep_index, ep_ring->stream_id, | ||
| 1835 | td, event_trb); | ||
| 1836 | } else { | ||
| 1837 | /* Update ring dequeue pointer */ | ||
| 1838 | while (ep_ring->dequeue != td->last_trb) | ||
| 1839 | inc_deq(xhci, ep_ring); | ||
| 1840 | inc_deq(xhci, ep_ring); | 1833 | inc_deq(xhci, ep_ring); |
| 1841 | } | 1834 | inc_deq(xhci, ep_ring); |
| 1835 | } | ||
| 1842 | 1836 | ||
| 1843 | td_cleanup: | 1837 | td_cleanup: |
| 1844 | /* Clean up the endpoint's TD list */ | 1838 | /* Clean up the endpoint's TD list */ |
| 1845 | urb = td->urb; | 1839 | urb = td->urb; |
| 1846 | urb_priv = urb->hcpriv; | 1840 | urb_priv = urb->hcpriv; |
| 1847 | 1841 | ||
| 1848 | /* Do one last check of the actual transfer length. | 1842 | /* Do one last check of the actual transfer length. |
| 1849 | * If the host controller said we transferred more data than | 1843 | * If the host controller said we transferred more data than the buffer |
| 1850 | * the buffer length, urb->actual_length will be a very big | 1844 | * length, urb->actual_length will be a very big number (since it's |
| 1851 | * number (since it's unsigned). Play it safe and say we didn't | 1845 | * unsigned). Play it safe and say we didn't transfer anything. |
| 1852 | * transfer anything. | 1846 | */ |
| 1853 | */ | 1847 | if (urb->actual_length > urb->transfer_buffer_length) { |
| 1854 | if (urb->actual_length > urb->transfer_buffer_length) { | 1848 | xhci_warn(xhci, "URB transfer length is wrong, xHC issue? req. len = %u, act. len = %u\n", |
| 1855 | xhci_warn(xhci, "URB transfer length is wrong, " | 1849 | urb->transfer_buffer_length, |
| 1856 | "xHC issue? req. len = %u, " | 1850 | urb->actual_length); |
| 1857 | "act. len = %u\n", | 1851 | urb->actual_length = 0; |
| 1858 | urb->transfer_buffer_length, | 1852 | if (td->urb->transfer_flags & URB_SHORT_NOT_OK) |
| 1859 | urb->actual_length); | 1853 | *status = -EREMOTEIO; |
| 1860 | urb->actual_length = 0; | 1854 | else |
| 1861 | if (td->urb->transfer_flags & URB_SHORT_NOT_OK) | 1855 | *status = 0; |
| 1862 | *status = -EREMOTEIO; | 1856 | } |
| 1863 | else | 1857 | list_del_init(&td->td_list); |
| 1864 | *status = 0; | 1858 | /* Was this TD slated to be cancelled but completed anyway? */ |
| 1865 | } | 1859 | if (!list_empty(&td->cancelled_td_list)) |
| 1866 | list_del_init(&td->td_list); | 1860 | list_del_init(&td->cancelled_td_list); |
| 1867 | /* Was this TD slated to be cancelled but completed anyway? */ | 1861 | |
| 1868 | if (!list_empty(&td->cancelled_td_list)) | 1862 | urb_priv->td_cnt++; |
| 1869 | list_del_init(&td->cancelled_td_list); | 1863 | /* Giveback the urb when all the tds are completed */ |
| 1870 | 1864 | if (urb_priv->td_cnt == urb_priv->length) { | |
| 1871 | urb_priv->td_cnt++; | 1865 | ret = 1; |
| 1872 | /* Giveback the urb when all the tds are completed */ | 1866 | if (usb_pipetype(urb->pipe) == PIPE_ISOCHRONOUS) { |
| 1873 | if (urb_priv->td_cnt == urb_priv->length) { | 1867 | xhci_to_hcd(xhci)->self.bandwidth_isoc_reqs--; |
| 1874 | ret = 1; | 1868 | if (xhci_to_hcd(xhci)->self.bandwidth_isoc_reqs == 0) { |
| 1875 | if (usb_pipetype(urb->pipe) == PIPE_ISOCHRONOUS) { | 1869 | if (xhci->quirks & XHCI_AMD_PLL_FIX) |
| 1876 | xhci_to_hcd(xhci)->self.bandwidth_isoc_reqs--; | 1870 | usb_amd_quirk_pll_enable(); |
| 1877 | if (xhci_to_hcd(xhci)->self.bandwidth_isoc_reqs | ||
| 1878 | == 0) { | ||
| 1879 | if (xhci->quirks & XHCI_AMD_PLL_FIX) | ||
| 1880 | usb_amd_quirk_pll_enable(); | ||
| 1881 | } | ||
| 1882 | } | 1871 | } |
| 1883 | } | 1872 | } |
| 1884 | } | 1873 | } |
diff --git a/drivers/usb/host/xhci.c b/drivers/usb/host/xhci.c index cf3413116aff..01fcbb5eb06e 100644 --- a/drivers/usb/host/xhci.c +++ b/drivers/usb/host/xhci.c | |||
| @@ -2912,10 +2912,11 @@ static void xhci_setup_input_ctx_for_quirk(struct xhci_hcd *xhci, | |||
| 2912 | } | 2912 | } |
| 2913 | 2913 | ||
| 2914 | void xhci_cleanup_stalled_ring(struct xhci_hcd *xhci, | 2914 | void xhci_cleanup_stalled_ring(struct xhci_hcd *xhci, |
| 2915 | struct usb_device *udev, unsigned int ep_index) | 2915 | unsigned int ep_index, struct xhci_td *td) |
| 2916 | { | 2916 | { |
| 2917 | struct xhci_dequeue_state deq_state; | 2917 | struct xhci_dequeue_state deq_state; |
| 2918 | struct xhci_virt_ep *ep; | 2918 | struct xhci_virt_ep *ep; |
| 2919 | struct usb_device *udev = td->urb->dev; | ||
| 2919 | 2920 | ||
| 2920 | xhci_dbg_trace(xhci, trace_xhci_dbg_reset_ep, | 2921 | xhci_dbg_trace(xhci, trace_xhci_dbg_reset_ep, |
| 2921 | "Cleaning up stalled endpoint ring"); | 2922 | "Cleaning up stalled endpoint ring"); |
| @@ -2924,8 +2925,7 @@ void xhci_cleanup_stalled_ring(struct xhci_hcd *xhci, | |||
| 2924 | * or it will attempt to resend it on the next doorbell ring. | 2925 | * or it will attempt to resend it on the next doorbell ring. |
| 2925 | */ | 2926 | */ |
| 2926 | xhci_find_new_dequeue_state(xhci, udev->slot_id, | 2927 | xhci_find_new_dequeue_state(xhci, udev->slot_id, |
| 2927 | ep_index, ep->stopped_stream, ep->stopped_td, | 2928 | ep_index, ep->stopped_stream, td, &deq_state); |
| 2928 | &deq_state); | ||
| 2929 | 2929 | ||
| 2930 | if (!deq_state.new_deq_ptr || !deq_state.new_deq_seg) | 2930 | if (!deq_state.new_deq_ptr || !deq_state.new_deq_seg) |
| 2931 | return; | 2931 | return; |
| @@ -4009,6 +4009,7 @@ static int __maybe_unused xhci_change_max_exit_latency(struct xhci_hcd *xhci, | |||
| 4009 | slot_ctx = xhci_get_slot_ctx(xhci, command->in_ctx); | 4009 | slot_ctx = xhci_get_slot_ctx(xhci, command->in_ctx); |
| 4010 | slot_ctx->dev_info2 &= cpu_to_le32(~((u32) MAX_EXIT)); | 4010 | slot_ctx->dev_info2 &= cpu_to_le32(~((u32) MAX_EXIT)); |
| 4011 | slot_ctx->dev_info2 |= cpu_to_le32(max_exit_latency); | 4011 | slot_ctx->dev_info2 |= cpu_to_le32(max_exit_latency); |
| 4012 | slot_ctx->dev_state = 0; | ||
| 4012 | 4013 | ||
| 4013 | xhci_dbg_trace(xhci, trace_xhci_dbg_context_change, | 4014 | xhci_dbg_trace(xhci, trace_xhci_dbg_context_change, |
| 4014 | "Set up evaluate context for LPM MEL change."); | 4015 | "Set up evaluate context for LPM MEL change."); |
diff --git a/drivers/usb/host/xhci.h b/drivers/usb/host/xhci.h index d745715a1e2f..cc7c5bb7cbcf 100644 --- a/drivers/usb/host/xhci.h +++ b/drivers/usb/host/xhci.h | |||
| @@ -358,7 +358,7 @@ struct xhci_op_regs { | |||
| 358 | /* wake on over-current (enable) */ | 358 | /* wake on over-current (enable) */ |
| 359 | #define PORT_WKOC_E (1 << 27) | 359 | #define PORT_WKOC_E (1 << 27) |
| 360 | /* bits 28:29 reserved */ | 360 | /* bits 28:29 reserved */ |
| 361 | /* true: device is removable - for USB 3.0 roothub emulation */ | 361 | /* true: device is non-removable - for USB 3.0 roothub emulation */ |
| 362 | #define PORT_DEV_REMOVE (1 << 30) | 362 | #define PORT_DEV_REMOVE (1 << 30) |
| 363 | /* Initiate a warm port reset - complete when PORT_WRC is '1' */ | 363 | /* Initiate a warm port reset - complete when PORT_WRC is '1' */ |
| 364 | #define PORT_WR (1 << 31) | 364 | #define PORT_WR (1 << 31) |
| @@ -1825,7 +1825,7 @@ void xhci_queue_new_dequeue_state(struct xhci_hcd *xhci, | |||
| 1825 | unsigned int stream_id, | 1825 | unsigned int stream_id, |
| 1826 | struct xhci_dequeue_state *deq_state); | 1826 | struct xhci_dequeue_state *deq_state); |
| 1827 | void xhci_cleanup_stalled_ring(struct xhci_hcd *xhci, | 1827 | void xhci_cleanup_stalled_ring(struct xhci_hcd *xhci, |
| 1828 | struct usb_device *udev, unsigned int ep_index); | 1828 | unsigned int ep_index, struct xhci_td *td); |
| 1829 | void xhci_queue_config_ep_quirk(struct xhci_hcd *xhci, | 1829 | void xhci_queue_config_ep_quirk(struct xhci_hcd *xhci, |
| 1830 | unsigned int slot_id, unsigned int ep_index, | 1830 | unsigned int slot_id, unsigned int ep_index, |
| 1831 | struct xhci_dequeue_state *deq_state); | 1831 | struct xhci_dequeue_state *deq_state); |
diff --git a/drivers/usb/misc/adutux.c b/drivers/usb/misc/adutux.c index 493c7f268b6f..3071c0ef909b 100644 --- a/drivers/usb/misc/adutux.c +++ b/drivers/usb/misc/adutux.c | |||
| @@ -814,15 +814,10 @@ static void adu_disconnect(struct usb_interface *interface) | |||
| 814 | usb_set_intfdata(interface, NULL); | 814 | usb_set_intfdata(interface, NULL); |
| 815 | 815 | ||
| 816 | /* if the device is not opened, then we clean up right now */ | 816 | /* if the device is not opened, then we clean up right now */ |
| 817 | dev_dbg(&dev->udev->dev, "%s : open count %d\n", | ||
| 818 | __func__, dev->open_count); | ||
| 819 | if (!dev->open_count) | 817 | if (!dev->open_count) |
| 820 | adu_delete(dev); | 818 | adu_delete(dev); |
| 821 | 819 | ||
| 822 | mutex_unlock(&adutux_mutex); | 820 | mutex_unlock(&adutux_mutex); |
| 823 | |||
| 824 | dev_info(&interface->dev, "ADU device adutux%d now disconnected\n", | ||
| 825 | (minor - ADU_MINOR_BASE)); | ||
| 826 | } | 821 | } |
| 827 | 822 | ||
| 828 | /* usb specific object needed to register this driver with the usb subsystem */ | 823 | /* usb specific object needed to register this driver with the usb subsystem */ |
diff --git a/drivers/usb/misc/sisusbvga/sisusb.c b/drivers/usb/misc/sisusbvga/sisusb.c index 633caf643122..022dc0008f2a 100644 --- a/drivers/usb/misc/sisusbvga/sisusb.c +++ b/drivers/usb/misc/sisusbvga/sisusb.c | |||
| @@ -2472,8 +2472,7 @@ sisusb_delete(struct kref *kref) | |||
| 2472 | if (!sisusb) | 2472 | if (!sisusb) |
| 2473 | return; | 2473 | return; |
| 2474 | 2474 | ||
| 2475 | if (sisusb->sisusb_dev) | 2475 | usb_put_dev(sisusb->sisusb_dev); |
| 2476 | usb_put_dev(sisusb->sisusb_dev); | ||
| 2477 | 2476 | ||
| 2478 | sisusb->sisusb_dev = NULL; | 2477 | sisusb->sisusb_dev = NULL; |
| 2479 | sisusb_free_buffers(sisusb); | 2478 | sisusb_free_buffers(sisusb); |
diff --git a/drivers/usb/misc/usb3503.c b/drivers/usb/misc/usb3503.c index ae7e1206ca54..b9af8cb19215 100644 --- a/drivers/usb/misc/usb3503.c +++ b/drivers/usb/misc/usb3503.c | |||
| @@ -314,10 +314,8 @@ static int usb3503_i2c_probe(struct i2c_client *i2c, | |||
| 314 | int err; | 314 | int err; |
| 315 | 315 | ||
| 316 | hub = devm_kzalloc(&i2c->dev, sizeof(struct usb3503), GFP_KERNEL); | 316 | hub = devm_kzalloc(&i2c->dev, sizeof(struct usb3503), GFP_KERNEL); |
| 317 | if (!hub) { | 317 | if (!hub) |
| 318 | dev_err(&i2c->dev, "private data alloc fail\n"); | ||
| 319 | return -ENOMEM; | 318 | return -ENOMEM; |
| 320 | } | ||
| 321 | 319 | ||
| 322 | i2c_set_clientdata(i2c, hub); | 320 | i2c_set_clientdata(i2c, hub); |
| 323 | hub->regmap = devm_regmap_init_i2c(i2c, &usb3503_regmap_config); | 321 | hub->regmap = devm_regmap_init_i2c(i2c, &usb3503_regmap_config); |
| @@ -336,10 +334,8 @@ static int usb3503_platform_probe(struct platform_device *pdev) | |||
| 336 | struct usb3503 *hub; | 334 | struct usb3503 *hub; |
| 337 | 335 | ||
| 338 | hub = devm_kzalloc(&pdev->dev, sizeof(struct usb3503), GFP_KERNEL); | 336 | hub = devm_kzalloc(&pdev->dev, sizeof(struct usb3503), GFP_KERNEL); |
| 339 | if (!hub) { | 337 | if (!hub) |
| 340 | dev_err(&pdev->dev, "private data alloc fail\n"); | ||
| 341 | return -ENOMEM; | 338 | return -ENOMEM; |
| 342 | } | ||
| 343 | hub->dev = &pdev->dev; | 339 | hub->dev = &pdev->dev; |
| 344 | 340 | ||
| 345 | return usb3503_probe(hub); | 341 | return usb3503_probe(hub); |
diff --git a/drivers/usb/misc/yurex.c b/drivers/usb/misc/yurex.c index c3a45da11610..343fa6ff9f4b 100644 --- a/drivers/usb/misc/yurex.c +++ b/drivers/usb/misc/yurex.c | |||
| @@ -410,7 +410,8 @@ static int yurex_release(struct inode *inode, struct file *file) | |||
| 410 | return 0; | 410 | return 0; |
| 411 | } | 411 | } |
| 412 | 412 | ||
| 413 | static ssize_t yurex_read(struct file *file, char *buffer, size_t count, loff_t *ppos) | 413 | static ssize_t yurex_read(struct file *file, char __user *buffer, size_t count, |
| 414 | loff_t *ppos) | ||
| 414 | { | 415 | { |
| 415 | struct usb_yurex *dev; | 416 | struct usb_yurex *dev; |
| 416 | int retval = 0; | 417 | int retval = 0; |
| @@ -444,7 +445,8 @@ exit: | |||
| 444 | return retval; | 445 | return retval; |
| 445 | } | 446 | } |
| 446 | 447 | ||
| 447 | static ssize_t yurex_write(struct file *file, const char *user_buffer, size_t count, loff_t *ppos) | 448 | static ssize_t yurex_write(struct file *file, const char __user *user_buffer, |
| 449 | size_t count, loff_t *ppos) | ||
| 448 | { | 450 | { |
| 449 | struct usb_yurex *dev; | 451 | struct usb_yurex *dev; |
| 450 | int i, set = 0, retval = 0; | 452 | int i, set = 0, retval = 0; |
diff --git a/drivers/usb/musb/Kconfig b/drivers/usb/musb/Kconfig index 06cc5d6ea681..9d68372dd9aa 100644 --- a/drivers/usb/musb/Kconfig +++ b/drivers/usb/musb/Kconfig | |||
| @@ -58,8 +58,7 @@ config USB_MUSB_DUAL_ROLE | |||
| 58 | 58 | ||
| 59 | endchoice | 59 | endchoice |
| 60 | 60 | ||
| 61 | choice | 61 | comment "Platform Glue Layer" |
| 62 | prompt "Platform Glue Layer" | ||
| 63 | 62 | ||
| 64 | config USB_MUSB_DAVINCI | 63 | config USB_MUSB_DAVINCI |
| 65 | tristate "DaVinci" | 64 | tristate "DaVinci" |
| @@ -101,8 +100,6 @@ config USB_MUSB_JZ4740 | |||
| 101 | depends on USB_MUSB_GADGET | 100 | depends on USB_MUSB_GADGET |
| 102 | depends on USB_OTG_BLACKLIST_HUB | 101 | depends on USB_OTG_BLACKLIST_HUB |
| 103 | 102 | ||
| 104 | endchoice | ||
| 105 | |||
| 106 | config USB_MUSB_AM335X_CHILD | 103 | config USB_MUSB_AM335X_CHILD |
| 107 | tristate | 104 | tristate |
| 108 | 105 | ||
diff --git a/drivers/usb/musb/am35x.c b/drivers/usb/musb/am35x.c index a2735df24cc6..220fd4d3b41c 100644 --- a/drivers/usb/musb/am35x.c +++ b/drivers/usb/musb/am35x.c | |||
| @@ -149,25 +149,25 @@ static void otg_timer(unsigned long _musb) | |||
| 149 | */ | 149 | */ |
| 150 | devctl = musb_readb(mregs, MUSB_DEVCTL); | 150 | devctl = musb_readb(mregs, MUSB_DEVCTL); |
| 151 | dev_dbg(musb->controller, "Poll devctl %02x (%s)\n", devctl, | 151 | dev_dbg(musb->controller, "Poll devctl %02x (%s)\n", devctl, |
| 152 | usb_otg_state_string(musb->xceiv->state)); | 152 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 153 | 153 | ||
| 154 | spin_lock_irqsave(&musb->lock, flags); | 154 | spin_lock_irqsave(&musb->lock, flags); |
| 155 | switch (musb->xceiv->state) { | 155 | switch (musb->xceiv->otg->state) { |
| 156 | case OTG_STATE_A_WAIT_BCON: | 156 | case OTG_STATE_A_WAIT_BCON: |
| 157 | devctl &= ~MUSB_DEVCTL_SESSION; | 157 | devctl &= ~MUSB_DEVCTL_SESSION; |
| 158 | musb_writeb(musb->mregs, MUSB_DEVCTL, devctl); | 158 | musb_writeb(musb->mregs, MUSB_DEVCTL, devctl); |
| 159 | 159 | ||
| 160 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); | 160 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); |
| 161 | if (devctl & MUSB_DEVCTL_BDEVICE) { | 161 | if (devctl & MUSB_DEVCTL_BDEVICE) { |
| 162 | musb->xceiv->state = OTG_STATE_B_IDLE; | 162 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 163 | MUSB_DEV_MODE(musb); | 163 | MUSB_DEV_MODE(musb); |
| 164 | } else { | 164 | } else { |
| 165 | musb->xceiv->state = OTG_STATE_A_IDLE; | 165 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 166 | MUSB_HST_MODE(musb); | 166 | MUSB_HST_MODE(musb); |
| 167 | } | 167 | } |
| 168 | break; | 168 | break; |
| 169 | case OTG_STATE_A_WAIT_VFALL: | 169 | case OTG_STATE_A_WAIT_VFALL: |
| 170 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 170 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 171 | musb_writel(musb->ctrl_base, CORE_INTR_SRC_SET_REG, | 171 | musb_writel(musb->ctrl_base, CORE_INTR_SRC_SET_REG, |
| 172 | MUSB_INTR_VBUSERROR << AM35X_INTR_USB_SHIFT); | 172 | MUSB_INTR_VBUSERROR << AM35X_INTR_USB_SHIFT); |
| 173 | break; | 173 | break; |
| @@ -176,7 +176,7 @@ static void otg_timer(unsigned long _musb) | |||
| 176 | if (devctl & MUSB_DEVCTL_BDEVICE) | 176 | if (devctl & MUSB_DEVCTL_BDEVICE) |
| 177 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 177 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 178 | else | 178 | else |
| 179 | musb->xceiv->state = OTG_STATE_A_IDLE; | 179 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 180 | break; | 180 | break; |
| 181 | default: | 181 | default: |
| 182 | break; | 182 | break; |
| @@ -193,9 +193,9 @@ static void am35x_musb_try_idle(struct musb *musb, unsigned long timeout) | |||
| 193 | 193 | ||
| 194 | /* Never idle if active, or when VBUS timeout is not set as host */ | 194 | /* Never idle if active, or when VBUS timeout is not set as host */ |
| 195 | if (musb->is_active || (musb->a_wait_bcon == 0 && | 195 | if (musb->is_active || (musb->a_wait_bcon == 0 && |
| 196 | musb->xceiv->state == OTG_STATE_A_WAIT_BCON)) { | 196 | musb->xceiv->otg->state == OTG_STATE_A_WAIT_BCON)) { |
| 197 | dev_dbg(musb->controller, "%s active, deleting timer\n", | 197 | dev_dbg(musb->controller, "%s active, deleting timer\n", |
| 198 | usb_otg_state_string(musb->xceiv->state)); | 198 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 199 | del_timer(&otg_workaround); | 199 | del_timer(&otg_workaround); |
| 200 | last_timer = jiffies; | 200 | last_timer = jiffies; |
| 201 | return; | 201 | return; |
| @@ -208,7 +208,7 @@ static void am35x_musb_try_idle(struct musb *musb, unsigned long timeout) | |||
| 208 | last_timer = timeout; | 208 | last_timer = timeout; |
| 209 | 209 | ||
| 210 | dev_dbg(musb->controller, "%s inactive, starting idle timer for %u ms\n", | 210 | dev_dbg(musb->controller, "%s inactive, starting idle timer for %u ms\n", |
| 211 | usb_otg_state_string(musb->xceiv->state), | 211 | usb_otg_state_string(musb->xceiv->otg->state), |
| 212 | jiffies_to_msecs(timeout - jiffies)); | 212 | jiffies_to_msecs(timeout - jiffies)); |
| 213 | mod_timer(&otg_workaround, timeout); | 213 | mod_timer(&otg_workaround, timeout); |
| 214 | } | 214 | } |
| @@ -278,27 +278,27 @@ static irqreturn_t am35x_musb_interrupt(int irq, void *hci) | |||
| 278 | * devctl. | 278 | * devctl. |
| 279 | */ | 279 | */ |
| 280 | musb->int_usb &= ~MUSB_INTR_VBUSERROR; | 280 | musb->int_usb &= ~MUSB_INTR_VBUSERROR; |
| 281 | musb->xceiv->state = OTG_STATE_A_WAIT_VFALL; | 281 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VFALL; |
| 282 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 282 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 283 | WARNING("VBUS error workaround (delay coming)\n"); | 283 | WARNING("VBUS error workaround (delay coming)\n"); |
| 284 | } else if (drvvbus) { | 284 | } else if (drvvbus) { |
| 285 | MUSB_HST_MODE(musb); | 285 | MUSB_HST_MODE(musb); |
| 286 | otg->default_a = 1; | 286 | otg->default_a = 1; |
| 287 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 287 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 288 | portstate(musb->port1_status |= USB_PORT_STAT_POWER); | 288 | portstate(musb->port1_status |= USB_PORT_STAT_POWER); |
| 289 | del_timer(&otg_workaround); | 289 | del_timer(&otg_workaround); |
| 290 | } else { | 290 | } else { |
| 291 | musb->is_active = 0; | 291 | musb->is_active = 0; |
| 292 | MUSB_DEV_MODE(musb); | 292 | MUSB_DEV_MODE(musb); |
| 293 | otg->default_a = 0; | 293 | otg->default_a = 0; |
| 294 | musb->xceiv->state = OTG_STATE_B_IDLE; | 294 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 295 | portstate(musb->port1_status &= ~USB_PORT_STAT_POWER); | 295 | portstate(musb->port1_status &= ~USB_PORT_STAT_POWER); |
| 296 | } | 296 | } |
| 297 | 297 | ||
| 298 | /* NOTE: this must complete power-on within 100 ms. */ | 298 | /* NOTE: this must complete power-on within 100 ms. */ |
| 299 | dev_dbg(musb->controller, "VBUS %s (%s)%s, devctl %02x\n", | 299 | dev_dbg(musb->controller, "VBUS %s (%s)%s, devctl %02x\n", |
| 300 | drvvbus ? "on" : "off", | 300 | drvvbus ? "on" : "off", |
| 301 | usb_otg_state_string(musb->xceiv->state), | 301 | usb_otg_state_string(musb->xceiv->otg->state), |
| 302 | err ? " ERROR" : "", | 302 | err ? " ERROR" : "", |
| 303 | devctl); | 303 | devctl); |
| 304 | ret = IRQ_HANDLED; | 304 | ret = IRQ_HANDLED; |
| @@ -324,7 +324,7 @@ eoi: | |||
| 324 | } | 324 | } |
| 325 | 325 | ||
| 326 | /* Poll for ID change */ | 326 | /* Poll for ID change */ |
| 327 | if (musb->xceiv->state == OTG_STATE_B_IDLE) | 327 | if (musb->xceiv->otg->state == OTG_STATE_B_IDLE) |
| 328 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 328 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 329 | 329 | ||
| 330 | spin_unlock_irqrestore(&musb->lock, flags); | 330 | spin_unlock_irqrestore(&musb->lock, flags); |
| @@ -408,7 +408,7 @@ static int am35x_musb_exit(struct musb *musb) | |||
| 408 | } | 408 | } |
| 409 | 409 | ||
| 410 | /* AM35x supports only 32bit read operation */ | 410 | /* AM35x supports only 32bit read operation */ |
| 411 | void musb_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *dst) | 411 | static void am35x_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *dst) |
| 412 | { | 412 | { |
| 413 | void __iomem *fifo = hw_ep->fifo; | 413 | void __iomem *fifo = hw_ep->fifo; |
| 414 | u32 val; | 414 | u32 val; |
| @@ -438,9 +438,11 @@ void musb_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *dst) | |||
| 438 | } | 438 | } |
| 439 | 439 | ||
| 440 | static const struct musb_platform_ops am35x_ops = { | 440 | static const struct musb_platform_ops am35x_ops = { |
| 441 | .quirks = MUSB_INDEXED_EP, | ||
| 441 | .init = am35x_musb_init, | 442 | .init = am35x_musb_init, |
| 442 | .exit = am35x_musb_exit, | 443 | .exit = am35x_musb_exit, |
| 443 | 444 | ||
| 445 | .read_fifo = am35x_read_fifo, | ||
| 444 | .enable = am35x_musb_enable, | 446 | .enable = am35x_musb_enable, |
| 445 | .disable = am35x_musb_disable, | 447 | .disable = am35x_musb_disable, |
| 446 | 448 | ||
diff --git a/drivers/usb/musb/blackfin.c b/drivers/usb/musb/blackfin.c index ac4422b33dcd..a441a2de8619 100644 --- a/drivers/usb/musb/blackfin.c +++ b/drivers/usb/musb/blackfin.c | |||
| @@ -33,10 +33,45 @@ struct bfin_glue { | |||
| 33 | }; | 33 | }; |
| 34 | #define glue_to_musb(g) platform_get_drvdata(g->musb) | 34 | #define glue_to_musb(g) platform_get_drvdata(g->musb) |
| 35 | 35 | ||
| 36 | static u32 bfin_fifo_offset(u8 epnum) | ||
| 37 | { | ||
| 38 | return USB_OFFSET(USB_EP0_FIFO) + (epnum * 8); | ||
| 39 | } | ||
| 40 | |||
| 41 | static u8 bfin_readb(const void __iomem *addr, unsigned offset) | ||
| 42 | { | ||
| 43 | return (u8)(bfin_read16(addr + offset)); | ||
| 44 | } | ||
| 45 | |||
| 46 | static u16 bfin_readw(const void __iomem *addr, unsigned offset) | ||
| 47 | { | ||
| 48 | return bfin_read16(addr + offset); | ||
| 49 | } | ||
| 50 | |||
| 51 | static u32 bfin_readl(const void __iomem *addr, unsigned offset) | ||
| 52 | { | ||
| 53 | return (u32)(bfin_read16(addr + offset)); | ||
| 54 | } | ||
| 55 | |||
| 56 | static void bfin_writeb(void __iomem *addr, unsigned offset, u8 data) | ||
| 57 | { | ||
| 58 | bfin_write16(addr + offset, (u16)data); | ||
| 59 | } | ||
| 60 | |||
| 61 | static void bfin_writew(void __iomem *addr, unsigned offset, u16 data) | ||
| 62 | { | ||
| 63 | bfin_write16(addr + offset, data); | ||
| 64 | } | ||
| 65 | |||
| 66 | static void binf_writel(void __iomem *addr, unsigned offset, u32 data) | ||
| 67 | { | ||
| 68 | bfin_write16(addr + offset, (u16)data); | ||
| 69 | } | ||
| 70 | |||
| 36 | /* | 71 | /* |
| 37 | * Load an endpoint's FIFO | 72 | * Load an endpoint's FIFO |
| 38 | */ | 73 | */ |
| 39 | void musb_write_fifo(struct musb_hw_ep *hw_ep, u16 len, const u8 *src) | 74 | static void bfin_write_fifo(struct musb_hw_ep *hw_ep, u16 len, const u8 *src) |
| 40 | { | 75 | { |
| 41 | struct musb *musb = hw_ep->musb; | 76 | struct musb *musb = hw_ep->musb; |
| 42 | void __iomem *fifo = hw_ep->fifo; | 77 | void __iomem *fifo = hw_ep->fifo; |
| @@ -100,7 +135,7 @@ void musb_write_fifo(struct musb_hw_ep *hw_ep, u16 len, const u8 *src) | |||
| 100 | /* | 135 | /* |
| 101 | * Unload an endpoint's FIFO | 136 | * Unload an endpoint's FIFO |
| 102 | */ | 137 | */ |
| 103 | void musb_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *dst) | 138 | static void bfin_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *dst) |
| 104 | { | 139 | { |
| 105 | struct musb *musb = hw_ep->musb; | 140 | struct musb *musb = hw_ep->musb; |
| 106 | void __iomem *fifo = hw_ep->fifo; | 141 | void __iomem *fifo = hw_ep->fifo; |
| @@ -185,8 +220,8 @@ static irqreturn_t blackfin_interrupt(int irq, void *__hci) | |||
| 185 | } | 220 | } |
| 186 | 221 | ||
| 187 | /* Start sampling ID pin, when plug is removed from MUSB */ | 222 | /* Start sampling ID pin, when plug is removed from MUSB */ |
| 188 | if ((musb->xceiv->state == OTG_STATE_B_IDLE | 223 | if ((musb->xceiv->otg->state == OTG_STATE_B_IDLE |
| 189 | || musb->xceiv->state == OTG_STATE_A_WAIT_BCON) || | 224 | || musb->xceiv->otg->state == OTG_STATE_A_WAIT_BCON) || |
| 190 | (musb->int_usb & MUSB_INTR_DISCONNECT && is_host_active(musb))) { | 225 | (musb->int_usb & MUSB_INTR_DISCONNECT && is_host_active(musb))) { |
| 191 | mod_timer(&musb_conn_timer, jiffies + TIMER_DELAY); | 226 | mod_timer(&musb_conn_timer, jiffies + TIMER_DELAY); |
| 192 | musb->a_wait_bcon = TIMER_DELAY; | 227 | musb->a_wait_bcon = TIMER_DELAY; |
| @@ -205,7 +240,7 @@ static void musb_conn_timer_handler(unsigned long _musb) | |||
| 205 | static u8 toggle; | 240 | static u8 toggle; |
| 206 | 241 | ||
| 207 | spin_lock_irqsave(&musb->lock, flags); | 242 | spin_lock_irqsave(&musb->lock, flags); |
| 208 | switch (musb->xceiv->state) { | 243 | switch (musb->xceiv->otg->state) { |
| 209 | case OTG_STATE_A_IDLE: | 244 | case OTG_STATE_A_IDLE: |
| 210 | case OTG_STATE_A_WAIT_BCON: | 245 | case OTG_STATE_A_WAIT_BCON: |
| 211 | /* Start a new session */ | 246 | /* Start a new session */ |
| @@ -219,7 +254,7 @@ static void musb_conn_timer_handler(unsigned long _musb) | |||
| 219 | 254 | ||
| 220 | if (!(val & MUSB_DEVCTL_BDEVICE)) { | 255 | if (!(val & MUSB_DEVCTL_BDEVICE)) { |
| 221 | gpio_set_value(musb->config->gpio_vrsel, 1); | 256 | gpio_set_value(musb->config->gpio_vrsel, 1); |
| 222 | musb->xceiv->state = OTG_STATE_A_WAIT_BCON; | 257 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_BCON; |
| 223 | } else { | 258 | } else { |
| 224 | gpio_set_value(musb->config->gpio_vrsel, 0); | 259 | gpio_set_value(musb->config->gpio_vrsel, 0); |
| 225 | /* Ignore VBUSERROR and SUSPEND IRQ */ | 260 | /* Ignore VBUSERROR and SUSPEND IRQ */ |
| @@ -229,7 +264,7 @@ static void musb_conn_timer_handler(unsigned long _musb) | |||
| 229 | 264 | ||
| 230 | val = MUSB_INTR_SUSPEND | MUSB_INTR_VBUSERROR; | 265 | val = MUSB_INTR_SUSPEND | MUSB_INTR_VBUSERROR; |
| 231 | musb_writeb(musb->mregs, MUSB_INTRUSB, val); | 266 | musb_writeb(musb->mregs, MUSB_INTRUSB, val); |
| 232 | musb->xceiv->state = OTG_STATE_B_IDLE; | 267 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 233 | } | 268 | } |
| 234 | mod_timer(&musb_conn_timer, jiffies + TIMER_DELAY); | 269 | mod_timer(&musb_conn_timer, jiffies + TIMER_DELAY); |
| 235 | break; | 270 | break; |
| @@ -245,7 +280,7 @@ static void musb_conn_timer_handler(unsigned long _musb) | |||
| 245 | 280 | ||
| 246 | if (!(val & MUSB_DEVCTL_BDEVICE)) { | 281 | if (!(val & MUSB_DEVCTL_BDEVICE)) { |
| 247 | gpio_set_value(musb->config->gpio_vrsel, 1); | 282 | gpio_set_value(musb->config->gpio_vrsel, 1); |
| 248 | musb->xceiv->state = OTG_STATE_A_WAIT_BCON; | 283 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_BCON; |
| 249 | } else { | 284 | } else { |
| 250 | gpio_set_value(musb->config->gpio_vrsel, 0); | 285 | gpio_set_value(musb->config->gpio_vrsel, 0); |
| 251 | 286 | ||
| @@ -280,13 +315,13 @@ static void musb_conn_timer_handler(unsigned long _musb) | |||
| 280 | break; | 315 | break; |
| 281 | default: | 316 | default: |
| 282 | dev_dbg(musb->controller, "%s state not handled\n", | 317 | dev_dbg(musb->controller, "%s state not handled\n", |
| 283 | usb_otg_state_string(musb->xceiv->state)); | 318 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 284 | break; | 319 | break; |
| 285 | } | 320 | } |
| 286 | spin_unlock_irqrestore(&musb->lock, flags); | 321 | spin_unlock_irqrestore(&musb->lock, flags); |
| 287 | 322 | ||
| 288 | dev_dbg(musb->controller, "state is %s\n", | 323 | dev_dbg(musb->controller, "state is %s\n", |
| 289 | usb_otg_state_string(musb->xceiv->state)); | 324 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 290 | } | 325 | } |
| 291 | 326 | ||
| 292 | static void bfin_musb_enable(struct musb *musb) | 327 | static void bfin_musb_enable(struct musb *musb) |
| @@ -307,7 +342,7 @@ static void bfin_musb_set_vbus(struct musb *musb, int is_on) | |||
| 307 | 342 | ||
| 308 | dev_dbg(musb->controller, "VBUS %s, devctl %02x " | 343 | dev_dbg(musb->controller, "VBUS %s, devctl %02x " |
| 309 | /* otg %3x conf %08x prcm %08x */ "\n", | 344 | /* otg %3x conf %08x prcm %08x */ "\n", |
| 310 | usb_otg_state_string(musb->xceiv->state), | 345 | usb_otg_state_string(musb->xceiv->otg->state), |
| 311 | musb_readb(musb->mregs, MUSB_DEVCTL)); | 346 | musb_readb(musb->mregs, MUSB_DEVCTL)); |
| 312 | } | 347 | } |
| 313 | 348 | ||
| @@ -433,6 +468,15 @@ static const struct musb_platform_ops bfin_ops = { | |||
| 433 | .init = bfin_musb_init, | 468 | .init = bfin_musb_init, |
| 434 | .exit = bfin_musb_exit, | 469 | .exit = bfin_musb_exit, |
| 435 | 470 | ||
| 471 | .readb = bfin_readb, | ||
| 472 | .writeb = bfin_writeb, | ||
| 473 | .readw = bfin_readw, | ||
| 474 | .writew = bfin_writew, | ||
| 475 | .readl = bfin_readl, | ||
| 476 | .writel = bfin_writel, | ||
| 477 | .fifo_mode = 2, | ||
| 478 | .read_fifo = bfin_read_fifo, | ||
| 479 | .write_fifo = bfin_write_fifo, | ||
| 436 | .enable = bfin_musb_enable, | 480 | .enable = bfin_musb_enable, |
| 437 | .disable = bfin_musb_disable, | 481 | .disable = bfin_musb_disable, |
| 438 | 482 | ||
| @@ -456,16 +500,12 @@ static int bfin_probe(struct platform_device *pdev) | |||
| 456 | int ret = -ENOMEM; | 500 | int ret = -ENOMEM; |
| 457 | 501 | ||
| 458 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); | 502 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); |
| 459 | if (!glue) { | 503 | if (!glue) |
| 460 | dev_err(&pdev->dev, "failed to allocate glue context\n"); | ||
| 461 | goto err0; | 504 | goto err0; |
| 462 | } | ||
| 463 | 505 | ||
| 464 | musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); | 506 | musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); |
| 465 | if (!musb) { | 507 | if (!musb) |
| 466 | dev_err(&pdev->dev, "failed to allocate musb device\n"); | ||
| 467 | goto err0; | 508 | goto err0; |
| 468 | } | ||
| 469 | 509 | ||
| 470 | musb->dev.parent = &pdev->dev; | 510 | musb->dev.parent = &pdev->dev; |
| 471 | musb->dev.dma_mask = &bfin_dmamask; | 511 | musb->dev.dma_mask = &bfin_dmamask; |
diff --git a/drivers/usb/musb/da8xx.c b/drivers/usb/musb/da8xx.c index 058775e647ad..9a9c82a4d35d 100644 --- a/drivers/usb/musb/da8xx.c +++ b/drivers/usb/musb/da8xx.c | |||
| @@ -198,20 +198,20 @@ static void otg_timer(unsigned long _musb) | |||
| 198 | */ | 198 | */ |
| 199 | devctl = musb_readb(mregs, MUSB_DEVCTL); | 199 | devctl = musb_readb(mregs, MUSB_DEVCTL); |
| 200 | dev_dbg(musb->controller, "Poll devctl %02x (%s)\n", devctl, | 200 | dev_dbg(musb->controller, "Poll devctl %02x (%s)\n", devctl, |
| 201 | usb_otg_state_string(musb->xceiv->state)); | 201 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 202 | 202 | ||
| 203 | spin_lock_irqsave(&musb->lock, flags); | 203 | spin_lock_irqsave(&musb->lock, flags); |
| 204 | switch (musb->xceiv->state) { | 204 | switch (musb->xceiv->otg->state) { |
| 205 | case OTG_STATE_A_WAIT_BCON: | 205 | case OTG_STATE_A_WAIT_BCON: |
| 206 | devctl &= ~MUSB_DEVCTL_SESSION; | 206 | devctl &= ~MUSB_DEVCTL_SESSION; |
| 207 | musb_writeb(musb->mregs, MUSB_DEVCTL, devctl); | 207 | musb_writeb(musb->mregs, MUSB_DEVCTL, devctl); |
| 208 | 208 | ||
| 209 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); | 209 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); |
| 210 | if (devctl & MUSB_DEVCTL_BDEVICE) { | 210 | if (devctl & MUSB_DEVCTL_BDEVICE) { |
| 211 | musb->xceiv->state = OTG_STATE_B_IDLE; | 211 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 212 | MUSB_DEV_MODE(musb); | 212 | MUSB_DEV_MODE(musb); |
| 213 | } else { | 213 | } else { |
| 214 | musb->xceiv->state = OTG_STATE_A_IDLE; | 214 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 215 | MUSB_HST_MODE(musb); | 215 | MUSB_HST_MODE(musb); |
| 216 | } | 216 | } |
| 217 | break; | 217 | break; |
| @@ -226,7 +226,7 @@ static void otg_timer(unsigned long _musb) | |||
| 226 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 226 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 227 | break; | 227 | break; |
| 228 | } | 228 | } |
| 229 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 229 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 230 | musb_writel(musb->ctrl_base, DA8XX_USB_INTR_SRC_SET_REG, | 230 | musb_writel(musb->ctrl_base, DA8XX_USB_INTR_SRC_SET_REG, |
| 231 | MUSB_INTR_VBUSERROR << DA8XX_INTR_USB_SHIFT); | 231 | MUSB_INTR_VBUSERROR << DA8XX_INTR_USB_SHIFT); |
| 232 | break; | 232 | break; |
| @@ -248,7 +248,7 @@ static void otg_timer(unsigned long _musb) | |||
| 248 | if (devctl & MUSB_DEVCTL_BDEVICE) | 248 | if (devctl & MUSB_DEVCTL_BDEVICE) |
| 249 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 249 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 250 | else | 250 | else |
| 251 | musb->xceiv->state = OTG_STATE_A_IDLE; | 251 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 252 | break; | 252 | break; |
| 253 | default: | 253 | default: |
| 254 | break; | 254 | break; |
| @@ -265,9 +265,9 @@ static void da8xx_musb_try_idle(struct musb *musb, unsigned long timeout) | |||
| 265 | 265 | ||
| 266 | /* Never idle if active, or when VBUS timeout is not set as host */ | 266 | /* Never idle if active, or when VBUS timeout is not set as host */ |
| 267 | if (musb->is_active || (musb->a_wait_bcon == 0 && | 267 | if (musb->is_active || (musb->a_wait_bcon == 0 && |
| 268 | musb->xceiv->state == OTG_STATE_A_WAIT_BCON)) { | 268 | musb->xceiv->otg->state == OTG_STATE_A_WAIT_BCON)) { |
| 269 | dev_dbg(musb->controller, "%s active, deleting timer\n", | 269 | dev_dbg(musb->controller, "%s active, deleting timer\n", |
| 270 | usb_otg_state_string(musb->xceiv->state)); | 270 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 271 | del_timer(&otg_workaround); | 271 | del_timer(&otg_workaround); |
| 272 | last_timer = jiffies; | 272 | last_timer = jiffies; |
| 273 | return; | 273 | return; |
| @@ -280,7 +280,7 @@ static void da8xx_musb_try_idle(struct musb *musb, unsigned long timeout) | |||
| 280 | last_timer = timeout; | 280 | last_timer = timeout; |
| 281 | 281 | ||
| 282 | dev_dbg(musb->controller, "%s inactive, starting idle timer for %u ms\n", | 282 | dev_dbg(musb->controller, "%s inactive, starting idle timer for %u ms\n", |
| 283 | usb_otg_state_string(musb->xceiv->state), | 283 | usb_otg_state_string(musb->xceiv->otg->state), |
| 284 | jiffies_to_msecs(timeout - jiffies)); | 284 | jiffies_to_msecs(timeout - jiffies)); |
| 285 | mod_timer(&otg_workaround, timeout); | 285 | mod_timer(&otg_workaround, timeout); |
| 286 | } | 286 | } |
| @@ -341,26 +341,26 @@ static irqreturn_t da8xx_musb_interrupt(int irq, void *hci) | |||
| 341 | * devctl. | 341 | * devctl. |
| 342 | */ | 342 | */ |
| 343 | musb->int_usb &= ~MUSB_INTR_VBUSERROR; | 343 | musb->int_usb &= ~MUSB_INTR_VBUSERROR; |
| 344 | musb->xceiv->state = OTG_STATE_A_WAIT_VFALL; | 344 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VFALL; |
| 345 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 345 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 346 | WARNING("VBUS error workaround (delay coming)\n"); | 346 | WARNING("VBUS error workaround (delay coming)\n"); |
| 347 | } else if (drvvbus) { | 347 | } else if (drvvbus) { |
| 348 | MUSB_HST_MODE(musb); | 348 | MUSB_HST_MODE(musb); |
| 349 | otg->default_a = 1; | 349 | otg->default_a = 1; |
| 350 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 350 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 351 | portstate(musb->port1_status |= USB_PORT_STAT_POWER); | 351 | portstate(musb->port1_status |= USB_PORT_STAT_POWER); |
| 352 | del_timer(&otg_workaround); | 352 | del_timer(&otg_workaround); |
| 353 | } else { | 353 | } else { |
| 354 | musb->is_active = 0; | 354 | musb->is_active = 0; |
| 355 | MUSB_DEV_MODE(musb); | 355 | MUSB_DEV_MODE(musb); |
| 356 | otg->default_a = 0; | 356 | otg->default_a = 0; |
| 357 | musb->xceiv->state = OTG_STATE_B_IDLE; | 357 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 358 | portstate(musb->port1_status &= ~USB_PORT_STAT_POWER); | 358 | portstate(musb->port1_status &= ~USB_PORT_STAT_POWER); |
| 359 | } | 359 | } |
| 360 | 360 | ||
| 361 | dev_dbg(musb->controller, "VBUS %s (%s)%s, devctl %02x\n", | 361 | dev_dbg(musb->controller, "VBUS %s (%s)%s, devctl %02x\n", |
| 362 | drvvbus ? "on" : "off", | 362 | drvvbus ? "on" : "off", |
| 363 | usb_otg_state_string(musb->xceiv->state), | 363 | usb_otg_state_string(musb->xceiv->otg->state), |
| 364 | err ? " ERROR" : "", | 364 | err ? " ERROR" : "", |
| 365 | devctl); | 365 | devctl); |
| 366 | ret = IRQ_HANDLED; | 366 | ret = IRQ_HANDLED; |
| @@ -375,7 +375,7 @@ static irqreturn_t da8xx_musb_interrupt(int irq, void *hci) | |||
| 375 | musb_writel(reg_base, DA8XX_USB_END_OF_INTR_REG, 0); | 375 | musb_writel(reg_base, DA8XX_USB_END_OF_INTR_REG, 0); |
| 376 | 376 | ||
| 377 | /* Poll for ID change */ | 377 | /* Poll for ID change */ |
| 378 | if (musb->xceiv->state == OTG_STATE_B_IDLE) | 378 | if (musb->xceiv->otg->state == OTG_STATE_B_IDLE) |
| 379 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 379 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 380 | 380 | ||
| 381 | spin_unlock_irqrestore(&musb->lock, flags); | 381 | spin_unlock_irqrestore(&musb->lock, flags); |
| @@ -458,9 +458,11 @@ static int da8xx_musb_exit(struct musb *musb) | |||
| 458 | } | 458 | } |
| 459 | 459 | ||
| 460 | static const struct musb_platform_ops da8xx_ops = { | 460 | static const struct musb_platform_ops da8xx_ops = { |
| 461 | .quirks = MUSB_INDEXED_EP, | ||
| 461 | .init = da8xx_musb_init, | 462 | .init = da8xx_musb_init, |
| 462 | .exit = da8xx_musb_exit, | 463 | .exit = da8xx_musb_exit, |
| 463 | 464 | ||
| 465 | .fifo_mode = 2, | ||
| 464 | .enable = da8xx_musb_enable, | 466 | .enable = da8xx_musb_enable, |
| 465 | .disable = da8xx_musb_disable, | 467 | .disable = da8xx_musb_disable, |
| 466 | 468 | ||
diff --git a/drivers/usb/musb/davinci.c b/drivers/usb/musb/davinci.c index 110b78415bf0..3c1d9b211b51 100644 --- a/drivers/usb/musb/davinci.c +++ b/drivers/usb/musb/davinci.c | |||
| @@ -214,10 +214,10 @@ static void otg_timer(unsigned long _musb) | |||
| 214 | */ | 214 | */ |
| 215 | devctl = musb_readb(mregs, MUSB_DEVCTL); | 215 | devctl = musb_readb(mregs, MUSB_DEVCTL); |
| 216 | dev_dbg(musb->controller, "poll devctl %02x (%s)\n", devctl, | 216 | dev_dbg(musb->controller, "poll devctl %02x (%s)\n", devctl, |
| 217 | usb_otg_state_string(musb->xceiv->state)); | 217 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 218 | 218 | ||
| 219 | spin_lock_irqsave(&musb->lock, flags); | 219 | spin_lock_irqsave(&musb->lock, flags); |
| 220 | switch (musb->xceiv->state) { | 220 | switch (musb->xceiv->otg->state) { |
| 221 | case OTG_STATE_A_WAIT_VFALL: | 221 | case OTG_STATE_A_WAIT_VFALL: |
| 222 | /* Wait till VBUS falls below SessionEnd (~0.2V); the 1.3 RTL | 222 | /* Wait till VBUS falls below SessionEnd (~0.2V); the 1.3 RTL |
| 223 | * seems to mis-handle session "start" otherwise (or in our | 223 | * seems to mis-handle session "start" otherwise (or in our |
| @@ -228,7 +228,7 @@ static void otg_timer(unsigned long _musb) | |||
| 228 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 228 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 229 | break; | 229 | break; |
| 230 | } | 230 | } |
| 231 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 231 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 232 | musb_writel(musb->ctrl_base, DAVINCI_USB_INT_SET_REG, | 232 | musb_writel(musb->ctrl_base, DAVINCI_USB_INT_SET_REG, |
| 233 | MUSB_INTR_VBUSERROR << DAVINCI_USB_USBINT_SHIFT); | 233 | MUSB_INTR_VBUSERROR << DAVINCI_USB_USBINT_SHIFT); |
| 234 | break; | 234 | break; |
| @@ -251,7 +251,7 @@ static void otg_timer(unsigned long _musb) | |||
| 251 | if (devctl & MUSB_DEVCTL_BDEVICE) | 251 | if (devctl & MUSB_DEVCTL_BDEVICE) |
| 252 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 252 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 253 | else | 253 | else |
| 254 | musb->xceiv->state = OTG_STATE_A_IDLE; | 254 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 255 | break; | 255 | break; |
| 256 | default: | 256 | default: |
| 257 | break; | 257 | break; |
| @@ -325,20 +325,20 @@ static irqreturn_t davinci_musb_interrupt(int irq, void *__hci) | |||
| 325 | * to stop registering in devctl. | 325 | * to stop registering in devctl. |
| 326 | */ | 326 | */ |
| 327 | musb->int_usb &= ~MUSB_INTR_VBUSERROR; | 327 | musb->int_usb &= ~MUSB_INTR_VBUSERROR; |
| 328 | musb->xceiv->state = OTG_STATE_A_WAIT_VFALL; | 328 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VFALL; |
| 329 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 329 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 330 | WARNING("VBUS error workaround (delay coming)\n"); | 330 | WARNING("VBUS error workaround (delay coming)\n"); |
| 331 | } else if (drvvbus) { | 331 | } else if (drvvbus) { |
| 332 | MUSB_HST_MODE(musb); | 332 | MUSB_HST_MODE(musb); |
| 333 | otg->default_a = 1; | 333 | otg->default_a = 1; |
| 334 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 334 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 335 | portstate(musb->port1_status |= USB_PORT_STAT_POWER); | 335 | portstate(musb->port1_status |= USB_PORT_STAT_POWER); |
| 336 | del_timer(&otg_workaround); | 336 | del_timer(&otg_workaround); |
| 337 | } else { | 337 | } else { |
| 338 | musb->is_active = 0; | 338 | musb->is_active = 0; |
| 339 | MUSB_DEV_MODE(musb); | 339 | MUSB_DEV_MODE(musb); |
| 340 | otg->default_a = 0; | 340 | otg->default_a = 0; |
| 341 | musb->xceiv->state = OTG_STATE_B_IDLE; | 341 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 342 | portstate(musb->port1_status &= ~USB_PORT_STAT_POWER); | 342 | portstate(musb->port1_status &= ~USB_PORT_STAT_POWER); |
| 343 | } | 343 | } |
| 344 | 344 | ||
| @@ -348,7 +348,7 @@ static irqreturn_t davinci_musb_interrupt(int irq, void *__hci) | |||
| 348 | davinci_musb_source_power(musb, drvvbus, 0); | 348 | davinci_musb_source_power(musb, drvvbus, 0); |
| 349 | dev_dbg(musb->controller, "VBUS %s (%s)%s, devctl %02x\n", | 349 | dev_dbg(musb->controller, "VBUS %s (%s)%s, devctl %02x\n", |
| 350 | drvvbus ? "on" : "off", | 350 | drvvbus ? "on" : "off", |
| 351 | usb_otg_state_string(musb->xceiv->state), | 351 | usb_otg_state_string(musb->xceiv->otg->state), |
| 352 | err ? " ERROR" : "", | 352 | err ? " ERROR" : "", |
| 353 | devctl); | 353 | devctl); |
| 354 | retval = IRQ_HANDLED; | 354 | retval = IRQ_HANDLED; |
| @@ -361,7 +361,7 @@ static irqreturn_t davinci_musb_interrupt(int irq, void *__hci) | |||
| 361 | musb_writel(tibase, DAVINCI_USB_EOI_REG, 0); | 361 | musb_writel(tibase, DAVINCI_USB_EOI_REG, 0); |
| 362 | 362 | ||
| 363 | /* poll for ID change */ | 363 | /* poll for ID change */ |
| 364 | if (musb->xceiv->state == OTG_STATE_B_IDLE) | 364 | if (musb->xceiv->otg->state == OTG_STATE_B_IDLE) |
| 365 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); | 365 | mod_timer(&otg_workaround, jiffies + POLL_SECONDS * HZ); |
| 366 | 366 | ||
| 367 | spin_unlock_irqrestore(&musb->lock, flags); | 367 | spin_unlock_irqrestore(&musb->lock, flags); |
| @@ -520,10 +520,8 @@ static int davinci_probe(struct platform_device *pdev) | |||
| 520 | int ret = -ENOMEM; | 520 | int ret = -ENOMEM; |
| 521 | 521 | ||
| 522 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); | 522 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); |
| 523 | if (!glue) { | 523 | if (!glue) |
| 524 | dev_err(&pdev->dev, "failed to allocate glue context\n"); | ||
| 525 | goto err0; | 524 | goto err0; |
| 526 | } | ||
| 527 | 525 | ||
| 528 | clk = devm_clk_get(&pdev->dev, "usb"); | 526 | clk = devm_clk_get(&pdev->dev, "usb"); |
| 529 | if (IS_ERR(clk)) { | 527 | if (IS_ERR(clk)) { |
diff --git a/drivers/usb/musb/jz4740.c b/drivers/usb/musb/jz4740.c index d1187290d4e3..bb7b26325a74 100644 --- a/drivers/usb/musb/jz4740.c +++ b/drivers/usb/musb/jz4740.c | |||
| @@ -106,6 +106,8 @@ static int jz4740_musb_exit(struct musb *musb) | |||
| 106 | } | 106 | } |
| 107 | 107 | ||
| 108 | static const struct musb_platform_ops jz4740_musb_ops = { | 108 | static const struct musb_platform_ops jz4740_musb_ops = { |
| 109 | .quirks = MUSB_INDEXED_EP, | ||
| 110 | .fifo_mode = 2, | ||
| 109 | .init = jz4740_musb_init, | 111 | .init = jz4740_musb_init, |
| 110 | .exit = jz4740_musb_exit, | 112 | .exit = jz4740_musb_exit, |
| 111 | }; | 113 | }; |
diff --git a/drivers/usb/musb/musb_core.c b/drivers/usb/musb/musb_core.c index b841ee0bff06..55fe0ff6fd87 100644 --- a/drivers/usb/musb/musb_core.c +++ b/drivers/usb/musb/musb_core.c | |||
| @@ -224,12 +224,67 @@ static struct usb_phy_io_ops musb_ulpi_access = { | |||
| 224 | 224 | ||
| 225 | /*-------------------------------------------------------------------------*/ | 225 | /*-------------------------------------------------------------------------*/ |
| 226 | 226 | ||
| 227 | #if !defined(CONFIG_USB_MUSB_TUSB6010) && !defined(CONFIG_USB_MUSB_BLACKFIN) | 227 | static u32 musb_default_fifo_offset(u8 epnum) |
| 228 | { | ||
| 229 | return 0x20 + (epnum * 4); | ||
| 230 | } | ||
| 231 | |||
| 232 | /* "flat" mapping: each endpoint has its own i/o address */ | ||
| 233 | static void musb_flat_ep_select(void __iomem *mbase, u8 epnum) | ||
| 234 | { | ||
| 235 | } | ||
| 236 | |||
| 237 | static u32 musb_flat_ep_offset(u8 epnum, u16 offset) | ||
| 238 | { | ||
| 239 | return 0x100 + (0x10 * epnum) + offset; | ||
| 240 | } | ||
| 241 | |||
| 242 | /* "indexed" mapping: INDEX register controls register bank select */ | ||
| 243 | static void musb_indexed_ep_select(void __iomem *mbase, u8 epnum) | ||
| 244 | { | ||
| 245 | musb_writeb(mbase, MUSB_INDEX, epnum); | ||
| 246 | } | ||
| 247 | |||
| 248 | static u32 musb_indexed_ep_offset(u8 epnum, u16 offset) | ||
| 249 | { | ||
| 250 | return 0x10 + offset; | ||
| 251 | } | ||
| 252 | |||
| 253 | static u8 musb_default_readb(const void __iomem *addr, unsigned offset) | ||
| 254 | { | ||
| 255 | return __raw_readb(addr + offset); | ||
| 256 | } | ||
| 257 | |||
| 258 | static void musb_default_writeb(void __iomem *addr, unsigned offset, u8 data) | ||
| 259 | { | ||
| 260 | __raw_writeb(data, addr + offset); | ||
| 261 | } | ||
| 262 | |||
| 263 | static u16 musb_default_readw(const void __iomem *addr, unsigned offset) | ||
| 264 | { | ||
| 265 | return __raw_readw(addr + offset); | ||
| 266 | } | ||
| 267 | |||
| 268 | static void musb_default_writew(void __iomem *addr, unsigned offset, u16 data) | ||
| 269 | { | ||
| 270 | __raw_writew(data, addr + offset); | ||
| 271 | } | ||
| 272 | |||
| 273 | static u32 musb_default_readl(const void __iomem *addr, unsigned offset) | ||
| 274 | { | ||
| 275 | return __raw_readl(addr + offset); | ||
| 276 | } | ||
| 277 | |||
| 278 | static void musb_default_writel(void __iomem *addr, unsigned offset, u32 data) | ||
| 279 | { | ||
| 280 | __raw_writel(data, addr + offset); | ||
| 281 | } | ||
| 228 | 282 | ||
| 229 | /* | 283 | /* |
| 230 | * Load an endpoint's FIFO | 284 | * Load an endpoint's FIFO |
| 231 | */ | 285 | */ |
| 232 | void musb_write_fifo(struct musb_hw_ep *hw_ep, u16 len, const u8 *src) | 286 | static void musb_default_write_fifo(struct musb_hw_ep *hw_ep, u16 len, |
| 287 | const u8 *src) | ||
| 233 | { | 288 | { |
| 234 | struct musb *musb = hw_ep->musb; | 289 | struct musb *musb = hw_ep->musb; |
| 235 | void __iomem *fifo = hw_ep->fifo; | 290 | void __iomem *fifo = hw_ep->fifo; |
| @@ -270,11 +325,10 @@ void musb_write_fifo(struct musb_hw_ep *hw_ep, u16 len, const u8 *src) | |||
| 270 | } | 325 | } |
| 271 | } | 326 | } |
| 272 | 327 | ||
| 273 | #if !defined(CONFIG_USB_MUSB_AM35X) | ||
| 274 | /* | 328 | /* |
| 275 | * Unload an endpoint's FIFO | 329 | * Unload an endpoint's FIFO |
| 276 | */ | 330 | */ |
| 277 | void musb_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *dst) | 331 | static void musb_default_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *dst) |
| 278 | { | 332 | { |
| 279 | struct musb *musb = hw_ep->musb; | 333 | struct musb *musb = hw_ep->musb; |
| 280 | void __iomem *fifo = hw_ep->fifo; | 334 | void __iomem *fifo = hw_ep->fifo; |
| @@ -312,10 +366,40 @@ void musb_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *dst) | |||
| 312 | ioread8_rep(fifo, dst, len); | 366 | ioread8_rep(fifo, dst, len); |
| 313 | } | 367 | } |
| 314 | } | 368 | } |
| 315 | #endif | ||
| 316 | 369 | ||
| 317 | #endif /* normal PIO */ | 370 | /* |
| 371 | * Old style IO functions | ||
| 372 | */ | ||
| 373 | u8 (*musb_readb)(const void __iomem *addr, unsigned offset); | ||
| 374 | EXPORT_SYMBOL_GPL(musb_readb); | ||
| 375 | |||
| 376 | void (*musb_writeb)(void __iomem *addr, unsigned offset, u8 data); | ||
| 377 | EXPORT_SYMBOL_GPL(musb_writeb); | ||
| 378 | |||
| 379 | u16 (*musb_readw)(const void __iomem *addr, unsigned offset); | ||
| 380 | EXPORT_SYMBOL_GPL(musb_readw); | ||
| 381 | |||
| 382 | void (*musb_writew)(void __iomem *addr, unsigned offset, u16 data); | ||
| 383 | EXPORT_SYMBOL_GPL(musb_writew); | ||
| 384 | |||
| 385 | u32 (*musb_readl)(const void __iomem *addr, unsigned offset); | ||
| 386 | EXPORT_SYMBOL_GPL(musb_readl); | ||
| 318 | 387 | ||
| 388 | void (*musb_writel)(void __iomem *addr, unsigned offset, u32 data); | ||
| 389 | EXPORT_SYMBOL_GPL(musb_writel); | ||
| 390 | |||
| 391 | /* | ||
| 392 | * New style IO functions | ||
| 393 | */ | ||
| 394 | void musb_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *dst) | ||
| 395 | { | ||
| 396 | return hw_ep->musb->io.read_fifo(hw_ep, len, dst); | ||
| 397 | } | ||
| 398 | |||
| 399 | void musb_write_fifo(struct musb_hw_ep *hw_ep, u16 len, const u8 *src) | ||
| 400 | { | ||
| 401 | return hw_ep->musb->io.write_fifo(hw_ep, len, src); | ||
| 402 | } | ||
| 319 | 403 | ||
| 320 | /*-------------------------------------------------------------------------*/ | 404 | /*-------------------------------------------------------------------------*/ |
| 321 | 405 | ||
| @@ -360,23 +444,23 @@ static void musb_otg_timer_func(unsigned long data) | |||
| 360 | unsigned long flags; | 444 | unsigned long flags; |
| 361 | 445 | ||
| 362 | spin_lock_irqsave(&musb->lock, flags); | 446 | spin_lock_irqsave(&musb->lock, flags); |
| 363 | switch (musb->xceiv->state) { | 447 | switch (musb->xceiv->otg->state) { |
| 364 | case OTG_STATE_B_WAIT_ACON: | 448 | case OTG_STATE_B_WAIT_ACON: |
| 365 | dev_dbg(musb->controller, "HNP: b_wait_acon timeout; back to b_peripheral\n"); | 449 | dev_dbg(musb->controller, "HNP: b_wait_acon timeout; back to b_peripheral\n"); |
| 366 | musb_g_disconnect(musb); | 450 | musb_g_disconnect(musb); |
| 367 | musb->xceiv->state = OTG_STATE_B_PERIPHERAL; | 451 | musb->xceiv->otg->state = OTG_STATE_B_PERIPHERAL; |
| 368 | musb->is_active = 0; | 452 | musb->is_active = 0; |
| 369 | break; | 453 | break; |
| 370 | case OTG_STATE_A_SUSPEND: | 454 | case OTG_STATE_A_SUSPEND: |
| 371 | case OTG_STATE_A_WAIT_BCON: | 455 | case OTG_STATE_A_WAIT_BCON: |
| 372 | dev_dbg(musb->controller, "HNP: %s timeout\n", | 456 | dev_dbg(musb->controller, "HNP: %s timeout\n", |
| 373 | usb_otg_state_string(musb->xceiv->state)); | 457 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 374 | musb_platform_set_vbus(musb, 0); | 458 | musb_platform_set_vbus(musb, 0); |
| 375 | musb->xceiv->state = OTG_STATE_A_WAIT_VFALL; | 459 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VFALL; |
| 376 | break; | 460 | break; |
| 377 | default: | 461 | default: |
| 378 | dev_dbg(musb->controller, "HNP: Unhandled mode %s\n", | 462 | dev_dbg(musb->controller, "HNP: Unhandled mode %s\n", |
| 379 | usb_otg_state_string(musb->xceiv->state)); | 463 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 380 | } | 464 | } |
| 381 | spin_unlock_irqrestore(&musb->lock, flags); | 465 | spin_unlock_irqrestore(&musb->lock, flags); |
| 382 | } | 466 | } |
| @@ -391,19 +475,19 @@ void musb_hnp_stop(struct musb *musb) | |||
| 391 | u8 reg; | 475 | u8 reg; |
| 392 | 476 | ||
| 393 | dev_dbg(musb->controller, "HNP: stop from %s\n", | 477 | dev_dbg(musb->controller, "HNP: stop from %s\n", |
| 394 | usb_otg_state_string(musb->xceiv->state)); | 478 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 395 | 479 | ||
| 396 | switch (musb->xceiv->state) { | 480 | switch (musb->xceiv->otg->state) { |
| 397 | case OTG_STATE_A_PERIPHERAL: | 481 | case OTG_STATE_A_PERIPHERAL: |
| 398 | musb_g_disconnect(musb); | 482 | musb_g_disconnect(musb); |
| 399 | dev_dbg(musb->controller, "HNP: back to %s\n", | 483 | dev_dbg(musb->controller, "HNP: back to %s\n", |
| 400 | usb_otg_state_string(musb->xceiv->state)); | 484 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 401 | break; | 485 | break; |
| 402 | case OTG_STATE_B_HOST: | 486 | case OTG_STATE_B_HOST: |
| 403 | dev_dbg(musb->controller, "HNP: Disabling HR\n"); | 487 | dev_dbg(musb->controller, "HNP: Disabling HR\n"); |
| 404 | if (hcd) | 488 | if (hcd) |
| 405 | hcd->self.is_b_host = 0; | 489 | hcd->self.is_b_host = 0; |
| 406 | musb->xceiv->state = OTG_STATE_B_PERIPHERAL; | 490 | musb->xceiv->otg->state = OTG_STATE_B_PERIPHERAL; |
| 407 | MUSB_DEV_MODE(musb); | 491 | MUSB_DEV_MODE(musb); |
| 408 | reg = musb_readb(mbase, MUSB_POWER); | 492 | reg = musb_readb(mbase, MUSB_POWER); |
| 409 | reg |= MUSB_POWER_SUSPENDM; | 493 | reg |= MUSB_POWER_SUSPENDM; |
| @@ -412,7 +496,7 @@ void musb_hnp_stop(struct musb *musb) | |||
| 412 | break; | 496 | break; |
| 413 | default: | 497 | default: |
| 414 | dev_dbg(musb->controller, "HNP: Stopping in unknown state %s\n", | 498 | dev_dbg(musb->controller, "HNP: Stopping in unknown state %s\n", |
| 415 | usb_otg_state_string(musb->xceiv->state)); | 499 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 416 | } | 500 | } |
| 417 | 501 | ||
| 418 | /* | 502 | /* |
| @@ -423,6 +507,7 @@ void musb_hnp_stop(struct musb *musb) | |||
| 423 | musb->port1_status &= ~(USB_PORT_STAT_C_CONNECTION << 16); | 507 | musb->port1_status &= ~(USB_PORT_STAT_C_CONNECTION << 16); |
| 424 | } | 508 | } |
| 425 | 509 | ||
| 510 | static void musb_generic_disable(struct musb *musb); | ||
| 426 | /* | 511 | /* |
| 427 | * Interrupt Service Routine to record USB "global" interrupts. | 512 | * Interrupt Service Routine to record USB "global" interrupts. |
| 428 | * Since these do not happen often and signify things of | 513 | * Since these do not happen often and signify things of |
| @@ -449,13 +534,13 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 449 | */ | 534 | */ |
| 450 | if (int_usb & MUSB_INTR_RESUME) { | 535 | if (int_usb & MUSB_INTR_RESUME) { |
| 451 | handled = IRQ_HANDLED; | 536 | handled = IRQ_HANDLED; |
| 452 | dev_dbg(musb->controller, "RESUME (%s)\n", usb_otg_state_string(musb->xceiv->state)); | 537 | dev_dbg(musb->controller, "RESUME (%s)\n", usb_otg_state_string(musb->xceiv->otg->state)); |
| 453 | 538 | ||
| 454 | if (devctl & MUSB_DEVCTL_HM) { | 539 | if (devctl & MUSB_DEVCTL_HM) { |
| 455 | void __iomem *mbase = musb->mregs; | 540 | void __iomem *mbase = musb->mregs; |
| 456 | u8 power; | 541 | u8 power; |
| 457 | 542 | ||
| 458 | switch (musb->xceiv->state) { | 543 | switch (musb->xceiv->otg->state) { |
| 459 | case OTG_STATE_A_SUSPEND: | 544 | case OTG_STATE_A_SUSPEND: |
| 460 | /* remote wakeup? later, GetPortStatus | 545 | /* remote wakeup? later, GetPortStatus |
| 461 | * will stop RESUME signaling | 546 | * will stop RESUME signaling |
| @@ -478,29 +563,26 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 478 | | MUSB_PORT_STAT_RESUME; | 563 | | MUSB_PORT_STAT_RESUME; |
| 479 | musb->rh_timer = jiffies | 564 | musb->rh_timer = jiffies |
| 480 | + msecs_to_jiffies(20); | 565 | + msecs_to_jiffies(20); |
| 481 | schedule_delayed_work( | 566 | musb->need_finish_resume = 1; |
| 482 | &musb->finish_resume_work, | ||
| 483 | msecs_to_jiffies(20)); | ||
| 484 | 567 | ||
| 485 | musb->xceiv->state = OTG_STATE_A_HOST; | 568 | musb->xceiv->otg->state = OTG_STATE_A_HOST; |
| 486 | musb->is_active = 1; | 569 | musb->is_active = 1; |
| 487 | musb_host_resume_root_hub(musb); | ||
| 488 | break; | 570 | break; |
| 489 | case OTG_STATE_B_WAIT_ACON: | 571 | case OTG_STATE_B_WAIT_ACON: |
| 490 | musb->xceiv->state = OTG_STATE_B_PERIPHERAL; | 572 | musb->xceiv->otg->state = OTG_STATE_B_PERIPHERAL; |
| 491 | musb->is_active = 1; | 573 | musb->is_active = 1; |
| 492 | MUSB_DEV_MODE(musb); | 574 | MUSB_DEV_MODE(musb); |
| 493 | break; | 575 | break; |
| 494 | default: | 576 | default: |
| 495 | WARNING("bogus %s RESUME (%s)\n", | 577 | WARNING("bogus %s RESUME (%s)\n", |
| 496 | "host", | 578 | "host", |
| 497 | usb_otg_state_string(musb->xceiv->state)); | 579 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 498 | } | 580 | } |
| 499 | } else { | 581 | } else { |
| 500 | switch (musb->xceiv->state) { | 582 | switch (musb->xceiv->otg->state) { |
| 501 | case OTG_STATE_A_SUSPEND: | 583 | case OTG_STATE_A_SUSPEND: |
| 502 | /* possibly DISCONNECT is upcoming */ | 584 | /* possibly DISCONNECT is upcoming */ |
| 503 | musb->xceiv->state = OTG_STATE_A_HOST; | 585 | musb->xceiv->otg->state = OTG_STATE_A_HOST; |
| 504 | musb_host_resume_root_hub(musb); | 586 | musb_host_resume_root_hub(musb); |
| 505 | break; | 587 | break; |
| 506 | case OTG_STATE_B_WAIT_ACON: | 588 | case OTG_STATE_B_WAIT_ACON: |
| @@ -523,7 +605,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 523 | default: | 605 | default: |
| 524 | WARNING("bogus %s RESUME (%s)\n", | 606 | WARNING("bogus %s RESUME (%s)\n", |
| 525 | "peripheral", | 607 | "peripheral", |
| 526 | usb_otg_state_string(musb->xceiv->state)); | 608 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 527 | } | 609 | } |
| 528 | } | 610 | } |
| 529 | } | 611 | } |
| @@ -539,7 +621,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 539 | } | 621 | } |
| 540 | 622 | ||
| 541 | dev_dbg(musb->controller, "SESSION_REQUEST (%s)\n", | 623 | dev_dbg(musb->controller, "SESSION_REQUEST (%s)\n", |
| 542 | usb_otg_state_string(musb->xceiv->state)); | 624 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 543 | 625 | ||
| 544 | /* IRQ arrives from ID pin sense or (later, if VBUS power | 626 | /* IRQ arrives from ID pin sense or (later, if VBUS power |
| 545 | * is removed) SRP. responses are time critical: | 627 | * is removed) SRP. responses are time critical: |
| @@ -550,7 +632,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 550 | */ | 632 | */ |
| 551 | musb_writeb(mbase, MUSB_DEVCTL, MUSB_DEVCTL_SESSION); | 633 | musb_writeb(mbase, MUSB_DEVCTL, MUSB_DEVCTL_SESSION); |
| 552 | musb->ep0_stage = MUSB_EP0_START; | 634 | musb->ep0_stage = MUSB_EP0_START; |
| 553 | musb->xceiv->state = OTG_STATE_A_IDLE; | 635 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 554 | MUSB_HST_MODE(musb); | 636 | MUSB_HST_MODE(musb); |
| 555 | musb_platform_set_vbus(musb, 1); | 637 | musb_platform_set_vbus(musb, 1); |
| 556 | 638 | ||
| @@ -576,7 +658,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 576 | * REVISIT: do delays from lots of DEBUG_KERNEL checks | 658 | * REVISIT: do delays from lots of DEBUG_KERNEL checks |
| 577 | * make trouble here, keeping VBUS < 4.4V ? | 659 | * make trouble here, keeping VBUS < 4.4V ? |
| 578 | */ | 660 | */ |
| 579 | switch (musb->xceiv->state) { | 661 | switch (musb->xceiv->otg->state) { |
| 580 | case OTG_STATE_A_HOST: | 662 | case OTG_STATE_A_HOST: |
| 581 | /* recovery is dicey once we've gotten past the | 663 | /* recovery is dicey once we've gotten past the |
| 582 | * initial stages of enumeration, but if VBUS | 664 | * initial stages of enumeration, but if VBUS |
| @@ -605,7 +687,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 605 | 687 | ||
| 606 | dev_printk(ignore ? KERN_DEBUG : KERN_ERR, musb->controller, | 688 | dev_printk(ignore ? KERN_DEBUG : KERN_ERR, musb->controller, |
| 607 | "VBUS_ERROR in %s (%02x, %s), retry #%d, port1 %08x\n", | 689 | "VBUS_ERROR in %s (%02x, %s), retry #%d, port1 %08x\n", |
| 608 | usb_otg_state_string(musb->xceiv->state), | 690 | usb_otg_state_string(musb->xceiv->otg->state), |
| 609 | devctl, | 691 | devctl, |
| 610 | ({ char *s; | 692 | ({ char *s; |
| 611 | switch (devctl & MUSB_DEVCTL_VBUS) { | 693 | switch (devctl & MUSB_DEVCTL_VBUS) { |
| @@ -630,10 +712,10 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 630 | 712 | ||
| 631 | if (int_usb & MUSB_INTR_SUSPEND) { | 713 | if (int_usb & MUSB_INTR_SUSPEND) { |
| 632 | dev_dbg(musb->controller, "SUSPEND (%s) devctl %02x\n", | 714 | dev_dbg(musb->controller, "SUSPEND (%s) devctl %02x\n", |
| 633 | usb_otg_state_string(musb->xceiv->state), devctl); | 715 | usb_otg_state_string(musb->xceiv->otg->state), devctl); |
| 634 | handled = IRQ_HANDLED; | 716 | handled = IRQ_HANDLED; |
| 635 | 717 | ||
| 636 | switch (musb->xceiv->state) { | 718 | switch (musb->xceiv->otg->state) { |
| 637 | case OTG_STATE_A_PERIPHERAL: | 719 | case OTG_STATE_A_PERIPHERAL: |
| 638 | /* We also come here if the cable is removed, since | 720 | /* We also come here if the cable is removed, since |
| 639 | * this silicon doesn't report ID-no-longer-grounded. | 721 | * this silicon doesn't report ID-no-longer-grounded. |
| @@ -657,7 +739,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 657 | musb_g_suspend(musb); | 739 | musb_g_suspend(musb); |
| 658 | musb->is_active = musb->g.b_hnp_enable; | 740 | musb->is_active = musb->g.b_hnp_enable; |
| 659 | if (musb->is_active) { | 741 | if (musb->is_active) { |
| 660 | musb->xceiv->state = OTG_STATE_B_WAIT_ACON; | 742 | musb->xceiv->otg->state = OTG_STATE_B_WAIT_ACON; |
| 661 | dev_dbg(musb->controller, "HNP: Setting timer for b_ase0_brst\n"); | 743 | dev_dbg(musb->controller, "HNP: Setting timer for b_ase0_brst\n"); |
| 662 | mod_timer(&musb->otg_timer, jiffies | 744 | mod_timer(&musb->otg_timer, jiffies |
| 663 | + msecs_to_jiffies( | 745 | + msecs_to_jiffies( |
| @@ -670,7 +752,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 670 | + msecs_to_jiffies(musb->a_wait_bcon)); | 752 | + msecs_to_jiffies(musb->a_wait_bcon)); |
| 671 | break; | 753 | break; |
| 672 | case OTG_STATE_A_HOST: | 754 | case OTG_STATE_A_HOST: |
| 673 | musb->xceiv->state = OTG_STATE_A_SUSPEND; | 755 | musb->xceiv->otg->state = OTG_STATE_A_SUSPEND; |
| 674 | musb->is_active = musb->hcd->self.b_hnp_enable; | 756 | musb->is_active = musb->hcd->self.b_hnp_enable; |
| 675 | break; | 757 | break; |
| 676 | case OTG_STATE_B_HOST: | 758 | case OTG_STATE_B_HOST: |
| @@ -713,7 +795,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 713 | musb->port1_status |= USB_PORT_STAT_LOW_SPEED; | 795 | musb->port1_status |= USB_PORT_STAT_LOW_SPEED; |
| 714 | 796 | ||
| 715 | /* indicate new connection to OTG machine */ | 797 | /* indicate new connection to OTG machine */ |
| 716 | switch (musb->xceiv->state) { | 798 | switch (musb->xceiv->otg->state) { |
| 717 | case OTG_STATE_B_PERIPHERAL: | 799 | case OTG_STATE_B_PERIPHERAL: |
| 718 | if (int_usb & MUSB_INTR_SUSPEND) { | 800 | if (int_usb & MUSB_INTR_SUSPEND) { |
| 719 | dev_dbg(musb->controller, "HNP: SUSPEND+CONNECT, now b_host\n"); | 801 | dev_dbg(musb->controller, "HNP: SUSPEND+CONNECT, now b_host\n"); |
| @@ -725,7 +807,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, | |||
| 725 | case OTG_STATE_B_WAIT_ACON: | 807 | case OTG_STATE_B_WAIT_ACON: |
| 726 | dev_dbg(musb->controller, "HNP: CONNECT, now b_host\n"); | 808 | dev_dbg(musb->controller, "HNP: CONNECT, now b_host\n"); |
| 727 | b_host: | 809 | b_host: |
| 728 | musb->xceiv->state = OTG_STATE_B_HOST; | 810 | musb->xceiv->otg->state = OTG_STATE_B_HOST; |
| 729 | if (musb->hcd) | 811 | if (musb->hcd) |
| 730 | musb->hcd->self.is_b_host = 1; | 812 | musb->hcd->self.is_b_host = 1; |
| 731 | del_timer(&musb->otg_timer); | 813 | del_timer(&musb->otg_timer); |
| @@ -733,7 +815,7 @@ b_host: | |||
| 733 | default: | 815 | default: |
| 734 | if ((devctl & MUSB_DEVCTL_VBUS) | 816 | if ((devctl & MUSB_DEVCTL_VBUS) |
| 735 | == (3 << MUSB_DEVCTL_VBUS_SHIFT)) { | 817 | == (3 << MUSB_DEVCTL_VBUS_SHIFT)) { |
| 736 | musb->xceiv->state = OTG_STATE_A_HOST; | 818 | musb->xceiv->otg->state = OTG_STATE_A_HOST; |
| 737 | if (hcd) | 819 | if (hcd) |
| 738 | hcd->self.is_b_host = 0; | 820 | hcd->self.is_b_host = 0; |
| 739 | } | 821 | } |
| @@ -743,16 +825,16 @@ b_host: | |||
| 743 | musb_host_poke_root_hub(musb); | 825 | musb_host_poke_root_hub(musb); |
| 744 | 826 | ||
| 745 | dev_dbg(musb->controller, "CONNECT (%s) devctl %02x\n", | 827 | dev_dbg(musb->controller, "CONNECT (%s) devctl %02x\n", |
| 746 | usb_otg_state_string(musb->xceiv->state), devctl); | 828 | usb_otg_state_string(musb->xceiv->otg->state), devctl); |
| 747 | } | 829 | } |
| 748 | 830 | ||
| 749 | if (int_usb & MUSB_INTR_DISCONNECT) { | 831 | if (int_usb & MUSB_INTR_DISCONNECT) { |
| 750 | dev_dbg(musb->controller, "DISCONNECT (%s) as %s, devctl %02x\n", | 832 | dev_dbg(musb->controller, "DISCONNECT (%s) as %s, devctl %02x\n", |
| 751 | usb_otg_state_string(musb->xceiv->state), | 833 | usb_otg_state_string(musb->xceiv->otg->state), |
| 752 | MUSB_MODE(musb), devctl); | 834 | MUSB_MODE(musb), devctl); |
| 753 | handled = IRQ_HANDLED; | 835 | handled = IRQ_HANDLED; |
| 754 | 836 | ||
| 755 | switch (musb->xceiv->state) { | 837 | switch (musb->xceiv->otg->state) { |
| 756 | case OTG_STATE_A_HOST: | 838 | case OTG_STATE_A_HOST: |
| 757 | case OTG_STATE_A_SUSPEND: | 839 | case OTG_STATE_A_SUSPEND: |
| 758 | musb_host_resume_root_hub(musb); | 840 | musb_host_resume_root_hub(musb); |
| @@ -770,7 +852,7 @@ b_host: | |||
| 770 | musb_root_disconnect(musb); | 852 | musb_root_disconnect(musb); |
| 771 | if (musb->hcd) | 853 | if (musb->hcd) |
| 772 | musb->hcd->self.is_b_host = 0; | 854 | musb->hcd->self.is_b_host = 0; |
| 773 | musb->xceiv->state = OTG_STATE_B_PERIPHERAL; | 855 | musb->xceiv->otg->state = OTG_STATE_B_PERIPHERAL; |
| 774 | MUSB_DEV_MODE(musb); | 856 | MUSB_DEV_MODE(musb); |
| 775 | musb_g_disconnect(musb); | 857 | musb_g_disconnect(musb); |
| 776 | break; | 858 | break; |
| @@ -786,7 +868,7 @@ b_host: | |||
| 786 | break; | 868 | break; |
| 787 | default: | 869 | default: |
| 788 | WARNING("unhandled DISCONNECT transition (%s)\n", | 870 | WARNING("unhandled DISCONNECT transition (%s)\n", |
| 789 | usb_otg_state_string(musb->xceiv->state)); | 871 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 790 | break; | 872 | break; |
| 791 | } | 873 | } |
| 792 | } | 874 | } |
| @@ -812,15 +894,15 @@ b_host: | |||
| 812 | } | 894 | } |
| 813 | } else { | 895 | } else { |
| 814 | dev_dbg(musb->controller, "BUS RESET as %s\n", | 896 | dev_dbg(musb->controller, "BUS RESET as %s\n", |
| 815 | usb_otg_state_string(musb->xceiv->state)); | 897 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 816 | switch (musb->xceiv->state) { | 898 | switch (musb->xceiv->otg->state) { |
| 817 | case OTG_STATE_A_SUSPEND: | 899 | case OTG_STATE_A_SUSPEND: |
| 818 | musb_g_reset(musb); | 900 | musb_g_reset(musb); |
| 819 | /* FALLTHROUGH */ | 901 | /* FALLTHROUGH */ |
| 820 | case OTG_STATE_A_WAIT_BCON: /* OPT TD.4.7-900ms */ | 902 | case OTG_STATE_A_WAIT_BCON: /* OPT TD.4.7-900ms */ |
| 821 | /* never use invalid T(a_wait_bcon) */ | 903 | /* never use invalid T(a_wait_bcon) */ |
| 822 | dev_dbg(musb->controller, "HNP: in %s, %d msec timeout\n", | 904 | dev_dbg(musb->controller, "HNP: in %s, %d msec timeout\n", |
| 823 | usb_otg_state_string(musb->xceiv->state), | 905 | usb_otg_state_string(musb->xceiv->otg->state), |
| 824 | TA_WAIT_BCON(musb)); | 906 | TA_WAIT_BCON(musb)); |
| 825 | mod_timer(&musb->otg_timer, jiffies | 907 | mod_timer(&musb->otg_timer, jiffies |
| 826 | + msecs_to_jiffies(TA_WAIT_BCON(musb))); | 908 | + msecs_to_jiffies(TA_WAIT_BCON(musb))); |
| @@ -831,27 +913,29 @@ b_host: | |||
| 831 | break; | 913 | break; |
| 832 | case OTG_STATE_B_WAIT_ACON: | 914 | case OTG_STATE_B_WAIT_ACON: |
| 833 | dev_dbg(musb->controller, "HNP: RESET (%s), to b_peripheral\n", | 915 | dev_dbg(musb->controller, "HNP: RESET (%s), to b_peripheral\n", |
| 834 | usb_otg_state_string(musb->xceiv->state)); | 916 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 835 | musb->xceiv->state = OTG_STATE_B_PERIPHERAL; | 917 | musb->xceiv->otg->state = OTG_STATE_B_PERIPHERAL; |
| 836 | musb_g_reset(musb); | 918 | musb_g_reset(musb); |
| 837 | break; | 919 | break; |
| 838 | case OTG_STATE_B_IDLE: | 920 | case OTG_STATE_B_IDLE: |
| 839 | musb->xceiv->state = OTG_STATE_B_PERIPHERAL; | 921 | musb->xceiv->otg->state = OTG_STATE_B_PERIPHERAL; |
| 840 | /* FALLTHROUGH */ | 922 | /* FALLTHROUGH */ |
| 841 | case OTG_STATE_B_PERIPHERAL: | 923 | case OTG_STATE_B_PERIPHERAL: |
| 842 | musb_g_reset(musb); | 924 | musb_g_reset(musb); |
| 843 | break; | 925 | break; |
| 844 | default: | 926 | default: |
| 845 | dev_dbg(musb->controller, "Unhandled BUS RESET as %s\n", | 927 | dev_dbg(musb->controller, "Unhandled BUS RESET as %s\n", |
| 846 | usb_otg_state_string(musb->xceiv->state)); | 928 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 847 | } | 929 | } |
| 848 | } | 930 | } |
| 849 | } | 931 | } |
| 850 | 932 | ||
| 851 | /* handle babble condition */ | 933 | /* handle babble condition */ |
| 852 | if (int_usb & MUSB_INTR_BABBLE && is_host_active(musb)) | 934 | if (int_usb & MUSB_INTR_BABBLE && is_host_active(musb)) { |
| 935 | musb_generic_disable(musb); | ||
| 853 | schedule_delayed_work(&musb->recover_work, | 936 | schedule_delayed_work(&musb->recover_work, |
| 854 | msecs_to_jiffies(100)); | 937 | msecs_to_jiffies(100)); |
| 938 | } | ||
| 855 | 939 | ||
| 856 | #if 0 | 940 | #if 0 |
| 857 | /* REVISIT ... this would be for multiplexing periodic endpoints, or | 941 | /* REVISIT ... this would be for multiplexing periodic endpoints, or |
| @@ -1032,21 +1116,7 @@ static void musb_shutdown(struct platform_device *pdev) | |||
| 1032 | * We don't currently use dynamic fifo setup capability to do anything | 1116 | * We don't currently use dynamic fifo setup capability to do anything |
| 1033 | * more than selecting one of a bunch of predefined configurations. | 1117 | * more than selecting one of a bunch of predefined configurations. |
| 1034 | */ | 1118 | */ |
| 1035 | #if defined(CONFIG_USB_MUSB_TUSB6010) \ | 1119 | static ushort fifo_mode; |
| 1036 | || defined(CONFIG_USB_MUSB_TUSB6010_MODULE) \ | ||
| 1037 | || defined(CONFIG_USB_MUSB_OMAP2PLUS) \ | ||
| 1038 | || defined(CONFIG_USB_MUSB_OMAP2PLUS_MODULE) \ | ||
| 1039 | || defined(CONFIG_USB_MUSB_AM35X) \ | ||
| 1040 | || defined(CONFIG_USB_MUSB_AM35X_MODULE) \ | ||
| 1041 | || defined(CONFIG_USB_MUSB_DSPS) \ | ||
| 1042 | || defined(CONFIG_USB_MUSB_DSPS_MODULE) | ||
| 1043 | static ushort fifo_mode = 4; | ||
| 1044 | #elif defined(CONFIG_USB_MUSB_UX500) \ | ||
| 1045 | || defined(CONFIG_USB_MUSB_UX500_MODULE) | ||
| 1046 | static ushort fifo_mode = 5; | ||
| 1047 | #else | ||
| 1048 | static ushort fifo_mode = 2; | ||
| 1049 | #endif | ||
| 1050 | 1120 | ||
| 1051 | /* "modprobe ... fifo_mode=1" etc */ | 1121 | /* "modprobe ... fifo_mode=1" etc */ |
| 1052 | module_param(fifo_mode, ushort, 0); | 1122 | module_param(fifo_mode, ushort, 0); |
| @@ -1456,20 +1526,25 @@ static int musb_core_init(u16 musb_type, struct musb *musb) | |||
| 1456 | for (i = 0; i < musb->nr_endpoints; i++) { | 1526 | for (i = 0; i < musb->nr_endpoints; i++) { |
| 1457 | struct musb_hw_ep *hw_ep = musb->endpoints + i; | 1527 | struct musb_hw_ep *hw_ep = musb->endpoints + i; |
| 1458 | 1528 | ||
| 1459 | hw_ep->fifo = MUSB_FIFO_OFFSET(i) + mbase; | 1529 | hw_ep->fifo = musb->io.fifo_offset(i) + mbase; |
| 1460 | #if defined(CONFIG_USB_MUSB_TUSB6010) || defined (CONFIG_USB_MUSB_TUSB6010_MODULE) | 1530 | #if IS_ENABLED(CONFIG_USB_MUSB_TUSB6010) |
| 1461 | hw_ep->fifo_async = musb->async + 0x400 + MUSB_FIFO_OFFSET(i); | 1531 | if (musb->io.quirks & MUSB_IN_TUSB) { |
| 1462 | hw_ep->fifo_sync = musb->sync + 0x400 + MUSB_FIFO_OFFSET(i); | 1532 | hw_ep->fifo_async = musb->async + 0x400 + |
| 1463 | hw_ep->fifo_sync_va = | 1533 | musb->io.fifo_offset(i); |
| 1464 | musb->sync_va + 0x400 + MUSB_FIFO_OFFSET(i); | 1534 | hw_ep->fifo_sync = musb->sync + 0x400 + |
| 1465 | 1535 | musb->io.fifo_offset(i); | |
| 1466 | if (i == 0) | 1536 | hw_ep->fifo_sync_va = |
| 1467 | hw_ep->conf = mbase - 0x400 + TUSB_EP0_CONF; | 1537 | musb->sync_va + 0x400 + musb->io.fifo_offset(i); |
| 1468 | else | 1538 | |
| 1469 | hw_ep->conf = mbase + 0x400 + (((i - 1) & 0xf) << 2); | 1539 | if (i == 0) |
| 1540 | hw_ep->conf = mbase - 0x400 + TUSB_EP0_CONF; | ||
| 1541 | else | ||
| 1542 | hw_ep->conf = mbase + 0x400 + | ||
| 1543 | (((i - 1) & 0xf) << 2); | ||
| 1544 | } | ||
| 1470 | #endif | 1545 | #endif |
| 1471 | 1546 | ||
| 1472 | hw_ep->regs = MUSB_EP_OFFSET(i, 0) + mbase; | 1547 | hw_ep->regs = musb->io.ep_offset(i, 0) + mbase; |
| 1473 | hw_ep->target_regs = musb_read_target_reg_base(i, mbase); | 1548 | hw_ep->target_regs = musb_read_target_reg_base(i, mbase); |
| 1474 | hw_ep->rx_reinit = 1; | 1549 | hw_ep->rx_reinit = 1; |
| 1475 | hw_ep->tx_reinit = 1; | 1550 | hw_ep->tx_reinit = 1; |
| @@ -1630,7 +1705,7 @@ musb_mode_show(struct device *dev, struct device_attribute *attr, char *buf) | |||
| 1630 | int ret = -EINVAL; | 1705 | int ret = -EINVAL; |
| 1631 | 1706 | ||
| 1632 | spin_lock_irqsave(&musb->lock, flags); | 1707 | spin_lock_irqsave(&musb->lock, flags); |
| 1633 | ret = sprintf(buf, "%s\n", usb_otg_state_string(musb->xceiv->state)); | 1708 | ret = sprintf(buf, "%s\n", usb_otg_state_string(musb->xceiv->otg->state)); |
| 1634 | spin_unlock_irqrestore(&musb->lock, flags); | 1709 | spin_unlock_irqrestore(&musb->lock, flags); |
| 1635 | 1710 | ||
| 1636 | return ret; | 1711 | return ret; |
| @@ -1675,7 +1750,7 @@ musb_vbus_store(struct device *dev, struct device_attribute *attr, | |||
| 1675 | spin_lock_irqsave(&musb->lock, flags); | 1750 | spin_lock_irqsave(&musb->lock, flags); |
| 1676 | /* force T(a_wait_bcon) to be zero/unlimited *OR* valid */ | 1751 | /* force T(a_wait_bcon) to be zero/unlimited *OR* valid */ |
| 1677 | musb->a_wait_bcon = val ? max_t(int, val, OTG_TIME_A_WAIT_BCON) : 0 ; | 1752 | musb->a_wait_bcon = val ? max_t(int, val, OTG_TIME_A_WAIT_BCON) : 0 ; |
| 1678 | if (musb->xceiv->state == OTG_STATE_A_WAIT_BCON) | 1753 | if (musb->xceiv->otg->state == OTG_STATE_A_WAIT_BCON) |
| 1679 | musb->is_active = 0; | 1754 | musb->is_active = 0; |
| 1680 | musb_platform_try_idle(musb, jiffies + msecs_to_jiffies(val)); | 1755 | musb_platform_try_idle(musb, jiffies + msecs_to_jiffies(val)); |
| 1681 | spin_unlock_irqrestore(&musb->lock, flags); | 1756 | spin_unlock_irqrestore(&musb->lock, flags); |
| @@ -1743,8 +1818,8 @@ static void musb_irq_work(struct work_struct *data) | |||
| 1743 | { | 1818 | { |
| 1744 | struct musb *musb = container_of(data, struct musb, irq_work); | 1819 | struct musb *musb = container_of(data, struct musb, irq_work); |
| 1745 | 1820 | ||
| 1746 | if (musb->xceiv->state != musb->xceiv_old_state) { | 1821 | if (musb->xceiv->otg->state != musb->xceiv_old_state) { |
| 1747 | musb->xceiv_old_state = musb->xceiv->state; | 1822 | musb->xceiv_old_state = musb->xceiv->otg->state; |
| 1748 | sysfs_notify(&musb->controller->kobj, NULL, "mode"); | 1823 | sysfs_notify(&musb->controller->kobj, NULL, "mode"); |
| 1749 | } | 1824 | } |
| 1750 | } | 1825 | } |
| @@ -1903,6 +1978,18 @@ musb_init_controller(struct device *dev, int nIrq, void __iomem *ctrl) | |||
| 1903 | musb->ops = plat->platform_ops; | 1978 | musb->ops = plat->platform_ops; |
| 1904 | musb->port_mode = plat->mode; | 1979 | musb->port_mode = plat->mode; |
| 1905 | 1980 | ||
| 1981 | /* | ||
| 1982 | * Initialize the default IO functions. At least omap2430 needs | ||
| 1983 | * these early. We initialize the platform specific IO functions | ||
| 1984 | * later on. | ||
| 1985 | */ | ||
| 1986 | musb_readb = musb_default_readb; | ||
| 1987 | musb_writeb = musb_default_writeb; | ||
| 1988 | musb_readw = musb_default_readw; | ||
| 1989 | musb_writew = musb_default_writew; | ||
| 1990 | musb_readl = musb_default_readl; | ||
| 1991 | musb_writel = musb_default_writel; | ||
| 1992 | |||
| 1906 | /* The musb_platform_init() call: | 1993 | /* The musb_platform_init() call: |
| 1907 | * - adjusts musb->mregs | 1994 | * - adjusts musb->mregs |
| 1908 | * - sets the musb->isr | 1995 | * - sets the musb->isr |
| @@ -1924,6 +2011,57 @@ musb_init_controller(struct device *dev, int nIrq, void __iomem *ctrl) | |||
| 1924 | goto fail2; | 2011 | goto fail2; |
| 1925 | } | 2012 | } |
| 1926 | 2013 | ||
| 2014 | if (musb->ops->quirks) | ||
| 2015 | musb->io.quirks = musb->ops->quirks; | ||
| 2016 | |||
| 2017 | /* At least tusb6010 has it's own offsets.. */ | ||
| 2018 | if (musb->ops->ep_offset) | ||
| 2019 | musb->io.ep_offset = musb->ops->ep_offset; | ||
| 2020 | if (musb->ops->ep_select) | ||
| 2021 | musb->io.ep_select = musb->ops->ep_select; | ||
| 2022 | |||
| 2023 | /* ..and some devices use indexed offset or flat offset */ | ||
| 2024 | if (musb->io.quirks & MUSB_INDEXED_EP) { | ||
| 2025 | musb->io.ep_offset = musb_indexed_ep_offset; | ||
| 2026 | musb->io.ep_select = musb_indexed_ep_select; | ||
| 2027 | } else { | ||
| 2028 | musb->io.ep_offset = musb_flat_ep_offset; | ||
| 2029 | musb->io.ep_select = musb_flat_ep_select; | ||
| 2030 | } | ||
| 2031 | |||
| 2032 | if (musb->ops->fifo_mode) | ||
| 2033 | fifo_mode = musb->ops->fifo_mode; | ||
| 2034 | else | ||
| 2035 | fifo_mode = 4; | ||
| 2036 | |||
| 2037 | if (musb->ops->fifo_offset) | ||
| 2038 | musb->io.fifo_offset = musb->ops->fifo_offset; | ||
| 2039 | else | ||
| 2040 | musb->io.fifo_offset = musb_default_fifo_offset; | ||
| 2041 | |||
| 2042 | if (musb->ops->readb) | ||
| 2043 | musb_readb = musb->ops->readb; | ||
| 2044 | if (musb->ops->writeb) | ||
| 2045 | musb_writeb = musb->ops->writeb; | ||
| 2046 | if (musb->ops->readw) | ||
| 2047 | musb_readw = musb->ops->readw; | ||
| 2048 | if (musb->ops->writew) | ||
| 2049 | musb_writew = musb->ops->writew; | ||
| 2050 | if (musb->ops->readl) | ||
| 2051 | musb_readl = musb->ops->readl; | ||
| 2052 | if (musb->ops->writel) | ||
| 2053 | musb_writel = musb->ops->writel; | ||
| 2054 | |||
| 2055 | if (musb->ops->read_fifo) | ||
| 2056 | musb->io.read_fifo = musb->ops->read_fifo; | ||
| 2057 | else | ||
| 2058 | musb->io.read_fifo = musb_default_read_fifo; | ||
| 2059 | |||
| 2060 | if (musb->ops->write_fifo) | ||
| 2061 | musb->io.write_fifo = musb->ops->write_fifo; | ||
| 2062 | else | ||
| 2063 | musb->io.write_fifo = musb_default_write_fifo; | ||
| 2064 | |||
| 1927 | if (!musb->xceiv->io_ops) { | 2065 | if (!musb->xceiv->io_ops) { |
| 1928 | musb->xceiv->io_dev = musb->controller; | 2066 | musb->xceiv->io_dev = musb->controller; |
| 1929 | musb->xceiv->io_priv = musb->mregs; | 2067 | musb->xceiv->io_priv = musb->mregs; |
| @@ -1983,10 +2121,10 @@ musb_init_controller(struct device *dev, int nIrq, void __iomem *ctrl) | |||
| 1983 | 2121 | ||
| 1984 | if (musb->xceiv->otg->default_a) { | 2122 | if (musb->xceiv->otg->default_a) { |
| 1985 | MUSB_HST_MODE(musb); | 2123 | MUSB_HST_MODE(musb); |
| 1986 | musb->xceiv->state = OTG_STATE_A_IDLE; | 2124 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 1987 | } else { | 2125 | } else { |
| 1988 | MUSB_DEV_MODE(musb); | 2126 | MUSB_DEV_MODE(musb); |
| 1989 | musb->xceiv->state = OTG_STATE_B_IDLE; | 2127 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 1990 | } | 2128 | } |
| 1991 | 2129 | ||
| 1992 | switch (musb->port_mode) { | 2130 | switch (musb->port_mode) { |
| @@ -2080,10 +2218,10 @@ static int musb_probe(struct platform_device *pdev) | |||
| 2080 | struct resource *iomem; | 2218 | struct resource *iomem; |
| 2081 | void __iomem *base; | 2219 | void __iomem *base; |
| 2082 | 2220 | ||
| 2083 | iomem = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 2221 | if (irq <= 0) |
| 2084 | if (!iomem || irq <= 0) | ||
| 2085 | return -ENODEV; | 2222 | return -ENODEV; |
| 2086 | 2223 | ||
| 2224 | iomem = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 2087 | base = devm_ioremap_resource(dev, iomem); | 2225 | base = devm_ioremap_resource(dev, iomem); |
| 2088 | if (IS_ERR(base)) | 2226 | if (IS_ERR(base)) |
| 2089 | return PTR_ERR(base); | 2227 | return PTR_ERR(base); |
| @@ -2297,9 +2435,11 @@ static int musb_suspend(struct device *dev) | |||
| 2297 | return 0; | 2435 | return 0; |
| 2298 | } | 2436 | } |
| 2299 | 2437 | ||
| 2300 | static int musb_resume_noirq(struct device *dev) | 2438 | static int musb_resume(struct device *dev) |
| 2301 | { | 2439 | { |
| 2302 | struct musb *musb = dev_to_musb(dev); | 2440 | struct musb *musb = dev_to_musb(dev); |
| 2441 | u8 devctl; | ||
| 2442 | u8 mask; | ||
| 2303 | 2443 | ||
| 2304 | /* | 2444 | /* |
| 2305 | * For static cmos like DaVinci, register values were preserved | 2445 | * For static cmos like DaVinci, register values were preserved |
| @@ -2313,6 +2453,23 @@ static int musb_resume_noirq(struct device *dev) | |||
| 2313 | 2453 | ||
| 2314 | musb_restore_context(musb); | 2454 | musb_restore_context(musb); |
| 2315 | 2455 | ||
| 2456 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); | ||
| 2457 | mask = MUSB_DEVCTL_BDEVICE | MUSB_DEVCTL_FSDEV | MUSB_DEVCTL_LSDEV; | ||
| 2458 | if ((devctl & mask) != (musb->context.devctl & mask)) | ||
| 2459 | musb->port1_status = 0; | ||
| 2460 | if (musb->need_finish_resume) { | ||
| 2461 | musb->need_finish_resume = 0; | ||
| 2462 | schedule_delayed_work(&musb->finish_resume_work, | ||
| 2463 | msecs_to_jiffies(20)); | ||
| 2464 | } | ||
| 2465 | |||
| 2466 | /* | ||
| 2467 | * The USB HUB code expects the device to be in RPM_ACTIVE once it came | ||
| 2468 | * out of suspend | ||
| 2469 | */ | ||
| 2470 | pm_runtime_disable(dev); | ||
| 2471 | pm_runtime_set_active(dev); | ||
| 2472 | pm_runtime_enable(dev); | ||
| 2316 | return 0; | 2473 | return 0; |
| 2317 | } | 2474 | } |
| 2318 | 2475 | ||
| @@ -2348,7 +2505,7 @@ static int musb_runtime_resume(struct device *dev) | |||
| 2348 | 2505 | ||
| 2349 | static const struct dev_pm_ops musb_dev_pm_ops = { | 2506 | static const struct dev_pm_ops musb_dev_pm_ops = { |
| 2350 | .suspend = musb_suspend, | 2507 | .suspend = musb_suspend, |
| 2351 | .resume_noirq = musb_resume_noirq, | 2508 | .resume = musb_resume, |
| 2352 | .runtime_suspend = musb_runtime_suspend, | 2509 | .runtime_suspend = musb_runtime_suspend, |
| 2353 | .runtime_resume = musb_runtime_resume, | 2510 | .runtime_resume = musb_runtime_resume, |
| 2354 | }; | 2511 | }; |
diff --git a/drivers/usb/musb/musb_core.h b/drivers/usb/musb/musb_core.h index 414e57a984bb..5e65958f7915 100644 --- a/drivers/usb/musb/musb_core.h +++ b/drivers/usb/musb/musb_core.h | |||
| @@ -124,41 +124,6 @@ enum musb_g_ep0_state { | |||
| 124 | #define OTG_TIME_A_AIDL_BDIS 200 /* min 200 msec */ | 124 | #define OTG_TIME_A_AIDL_BDIS 200 /* min 200 msec */ |
| 125 | #define OTG_TIME_B_ASE0_BRST 100 /* min 3.125 ms */ | 125 | #define OTG_TIME_B_ASE0_BRST 100 /* min 3.125 ms */ |
| 126 | 126 | ||
| 127 | |||
| 128 | /*************************** REGISTER ACCESS ********************************/ | ||
| 129 | |||
| 130 | /* Endpoint registers (other than dynfifo setup) can be accessed either | ||
| 131 | * directly with the "flat" model, or after setting up an index register. | ||
| 132 | */ | ||
| 133 | |||
| 134 | #if defined(CONFIG_ARCH_DAVINCI) || defined(CONFIG_SOC_OMAP2430) \ | ||
| 135 | || defined(CONFIG_SOC_OMAP3430) || defined(CONFIG_BLACKFIN) \ | ||
| 136 | || defined(CONFIG_ARCH_OMAP4) | ||
| 137 | /* REVISIT indexed access seemed to | ||
| 138 | * misbehave (on DaVinci) for at least peripheral IN ... | ||
| 139 | */ | ||
| 140 | #define MUSB_FLAT_REG | ||
| 141 | #endif | ||
| 142 | |||
| 143 | /* TUSB mapping: "flat" plus ep0 special cases */ | ||
| 144 | #if defined(CONFIG_USB_MUSB_TUSB6010) || \ | ||
| 145 | defined(CONFIG_USB_MUSB_TUSB6010_MODULE) | ||
| 146 | #define musb_ep_select(_mbase, _epnum) \ | ||
| 147 | musb_writeb((_mbase), MUSB_INDEX, (_epnum)) | ||
| 148 | #define MUSB_EP_OFFSET MUSB_TUSB_OFFSET | ||
| 149 | |||
| 150 | /* "flat" mapping: each endpoint has its own i/o address */ | ||
| 151 | #elif defined(MUSB_FLAT_REG) | ||
| 152 | #define musb_ep_select(_mbase, _epnum) (((void)(_mbase)), ((void)(_epnum))) | ||
| 153 | #define MUSB_EP_OFFSET MUSB_FLAT_OFFSET | ||
| 154 | |||
| 155 | /* "indexed" mapping: INDEX register controls register bank select */ | ||
| 156 | #else | ||
| 157 | #define musb_ep_select(_mbase, _epnum) \ | ||
| 158 | musb_writeb((_mbase), MUSB_INDEX, (_epnum)) | ||
| 159 | #define MUSB_EP_OFFSET MUSB_INDEXED_OFFSET | ||
| 160 | #endif | ||
| 161 | |||
| 162 | /****************************** FUNCTIONS ********************************/ | 127 | /****************************** FUNCTIONS ********************************/ |
| 163 | 128 | ||
| 164 | #define MUSB_HST_MODE(_musb)\ | 129 | #define MUSB_HST_MODE(_musb)\ |
| @@ -173,8 +138,25 @@ enum musb_g_ep0_state { | |||
| 173 | 138 | ||
| 174 | /******************************** TYPES *************************************/ | 139 | /******************************** TYPES *************************************/ |
| 175 | 140 | ||
| 141 | struct musb_io; | ||
| 142 | |||
| 176 | /** | 143 | /** |
| 177 | * struct musb_platform_ops - Operations passed to musb_core by HW glue layer | 144 | * struct musb_platform_ops - Operations passed to musb_core by HW glue layer |
| 145 | * @quirks: flags for platform specific quirks | ||
| 146 | * @enable: enable device | ||
| 147 | * @disable: disable device | ||
| 148 | * @ep_offset: returns the end point offset | ||
| 149 | * @ep_select: selects the specified end point | ||
| 150 | * @fifo_mode: sets the fifo mode | ||
| 151 | * @fifo_offset: returns the fifo offset | ||
| 152 | * @readb: read 8 bits | ||
| 153 | * @writeb: write 8 bits | ||
| 154 | * @readw: read 16 bits | ||
| 155 | * @writew: write 16 bits | ||
| 156 | * @readl: read 32 bits | ||
| 157 | * @writel: write 32 bits | ||
| 158 | * @read_fifo: reads the fifo | ||
| 159 | * @write_fifo: writes to fifo | ||
| 178 | * @init: turns on clocks, sets up platform-specific registers, etc | 160 | * @init: turns on clocks, sets up platform-specific registers, etc |
| 179 | * @exit: undoes @init | 161 | * @exit: undoes @init |
| 180 | * @set_mode: forcefully changes operating mode | 162 | * @set_mode: forcefully changes operating mode |
| @@ -184,12 +166,34 @@ enum musb_g_ep0_state { | |||
| 184 | * @adjust_channel_params: pre check for standard dma channel_program func | 166 | * @adjust_channel_params: pre check for standard dma channel_program func |
| 185 | */ | 167 | */ |
| 186 | struct musb_platform_ops { | 168 | struct musb_platform_ops { |
| 169 | |||
| 170 | #define MUSB_DMA_UX500 BIT(6) | ||
| 171 | #define MUSB_DMA_CPPI41 BIT(5) | ||
| 172 | #define MUSB_DMA_CPPI BIT(4) | ||
| 173 | #define MUSB_DMA_TUSB_OMAP BIT(3) | ||
| 174 | #define MUSB_DMA_INVENTRA BIT(2) | ||
| 175 | #define MUSB_IN_TUSB BIT(1) | ||
| 176 | #define MUSB_INDEXED_EP BIT(0) | ||
| 177 | u32 quirks; | ||
| 178 | |||
| 187 | int (*init)(struct musb *musb); | 179 | int (*init)(struct musb *musb); |
| 188 | int (*exit)(struct musb *musb); | 180 | int (*exit)(struct musb *musb); |
| 189 | 181 | ||
| 190 | void (*enable)(struct musb *musb); | 182 | void (*enable)(struct musb *musb); |
| 191 | void (*disable)(struct musb *musb); | 183 | void (*disable)(struct musb *musb); |
| 192 | 184 | ||
| 185 | u32 (*ep_offset)(u8 epnum, u16 offset); | ||
| 186 | void (*ep_select)(void __iomem *mbase, u8 epnum); | ||
| 187 | u16 fifo_mode; | ||
| 188 | u32 (*fifo_offset)(u8 epnum); | ||
| 189 | u8 (*readb)(const void __iomem *addr, unsigned offset); | ||
| 190 | void (*writeb)(void __iomem *addr, unsigned offset, u8 data); | ||
| 191 | u16 (*readw)(const void __iomem *addr, unsigned offset); | ||
| 192 | void (*writew)(void __iomem *addr, unsigned offset, u16 data); | ||
| 193 | u32 (*readl)(const void __iomem *addr, unsigned offset); | ||
| 194 | void (*writel)(void __iomem *addr, unsigned offset, u32 data); | ||
| 195 | void (*read_fifo)(struct musb_hw_ep *hw_ep, u16 len, u8 *buf); | ||
| 196 | void (*write_fifo)(struct musb_hw_ep *hw_ep, u16 len, const u8 *buf); | ||
| 193 | int (*set_mode)(struct musb *musb, u8 mode); | 197 | int (*set_mode)(struct musb *musb, u8 mode); |
| 194 | void (*try_idle)(struct musb *musb, unsigned long timeout); | 198 | void (*try_idle)(struct musb *musb, unsigned long timeout); |
| 195 | int (*reset)(struct musb *musb); | 199 | int (*reset)(struct musb *musb); |
| @@ -212,8 +216,7 @@ struct musb_hw_ep { | |||
| 212 | void __iomem *fifo; | 216 | void __iomem *fifo; |
| 213 | void __iomem *regs; | 217 | void __iomem *regs; |
| 214 | 218 | ||
| 215 | #if defined(CONFIG_USB_MUSB_TUSB6010) || \ | 219 | #if IS_ENABLED(CONFIG_USB_MUSB_TUSB6010) |
| 216 | defined(CONFIG_USB_MUSB_TUSB6010_MODULE) | ||
| 217 | void __iomem *conf; | 220 | void __iomem *conf; |
| 218 | #endif | 221 | #endif |
| 219 | 222 | ||
| @@ -230,8 +233,7 @@ struct musb_hw_ep { | |||
| 230 | struct dma_channel *tx_channel; | 233 | struct dma_channel *tx_channel; |
| 231 | struct dma_channel *rx_channel; | 234 | struct dma_channel *rx_channel; |
| 232 | 235 | ||
| 233 | #if defined(CONFIG_USB_MUSB_TUSB6010) || \ | 236 | #if IS_ENABLED(CONFIG_USB_MUSB_TUSB6010) |
| 234 | defined(CONFIG_USB_MUSB_TUSB6010_MODULE) | ||
| 235 | /* TUSB has "asynchronous" and "synchronous" dma modes */ | 237 | /* TUSB has "asynchronous" and "synchronous" dma modes */ |
| 236 | dma_addr_t fifo_async; | 238 | dma_addr_t fifo_async; |
| 237 | dma_addr_t fifo_sync; | 239 | dma_addr_t fifo_sync; |
| @@ -292,6 +294,7 @@ struct musb { | |||
| 292 | /* device lock */ | 294 | /* device lock */ |
| 293 | spinlock_t lock; | 295 | spinlock_t lock; |
| 294 | 296 | ||
| 297 | struct musb_io io; | ||
| 295 | const struct musb_platform_ops *ops; | 298 | const struct musb_platform_ops *ops; |
| 296 | struct musb_context_registers context; | 299 | struct musb_context_registers context; |
| 297 | 300 | ||
| @@ -334,8 +337,7 @@ struct musb { | |||
| 334 | void __iomem *ctrl_base; | 337 | void __iomem *ctrl_base; |
| 335 | void __iomem *mregs; | 338 | void __iomem *mregs; |
| 336 | 339 | ||
| 337 | #if defined(CONFIG_USB_MUSB_TUSB6010) || \ | 340 | #if IS_ENABLED(CONFIG_USB_MUSB_TUSB6010) |
| 338 | defined(CONFIG_USB_MUSB_TUSB6010_MODULE) | ||
| 339 | dma_addr_t async; | 341 | dma_addr_t async; |
| 340 | dma_addr_t sync; | 342 | dma_addr_t sync; |
| 341 | void __iomem *sync_va; | 343 | void __iomem *sync_va; |
| @@ -390,6 +392,7 @@ struct musb { | |||
| 390 | 392 | ||
| 391 | /* is_suspended means USB B_PERIPHERAL suspend */ | 393 | /* is_suspended means USB B_PERIPHERAL suspend */ |
| 392 | unsigned is_suspended:1; | 394 | unsigned is_suspended:1; |
| 395 | unsigned need_finish_resume :1; | ||
| 393 | 396 | ||
| 394 | /* may_wakeup means remote wakeup is enabled */ | 397 | /* may_wakeup means remote wakeup is enabled */ |
| 395 | unsigned may_wakeup:1; | 398 | unsigned may_wakeup:1; |
| @@ -474,7 +477,7 @@ static inline int musb_read_fifosize(struct musb *musb, | |||
| 474 | u8 reg = 0; | 477 | u8 reg = 0; |
| 475 | 478 | ||
| 476 | /* read from core using indexed model */ | 479 | /* read from core using indexed model */ |
| 477 | reg = musb_readb(mbase, MUSB_EP_OFFSET(epnum, MUSB_FIFOSIZE)); | 480 | reg = musb_readb(mbase, musb->io.ep_offset(epnum, MUSB_FIFOSIZE)); |
| 478 | /* 0's returned when no more endpoints */ | 481 | /* 0's returned when no more endpoints */ |
| 479 | if (!reg) | 482 | if (!reg) |
| 480 | return -ENODEV; | 483 | return -ENODEV; |
diff --git a/drivers/usb/musb/musb_cppi41.c b/drivers/usb/musb/musb_cppi41.c index 5a9b977fbc19..f64fd964dc6d 100644 --- a/drivers/usb/musb/musb_cppi41.c +++ b/drivers/usb/musb/musb_cppi41.c | |||
| @@ -253,6 +253,7 @@ static void cppi41_dma_callback(void *private_data) | |||
| 253 | cppi41_trans_done(cppi41_channel); | 253 | cppi41_trans_done(cppi41_channel); |
| 254 | } else { | 254 | } else { |
| 255 | struct cppi41_dma_controller *controller; | 255 | struct cppi41_dma_controller *controller; |
| 256 | int is_hs = 0; | ||
| 256 | /* | 257 | /* |
| 257 | * On AM335x it has been observed that the TX interrupt fires | 258 | * On AM335x it has been observed that the TX interrupt fires |
| 258 | * too early that means the TXFIFO is not yet empty but the DMA | 259 | * too early that means the TXFIFO is not yet empty but the DMA |
| @@ -265,7 +266,14 @@ static void cppi41_dma_callback(void *private_data) | |||
| 265 | */ | 266 | */ |
| 266 | controller = cppi41_channel->controller; | 267 | controller = cppi41_channel->controller; |
| 267 | 268 | ||
| 268 | if (musb->g.speed == USB_SPEED_HIGH) { | 269 | if (is_host_active(musb)) { |
| 270 | if (musb->port1_status & USB_PORT_STAT_HIGH_SPEED) | ||
| 271 | is_hs = 1; | ||
| 272 | } else { | ||
| 273 | if (musb->g.speed == USB_SPEED_HIGH) | ||
| 274 | is_hs = 1; | ||
| 275 | } | ||
| 276 | if (is_hs) { | ||
| 269 | unsigned wait = 25; | 277 | unsigned wait = 25; |
| 270 | 278 | ||
| 271 | do { | 279 | do { |
diff --git a/drivers/usb/musb/musb_debugfs.c b/drivers/usb/musb/musb_debugfs.c index 4c216790e86b..ad3701a97389 100644 --- a/drivers/usb/musb/musb_debugfs.c +++ b/drivers/usb/musb/musb_debugfs.c | |||
| @@ -49,33 +49,36 @@ struct musb_register_map { | |||
| 49 | }; | 49 | }; |
| 50 | 50 | ||
| 51 | static const struct musb_register_map musb_regmap[] = { | 51 | static const struct musb_register_map musb_regmap[] = { |
| 52 | { "FAddr", 0x00, 8 }, | 52 | { "FAddr", MUSB_FADDR, 8 }, |
| 53 | { "Power", 0x01, 8 }, | 53 | { "Power", MUSB_POWER, 8 }, |
| 54 | { "Frame", 0x0c, 16 }, | 54 | { "Frame", MUSB_FRAME, 16 }, |
| 55 | { "Index", 0x0e, 8 }, | 55 | { "Index", MUSB_INDEX, 8 }, |
| 56 | { "Testmode", 0x0f, 8 }, | 56 | { "Testmode", MUSB_TESTMODE, 8 }, |
| 57 | { "TxMaxPp", 0x10, 16 }, | 57 | { "TxMaxPp", MUSB_TXMAXP, 16 }, |
| 58 | { "TxCSRp", 0x12, 16 }, | 58 | { "TxCSRp", MUSB_TXCSR, 16 }, |
| 59 | { "RxMaxPp", 0x14, 16 }, | 59 | { "RxMaxPp", MUSB_RXMAXP, 16 }, |
| 60 | { "RxCSR", 0x16, 16 }, | 60 | { "RxCSR", MUSB_RXCSR, 16 }, |
| 61 | { "RxCount", 0x18, 16 }, | 61 | { "RxCount", MUSB_RXCOUNT, 16 }, |
| 62 | { "ConfigData", 0x1f, 8 }, | 62 | { "ConfigData", MUSB_CONFIGDATA,8 }, |
| 63 | { "DevCtl", 0x60, 8 }, | 63 | { "IntrRxE", MUSB_INTRRXE, 16 }, |
| 64 | { "MISC", 0x61, 8 }, | 64 | { "IntrTxE", MUSB_INTRTXE, 16 }, |
| 65 | { "TxFIFOsz", 0x62, 8 }, | 65 | { "IntrUsbE", MUSB_INTRUSBE, 8 }, |
| 66 | { "RxFIFOsz", 0x63, 8 }, | 66 | { "DevCtl", MUSB_DEVCTL, 8 }, |
| 67 | { "TxFIFOadd", 0x64, 16 }, | 67 | { "BabbleCtl", MUSB_BABBLE_CTL,8 }, |
| 68 | { "RxFIFOadd", 0x66, 16 }, | 68 | { "TxFIFOsz", MUSB_TXFIFOSZ, 8 }, |
| 69 | { "VControl", 0x68, 32 }, | 69 | { "RxFIFOsz", MUSB_RXFIFOSZ, 8 }, |
| 70 | { "HWVers", 0x6C, 16 }, | 70 | { "TxFIFOadd", MUSB_TXFIFOADD, 16 }, |
| 71 | { "EPInfo", 0x78, 8 }, | 71 | { "RxFIFOadd", MUSB_RXFIFOADD, 16 }, |
| 72 | { "RAMInfo", 0x79, 8 }, | 72 | { "VControl", 0x68, 32 }, |
| 73 | { "LinkInfo", 0x7A, 8 }, | 73 | { "HWVers", 0x69, 16 }, |
| 74 | { "VPLen", 0x7B, 8 }, | 74 | { "EPInfo", MUSB_EPINFO, 8 }, |
| 75 | { "HS_EOF1", 0x7C, 8 }, | 75 | { "RAMInfo", MUSB_RAMINFO, 8 }, |
| 76 | { "FS_EOF1", 0x7D, 8 }, | 76 | { "LinkInfo", MUSB_LINKINFO, 8 }, |
| 77 | { "LS_EOF1", 0x7E, 8 }, | 77 | { "VPLen", MUSB_VPLEN, 8 }, |
| 78 | { "SOFT_RST", 0x7F, 8 }, | 78 | { "HS_EOF1", MUSB_HS_EOF1, 8 }, |
| 79 | { "FS_EOF1", MUSB_FS_EOF1, 8 }, | ||
| 80 | { "LS_EOF1", MUSB_LS_EOF1, 8 }, | ||
| 81 | { "SOFT_RST", 0x7F, 8 }, | ||
| 79 | { "DMA_CNTLch0", 0x204, 16 }, | 82 | { "DMA_CNTLch0", 0x204, 16 }, |
| 80 | { "DMA_ADDRch0", 0x208, 32 }, | 83 | { "DMA_ADDRch0", 0x208, 32 }, |
| 81 | { "DMA_COUNTch0", 0x20C, 32 }, | 84 | { "DMA_COUNTch0", 0x20C, 32 }, |
diff --git a/drivers/usb/musb/musb_dsps.c b/drivers/usb/musb/musb_dsps.c index 48bc09e7b83b..53bd0e71d19f 100644 --- a/drivers/usb/musb/musb_dsps.c +++ b/drivers/usb/musb/musb_dsps.c | |||
| @@ -179,9 +179,9 @@ static void dsps_musb_try_idle(struct musb *musb, unsigned long timeout) | |||
| 179 | 179 | ||
| 180 | /* Never idle if active, or when VBUS timeout is not set as host */ | 180 | /* Never idle if active, or when VBUS timeout is not set as host */ |
| 181 | if (musb->is_active || (musb->a_wait_bcon == 0 && | 181 | if (musb->is_active || (musb->a_wait_bcon == 0 && |
| 182 | musb->xceiv->state == OTG_STATE_A_WAIT_BCON)) { | 182 | musb->xceiv->otg->state == OTG_STATE_A_WAIT_BCON)) { |
| 183 | dev_dbg(musb->controller, "%s active, deleting timer\n", | 183 | dev_dbg(musb->controller, "%s active, deleting timer\n", |
| 184 | usb_otg_state_string(musb->xceiv->state)); | 184 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 185 | del_timer(&glue->timer); | 185 | del_timer(&glue->timer); |
| 186 | glue->last_timer = jiffies; | 186 | glue->last_timer = jiffies; |
| 187 | return; | 187 | return; |
| @@ -201,7 +201,7 @@ static void dsps_musb_try_idle(struct musb *musb, unsigned long timeout) | |||
| 201 | glue->last_timer = timeout; | 201 | glue->last_timer = timeout; |
| 202 | 202 | ||
| 203 | dev_dbg(musb->controller, "%s inactive, starting idle timer for %u ms\n", | 203 | dev_dbg(musb->controller, "%s inactive, starting idle timer for %u ms\n", |
| 204 | usb_otg_state_string(musb->xceiv->state), | 204 | usb_otg_state_string(musb->xceiv->otg->state), |
| 205 | jiffies_to_msecs(timeout - jiffies)); | 205 | jiffies_to_msecs(timeout - jiffies)); |
| 206 | mod_timer(&glue->timer, timeout); | 206 | mod_timer(&glue->timer, timeout); |
| 207 | } | 207 | } |
| @@ -265,10 +265,10 @@ static void otg_timer(unsigned long _musb) | |||
| 265 | */ | 265 | */ |
| 266 | devctl = dsps_readb(mregs, MUSB_DEVCTL); | 266 | devctl = dsps_readb(mregs, MUSB_DEVCTL); |
| 267 | dev_dbg(musb->controller, "Poll devctl %02x (%s)\n", devctl, | 267 | dev_dbg(musb->controller, "Poll devctl %02x (%s)\n", devctl, |
| 268 | usb_otg_state_string(musb->xceiv->state)); | 268 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 269 | 269 | ||
| 270 | spin_lock_irqsave(&musb->lock, flags); | 270 | spin_lock_irqsave(&musb->lock, flags); |
| 271 | switch (musb->xceiv->state) { | 271 | switch (musb->xceiv->otg->state) { |
| 272 | case OTG_STATE_A_WAIT_BCON: | 272 | case OTG_STATE_A_WAIT_BCON: |
| 273 | dsps_writeb(musb->mregs, MUSB_DEVCTL, 0); | 273 | dsps_writeb(musb->mregs, MUSB_DEVCTL, 0); |
| 274 | skip_session = 1; | 274 | skip_session = 1; |
| @@ -277,10 +277,10 @@ static void otg_timer(unsigned long _musb) | |||
| 277 | case OTG_STATE_A_IDLE: | 277 | case OTG_STATE_A_IDLE: |
| 278 | case OTG_STATE_B_IDLE: | 278 | case OTG_STATE_B_IDLE: |
| 279 | if (devctl & MUSB_DEVCTL_BDEVICE) { | 279 | if (devctl & MUSB_DEVCTL_BDEVICE) { |
| 280 | musb->xceiv->state = OTG_STATE_B_IDLE; | 280 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 281 | MUSB_DEV_MODE(musb); | 281 | MUSB_DEV_MODE(musb); |
| 282 | } else { | 282 | } else { |
| 283 | musb->xceiv->state = OTG_STATE_A_IDLE; | 283 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 284 | MUSB_HST_MODE(musb); | 284 | MUSB_HST_MODE(musb); |
| 285 | } | 285 | } |
| 286 | if (!(devctl & MUSB_DEVCTL_SESSION) && !skip_session) | 286 | if (!(devctl & MUSB_DEVCTL_SESSION) && !skip_session) |
| @@ -288,7 +288,7 @@ static void otg_timer(unsigned long _musb) | |||
| 288 | mod_timer(&glue->timer, jiffies + wrp->poll_seconds * HZ); | 288 | mod_timer(&glue->timer, jiffies + wrp->poll_seconds * HZ); |
| 289 | break; | 289 | break; |
| 290 | case OTG_STATE_A_WAIT_VFALL: | 290 | case OTG_STATE_A_WAIT_VFALL: |
| 291 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 291 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 292 | dsps_writel(musb->ctrl_base, wrp->coreintr_set, | 292 | dsps_writel(musb->ctrl_base, wrp->coreintr_set, |
| 293 | MUSB_INTR_VBUSERROR << wrp->usb_shift); | 293 | MUSB_INTR_VBUSERROR << wrp->usb_shift); |
| 294 | break; | 294 | break; |
| @@ -373,26 +373,26 @@ static irqreturn_t dsps_interrupt(int irq, void *hci) | |||
| 373 | * devctl. | 373 | * devctl. |
| 374 | */ | 374 | */ |
| 375 | musb->int_usb &= ~MUSB_INTR_VBUSERROR; | 375 | musb->int_usb &= ~MUSB_INTR_VBUSERROR; |
| 376 | musb->xceiv->state = OTG_STATE_A_WAIT_VFALL; | 376 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VFALL; |
| 377 | mod_timer(&glue->timer, | 377 | mod_timer(&glue->timer, |
| 378 | jiffies + wrp->poll_seconds * HZ); | 378 | jiffies + wrp->poll_seconds * HZ); |
| 379 | WARNING("VBUS error workaround (delay coming)\n"); | 379 | WARNING("VBUS error workaround (delay coming)\n"); |
| 380 | } else if (drvvbus) { | 380 | } else if (drvvbus) { |
| 381 | MUSB_HST_MODE(musb); | 381 | MUSB_HST_MODE(musb); |
| 382 | musb->xceiv->otg->default_a = 1; | 382 | musb->xceiv->otg->default_a = 1; |
| 383 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 383 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 384 | del_timer(&glue->timer); | 384 | del_timer(&glue->timer); |
| 385 | } else { | 385 | } else { |
| 386 | musb->is_active = 0; | 386 | musb->is_active = 0; |
| 387 | MUSB_DEV_MODE(musb); | 387 | MUSB_DEV_MODE(musb); |
| 388 | musb->xceiv->otg->default_a = 0; | 388 | musb->xceiv->otg->default_a = 0; |
| 389 | musb->xceiv->state = OTG_STATE_B_IDLE; | 389 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 390 | } | 390 | } |
| 391 | 391 | ||
| 392 | /* NOTE: this must complete power-on within 100 ms. */ | 392 | /* NOTE: this must complete power-on within 100 ms. */ |
| 393 | dev_dbg(musb->controller, "VBUS %s (%s)%s, devctl %02x\n", | 393 | dev_dbg(musb->controller, "VBUS %s (%s)%s, devctl %02x\n", |
| 394 | drvvbus ? "on" : "off", | 394 | drvvbus ? "on" : "off", |
| 395 | usb_otg_state_string(musb->xceiv->state), | 395 | usb_otg_state_string(musb->xceiv->otg->state), |
| 396 | err ? " ERROR" : "", | 396 | err ? " ERROR" : "", |
| 397 | devctl); | 397 | devctl); |
| 398 | ret = IRQ_HANDLED; | 398 | ret = IRQ_HANDLED; |
| @@ -402,7 +402,7 @@ static irqreturn_t dsps_interrupt(int irq, void *hci) | |||
| 402 | ret |= musb_interrupt(musb); | 402 | ret |= musb_interrupt(musb); |
| 403 | 403 | ||
| 404 | /* Poll for ID change in OTG port mode */ | 404 | /* Poll for ID change in OTG port mode */ |
| 405 | if (musb->xceiv->state == OTG_STATE_B_IDLE && | 405 | if (musb->xceiv->otg->state == OTG_STATE_B_IDLE && |
| 406 | musb->port_mode == MUSB_PORT_MODE_DUAL_ROLE) | 406 | musb->port_mode == MUSB_PORT_MODE_DUAL_ROLE) |
| 407 | mod_timer(&glue->timer, jiffies + wrp->poll_seconds * HZ); | 407 | mod_timer(&glue->timer, jiffies + wrp->poll_seconds * HZ); |
| 408 | out: | 408 | out: |
| @@ -447,9 +447,6 @@ static int dsps_musb_init(struct musb *musb) | |||
| 447 | int ret; | 447 | int ret; |
| 448 | 448 | ||
| 449 | r = platform_get_resource_byname(parent, IORESOURCE_MEM, "control"); | 449 | r = platform_get_resource_byname(parent, IORESOURCE_MEM, "control"); |
| 450 | if (!r) | ||
| 451 | return -EINVAL; | ||
| 452 | |||
| 453 | reg_base = devm_ioremap_resource(dev, r); | 450 | reg_base = devm_ioremap_resource(dev, r); |
| 454 | if (IS_ERR(reg_base)) | 451 | if (IS_ERR(reg_base)) |
| 455 | return PTR_ERR(reg_base); | 452 | return PTR_ERR(reg_base); |
| @@ -636,6 +633,7 @@ static int dsps_musb_reset(struct musb *musb) | |||
| 636 | } | 633 | } |
| 637 | 634 | ||
| 638 | static struct musb_platform_ops dsps_ops = { | 635 | static struct musb_platform_ops dsps_ops = { |
| 636 | .quirks = MUSB_INDEXED_EP, | ||
| 639 | .init = dsps_musb_init, | 637 | .init = dsps_musb_init, |
| 640 | .exit = dsps_musb_exit, | 638 | .exit = dsps_musb_exit, |
| 641 | 639 | ||
| @@ -729,7 +727,6 @@ static int dsps_create_musb_pdev(struct dsps_glue *glue, | |||
| 729 | 727 | ||
| 730 | config = devm_kzalloc(&parent->dev, sizeof(*config), GFP_KERNEL); | 728 | config = devm_kzalloc(&parent->dev, sizeof(*config), GFP_KERNEL); |
| 731 | if (!config) { | 729 | if (!config) { |
| 732 | dev_err(dev, "failed to allocate musb hdrc config\n"); | ||
| 733 | ret = -ENOMEM; | 730 | ret = -ENOMEM; |
| 734 | goto err; | 731 | goto err; |
| 735 | } | 732 | } |
| @@ -781,10 +778,8 @@ static int dsps_probe(struct platform_device *pdev) | |||
| 781 | 778 | ||
| 782 | /* allocate glue */ | 779 | /* allocate glue */ |
| 783 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); | 780 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); |
| 784 | if (!glue) { | 781 | if (!glue) |
| 785 | dev_err(&pdev->dev, "unable to allocate glue memory\n"); | ||
| 786 | return -ENOMEM; | 782 | return -ENOMEM; |
| 787 | } | ||
| 788 | 783 | ||
| 789 | glue->dev = &pdev->dev; | 784 | glue->dev = &pdev->dev; |
| 790 | glue->wrp = wrp; | 785 | glue->wrp = wrp; |
| @@ -906,7 +901,7 @@ static int dsps_resume(struct device *dev) | |||
| 906 | dsps_writel(mbase, wrp->mode, glue->context.mode); | 901 | dsps_writel(mbase, wrp->mode, glue->context.mode); |
| 907 | dsps_writel(mbase, wrp->tx_mode, glue->context.tx_mode); | 902 | dsps_writel(mbase, wrp->tx_mode, glue->context.tx_mode); |
| 908 | dsps_writel(mbase, wrp->rx_mode, glue->context.rx_mode); | 903 | dsps_writel(mbase, wrp->rx_mode, glue->context.rx_mode); |
| 909 | if (musb->xceiv->state == OTG_STATE_B_IDLE && | 904 | if (musb->xceiv->otg->state == OTG_STATE_B_IDLE && |
| 910 | musb->port_mode == MUSB_PORT_MODE_DUAL_ROLE) | 905 | musb->port_mode == MUSB_PORT_MODE_DUAL_ROLE) |
| 911 | mod_timer(&glue->timer, jiffies + wrp->poll_seconds * HZ); | 906 | mod_timer(&glue->timer, jiffies + wrp->poll_seconds * HZ); |
| 912 | 907 | ||
diff --git a/drivers/usb/musb/musb_gadget.c b/drivers/usb/musb/musb_gadget.c index 24c8c0219790..49b04cb6f5ca 100644 --- a/drivers/usb/musb/musb_gadget.c +++ b/drivers/usb/musb/musb_gadget.c | |||
| @@ -1546,7 +1546,7 @@ static int musb_gadget_wakeup(struct usb_gadget *gadget) | |||
| 1546 | 1546 | ||
| 1547 | spin_lock_irqsave(&musb->lock, flags); | 1547 | spin_lock_irqsave(&musb->lock, flags); |
| 1548 | 1548 | ||
| 1549 | switch (musb->xceiv->state) { | 1549 | switch (musb->xceiv->otg->state) { |
| 1550 | case OTG_STATE_B_PERIPHERAL: | 1550 | case OTG_STATE_B_PERIPHERAL: |
| 1551 | /* NOTE: OTG state machine doesn't include B_SUSPENDED; | 1551 | /* NOTE: OTG state machine doesn't include B_SUSPENDED; |
| 1552 | * that's part of the standard usb 1.1 state machine, and | 1552 | * that's part of the standard usb 1.1 state machine, and |
| @@ -1587,7 +1587,7 @@ static int musb_gadget_wakeup(struct usb_gadget *gadget) | |||
| 1587 | goto done; | 1587 | goto done; |
| 1588 | default: | 1588 | default: |
| 1589 | dev_dbg(musb->controller, "Unhandled wake: %s\n", | 1589 | dev_dbg(musb->controller, "Unhandled wake: %s\n", |
| 1590 | usb_otg_state_string(musb->xceiv->state)); | 1590 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 1591 | goto done; | 1591 | goto done; |
| 1592 | } | 1592 | } |
| 1593 | 1593 | ||
| @@ -1684,8 +1684,7 @@ static int musb_gadget_pullup(struct usb_gadget *gadget, int is_on) | |||
| 1684 | 1684 | ||
| 1685 | static int musb_gadget_start(struct usb_gadget *g, | 1685 | static int musb_gadget_start(struct usb_gadget *g, |
| 1686 | struct usb_gadget_driver *driver); | 1686 | struct usb_gadget_driver *driver); |
| 1687 | static int musb_gadget_stop(struct usb_gadget *g, | 1687 | static int musb_gadget_stop(struct usb_gadget *g); |
| 1688 | struct usb_gadget_driver *driver); | ||
| 1689 | 1688 | ||
| 1690 | static const struct usb_gadget_ops musb_gadget_operations = { | 1689 | static const struct usb_gadget_ops musb_gadget_operations = { |
| 1691 | .get_frame = musb_gadget_get_frame, | 1690 | .get_frame = musb_gadget_get_frame, |
| @@ -1792,7 +1791,7 @@ int musb_gadget_setup(struct musb *musb) | |||
| 1792 | 1791 | ||
| 1793 | MUSB_DEV_MODE(musb); | 1792 | MUSB_DEV_MODE(musb); |
| 1794 | musb->xceiv->otg->default_a = 0; | 1793 | musb->xceiv->otg->default_a = 0; |
| 1795 | musb->xceiv->state = OTG_STATE_B_IDLE; | 1794 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 1796 | 1795 | ||
| 1797 | /* this "gadget" abstracts/virtualizes the controller */ | 1796 | /* this "gadget" abstracts/virtualizes the controller */ |
| 1798 | musb->g.name = musb_driver_name; | 1797 | musb->g.name = musb_driver_name; |
| @@ -1851,8 +1850,6 @@ static int musb_gadget_start(struct usb_gadget *g, | |||
| 1851 | 1850 | ||
| 1852 | pm_runtime_get_sync(musb->controller); | 1851 | pm_runtime_get_sync(musb->controller); |
| 1853 | 1852 | ||
| 1854 | dev_dbg(musb->controller, "registering driver %s\n", driver->function); | ||
| 1855 | |||
| 1856 | musb->softconnect = 0; | 1853 | musb->softconnect = 0; |
| 1857 | musb->gadget_driver = driver; | 1854 | musb->gadget_driver = driver; |
| 1858 | 1855 | ||
| @@ -1860,7 +1857,7 @@ static int musb_gadget_start(struct usb_gadget *g, | |||
| 1860 | musb->is_active = 1; | 1857 | musb->is_active = 1; |
| 1861 | 1858 | ||
| 1862 | otg_set_peripheral(otg, &musb->g); | 1859 | otg_set_peripheral(otg, &musb->g); |
| 1863 | musb->xceiv->state = OTG_STATE_B_IDLE; | 1860 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 1864 | spin_unlock_irqrestore(&musb->lock, flags); | 1861 | spin_unlock_irqrestore(&musb->lock, flags); |
| 1865 | 1862 | ||
| 1866 | musb_start(musb); | 1863 | musb_start(musb); |
| @@ -1925,8 +1922,7 @@ static void stop_activity(struct musb *musb, struct usb_gadget_driver *driver) | |||
| 1925 | * | 1922 | * |
| 1926 | * @param driver the gadget driver to unregister | 1923 | * @param driver the gadget driver to unregister |
| 1927 | */ | 1924 | */ |
| 1928 | static int musb_gadget_stop(struct usb_gadget *g, | 1925 | static int musb_gadget_stop(struct usb_gadget *g) |
| 1929 | struct usb_gadget_driver *driver) | ||
| 1930 | { | 1926 | { |
| 1931 | struct musb *musb = gadget_to_musb(g); | 1927 | struct musb *musb = gadget_to_musb(g); |
| 1932 | unsigned long flags; | 1928 | unsigned long flags; |
| @@ -1945,13 +1941,10 @@ static int musb_gadget_stop(struct usb_gadget *g, | |||
| 1945 | 1941 | ||
| 1946 | (void) musb_gadget_vbus_draw(&musb->g, 0); | 1942 | (void) musb_gadget_vbus_draw(&musb->g, 0); |
| 1947 | 1943 | ||
| 1948 | musb->xceiv->state = OTG_STATE_UNDEFINED; | 1944 | musb->xceiv->otg->state = OTG_STATE_UNDEFINED; |
| 1949 | stop_activity(musb, driver); | 1945 | stop_activity(musb, NULL); |
| 1950 | otg_set_peripheral(musb->xceiv->otg, NULL); | 1946 | otg_set_peripheral(musb->xceiv->otg, NULL); |
| 1951 | 1947 | ||
| 1952 | dev_dbg(musb->controller, "unregistering driver %s\n", | ||
| 1953 | driver ? driver->function : "(removed)"); | ||
| 1954 | |||
| 1955 | musb->is_active = 0; | 1948 | musb->is_active = 0; |
| 1956 | musb->gadget_driver = NULL; | 1949 | musb->gadget_driver = NULL; |
| 1957 | musb_platform_try_idle(musb, 0); | 1950 | musb_platform_try_idle(musb, 0); |
| @@ -1975,7 +1968,7 @@ static int musb_gadget_stop(struct usb_gadget *g, | |||
| 1975 | void musb_g_resume(struct musb *musb) | 1968 | void musb_g_resume(struct musb *musb) |
| 1976 | { | 1969 | { |
| 1977 | musb->is_suspended = 0; | 1970 | musb->is_suspended = 0; |
| 1978 | switch (musb->xceiv->state) { | 1971 | switch (musb->xceiv->otg->state) { |
| 1979 | case OTG_STATE_B_IDLE: | 1972 | case OTG_STATE_B_IDLE: |
| 1980 | break; | 1973 | break; |
| 1981 | case OTG_STATE_B_WAIT_ACON: | 1974 | case OTG_STATE_B_WAIT_ACON: |
| @@ -1989,7 +1982,7 @@ void musb_g_resume(struct musb *musb) | |||
| 1989 | break; | 1982 | break; |
| 1990 | default: | 1983 | default: |
| 1991 | WARNING("unhandled RESUME transition (%s)\n", | 1984 | WARNING("unhandled RESUME transition (%s)\n", |
| 1992 | usb_otg_state_string(musb->xceiv->state)); | 1985 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 1993 | } | 1986 | } |
| 1994 | } | 1987 | } |
| 1995 | 1988 | ||
| @@ -2001,10 +1994,10 @@ void musb_g_suspend(struct musb *musb) | |||
| 2001 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); | 1994 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); |
| 2002 | dev_dbg(musb->controller, "devctl %02x\n", devctl); | 1995 | dev_dbg(musb->controller, "devctl %02x\n", devctl); |
| 2003 | 1996 | ||
| 2004 | switch (musb->xceiv->state) { | 1997 | switch (musb->xceiv->otg->state) { |
| 2005 | case OTG_STATE_B_IDLE: | 1998 | case OTG_STATE_B_IDLE: |
| 2006 | if ((devctl & MUSB_DEVCTL_VBUS) == MUSB_DEVCTL_VBUS) | 1999 | if ((devctl & MUSB_DEVCTL_VBUS) == MUSB_DEVCTL_VBUS) |
| 2007 | musb->xceiv->state = OTG_STATE_B_PERIPHERAL; | 2000 | musb->xceiv->otg->state = OTG_STATE_B_PERIPHERAL; |
| 2008 | break; | 2001 | break; |
| 2009 | case OTG_STATE_B_PERIPHERAL: | 2002 | case OTG_STATE_B_PERIPHERAL: |
| 2010 | musb->is_suspended = 1; | 2003 | musb->is_suspended = 1; |
| @@ -2019,7 +2012,7 @@ void musb_g_suspend(struct musb *musb) | |||
| 2019 | * A_PERIPHERAL may need care too | 2012 | * A_PERIPHERAL may need care too |
| 2020 | */ | 2013 | */ |
| 2021 | WARNING("unhandled SUSPEND transition (%s)\n", | 2014 | WARNING("unhandled SUSPEND transition (%s)\n", |
| 2022 | usb_otg_state_string(musb->xceiv->state)); | 2015 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 2023 | } | 2016 | } |
| 2024 | } | 2017 | } |
| 2025 | 2018 | ||
| @@ -2050,22 +2043,22 @@ void musb_g_disconnect(struct musb *musb) | |||
| 2050 | spin_lock(&musb->lock); | 2043 | spin_lock(&musb->lock); |
| 2051 | } | 2044 | } |
| 2052 | 2045 | ||
| 2053 | switch (musb->xceiv->state) { | 2046 | switch (musb->xceiv->otg->state) { |
| 2054 | default: | 2047 | default: |
| 2055 | dev_dbg(musb->controller, "Unhandled disconnect %s, setting a_idle\n", | 2048 | dev_dbg(musb->controller, "Unhandled disconnect %s, setting a_idle\n", |
| 2056 | usb_otg_state_string(musb->xceiv->state)); | 2049 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 2057 | musb->xceiv->state = OTG_STATE_A_IDLE; | 2050 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 2058 | MUSB_HST_MODE(musb); | 2051 | MUSB_HST_MODE(musb); |
| 2059 | break; | 2052 | break; |
| 2060 | case OTG_STATE_A_PERIPHERAL: | 2053 | case OTG_STATE_A_PERIPHERAL: |
| 2061 | musb->xceiv->state = OTG_STATE_A_WAIT_BCON; | 2054 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_BCON; |
| 2062 | MUSB_HST_MODE(musb); | 2055 | MUSB_HST_MODE(musb); |
| 2063 | break; | 2056 | break; |
| 2064 | case OTG_STATE_B_WAIT_ACON: | 2057 | case OTG_STATE_B_WAIT_ACON: |
| 2065 | case OTG_STATE_B_HOST: | 2058 | case OTG_STATE_B_HOST: |
| 2066 | case OTG_STATE_B_PERIPHERAL: | 2059 | case OTG_STATE_B_PERIPHERAL: |
| 2067 | case OTG_STATE_B_IDLE: | 2060 | case OTG_STATE_B_IDLE: |
| 2068 | musb->xceiv->state = OTG_STATE_B_IDLE; | 2061 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 2069 | break; | 2062 | break; |
| 2070 | case OTG_STATE_B_SRP_INIT: | 2063 | case OTG_STATE_B_SRP_INIT: |
| 2071 | break; | 2064 | break; |
| @@ -2090,9 +2083,12 @@ __acquires(musb->lock) | |||
| 2090 | : NULL | 2083 | : NULL |
| 2091 | ); | 2084 | ); |
| 2092 | 2085 | ||
| 2093 | /* report disconnect, if we didn't already (flushing EP state) */ | 2086 | /* report reset, if we didn't already (flushing EP state) */ |
| 2094 | if (musb->g.speed != USB_SPEED_UNKNOWN) | 2087 | if (musb->gadget_driver && musb->g.speed != USB_SPEED_UNKNOWN) { |
| 2095 | musb_g_disconnect(musb); | 2088 | spin_unlock(&musb->lock); |
| 2089 | usb_gadget_udc_reset(&musb->g, musb->gadget_driver); | ||
| 2090 | spin_lock(&musb->lock); | ||
| 2091 | } | ||
| 2096 | 2092 | ||
| 2097 | /* clear HR */ | 2093 | /* clear HR */ |
| 2098 | else if (devctl & MUSB_DEVCTL_HR) | 2094 | else if (devctl & MUSB_DEVCTL_HR) |
| @@ -2125,13 +2121,13 @@ __acquires(musb->lock) | |||
| 2125 | * In that case, do not rely on devctl for setting | 2121 | * In that case, do not rely on devctl for setting |
| 2126 | * peripheral mode. | 2122 | * peripheral mode. |
| 2127 | */ | 2123 | */ |
| 2128 | musb->xceiv->state = OTG_STATE_B_PERIPHERAL; | 2124 | musb->xceiv->otg->state = OTG_STATE_B_PERIPHERAL; |
| 2129 | musb->g.is_a_peripheral = 0; | 2125 | musb->g.is_a_peripheral = 0; |
| 2130 | } else if (devctl & MUSB_DEVCTL_BDEVICE) { | 2126 | } else if (devctl & MUSB_DEVCTL_BDEVICE) { |
| 2131 | musb->xceiv->state = OTG_STATE_B_PERIPHERAL; | 2127 | musb->xceiv->otg->state = OTG_STATE_B_PERIPHERAL; |
| 2132 | musb->g.is_a_peripheral = 0; | 2128 | musb->g.is_a_peripheral = 0; |
| 2133 | } else { | 2129 | } else { |
| 2134 | musb->xceiv->state = OTG_STATE_A_PERIPHERAL; | 2130 | musb->xceiv->otg->state = OTG_STATE_A_PERIPHERAL; |
| 2135 | musb->g.is_a_peripheral = 1; | 2131 | musb->g.is_a_peripheral = 1; |
| 2136 | } | 2132 | } |
| 2137 | 2133 | ||
diff --git a/drivers/usb/musb/musb_host.c b/drivers/usb/musb/musb_host.c index 855793d701bb..23d474d3d7f4 100644 --- a/drivers/usb/musb/musb_host.c +++ b/drivers/usb/musb/musb_host.c | |||
| @@ -2463,7 +2463,7 @@ static int musb_bus_suspend(struct usb_hcd *hcd) | |||
| 2463 | if (!is_host_active(musb)) | 2463 | if (!is_host_active(musb)) |
| 2464 | return 0; | 2464 | return 0; |
| 2465 | 2465 | ||
| 2466 | switch (musb->xceiv->state) { | 2466 | switch (musb->xceiv->otg->state) { |
| 2467 | case OTG_STATE_A_SUSPEND: | 2467 | case OTG_STATE_A_SUSPEND: |
| 2468 | return 0; | 2468 | return 0; |
| 2469 | case OTG_STATE_A_WAIT_VRISE: | 2469 | case OTG_STATE_A_WAIT_VRISE: |
| @@ -2473,7 +2473,7 @@ static int musb_bus_suspend(struct usb_hcd *hcd) | |||
| 2473 | */ | 2473 | */ |
| 2474 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); | 2474 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); |
| 2475 | if ((devctl & MUSB_DEVCTL_VBUS) == MUSB_DEVCTL_VBUS) | 2475 | if ((devctl & MUSB_DEVCTL_VBUS) == MUSB_DEVCTL_VBUS) |
| 2476 | musb->xceiv->state = OTG_STATE_A_WAIT_BCON; | 2476 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_BCON; |
| 2477 | break; | 2477 | break; |
| 2478 | default: | 2478 | default: |
| 2479 | break; | 2479 | break; |
| @@ -2481,7 +2481,7 @@ static int musb_bus_suspend(struct usb_hcd *hcd) | |||
| 2481 | 2481 | ||
| 2482 | if (musb->is_active) { | 2482 | if (musb->is_active) { |
| 2483 | WARNING("trying to suspend as %s while active\n", | 2483 | WARNING("trying to suspend as %s while active\n", |
| 2484 | usb_otg_state_string(musb->xceiv->state)); | 2484 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 2485 | return -EBUSY; | 2485 | return -EBUSY; |
| 2486 | } else | 2486 | } else |
| 2487 | return 0; | 2487 | return 0; |
| @@ -2678,7 +2678,7 @@ int musb_host_setup(struct musb *musb, int power_budget) | |||
| 2678 | 2678 | ||
| 2679 | MUSB_HST_MODE(musb); | 2679 | MUSB_HST_MODE(musb); |
| 2680 | musb->xceiv->otg->default_a = 1; | 2680 | musb->xceiv->otg->default_a = 1; |
| 2681 | musb->xceiv->state = OTG_STATE_A_IDLE; | 2681 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 2682 | 2682 | ||
| 2683 | otg_set_host(musb->xceiv->otg, &hcd->self); | 2683 | otg_set_host(musb->xceiv->otg, &hcd->self); |
| 2684 | hcd->self.otg_port = 1; | 2684 | hcd->self.otg_port = 1; |
diff --git a/drivers/usb/musb/musb_io.h b/drivers/usb/musb/musb_io.h index eebeed78edd6..8a57a6f4b3a6 100644 --- a/drivers/usb/musb/musb_io.h +++ b/drivers/usb/musb/musb_io.h | |||
| @@ -37,86 +37,32 @@ | |||
| 37 | 37 | ||
| 38 | #include <linux/io.h> | 38 | #include <linux/io.h> |
| 39 | 39 | ||
| 40 | #ifndef CONFIG_BLACKFIN | 40 | #define musb_ep_select(_mbase, _epnum) musb->io.ep_select((_mbase), (_epnum)) |
| 41 | 41 | ||
| 42 | /* NOTE: these offsets are all in bytes */ | 42 | /** |
| 43 | 43 | * struct musb_io - IO functions for MUSB | |
| 44 | static inline u16 musb_readw(const void __iomem *addr, unsigned offset) | 44 | * @quirks: platform specific flags |
| 45 | { return __raw_readw(addr + offset); } | 45 | * @ep_offset: platform specific function to get end point offset |
| 46 | 46 | * @ep_select: platform specific function to select end point | |
| 47 | static inline u32 musb_readl(const void __iomem *addr, unsigned offset) | 47 | * @fifo_offset: platform specific function to get fifo offset |
| 48 | { return __raw_readl(addr + offset); } | 48 | * @read_fifo: platform specific function to read fifo |
| 49 | 49 | * @write_fifo: platform specific function to write fifo | |
| 50 | |||
| 51 | static inline void musb_writew(void __iomem *addr, unsigned offset, u16 data) | ||
| 52 | { __raw_writew(data, addr + offset); } | ||
| 53 | |||
| 54 | static inline void musb_writel(void __iomem *addr, unsigned offset, u32 data) | ||
| 55 | { __raw_writel(data, addr + offset); } | ||
| 56 | |||
| 57 | |||
| 58 | #if defined(CONFIG_USB_MUSB_TUSB6010) || defined (CONFIG_USB_MUSB_TUSB6010_MODULE) | ||
| 59 | |||
| 60 | /* | ||
| 61 | * TUSB6010 doesn't allow 8-bit access; 16-bit access is the minimum. | ||
| 62 | */ | 50 | */ |
| 63 | static inline u8 musb_readb(const void __iomem *addr, unsigned offset) | 51 | struct musb_io { |
| 64 | { | 52 | u32 quirks; |
| 65 | u16 tmp; | 53 | u32 (*ep_offset)(u8 epnum, u16 offset); |
| 66 | u8 val; | 54 | void (*ep_select)(void __iomem *mbase, u8 epnum); |
| 67 | 55 | u32 (*fifo_offset)(u8 epnum); | |
| 68 | tmp = __raw_readw(addr + (offset & ~1)); | 56 | void (*read_fifo)(struct musb_hw_ep *hw_ep, u16 len, u8 *buf); |
| 69 | if (offset & 1) | 57 | void (*write_fifo)(struct musb_hw_ep *hw_ep, u16 len, const u8 *buf); |
| 70 | val = (tmp >> 8); | 58 | }; |
| 71 | else | 59 | |
| 72 | val = tmp & 0xff; | 60 | /* Do not add new entries here, add them the struct musb_io instead */ |
| 73 | 61 | extern u8 (*musb_readb)(const void __iomem *addr, unsigned offset); | |
| 74 | return val; | 62 | extern void (*musb_writeb)(void __iomem *addr, unsigned offset, u8 data); |
| 75 | } | 63 | extern u16 (*musb_readw)(const void __iomem *addr, unsigned offset); |
| 76 | 64 | extern void (*musb_writew)(void __iomem *addr, unsigned offset, u16 data); | |
| 77 | static inline void musb_writeb(void __iomem *addr, unsigned offset, u8 data) | 65 | extern u32 (*musb_readl)(const void __iomem *addr, unsigned offset); |
| 78 | { | 66 | extern void (*musb_writel)(void __iomem *addr, unsigned offset, u32 data); |
| 79 | u16 tmp; | ||
| 80 | |||
| 81 | tmp = __raw_readw(addr + (offset & ~1)); | ||
| 82 | if (offset & 1) | ||
| 83 | tmp = (data << 8) | (tmp & 0xff); | ||
| 84 | else | ||
| 85 | tmp = (tmp & 0xff00) | data; | ||
| 86 | |||
| 87 | __raw_writew(tmp, addr + (offset & ~1)); | ||
| 88 | } | ||
| 89 | |||
| 90 | #else | ||
| 91 | |||
| 92 | static inline u8 musb_readb(const void __iomem *addr, unsigned offset) | ||
| 93 | { return __raw_readb(addr + offset); } | ||
| 94 | |||
| 95 | static inline void musb_writeb(void __iomem *addr, unsigned offset, u8 data) | ||
| 96 | { __raw_writeb(data, addr + offset); } | ||
| 97 | |||
| 98 | #endif /* CONFIG_USB_MUSB_TUSB6010 */ | ||
| 99 | |||
| 100 | #else | ||
| 101 | |||
| 102 | static inline u8 musb_readb(const void __iomem *addr, unsigned offset) | ||
| 103 | { return (u8) (bfin_read16(addr + offset)); } | ||
| 104 | |||
| 105 | static inline u16 musb_readw(const void __iomem *addr, unsigned offset) | ||
| 106 | { return bfin_read16(addr + offset); } | ||
| 107 | |||
| 108 | static inline u32 musb_readl(const void __iomem *addr, unsigned offset) | ||
| 109 | { return (u32) (bfin_read16(addr + offset)); } | ||
| 110 | |||
| 111 | static inline void musb_writeb(void __iomem *addr, unsigned offset, u8 data) | ||
| 112 | { bfin_write16(addr + offset, (u16) data); } | ||
| 113 | |||
| 114 | static inline void musb_writew(void __iomem *addr, unsigned offset, u16 data) | ||
| 115 | { bfin_write16(addr + offset, data); } | ||
| 116 | |||
| 117 | static inline void musb_writel(void __iomem *addr, unsigned offset, u32 data) | ||
| 118 | { bfin_write16(addr + offset, (u16) data); } | ||
| 119 | |||
| 120 | #endif /* CONFIG_BLACKFIN */ | ||
| 121 | 67 | ||
| 122 | #endif | 68 | #endif |
diff --git a/drivers/usb/musb/musb_regs.h b/drivers/usb/musb/musb_regs.h index 37122a480bc1..11f0be07491e 100644 --- a/drivers/usb/musb/musb_regs.h +++ b/drivers/usb/musb/musb_regs.h | |||
| @@ -239,14 +239,6 @@ | |||
| 239 | #define MUSB_INDEX 0x0E /* 8 bit */ | 239 | #define MUSB_INDEX 0x0E /* 8 bit */ |
| 240 | #define MUSB_TESTMODE 0x0F /* 8 bit */ | 240 | #define MUSB_TESTMODE 0x0F /* 8 bit */ |
| 241 | 241 | ||
| 242 | /* Get offset for a given FIFO from musb->mregs */ | ||
| 243 | #if defined(CONFIG_USB_MUSB_TUSB6010) || \ | ||
| 244 | defined(CONFIG_USB_MUSB_TUSB6010_MODULE) | ||
| 245 | #define MUSB_FIFO_OFFSET(epnum) (0x200 + ((epnum) * 0x20)) | ||
| 246 | #else | ||
| 247 | #define MUSB_FIFO_OFFSET(epnum) (0x20 + ((epnum) * 4)) | ||
| 248 | #endif | ||
| 249 | |||
| 250 | /* | 242 | /* |
| 251 | * Additional Control Registers | 243 | * Additional Control Registers |
| 252 | */ | 244 | */ |
| @@ -295,21 +287,7 @@ | |||
| 295 | #define MUSB_FIFOSIZE 0x0F | 287 | #define MUSB_FIFOSIZE 0x0F |
| 296 | #define MUSB_CONFIGDATA MUSB_FIFOSIZE /* Re-used for EP0 */ | 288 | #define MUSB_CONFIGDATA MUSB_FIFOSIZE /* Re-used for EP0 */ |
| 297 | 289 | ||
| 298 | /* Offsets to endpoint registers in indexed model (using INDEX register) */ | ||
| 299 | #define MUSB_INDEXED_OFFSET(_epnum, _offset) \ | ||
| 300 | (0x10 + (_offset)) | ||
| 301 | |||
| 302 | /* Offsets to endpoint registers in flat models */ | ||
| 303 | #define MUSB_FLAT_OFFSET(_epnum, _offset) \ | ||
| 304 | (0x100 + (0x10*(_epnum)) + (_offset)) | ||
| 305 | |||
| 306 | #if defined(CONFIG_USB_MUSB_TUSB6010) || \ | ||
| 307 | defined(CONFIG_USB_MUSB_TUSB6010_MODULE) | ||
| 308 | /* TUSB6010 EP0 configuration register is special */ | ||
| 309 | #define MUSB_TUSB_OFFSET(_epnum, _offset) \ | ||
| 310 | (0x10 + _offset) | ||
| 311 | #include "tusb6010.h" /* Needed "only" for TUSB_EP0_CONF */ | 290 | #include "tusb6010.h" /* Needed "only" for TUSB_EP0_CONF */ |
| 312 | #endif | ||
| 313 | 291 | ||
| 314 | #define MUSB_TXCSR_MODE 0x2000 | 292 | #define MUSB_TXCSR_MODE 0x2000 |
| 315 | 293 | ||
| @@ -480,10 +458,6 @@ static inline u8 musb_read_txhubport(void __iomem *mbase, u8 epnum) | |||
| 480 | #define MUSB_INDEX USB_OFFSET(USB_INDEX) /* 8 bit */ | 458 | #define MUSB_INDEX USB_OFFSET(USB_INDEX) /* 8 bit */ |
| 481 | #define MUSB_TESTMODE USB_OFFSET(USB_TESTMODE)/* 8 bit */ | 459 | #define MUSB_TESTMODE USB_OFFSET(USB_TESTMODE)/* 8 bit */ |
| 482 | 460 | ||
| 483 | /* Get offset for a given FIFO from musb->mregs */ | ||
| 484 | #define MUSB_FIFO_OFFSET(epnum) \ | ||
| 485 | (USB_OFFSET(USB_EP0_FIFO) + ((epnum) * 8)) | ||
| 486 | |||
| 487 | /* | 461 | /* |
| 488 | * Additional Control Registers | 462 | * Additional Control Registers |
| 489 | */ | 463 | */ |
diff --git a/drivers/usb/musb/musb_virthub.c b/drivers/usb/musb/musb_virthub.c index e2d2d8c9891b..b072420e44f5 100644 --- a/drivers/usb/musb/musb_virthub.c +++ b/drivers/usb/musb/musb_virthub.c | |||
| @@ -69,9 +69,10 @@ void musb_host_finish_resume(struct work_struct *work) | |||
| 69 | musb->port1_status |= USB_PORT_STAT_C_SUSPEND << 16; | 69 | musb->port1_status |= USB_PORT_STAT_C_SUSPEND << 16; |
| 70 | usb_hcd_poll_rh_status(musb->hcd); | 70 | usb_hcd_poll_rh_status(musb->hcd); |
| 71 | /* NOTE: it might really be A_WAIT_BCON ... */ | 71 | /* NOTE: it might really be A_WAIT_BCON ... */ |
| 72 | musb->xceiv->state = OTG_STATE_A_HOST; | 72 | musb->xceiv->otg->state = OTG_STATE_A_HOST; |
| 73 | 73 | ||
| 74 | spin_unlock_irqrestore(&musb->lock, flags); | 74 | spin_unlock_irqrestore(&musb->lock, flags); |
| 75 | musb_host_resume_root_hub(musb); | ||
| 75 | } | 76 | } |
| 76 | 77 | ||
| 77 | void musb_port_suspend(struct musb *musb, bool do_suspend) | 78 | void musb_port_suspend(struct musb *musb, bool do_suspend) |
| @@ -107,9 +108,9 @@ void musb_port_suspend(struct musb *musb, bool do_suspend) | |||
| 107 | dev_dbg(musb->controller, "Root port suspended, power %02x\n", power); | 108 | dev_dbg(musb->controller, "Root port suspended, power %02x\n", power); |
| 108 | 109 | ||
| 109 | musb->port1_status |= USB_PORT_STAT_SUSPEND; | 110 | musb->port1_status |= USB_PORT_STAT_SUSPEND; |
| 110 | switch (musb->xceiv->state) { | 111 | switch (musb->xceiv->otg->state) { |
| 111 | case OTG_STATE_A_HOST: | 112 | case OTG_STATE_A_HOST: |
| 112 | musb->xceiv->state = OTG_STATE_A_SUSPEND; | 113 | musb->xceiv->otg->state = OTG_STATE_A_SUSPEND; |
| 113 | musb->is_active = otg->host->b_hnp_enable; | 114 | musb->is_active = otg->host->b_hnp_enable; |
| 114 | if (musb->is_active) | 115 | if (musb->is_active) |
| 115 | mod_timer(&musb->otg_timer, jiffies | 116 | mod_timer(&musb->otg_timer, jiffies |
| @@ -118,13 +119,13 @@ void musb_port_suspend(struct musb *musb, bool do_suspend) | |||
| 118 | musb_platform_try_idle(musb, 0); | 119 | musb_platform_try_idle(musb, 0); |
| 119 | break; | 120 | break; |
| 120 | case OTG_STATE_B_HOST: | 121 | case OTG_STATE_B_HOST: |
| 121 | musb->xceiv->state = OTG_STATE_B_WAIT_ACON; | 122 | musb->xceiv->otg->state = OTG_STATE_B_WAIT_ACON; |
| 122 | musb->is_active = otg->host->b_hnp_enable; | 123 | musb->is_active = otg->host->b_hnp_enable; |
| 123 | musb_platform_try_idle(musb, 0); | 124 | musb_platform_try_idle(musb, 0); |
| 124 | break; | 125 | break; |
| 125 | default: | 126 | default: |
| 126 | dev_dbg(musb->controller, "bogus rh suspend? %s\n", | 127 | dev_dbg(musb->controller, "bogus rh suspend? %s\n", |
| 127 | usb_otg_state_string(musb->xceiv->state)); | 128 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 128 | } | 129 | } |
| 129 | } else if (power & MUSB_POWER_SUSPENDM) { | 130 | } else if (power & MUSB_POWER_SUSPENDM) { |
| 130 | power &= ~MUSB_POWER_SUSPENDM; | 131 | power &= ~MUSB_POWER_SUSPENDM; |
| @@ -145,7 +146,7 @@ void musb_port_reset(struct musb *musb, bool do_reset) | |||
| 145 | u8 power; | 146 | u8 power; |
| 146 | void __iomem *mbase = musb->mregs; | 147 | void __iomem *mbase = musb->mregs; |
| 147 | 148 | ||
| 148 | if (musb->xceiv->state == OTG_STATE_B_IDLE) { | 149 | if (musb->xceiv->otg->state == OTG_STATE_B_IDLE) { |
| 149 | dev_dbg(musb->controller, "HNP: Returning from HNP; no hub reset from b_idle\n"); | 150 | dev_dbg(musb->controller, "HNP: Returning from HNP; no hub reset from b_idle\n"); |
| 150 | musb->port1_status &= ~USB_PORT_STAT_RESET; | 151 | musb->port1_status &= ~USB_PORT_STAT_RESET; |
| 151 | return; | 152 | return; |
| @@ -224,24 +225,24 @@ void musb_root_disconnect(struct musb *musb) | |||
| 224 | usb_hcd_poll_rh_status(musb->hcd); | 225 | usb_hcd_poll_rh_status(musb->hcd); |
| 225 | musb->is_active = 0; | 226 | musb->is_active = 0; |
| 226 | 227 | ||
| 227 | switch (musb->xceiv->state) { | 228 | switch (musb->xceiv->otg->state) { |
| 228 | case OTG_STATE_A_SUSPEND: | 229 | case OTG_STATE_A_SUSPEND: |
| 229 | if (otg->host->b_hnp_enable) { | 230 | if (otg->host->b_hnp_enable) { |
| 230 | musb->xceiv->state = OTG_STATE_A_PERIPHERAL; | 231 | musb->xceiv->otg->state = OTG_STATE_A_PERIPHERAL; |
| 231 | musb->g.is_a_peripheral = 1; | 232 | musb->g.is_a_peripheral = 1; |
| 232 | break; | 233 | break; |
| 233 | } | 234 | } |
| 234 | /* FALLTHROUGH */ | 235 | /* FALLTHROUGH */ |
| 235 | case OTG_STATE_A_HOST: | 236 | case OTG_STATE_A_HOST: |
| 236 | musb->xceiv->state = OTG_STATE_A_WAIT_BCON; | 237 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_BCON; |
| 237 | musb->is_active = 0; | 238 | musb->is_active = 0; |
| 238 | break; | 239 | break; |
| 239 | case OTG_STATE_A_WAIT_VFALL: | 240 | case OTG_STATE_A_WAIT_VFALL: |
| 240 | musb->xceiv->state = OTG_STATE_B_IDLE; | 241 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 241 | break; | 242 | break; |
| 242 | default: | 243 | default: |
| 243 | dev_dbg(musb->controller, "host disconnect (%s)\n", | 244 | dev_dbg(musb->controller, "host disconnect (%s)\n", |
| 244 | usb_otg_state_string(musb->xceiv->state)); | 245 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 245 | } | 246 | } |
| 246 | } | 247 | } |
| 247 | 248 | ||
diff --git a/drivers/usb/musb/musbhsdma.c b/drivers/usb/musb/musbhsdma.c index e8e9f9aab203..ab7ec09a8afe 100644 --- a/drivers/usb/musb/musbhsdma.c +++ b/drivers/usb/musb/musbhsdma.c | |||
| @@ -195,6 +195,7 @@ static int dma_channel_abort(struct dma_channel *channel) | |||
| 195 | { | 195 | { |
| 196 | struct musb_dma_channel *musb_channel = channel->private_data; | 196 | struct musb_dma_channel *musb_channel = channel->private_data; |
| 197 | void __iomem *mbase = musb_channel->controller->base; | 197 | void __iomem *mbase = musb_channel->controller->base; |
| 198 | struct musb *musb = musb_channel->controller->private_data; | ||
| 198 | 199 | ||
| 199 | u8 bchannel = musb_channel->idx; | 200 | u8 bchannel = musb_channel->idx; |
| 200 | int offset; | 201 | int offset; |
| @@ -202,7 +203,7 @@ static int dma_channel_abort(struct dma_channel *channel) | |||
| 202 | 203 | ||
| 203 | if (channel->status == MUSB_DMA_STATUS_BUSY) { | 204 | if (channel->status == MUSB_DMA_STATUS_BUSY) { |
| 204 | if (musb_channel->transmit) { | 205 | if (musb_channel->transmit) { |
| 205 | offset = MUSB_EP_OFFSET(musb_channel->epnum, | 206 | offset = musb->io.ep_offset(musb_channel->epnum, |
| 206 | MUSB_TXCSR); | 207 | MUSB_TXCSR); |
| 207 | 208 | ||
| 208 | /* | 209 | /* |
| @@ -215,7 +216,7 @@ static int dma_channel_abort(struct dma_channel *channel) | |||
| 215 | csr &= ~MUSB_TXCSR_DMAMODE; | 216 | csr &= ~MUSB_TXCSR_DMAMODE; |
| 216 | musb_writew(mbase, offset, csr); | 217 | musb_writew(mbase, offset, csr); |
| 217 | } else { | 218 | } else { |
| 218 | offset = MUSB_EP_OFFSET(musb_channel->epnum, | 219 | offset = musb->io.ep_offset(musb_channel->epnum, |
| 219 | MUSB_RXCSR); | 220 | MUSB_RXCSR); |
| 220 | 221 | ||
| 221 | csr = musb_readw(mbase, offset); | 222 | csr = musb_readw(mbase, offset); |
| @@ -326,7 +327,7 @@ static irqreturn_t dma_controller_irq(int irq, void *private_data) | |||
| 326 | (musb_channel->max_packet_sz - 1))) | 327 | (musb_channel->max_packet_sz - 1))) |
| 327 | ) { | 328 | ) { |
| 328 | u8 epnum = musb_channel->epnum; | 329 | u8 epnum = musb_channel->epnum; |
| 329 | int offset = MUSB_EP_OFFSET(epnum, | 330 | int offset = musb->io.ep_offset(epnum, |
| 330 | MUSB_TXCSR); | 331 | MUSB_TXCSR); |
| 331 | u16 txcsr; | 332 | u16 txcsr; |
| 332 | 333 | ||
diff --git a/drivers/usb/musb/omap2430.c b/drivers/usb/musb/omap2430.c index d369bf1f3936..763649eb4987 100644 --- a/drivers/usb/musb/omap2430.c +++ b/drivers/usb/musb/omap2430.c | |||
| @@ -65,15 +65,15 @@ static void musb_do_idle(unsigned long _musb) | |||
| 65 | 65 | ||
| 66 | spin_lock_irqsave(&musb->lock, flags); | 66 | spin_lock_irqsave(&musb->lock, flags); |
| 67 | 67 | ||
| 68 | switch (musb->xceiv->state) { | 68 | switch (musb->xceiv->otg->state) { |
| 69 | case OTG_STATE_A_WAIT_BCON: | 69 | case OTG_STATE_A_WAIT_BCON: |
| 70 | 70 | ||
| 71 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); | 71 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); |
| 72 | if (devctl & MUSB_DEVCTL_BDEVICE) { | 72 | if (devctl & MUSB_DEVCTL_BDEVICE) { |
| 73 | musb->xceiv->state = OTG_STATE_B_IDLE; | 73 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 74 | MUSB_DEV_MODE(musb); | 74 | MUSB_DEV_MODE(musb); |
| 75 | } else { | 75 | } else { |
| 76 | musb->xceiv->state = OTG_STATE_A_IDLE; | 76 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 77 | MUSB_HST_MODE(musb); | 77 | MUSB_HST_MODE(musb); |
| 78 | } | 78 | } |
| 79 | break; | 79 | break; |
| @@ -90,15 +90,15 @@ static void musb_do_idle(unsigned long _musb) | |||
| 90 | musb->port1_status |= USB_PORT_STAT_C_SUSPEND << 16; | 90 | musb->port1_status |= USB_PORT_STAT_C_SUSPEND << 16; |
| 91 | usb_hcd_poll_rh_status(musb->hcd); | 91 | usb_hcd_poll_rh_status(musb->hcd); |
| 92 | /* NOTE: it might really be A_WAIT_BCON ... */ | 92 | /* NOTE: it might really be A_WAIT_BCON ... */ |
| 93 | musb->xceiv->state = OTG_STATE_A_HOST; | 93 | musb->xceiv->otg->state = OTG_STATE_A_HOST; |
| 94 | } | 94 | } |
| 95 | break; | 95 | break; |
| 96 | case OTG_STATE_A_HOST: | 96 | case OTG_STATE_A_HOST: |
| 97 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); | 97 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); |
| 98 | if (devctl & MUSB_DEVCTL_BDEVICE) | 98 | if (devctl & MUSB_DEVCTL_BDEVICE) |
| 99 | musb->xceiv->state = OTG_STATE_B_IDLE; | 99 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 100 | else | 100 | else |
| 101 | musb->xceiv->state = OTG_STATE_A_WAIT_BCON; | 101 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_BCON; |
| 102 | default: | 102 | default: |
| 103 | break; | 103 | break; |
| 104 | } | 104 | } |
| @@ -116,9 +116,9 @@ static void omap2430_musb_try_idle(struct musb *musb, unsigned long timeout) | |||
| 116 | 116 | ||
| 117 | /* Never idle if active, or when VBUS timeout is not set as host */ | 117 | /* Never idle if active, or when VBUS timeout is not set as host */ |
| 118 | if (musb->is_active || ((musb->a_wait_bcon == 0) | 118 | if (musb->is_active || ((musb->a_wait_bcon == 0) |
| 119 | && (musb->xceiv->state == OTG_STATE_A_WAIT_BCON))) { | 119 | && (musb->xceiv->otg->state == OTG_STATE_A_WAIT_BCON))) { |
| 120 | dev_dbg(musb->controller, "%s active, deleting timer\n", | 120 | dev_dbg(musb->controller, "%s active, deleting timer\n", |
| 121 | usb_otg_state_string(musb->xceiv->state)); | 121 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 122 | del_timer(&musb_idle_timer); | 122 | del_timer(&musb_idle_timer); |
| 123 | last_timer = jiffies; | 123 | last_timer = jiffies; |
| 124 | return; | 124 | return; |
| @@ -135,7 +135,7 @@ static void omap2430_musb_try_idle(struct musb *musb, unsigned long timeout) | |||
| 135 | last_timer = timeout; | 135 | last_timer = timeout; |
| 136 | 136 | ||
| 137 | dev_dbg(musb->controller, "%s inactive, for idle timer for %lu ms\n", | 137 | dev_dbg(musb->controller, "%s inactive, for idle timer for %lu ms\n", |
| 138 | usb_otg_state_string(musb->xceiv->state), | 138 | usb_otg_state_string(musb->xceiv->otg->state), |
| 139 | (unsigned long)jiffies_to_msecs(timeout - jiffies)); | 139 | (unsigned long)jiffies_to_msecs(timeout - jiffies)); |
| 140 | mod_timer(&musb_idle_timer, timeout); | 140 | mod_timer(&musb_idle_timer, timeout); |
| 141 | } | 141 | } |
| @@ -153,7 +153,7 @@ static void omap2430_musb_set_vbus(struct musb *musb, int is_on) | |||
| 153 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); | 153 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); |
| 154 | 154 | ||
| 155 | if (is_on) { | 155 | if (is_on) { |
| 156 | if (musb->xceiv->state == OTG_STATE_A_IDLE) { | 156 | if (musb->xceiv->otg->state == OTG_STATE_A_IDLE) { |
| 157 | int loops = 100; | 157 | int loops = 100; |
| 158 | /* start the session */ | 158 | /* start the session */ |
| 159 | devctl |= MUSB_DEVCTL_SESSION; | 159 | devctl |= MUSB_DEVCTL_SESSION; |
| @@ -162,7 +162,8 @@ static void omap2430_musb_set_vbus(struct musb *musb, int is_on) | |||
| 162 | * Wait for the musb to set as A device to enable the | 162 | * Wait for the musb to set as A device to enable the |
| 163 | * VBUS | 163 | * VBUS |
| 164 | */ | 164 | */ |
| 165 | while (musb_readb(musb->mregs, MUSB_DEVCTL) & 0x80) { | 165 | while (musb_readb(musb->mregs, MUSB_DEVCTL) & |
| 166 | MUSB_DEVCTL_BDEVICE) { | ||
| 166 | 167 | ||
| 167 | mdelay(5); | 168 | mdelay(5); |
| 168 | cpu_relax(); | 169 | cpu_relax(); |
| @@ -179,7 +180,7 @@ static void omap2430_musb_set_vbus(struct musb *musb, int is_on) | |||
| 179 | } else { | 180 | } else { |
| 180 | musb->is_active = 1; | 181 | musb->is_active = 1; |
| 181 | otg->default_a = 1; | 182 | otg->default_a = 1; |
| 182 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 183 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 183 | devctl |= MUSB_DEVCTL_SESSION; | 184 | devctl |= MUSB_DEVCTL_SESSION; |
| 184 | MUSB_HST_MODE(musb); | 185 | MUSB_HST_MODE(musb); |
| 185 | } | 186 | } |
| @@ -191,7 +192,7 @@ static void omap2430_musb_set_vbus(struct musb *musb, int is_on) | |||
| 191 | */ | 192 | */ |
| 192 | 193 | ||
| 193 | otg->default_a = 0; | 194 | otg->default_a = 0; |
| 194 | musb->xceiv->state = OTG_STATE_B_IDLE; | 195 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 195 | devctl &= ~MUSB_DEVCTL_SESSION; | 196 | devctl &= ~MUSB_DEVCTL_SESSION; |
| 196 | 197 | ||
| 197 | MUSB_DEV_MODE(musb); | 198 | MUSB_DEV_MODE(musb); |
| @@ -200,7 +201,7 @@ static void omap2430_musb_set_vbus(struct musb *musb, int is_on) | |||
| 200 | 201 | ||
| 201 | dev_dbg(musb->controller, "VBUS %s, devctl %02x " | 202 | dev_dbg(musb->controller, "VBUS %s, devctl %02x " |
| 202 | /* otg %3x conf %08x prcm %08x */ "\n", | 203 | /* otg %3x conf %08x prcm %08x */ "\n", |
| 203 | usb_otg_state_string(musb->xceiv->state), | 204 | usb_otg_state_string(musb->xceiv->otg->state), |
| 204 | musb_readb(musb->mregs, MUSB_DEVCTL)); | 205 | musb_readb(musb->mregs, MUSB_DEVCTL)); |
| 205 | } | 206 | } |
| 206 | 207 | ||
| @@ -265,7 +266,7 @@ static void omap_musb_set_mailbox(struct omap2430_glue *glue) | |||
| 265 | dev_dbg(dev, "ID GND\n"); | 266 | dev_dbg(dev, "ID GND\n"); |
| 266 | 267 | ||
| 267 | otg->default_a = true; | 268 | otg->default_a = true; |
| 268 | musb->xceiv->state = OTG_STATE_A_IDLE; | 269 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 269 | musb->xceiv->last_event = USB_EVENT_ID; | 270 | musb->xceiv->last_event = USB_EVENT_ID; |
| 270 | if (musb->gadget_driver) { | 271 | if (musb->gadget_driver) { |
| 271 | pm_runtime_get_sync(dev); | 272 | pm_runtime_get_sync(dev); |
| @@ -279,7 +280,7 @@ static void omap_musb_set_mailbox(struct omap2430_glue *glue) | |||
| 279 | dev_dbg(dev, "VBUS Connect\n"); | 280 | dev_dbg(dev, "VBUS Connect\n"); |
| 280 | 281 | ||
| 281 | otg->default_a = false; | 282 | otg->default_a = false; |
| 282 | musb->xceiv->state = OTG_STATE_B_IDLE; | 283 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 283 | musb->xceiv->last_event = USB_EVENT_VBUS; | 284 | musb->xceiv->last_event = USB_EVENT_VBUS; |
| 284 | if (musb->gadget_driver) | 285 | if (musb->gadget_driver) |
| 285 | pm_runtime_get_sync(dev); | 286 | pm_runtime_get_sync(dev); |
| @@ -518,10 +519,8 @@ static int omap2430_probe(struct platform_device *pdev) | |||
| 518 | int ret = -ENOMEM; | 519 | int ret = -ENOMEM; |
| 519 | 520 | ||
| 520 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); | 521 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); |
| 521 | if (!glue) { | 522 | if (!glue) |
| 522 | dev_err(&pdev->dev, "failed to allocate glue context\n"); | ||
| 523 | goto err0; | 523 | goto err0; |
| 524 | } | ||
| 525 | 524 | ||
| 526 | musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); | 525 | musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); |
| 527 | if (!musb) { | 526 | if (!musb) { |
| @@ -543,25 +542,16 @@ static int omap2430_probe(struct platform_device *pdev) | |||
| 543 | struct platform_device *control_pdev; | 542 | struct platform_device *control_pdev; |
| 544 | 543 | ||
| 545 | pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL); | 544 | pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL); |
| 546 | if (!pdata) { | 545 | if (!pdata) |
| 547 | dev_err(&pdev->dev, | ||
| 548 | "failed to allocate musb platform data\n"); | ||
| 549 | goto err2; | 546 | goto err2; |
| 550 | } | ||
| 551 | 547 | ||
| 552 | data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL); | 548 | data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL); |
| 553 | if (!data) { | 549 | if (!data) |
| 554 | dev_err(&pdev->dev, | ||
| 555 | "failed to allocate musb board data\n"); | ||
| 556 | goto err2; | 550 | goto err2; |
| 557 | } | ||
| 558 | 551 | ||
| 559 | config = devm_kzalloc(&pdev->dev, sizeof(*config), GFP_KERNEL); | 552 | config = devm_kzalloc(&pdev->dev, sizeof(*config), GFP_KERNEL); |
| 560 | if (!config) { | 553 | if (!config) |
| 561 | dev_err(&pdev->dev, | ||
| 562 | "failed to allocate musb hdrc config\n"); | ||
| 563 | goto err2; | 554 | goto err2; |
| 564 | } | ||
| 565 | 555 | ||
| 566 | of_property_read_u32(np, "mode", (u32 *)&pdata->mode); | 556 | of_property_read_u32(np, "mode", (u32 *)&pdata->mode); |
| 567 | of_property_read_u32(np, "interface-type", | 557 | of_property_read_u32(np, "interface-type", |
diff --git a/drivers/usb/musb/tusb6010.c b/drivers/usb/musb/tusb6010.c index 2daa779f1382..3a5ffd575438 100644 --- a/drivers/usb/musb/tusb6010.c +++ b/drivers/usb/musb/tusb6010.c | |||
| @@ -126,6 +126,52 @@ static void tusb_wbus_quirk(struct musb *musb, int enabled) | |||
| 126 | } | 126 | } |
| 127 | } | 127 | } |
| 128 | 128 | ||
| 129 | static u32 tusb_fifo_offset(u8 epnum) | ||
| 130 | { | ||
| 131 | return 0x200 + (epnum * 0x20); | ||
| 132 | } | ||
| 133 | |||
| 134 | static u32 tusb_ep_offset(u8 epnum, u16 offset) | ||
| 135 | { | ||
| 136 | return 0x10 + offset; | ||
| 137 | } | ||
| 138 | |||
| 139 | /* TUSB mapping: "flat" plus ep0 special cases */ | ||
| 140 | static void tusb_ep_select(void __iomem *mbase, u8 epnum) | ||
| 141 | { | ||
| 142 | musb_writeb(mbase, MUSB_INDEX, epnum); | ||
| 143 | } | ||
| 144 | |||
| 145 | /* | ||
| 146 | * TUSB6010 doesn't allow 8-bit access; 16-bit access is the minimum. | ||
| 147 | */ | ||
| 148 | static u8 tusb_readb(const void __iomem *addr, unsigned offset) | ||
| 149 | { | ||
| 150 | u16 tmp; | ||
| 151 | u8 val; | ||
| 152 | |||
| 153 | tmp = __raw_readw(addr + (offset & ~1)); | ||
| 154 | if (offset & 1) | ||
| 155 | val = (tmp >> 8); | ||
| 156 | else | ||
| 157 | val = tmp & 0xff; | ||
| 158 | |||
| 159 | return val; | ||
| 160 | } | ||
| 161 | |||
| 162 | static void tusb_writeb(void __iomem *addr, unsigned offset, u8 data) | ||
| 163 | { | ||
| 164 | u16 tmp; | ||
| 165 | |||
| 166 | tmp = __raw_readw(addr + (offset & ~1)); | ||
| 167 | if (offset & 1) | ||
| 168 | tmp = (data << 8) | (tmp & 0xff); | ||
| 169 | else | ||
| 170 | tmp = (tmp & 0xff00) | data; | ||
| 171 | |||
| 172 | __raw_writew(tmp, addr + (offset & ~1)); | ||
| 173 | } | ||
| 174 | |||
| 129 | /* | 175 | /* |
| 130 | * TUSB 6010 may use a parallel bus that doesn't support byte ops; | 176 | * TUSB 6010 may use a parallel bus that doesn't support byte ops; |
| 131 | * so both loading and unloading FIFOs need explicit byte counts. | 177 | * so both loading and unloading FIFOs need explicit byte counts. |
| @@ -173,7 +219,7 @@ static inline void tusb_fifo_read_unaligned(void __iomem *fifo, | |||
| 173 | } | 219 | } |
| 174 | } | 220 | } |
| 175 | 221 | ||
| 176 | void musb_write_fifo(struct musb_hw_ep *hw_ep, u16 len, const u8 *buf) | 222 | static void tusb_write_fifo(struct musb_hw_ep *hw_ep, u16 len, const u8 *buf) |
| 177 | { | 223 | { |
| 178 | struct musb *musb = hw_ep->musb; | 224 | struct musb *musb = hw_ep->musb; |
| 179 | void __iomem *ep_conf = hw_ep->conf; | 225 | void __iomem *ep_conf = hw_ep->conf; |
| @@ -223,7 +269,7 @@ void musb_write_fifo(struct musb_hw_ep *hw_ep, u16 len, const u8 *buf) | |||
| 223 | tusb_fifo_write_unaligned(fifo, buf, len); | 269 | tusb_fifo_write_unaligned(fifo, buf, len); |
| 224 | } | 270 | } |
| 225 | 271 | ||
| 226 | void musb_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *buf) | 272 | static void tusb_read_fifo(struct musb_hw_ep *hw_ep, u16 len, u8 *buf) |
| 227 | { | 273 | { |
| 228 | struct musb *musb = hw_ep->musb; | 274 | struct musb *musb = hw_ep->musb; |
| 229 | void __iomem *ep_conf = hw_ep->conf; | 275 | void __iomem *ep_conf = hw_ep->conf; |
| @@ -415,13 +461,13 @@ static void musb_do_idle(unsigned long _musb) | |||
| 415 | 461 | ||
| 416 | spin_lock_irqsave(&musb->lock, flags); | 462 | spin_lock_irqsave(&musb->lock, flags); |
| 417 | 463 | ||
| 418 | switch (musb->xceiv->state) { | 464 | switch (musb->xceiv->otg->state) { |
| 419 | case OTG_STATE_A_WAIT_BCON: | 465 | case OTG_STATE_A_WAIT_BCON: |
| 420 | if ((musb->a_wait_bcon != 0) | 466 | if ((musb->a_wait_bcon != 0) |
| 421 | && (musb->idle_timeout == 0 | 467 | && (musb->idle_timeout == 0 |
| 422 | || time_after(jiffies, musb->idle_timeout))) { | 468 | || time_after(jiffies, musb->idle_timeout))) { |
| 423 | dev_dbg(musb->controller, "Nothing connected %s, turning off VBUS\n", | 469 | dev_dbg(musb->controller, "Nothing connected %s, turning off VBUS\n", |
| 424 | usb_otg_state_string(musb->xceiv->state)); | 470 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 425 | } | 471 | } |
| 426 | /* FALLTHROUGH */ | 472 | /* FALLTHROUGH */ |
| 427 | case OTG_STATE_A_IDLE: | 473 | case OTG_STATE_A_IDLE: |
| @@ -474,9 +520,9 @@ static void tusb_musb_try_idle(struct musb *musb, unsigned long timeout) | |||
| 474 | 520 | ||
| 475 | /* Never idle if active, or when VBUS timeout is not set as host */ | 521 | /* Never idle if active, or when VBUS timeout is not set as host */ |
| 476 | if (musb->is_active || ((musb->a_wait_bcon == 0) | 522 | if (musb->is_active || ((musb->a_wait_bcon == 0) |
| 477 | && (musb->xceiv->state == OTG_STATE_A_WAIT_BCON))) { | 523 | && (musb->xceiv->otg->state == OTG_STATE_A_WAIT_BCON))) { |
| 478 | dev_dbg(musb->controller, "%s active, deleting timer\n", | 524 | dev_dbg(musb->controller, "%s active, deleting timer\n", |
| 479 | usb_otg_state_string(musb->xceiv->state)); | 525 | usb_otg_state_string(musb->xceiv->otg->state)); |
| 480 | del_timer(&musb_idle_timer); | 526 | del_timer(&musb_idle_timer); |
| 481 | last_timer = jiffies; | 527 | last_timer = jiffies; |
| 482 | return; | 528 | return; |
| @@ -493,7 +539,7 @@ static void tusb_musb_try_idle(struct musb *musb, unsigned long timeout) | |||
| 493 | last_timer = timeout; | 539 | last_timer = timeout; |
| 494 | 540 | ||
| 495 | dev_dbg(musb->controller, "%s inactive, for idle timer for %lu ms\n", | 541 | dev_dbg(musb->controller, "%s inactive, for idle timer for %lu ms\n", |
| 496 | usb_otg_state_string(musb->xceiv->state), | 542 | usb_otg_state_string(musb->xceiv->otg->state), |
| 497 | (unsigned long)jiffies_to_msecs(timeout - jiffies)); | 543 | (unsigned long)jiffies_to_msecs(timeout - jiffies)); |
| 498 | mod_timer(&musb_idle_timer, timeout); | 544 | mod_timer(&musb_idle_timer, timeout); |
| 499 | } | 545 | } |
| @@ -524,7 +570,7 @@ static void tusb_musb_set_vbus(struct musb *musb, int is_on) | |||
| 524 | if (is_on) { | 570 | if (is_on) { |
| 525 | timer = OTG_TIMER_MS(OTG_TIME_A_WAIT_VRISE); | 571 | timer = OTG_TIMER_MS(OTG_TIME_A_WAIT_VRISE); |
| 526 | otg->default_a = 1; | 572 | otg->default_a = 1; |
| 527 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 573 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 528 | devctl |= MUSB_DEVCTL_SESSION; | 574 | devctl |= MUSB_DEVCTL_SESSION; |
| 529 | 575 | ||
| 530 | conf |= TUSB_DEV_CONF_USB_HOST_MODE; | 576 | conf |= TUSB_DEV_CONF_USB_HOST_MODE; |
| @@ -537,16 +583,16 @@ static void tusb_musb_set_vbus(struct musb *musb, int is_on) | |||
| 537 | /* If ID pin is grounded, we want to be a_idle */ | 583 | /* If ID pin is grounded, we want to be a_idle */ |
| 538 | otg_stat = musb_readl(tbase, TUSB_DEV_OTG_STAT); | 584 | otg_stat = musb_readl(tbase, TUSB_DEV_OTG_STAT); |
| 539 | if (!(otg_stat & TUSB_DEV_OTG_STAT_ID_STATUS)) { | 585 | if (!(otg_stat & TUSB_DEV_OTG_STAT_ID_STATUS)) { |
| 540 | switch (musb->xceiv->state) { | 586 | switch (musb->xceiv->otg->state) { |
| 541 | case OTG_STATE_A_WAIT_VRISE: | 587 | case OTG_STATE_A_WAIT_VRISE: |
| 542 | case OTG_STATE_A_WAIT_BCON: | 588 | case OTG_STATE_A_WAIT_BCON: |
| 543 | musb->xceiv->state = OTG_STATE_A_WAIT_VFALL; | 589 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VFALL; |
| 544 | break; | 590 | break; |
| 545 | case OTG_STATE_A_WAIT_VFALL: | 591 | case OTG_STATE_A_WAIT_VFALL: |
| 546 | musb->xceiv->state = OTG_STATE_A_IDLE; | 592 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 547 | break; | 593 | break; |
| 548 | default: | 594 | default: |
| 549 | musb->xceiv->state = OTG_STATE_A_IDLE; | 595 | musb->xceiv->otg->state = OTG_STATE_A_IDLE; |
| 550 | } | 596 | } |
| 551 | musb->is_active = 0; | 597 | musb->is_active = 0; |
| 552 | otg->default_a = 1; | 598 | otg->default_a = 1; |
| @@ -554,7 +600,7 @@ static void tusb_musb_set_vbus(struct musb *musb, int is_on) | |||
| 554 | } else { | 600 | } else { |
| 555 | musb->is_active = 0; | 601 | musb->is_active = 0; |
| 556 | otg->default_a = 0; | 602 | otg->default_a = 0; |
| 557 | musb->xceiv->state = OTG_STATE_B_IDLE; | 603 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 558 | MUSB_DEV_MODE(musb); | 604 | MUSB_DEV_MODE(musb); |
| 559 | } | 605 | } |
| 560 | 606 | ||
| @@ -569,7 +615,7 @@ static void tusb_musb_set_vbus(struct musb *musb, int is_on) | |||
| 569 | musb_writeb(musb->mregs, MUSB_DEVCTL, devctl); | 615 | musb_writeb(musb->mregs, MUSB_DEVCTL, devctl); |
| 570 | 616 | ||
| 571 | dev_dbg(musb->controller, "VBUS %s, devctl %02x otg %3x conf %08x prcm %08x\n", | 617 | dev_dbg(musb->controller, "VBUS %s, devctl %02x otg %3x conf %08x prcm %08x\n", |
| 572 | usb_otg_state_string(musb->xceiv->state), | 618 | usb_otg_state_string(musb->xceiv->otg->state), |
| 573 | musb_readb(musb->mregs, MUSB_DEVCTL), | 619 | musb_readb(musb->mregs, MUSB_DEVCTL), |
| 574 | musb_readl(tbase, TUSB_DEV_OTG_STAT), | 620 | musb_readl(tbase, TUSB_DEV_OTG_STAT), |
| 575 | conf, prcm); | 621 | conf, prcm); |
| @@ -668,23 +714,23 @@ tusb_otg_ints(struct musb *musb, u32 int_src, void __iomem *tbase) | |||
| 668 | 714 | ||
| 669 | if (otg_stat & TUSB_DEV_OTG_STAT_SESS_END) { | 715 | if (otg_stat & TUSB_DEV_OTG_STAT_SESS_END) { |
| 670 | dev_dbg(musb->controller, "Forcing disconnect (no interrupt)\n"); | 716 | dev_dbg(musb->controller, "Forcing disconnect (no interrupt)\n"); |
| 671 | if (musb->xceiv->state != OTG_STATE_B_IDLE) { | 717 | if (musb->xceiv->otg->state != OTG_STATE_B_IDLE) { |
| 672 | /* INTR_DISCONNECT can hide... */ | 718 | /* INTR_DISCONNECT can hide... */ |
| 673 | musb->xceiv->state = OTG_STATE_B_IDLE; | 719 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 674 | musb->int_usb |= MUSB_INTR_DISCONNECT; | 720 | musb->int_usb |= MUSB_INTR_DISCONNECT; |
| 675 | } | 721 | } |
| 676 | musb->is_active = 0; | 722 | musb->is_active = 0; |
| 677 | } | 723 | } |
| 678 | dev_dbg(musb->controller, "vbus change, %s, otg %03x\n", | 724 | dev_dbg(musb->controller, "vbus change, %s, otg %03x\n", |
| 679 | usb_otg_state_string(musb->xceiv->state), otg_stat); | 725 | usb_otg_state_string(musb->xceiv->otg->state), otg_stat); |
| 680 | idle_timeout = jiffies + (1 * HZ); | 726 | idle_timeout = jiffies + (1 * HZ); |
| 681 | schedule_work(&musb->irq_work); | 727 | schedule_work(&musb->irq_work); |
| 682 | 728 | ||
| 683 | } else /* A-dev state machine */ { | 729 | } else /* A-dev state machine */ { |
| 684 | dev_dbg(musb->controller, "vbus change, %s, otg %03x\n", | 730 | dev_dbg(musb->controller, "vbus change, %s, otg %03x\n", |
| 685 | usb_otg_state_string(musb->xceiv->state), otg_stat); | 731 | usb_otg_state_string(musb->xceiv->otg->state), otg_stat); |
| 686 | 732 | ||
| 687 | switch (musb->xceiv->state) { | 733 | switch (musb->xceiv->otg->state) { |
| 688 | case OTG_STATE_A_IDLE: | 734 | case OTG_STATE_A_IDLE: |
| 689 | dev_dbg(musb->controller, "Got SRP, turning on VBUS\n"); | 735 | dev_dbg(musb->controller, "Got SRP, turning on VBUS\n"); |
| 690 | musb_platform_set_vbus(musb, 1); | 736 | musb_platform_set_vbus(musb, 1); |
| @@ -731,9 +777,9 @@ tusb_otg_ints(struct musb *musb, u32 int_src, void __iomem *tbase) | |||
| 731 | u8 devctl; | 777 | u8 devctl; |
| 732 | 778 | ||
| 733 | dev_dbg(musb->controller, "%s timer, %03x\n", | 779 | dev_dbg(musb->controller, "%s timer, %03x\n", |
| 734 | usb_otg_state_string(musb->xceiv->state), otg_stat); | 780 | usb_otg_state_string(musb->xceiv->otg->state), otg_stat); |
| 735 | 781 | ||
| 736 | switch (musb->xceiv->state) { | 782 | switch (musb->xceiv->otg->state) { |
| 737 | case OTG_STATE_A_WAIT_VRISE: | 783 | case OTG_STATE_A_WAIT_VRISE: |
| 738 | /* VBUS has probably been valid for a while now, | 784 | /* VBUS has probably been valid for a while now, |
| 739 | * but may well have bounced out of range a bit | 785 | * but may well have bounced out of range a bit |
| @@ -745,7 +791,7 @@ tusb_otg_ints(struct musb *musb, u32 int_src, void __iomem *tbase) | |||
| 745 | dev_dbg(musb->controller, "devctl %02x\n", devctl); | 791 | dev_dbg(musb->controller, "devctl %02x\n", devctl); |
| 746 | break; | 792 | break; |
| 747 | } | 793 | } |
| 748 | musb->xceiv->state = OTG_STATE_A_WAIT_BCON; | 794 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_BCON; |
| 749 | musb->is_active = 0; | 795 | musb->is_active = 0; |
| 750 | idle_timeout = jiffies | 796 | idle_timeout = jiffies |
| 751 | + msecs_to_jiffies(musb->a_wait_bcon); | 797 | + msecs_to_jiffies(musb->a_wait_bcon); |
| @@ -1135,9 +1181,17 @@ static int tusb_musb_exit(struct musb *musb) | |||
| 1135 | } | 1181 | } |
| 1136 | 1182 | ||
| 1137 | static const struct musb_platform_ops tusb_ops = { | 1183 | static const struct musb_platform_ops tusb_ops = { |
| 1184 | .quirks = MUSB_IN_TUSB, | ||
| 1138 | .init = tusb_musb_init, | 1185 | .init = tusb_musb_init, |
| 1139 | .exit = tusb_musb_exit, | 1186 | .exit = tusb_musb_exit, |
| 1140 | 1187 | ||
| 1188 | .ep_offset = tusb_ep_offset, | ||
| 1189 | .ep_select = tusb_ep_select, | ||
| 1190 | .fifo_offset = tusb_fifo_offset, | ||
| 1191 | .readb = tusb_readb, | ||
| 1192 | .writeb = tusb_writeb, | ||
| 1193 | .read_fifo = tusb_read_fifo, | ||
| 1194 | .write_fifo = tusb_write_fifo, | ||
| 1141 | .enable = tusb_musb_enable, | 1195 | .enable = tusb_musb_enable, |
| 1142 | .disable = tusb_musb_disable, | 1196 | .disable = tusb_musb_disable, |
| 1143 | 1197 | ||
| @@ -1164,10 +1218,8 @@ static int tusb_probe(struct platform_device *pdev) | |||
| 1164 | int ret; | 1218 | int ret; |
| 1165 | 1219 | ||
| 1166 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); | 1220 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); |
| 1167 | if (!glue) { | 1221 | if (!glue) |
| 1168 | dev_err(&pdev->dev, "failed to allocate glue context\n"); | ||
| 1169 | return -ENOMEM; | 1222 | return -ENOMEM; |
| 1170 | } | ||
| 1171 | 1223 | ||
| 1172 | glue->dev = &pdev->dev; | 1224 | glue->dev = &pdev->dev; |
| 1173 | 1225 | ||
diff --git a/drivers/usb/musb/ux500.c b/drivers/usb/musb/ux500.c index dc666e96f45f..abf72728825f 100644 --- a/drivers/usb/musb/ux500.c +++ b/drivers/usb/musb/ux500.c | |||
| @@ -56,7 +56,7 @@ static void ux500_musb_set_vbus(struct musb *musb, int is_on) | |||
| 56 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); | 56 | devctl = musb_readb(musb->mregs, MUSB_DEVCTL); |
| 57 | 57 | ||
| 58 | if (is_on) { | 58 | if (is_on) { |
| 59 | if (musb->xceiv->state == OTG_STATE_A_IDLE) { | 59 | if (musb->xceiv->otg->state == OTG_STATE_A_IDLE) { |
| 60 | /* start the session */ | 60 | /* start the session */ |
| 61 | devctl |= MUSB_DEVCTL_SESSION; | 61 | devctl |= MUSB_DEVCTL_SESSION; |
| 62 | musb_writeb(musb->mregs, MUSB_DEVCTL, devctl); | 62 | musb_writeb(musb->mregs, MUSB_DEVCTL, devctl); |
| @@ -76,7 +76,7 @@ static void ux500_musb_set_vbus(struct musb *musb, int is_on) | |||
| 76 | } else { | 76 | } else { |
| 77 | musb->is_active = 1; | 77 | musb->is_active = 1; |
| 78 | musb->xceiv->otg->default_a = 1; | 78 | musb->xceiv->otg->default_a = 1; |
| 79 | musb->xceiv->state = OTG_STATE_A_WAIT_VRISE; | 79 | musb->xceiv->otg->state = OTG_STATE_A_WAIT_VRISE; |
| 80 | devctl |= MUSB_DEVCTL_SESSION; | 80 | devctl |= MUSB_DEVCTL_SESSION; |
| 81 | MUSB_HST_MODE(musb); | 81 | MUSB_HST_MODE(musb); |
| 82 | } | 82 | } |
| @@ -102,7 +102,7 @@ static void ux500_musb_set_vbus(struct musb *musb, int is_on) | |||
| 102 | mdelay(200); | 102 | mdelay(200); |
| 103 | 103 | ||
| 104 | dev_dbg(musb->controller, "VBUS %s, devctl %02x\n", | 104 | dev_dbg(musb->controller, "VBUS %s, devctl %02x\n", |
| 105 | usb_otg_state_string(musb->xceiv->state), | 105 | usb_otg_state_string(musb->xceiv->otg->state), |
| 106 | musb_readb(musb->mregs, MUSB_DEVCTL)); | 106 | musb_readb(musb->mregs, MUSB_DEVCTL)); |
| 107 | } | 107 | } |
| 108 | 108 | ||
| @@ -112,7 +112,7 @@ static int musb_otg_notifications(struct notifier_block *nb, | |||
| 112 | struct musb *musb = container_of(nb, struct musb, nb); | 112 | struct musb *musb = container_of(nb, struct musb, nb); |
| 113 | 113 | ||
| 114 | dev_dbg(musb->controller, "musb_otg_notifications %ld %s\n", | 114 | dev_dbg(musb->controller, "musb_otg_notifications %ld %s\n", |
| 115 | event, usb_otg_state_string(musb->xceiv->state)); | 115 | event, usb_otg_state_string(musb->xceiv->otg->state)); |
| 116 | 116 | ||
| 117 | switch (event) { | 117 | switch (event) { |
| 118 | case UX500_MUSB_ID: | 118 | case UX500_MUSB_ID: |
| @@ -127,7 +127,7 @@ static int musb_otg_notifications(struct notifier_block *nb, | |||
| 127 | if (is_host_active(musb)) | 127 | if (is_host_active(musb)) |
| 128 | ux500_musb_set_vbus(musb, 0); | 128 | ux500_musb_set_vbus(musb, 0); |
| 129 | else | 129 | else |
| 130 | musb->xceiv->state = OTG_STATE_B_IDLE; | 130 | musb->xceiv->otg->state = OTG_STATE_B_IDLE; |
| 131 | break; | 131 | break; |
| 132 | default: | 132 | default: |
| 133 | dev_dbg(musb->controller, "ID float\n"); | 133 | dev_dbg(musb->controller, "ID float\n"); |
| @@ -188,8 +188,10 @@ static int ux500_musb_exit(struct musb *musb) | |||
| 188 | } | 188 | } |
| 189 | 189 | ||
| 190 | static const struct musb_platform_ops ux500_ops = { | 190 | static const struct musb_platform_ops ux500_ops = { |
| 191 | .quirks = MUSB_INDEXED_EP, | ||
| 191 | .init = ux500_musb_init, | 192 | .init = ux500_musb_init, |
| 192 | .exit = ux500_musb_exit, | 193 | .exit = ux500_musb_exit, |
| 194 | .fifo_mode = 5, | ||
| 193 | 195 | ||
| 194 | .set_vbus = ux500_musb_set_vbus, | 196 | .set_vbus = ux500_musb_set_vbus, |
| 195 | }; | 197 | }; |
| @@ -247,10 +249,8 @@ static int ux500_probe(struct platform_device *pdev) | |||
| 247 | } | 249 | } |
| 248 | 250 | ||
| 249 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); | 251 | glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); |
| 250 | if (!glue) { | 252 | if (!glue) |
| 251 | dev_err(&pdev->dev, "failed to allocate glue context\n"); | ||
| 252 | goto err0; | 253 | goto err0; |
| 253 | } | ||
| 254 | 254 | ||
| 255 | musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); | 255 | musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); |
| 256 | if (!musb) { | 256 | if (!musb) { |
diff --git a/drivers/usb/musb/ux500_dma.c b/drivers/usb/musb/ux500_dma.c index 221faed9f074..e93845c26bdb 100644 --- a/drivers/usb/musb/ux500_dma.c +++ b/drivers/usb/musb/ux500_dma.c | |||
| @@ -91,9 +91,9 @@ static bool ux500_configure_channel(struct dma_channel *channel, | |||
| 91 | struct scatterlist sg; | 91 | struct scatterlist sg; |
| 92 | struct dma_slave_config slave_conf; | 92 | struct dma_slave_config slave_conf; |
| 93 | enum dma_slave_buswidth addr_width; | 93 | enum dma_slave_buswidth addr_width; |
| 94 | dma_addr_t usb_fifo_addr = (MUSB_FIFO_OFFSET(hw_ep->epnum) + | ||
| 95 | ux500_channel->controller->phy_base); | ||
| 96 | struct musb *musb = ux500_channel->controller->private_data; | 94 | struct musb *musb = ux500_channel->controller->private_data; |
| 95 | dma_addr_t usb_fifo_addr = (musb->io.fifo_offset(hw_ep->epnum) + | ||
| 96 | ux500_channel->controller->phy_base); | ||
| 97 | 97 | ||
| 98 | dev_dbg(musb->controller, | 98 | dev_dbg(musb->controller, |
| 99 | "packet_sz=%d, mode=%d, dma_addr=0x%llx, len=%d is_tx=%d\n", | 99 | "packet_sz=%d, mode=%d, dma_addr=0x%llx, len=%d is_tx=%d\n", |
| @@ -121,8 +121,7 @@ static bool ux500_configure_channel(struct dma_channel *channel, | |||
| 121 | slave_conf.dst_maxburst = 16; | 121 | slave_conf.dst_maxburst = 16; |
| 122 | slave_conf.device_fc = false; | 122 | slave_conf.device_fc = false; |
| 123 | 123 | ||
| 124 | dma_chan->device->device_control(dma_chan, DMA_SLAVE_CONFIG, | 124 | dmaengine_slave_config(dma_chan, &slave_conf); |
| 125 | (unsigned long) &slave_conf); | ||
| 126 | 125 | ||
| 127 | dma_desc = dmaengine_prep_slave_sg(dma_chan, &sg, 1, direction, | 126 | dma_desc = dmaengine_prep_slave_sg(dma_chan, &sg, 1, direction, |
| 128 | DMA_PREP_INTERRUPT | DMA_CTRL_ACK); | 127 | DMA_PREP_INTERRUPT | DMA_CTRL_ACK); |
| @@ -246,9 +245,7 @@ static int ux500_dma_channel_abort(struct dma_channel *channel) | |||
| 246 | musb_writew(epio, MUSB_RXCSR, csr); | 245 | musb_writew(epio, MUSB_RXCSR, csr); |
| 247 | } | 246 | } |
| 248 | 247 | ||
| 249 | ux500_channel->dma_chan->device-> | 248 | dmaengine_terminate_all(ux500_channel->dma_chan); |
| 250 | device_control(ux500_channel->dma_chan, | ||
| 251 | DMA_TERMINATE_ALL, 0); | ||
| 252 | channel->status = MUSB_DMA_STATUS_FREE; | 249 | channel->status = MUSB_DMA_STATUS_FREE; |
| 253 | } | 250 | } |
| 254 | return 0; | 251 | return 0; |
diff --git a/drivers/usb/phy/phy-ab8500-usb.c b/drivers/usb/phy/phy-ab8500-usb.c index 11ab2c45e462..8cd7d193c2ca 100644 --- a/drivers/usb/phy/phy-ab8500-usb.c +++ b/drivers/usb/phy/phy-ab8500-usb.c | |||
| @@ -1,6 +1,4 @@ | |||
| 1 | /* | 1 | /* |
| 2 | * drivers/usb/otg/ab8500_usb.c | ||
| 3 | * | ||
| 4 | * USB transceiver driver for AB8500 family chips | 2 | * USB transceiver driver for AB8500 family chips |
| 5 | * | 3 | * |
| 6 | * Copyright (C) 2010-2013 ST-Ericsson AB | 4 | * Copyright (C) 2010-2013 ST-Ericsson AB |
| @@ -446,7 +444,8 @@ static int ab9540_usb_link_status_update(struct ab8500_usb *ab, | |||
| 446 | if (event != UX500_MUSB_RIDB) | 444 | if (event != UX500_MUSB_RIDB) |
| 447 | event = UX500_MUSB_NONE; | 445 | event = UX500_MUSB_NONE; |
| 448 | /* Fallback to default B_IDLE as nothing is connected. */ | 446 | /* Fallback to default B_IDLE as nothing is connected. */ |
| 449 | ab->phy.state = OTG_STATE_B_IDLE; | 447 | ab->phy.otg->state = OTG_STATE_B_IDLE; |
| 448 | usb_phy_set_event(&ab->phy, USB_EVENT_NONE); | ||
| 450 | break; | 449 | break; |
| 451 | 450 | ||
| 452 | case USB_LINK_ACA_RID_C_NM_9540: | 451 | case USB_LINK_ACA_RID_C_NM_9540: |
| @@ -461,12 +460,14 @@ static int ab9540_usb_link_status_update(struct ab8500_usb *ab, | |||
| 461 | ab8500_usb_peri_phy_en(ab); | 460 | ab8500_usb_peri_phy_en(ab); |
| 462 | atomic_notifier_call_chain(&ab->phy.notifier, | 461 | atomic_notifier_call_chain(&ab->phy.notifier, |
| 463 | UX500_MUSB_PREPARE, &ab->vbus_draw); | 462 | UX500_MUSB_PREPARE, &ab->vbus_draw); |
| 463 | usb_phy_set_event(&ab->phy, USB_EVENT_ENUMERATED); | ||
| 464 | } | 464 | } |
| 465 | if (ab->mode == USB_IDLE) { | 465 | if (ab->mode == USB_IDLE) { |
| 466 | ab->mode = USB_PERIPHERAL; | 466 | ab->mode = USB_PERIPHERAL; |
| 467 | ab8500_usb_peri_phy_en(ab); | 467 | ab8500_usb_peri_phy_en(ab); |
| 468 | atomic_notifier_call_chain(&ab->phy.notifier, | 468 | atomic_notifier_call_chain(&ab->phy.notifier, |
| 469 | UX500_MUSB_PREPARE, &ab->vbus_draw); | 469 | UX500_MUSB_PREPARE, &ab->vbus_draw); |
| 470 | usb_phy_set_event(&ab->phy, USB_EVENT_ENUMERATED); | ||
| 470 | } | 471 | } |
| 471 | if (event != UX500_MUSB_RIDC) | 472 | if (event != UX500_MUSB_RIDC) |
| 472 | event = UX500_MUSB_VBUS; | 473 | event = UX500_MUSB_VBUS; |
| @@ -502,6 +503,7 @@ static int ab9540_usb_link_status_update(struct ab8500_usb *ab, | |||
| 502 | event = UX500_MUSB_CHARGER; | 503 | event = UX500_MUSB_CHARGER; |
| 503 | atomic_notifier_call_chain(&ab->phy.notifier, | 504 | atomic_notifier_call_chain(&ab->phy.notifier, |
| 504 | event, &ab->vbus_draw); | 505 | event, &ab->vbus_draw); |
| 506 | usb_phy_set_event(&ab->phy, USB_EVENT_CHARGER); | ||
| 505 | break; | 507 | break; |
| 506 | 508 | ||
| 507 | case USB_LINK_PHYEN_NO_VBUS_NO_IDGND_9540: | 509 | case USB_LINK_PHYEN_NO_VBUS_NO_IDGND_9540: |
| @@ -526,6 +528,7 @@ static int ab9540_usb_link_status_update(struct ab8500_usb *ab, | |||
| 526 | ab->mode = USB_IDLE; | 528 | ab->mode = USB_IDLE; |
| 527 | ab->phy.otg->default_a = false; | 529 | ab->phy.otg->default_a = false; |
| 528 | ab->vbus_draw = 0; | 530 | ab->vbus_draw = 0; |
| 531 | usb_phy_set_event(&ab->phy, USB_EVENT_NONE); | ||
| 529 | } | 532 | } |
| 530 | } | 533 | } |
| 531 | break; | 534 | break; |
| @@ -584,7 +587,8 @@ static int ab8540_usb_link_status_update(struct ab8500_usb *ab, | |||
| 584 | * Fallback to default B_IDLE as nothing | 587 | * Fallback to default B_IDLE as nothing |
| 585 | * is connected | 588 | * is connected |
| 586 | */ | 589 | */ |
| 587 | ab->phy.state = OTG_STATE_B_IDLE; | 590 | ab->phy.otg->state = OTG_STATE_B_IDLE; |
| 591 | usb_phy_set_event(&ab->phy, USB_EVENT_NONE); | ||
| 588 | break; | 592 | break; |
| 589 | 593 | ||
| 590 | case USB_LINK_ACA_RID_C_NM_8540: | 594 | case USB_LINK_ACA_RID_C_NM_8540: |
| @@ -598,6 +602,7 @@ static int ab8540_usb_link_status_update(struct ab8500_usb *ab, | |||
| 598 | ab8500_usb_peri_phy_en(ab); | 602 | ab8500_usb_peri_phy_en(ab); |
| 599 | atomic_notifier_call_chain(&ab->phy.notifier, | 603 | atomic_notifier_call_chain(&ab->phy.notifier, |
| 600 | UX500_MUSB_PREPARE, &ab->vbus_draw); | 604 | UX500_MUSB_PREPARE, &ab->vbus_draw); |
| 605 | usb_phy_set_event(&ab->phy, USB_EVENT_ENUMERATED); | ||
| 601 | } | 606 | } |
| 602 | if (event != UX500_MUSB_RIDC) | 607 | if (event != UX500_MUSB_RIDC) |
| 603 | event = UX500_MUSB_VBUS; | 608 | event = UX500_MUSB_VBUS; |
| @@ -626,6 +631,7 @@ static int ab8540_usb_link_status_update(struct ab8500_usb *ab, | |||
| 626 | event = UX500_MUSB_CHARGER; | 631 | event = UX500_MUSB_CHARGER; |
| 627 | atomic_notifier_call_chain(&ab->phy.notifier, | 632 | atomic_notifier_call_chain(&ab->phy.notifier, |
| 628 | event, &ab->vbus_draw); | 633 | event, &ab->vbus_draw); |
| 634 | usb_phy_set_event(&ab->phy, USB_EVENT_CHARGER); | ||
| 629 | break; | 635 | break; |
| 630 | 636 | ||
| 631 | case USB_LINK_PHYEN_NO_VBUS_NO_IDGND_8540: | 637 | case USB_LINK_PHYEN_NO_VBUS_NO_IDGND_8540: |
| @@ -648,6 +654,7 @@ static int ab8540_usb_link_status_update(struct ab8500_usb *ab, | |||
| 648 | ab->mode = USB_IDLE; | 654 | ab->mode = USB_IDLE; |
| 649 | ab->phy.otg->default_a = false; | 655 | ab->phy.otg->default_a = false; |
| 650 | ab->vbus_draw = 0; | 656 | ab->vbus_draw = 0; |
| 657 | usb_phy_set_event(&ab->phy, USB_EVENT_NONE); | ||
| 651 | } | 658 | } |
| 652 | break; | 659 | break; |
| 653 | 660 | ||
| @@ -693,7 +700,8 @@ static int ab8505_usb_link_status_update(struct ab8500_usb *ab, | |||
| 693 | * Fallback to default B_IDLE as nothing | 700 | * Fallback to default B_IDLE as nothing |
| 694 | * is connected | 701 | * is connected |
| 695 | */ | 702 | */ |
| 696 | ab->phy.state = OTG_STATE_B_IDLE; | 703 | ab->phy.otg->state = OTG_STATE_B_IDLE; |
| 704 | usb_phy_set_event(&ab->phy, USB_EVENT_NONE); | ||
| 697 | break; | 705 | break; |
| 698 | 706 | ||
| 699 | case USB_LINK_ACA_RID_C_NM_8505: | 707 | case USB_LINK_ACA_RID_C_NM_8505: |
| @@ -707,6 +715,7 @@ static int ab8505_usb_link_status_update(struct ab8500_usb *ab, | |||
| 707 | ab8500_usb_peri_phy_en(ab); | 715 | ab8500_usb_peri_phy_en(ab); |
| 708 | atomic_notifier_call_chain(&ab->phy.notifier, | 716 | atomic_notifier_call_chain(&ab->phy.notifier, |
| 709 | UX500_MUSB_PREPARE, &ab->vbus_draw); | 717 | UX500_MUSB_PREPARE, &ab->vbus_draw); |
| 718 | usb_phy_set_event(&ab->phy, USB_EVENT_ENUMERATED); | ||
| 710 | } | 719 | } |
| 711 | if (event != UX500_MUSB_RIDC) | 720 | if (event != UX500_MUSB_RIDC) |
| 712 | event = UX500_MUSB_VBUS; | 721 | event = UX500_MUSB_VBUS; |
| @@ -734,6 +743,7 @@ static int ab8505_usb_link_status_update(struct ab8500_usb *ab, | |||
| 734 | event = UX500_MUSB_CHARGER; | 743 | event = UX500_MUSB_CHARGER; |
| 735 | atomic_notifier_call_chain(&ab->phy.notifier, | 744 | atomic_notifier_call_chain(&ab->phy.notifier, |
| 736 | event, &ab->vbus_draw); | 745 | event, &ab->vbus_draw); |
| 746 | usb_phy_set_event(&ab->phy, USB_EVENT_CHARGER); | ||
| 737 | break; | 747 | break; |
| 738 | 748 | ||
| 739 | default: | 749 | default: |
| @@ -776,7 +786,8 @@ static int ab8500_usb_link_status_update(struct ab8500_usb *ab, | |||
| 776 | if (event != UX500_MUSB_RIDB) | 786 | if (event != UX500_MUSB_RIDB) |
| 777 | event = UX500_MUSB_NONE; | 787 | event = UX500_MUSB_NONE; |
| 778 | /* Fallback to default B_IDLE as nothing is connected */ | 788 | /* Fallback to default B_IDLE as nothing is connected */ |
| 779 | ab->phy.state = OTG_STATE_B_IDLE; | 789 | ab->phy.otg->state = OTG_STATE_B_IDLE; |
| 790 | usb_phy_set_event(&ab->phy, USB_EVENT_NONE); | ||
| 780 | break; | 791 | break; |
| 781 | 792 | ||
| 782 | case USB_LINK_ACA_RID_C_NM_8500: | 793 | case USB_LINK_ACA_RID_C_NM_8500: |
| @@ -794,6 +805,7 @@ static int ab8500_usb_link_status_update(struct ab8500_usb *ab, | |||
| 794 | ab8500_usb_peri_phy_en(ab); | 805 | ab8500_usb_peri_phy_en(ab); |
| 795 | atomic_notifier_call_chain(&ab->phy.notifier, | 806 | atomic_notifier_call_chain(&ab->phy.notifier, |
| 796 | UX500_MUSB_PREPARE, &ab->vbus_draw); | 807 | UX500_MUSB_PREPARE, &ab->vbus_draw); |
| 808 | usb_phy_set_event(&ab->phy, USB_EVENT_ENUMERATED); | ||
| 797 | } | 809 | } |
| 798 | if (event != UX500_MUSB_RIDC) | 810 | if (event != UX500_MUSB_RIDC) |
| 799 | event = UX500_MUSB_VBUS; | 811 | event = UX500_MUSB_VBUS; |
| @@ -820,6 +832,7 @@ static int ab8500_usb_link_status_update(struct ab8500_usb *ab, | |||
| 820 | event = UX500_MUSB_CHARGER; | 832 | event = UX500_MUSB_CHARGER; |
| 821 | atomic_notifier_call_chain(&ab->phy.notifier, | 833 | atomic_notifier_call_chain(&ab->phy.notifier, |
| 822 | event, &ab->vbus_draw); | 834 | event, &ab->vbus_draw); |
| 835 | usb_phy_set_event(&ab->phy, USB_EVENT_CHARGER); | ||
| 823 | break; | 836 | break; |
| 824 | 837 | ||
| 825 | case USB_LINK_RESERVED_8500: | 838 | case USB_LINK_RESERVED_8500: |
| @@ -1056,7 +1069,7 @@ static int ab8500_usb_set_peripheral(struct usb_otg *otg, | |||
| 1056 | if (!otg) | 1069 | if (!otg) |
| 1057 | return -ENODEV; | 1070 | return -ENODEV; |
| 1058 | 1071 | ||
| 1059 | ab = phy_to_ab(otg->phy); | 1072 | ab = phy_to_ab(otg->usb_phy); |
| 1060 | 1073 | ||
| 1061 | ab->phy.otg->gadget = gadget; | 1074 | ab->phy.otg->gadget = gadget; |
| 1062 | 1075 | ||
| @@ -1080,7 +1093,7 @@ static int ab8500_usb_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
| 1080 | if (!otg) | 1093 | if (!otg) |
| 1081 | return -ENODEV; | 1094 | return -ENODEV; |
| 1082 | 1095 | ||
| 1083 | ab = phy_to_ab(otg->phy); | 1096 | ab = phy_to_ab(otg->usb_phy); |
| 1084 | 1097 | ||
| 1085 | ab->phy.otg->host = host; | 1098 | ab->phy.otg->host = host; |
| 1086 | 1099 | ||
| @@ -1380,9 +1393,9 @@ static int ab8500_usb_probe(struct platform_device *pdev) | |||
| 1380 | ab->phy.label = "ab8500"; | 1393 | ab->phy.label = "ab8500"; |
| 1381 | ab->phy.set_suspend = ab8500_usb_set_suspend; | 1394 | ab->phy.set_suspend = ab8500_usb_set_suspend; |
| 1382 | ab->phy.set_power = ab8500_usb_set_power; | 1395 | ab->phy.set_power = ab8500_usb_set_power; |
| 1383 | ab->phy.state = OTG_STATE_UNDEFINED; | 1396 | ab->phy.otg->state = OTG_STATE_UNDEFINED; |
| 1384 | 1397 | ||
| 1385 | otg->phy = &ab->phy; | 1398 | otg->usb_phy = &ab->phy; |
| 1386 | otg->set_host = ab8500_usb_set_host; | 1399 | otg->set_host = ab8500_usb_set_host; |
| 1387 | otg->set_peripheral = ab8500_usb_set_peripheral; | 1400 | otg->set_peripheral = ab8500_usb_set_peripheral; |
| 1388 | 1401 | ||
diff --git a/drivers/usb/phy/phy-am335x-control.c b/drivers/usb/phy/phy-am335x-control.c index 35b6083b7999..2e923c581809 100644 --- a/drivers/usb/phy/phy-am335x-control.c +++ b/drivers/usb/phy/phy-am335x-control.c | |||
| @@ -147,10 +147,8 @@ static int am335x_control_usb_probe(struct platform_device *pdev) | |||
| 147 | phy_ctrl = of_id->data; | 147 | phy_ctrl = of_id->data; |
| 148 | 148 | ||
| 149 | ctrl_usb = devm_kzalloc(&pdev->dev, sizeof(*ctrl_usb), GFP_KERNEL); | 149 | ctrl_usb = devm_kzalloc(&pdev->dev, sizeof(*ctrl_usb), GFP_KERNEL); |
| 150 | if (!ctrl_usb) { | 150 | if (!ctrl_usb) |
| 151 | dev_err(&pdev->dev, "unable to alloc memory for control usb\n"); | ||
| 152 | return -ENOMEM; | 151 | return -ENOMEM; |
| 153 | } | ||
| 154 | 152 | ||
| 155 | ctrl_usb->dev = &pdev->dev; | 153 | ctrl_usb->dev = &pdev->dev; |
| 156 | 154 | ||
diff --git a/drivers/usb/phy/phy-fsl-usb.c b/drivers/usb/phy/phy-fsl-usb.c index f1ea5990a50a..ab38aa32a6c1 100644 --- a/drivers/usb/phy/phy-fsl-usb.c +++ b/drivers/usb/phy/phy-fsl-usb.c | |||
| @@ -274,7 +274,7 @@ void b_srp_end(unsigned long foo) | |||
| 274 | fsl_otg_dischrg_vbus(0); | 274 | fsl_otg_dischrg_vbus(0); |
| 275 | srp_wait_done = 1; | 275 | srp_wait_done = 1; |
| 276 | 276 | ||
| 277 | if ((fsl_otg_dev->phy.state == OTG_STATE_B_SRP_INIT) && | 277 | if ((fsl_otg_dev->phy.otg->state == OTG_STATE_B_SRP_INIT) && |
| 278 | fsl_otg_dev->fsm.b_sess_vld) | 278 | fsl_otg_dev->fsm.b_sess_vld) |
| 279 | fsl_otg_dev->fsm.b_srp_done = 1; | 279 | fsl_otg_dev->fsm.b_srp_done = 1; |
| 280 | } | 280 | } |
| @@ -499,7 +499,8 @@ int fsl_otg_start_host(struct otg_fsm *fsm, int on) | |||
| 499 | { | 499 | { |
| 500 | struct usb_otg *otg = fsm->otg; | 500 | struct usb_otg *otg = fsm->otg; |
| 501 | struct device *dev; | 501 | struct device *dev; |
| 502 | struct fsl_otg *otg_dev = container_of(otg->phy, struct fsl_otg, phy); | 502 | struct fsl_otg *otg_dev = |
| 503 | container_of(otg->usb_phy, struct fsl_otg, phy); | ||
| 503 | u32 retval = 0; | 504 | u32 retval = 0; |
| 504 | 505 | ||
| 505 | if (!otg->host) | 506 | if (!otg->host) |
| @@ -594,7 +595,7 @@ static int fsl_otg_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
| 594 | if (!otg) | 595 | if (!otg) |
| 595 | return -ENODEV; | 596 | return -ENODEV; |
| 596 | 597 | ||
| 597 | otg_dev = container_of(otg->phy, struct fsl_otg, phy); | 598 | otg_dev = container_of(otg->usb_phy, struct fsl_otg, phy); |
| 598 | if (otg_dev != fsl_otg_dev) | 599 | if (otg_dev != fsl_otg_dev) |
| 599 | return -ENODEV; | 600 | return -ENODEV; |
| 600 | 601 | ||
| @@ -623,7 +624,7 @@ static int fsl_otg_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
| 623 | /* Mini-A cable connected */ | 624 | /* Mini-A cable connected */ |
| 624 | struct otg_fsm *fsm = &otg_dev->fsm; | 625 | struct otg_fsm *fsm = &otg_dev->fsm; |
| 625 | 626 | ||
| 626 | otg->phy->state = OTG_STATE_UNDEFINED; | 627 | otg->state = OTG_STATE_UNDEFINED; |
| 627 | fsm->protocol = PROTO_UNDEF; | 628 | fsm->protocol = PROTO_UNDEF; |
| 628 | } | 629 | } |
| 629 | } | 630 | } |
| @@ -644,7 +645,7 @@ static int fsl_otg_set_peripheral(struct usb_otg *otg, | |||
| 644 | if (!otg) | 645 | if (!otg) |
| 645 | return -ENODEV; | 646 | return -ENODEV; |
| 646 | 647 | ||
| 647 | otg_dev = container_of(otg->phy, struct fsl_otg, phy); | 648 | otg_dev = container_of(otg->usb_phy, struct fsl_otg, phy); |
| 648 | VDBG("otg_dev 0x%x\n", (int)otg_dev); | 649 | VDBG("otg_dev 0x%x\n", (int)otg_dev); |
| 649 | VDBG("fsl_otg_dev 0x%x\n", (int)fsl_otg_dev); | 650 | VDBG("fsl_otg_dev 0x%x\n", (int)fsl_otg_dev); |
| 650 | if (otg_dev != fsl_otg_dev) | 651 | if (otg_dev != fsl_otg_dev) |
| @@ -681,7 +682,7 @@ static int fsl_otg_set_power(struct usb_phy *phy, unsigned mA) | |||
| 681 | { | 682 | { |
| 682 | if (!fsl_otg_dev) | 683 | if (!fsl_otg_dev) |
| 683 | return -ENODEV; | 684 | return -ENODEV; |
| 684 | if (phy->state == OTG_STATE_B_PERIPHERAL) | 685 | if (phy->otg->state == OTG_STATE_B_PERIPHERAL) |
| 685 | pr_info("FSL OTG: Draw %d mA\n", mA); | 686 | pr_info("FSL OTG: Draw %d mA\n", mA); |
| 686 | 687 | ||
| 687 | return 0; | 688 | return 0; |
| @@ -714,10 +715,10 @@ static int fsl_otg_start_srp(struct usb_otg *otg) | |||
| 714 | { | 715 | { |
| 715 | struct fsl_otg *otg_dev; | 716 | struct fsl_otg *otg_dev; |
| 716 | 717 | ||
| 717 | if (!otg || otg->phy->state != OTG_STATE_B_IDLE) | 718 | if (!otg || otg->state != OTG_STATE_B_IDLE) |
| 718 | return -ENODEV; | 719 | return -ENODEV; |
| 719 | 720 | ||
| 720 | otg_dev = container_of(otg->phy, struct fsl_otg, phy); | 721 | otg_dev = container_of(otg->usb_phy, struct fsl_otg, phy); |
| 721 | if (otg_dev != fsl_otg_dev) | 722 | if (otg_dev != fsl_otg_dev) |
| 722 | return -ENODEV; | 723 | return -ENODEV; |
| 723 | 724 | ||
| @@ -735,7 +736,7 @@ static int fsl_otg_start_hnp(struct usb_otg *otg) | |||
| 735 | if (!otg) | 736 | if (!otg) |
| 736 | return -ENODEV; | 737 | return -ENODEV; |
| 737 | 738 | ||
| 738 | otg_dev = container_of(otg->phy, struct fsl_otg, phy); | 739 | otg_dev = container_of(otg->usb_phy, struct fsl_otg, phy); |
| 739 | if (otg_dev != fsl_otg_dev) | 740 | if (otg_dev != fsl_otg_dev) |
| 740 | return -ENODEV; | 741 | return -ENODEV; |
| 741 | 742 | ||
| @@ -857,7 +858,7 @@ static int fsl_otg_conf(struct platform_device *pdev) | |||
| 857 | fsl_otg_tc->phy.dev = &pdev->dev; | 858 | fsl_otg_tc->phy.dev = &pdev->dev; |
| 858 | fsl_otg_tc->phy.set_power = fsl_otg_set_power; | 859 | fsl_otg_tc->phy.set_power = fsl_otg_set_power; |
| 859 | 860 | ||
| 860 | fsl_otg_tc->phy.otg->phy = &fsl_otg_tc->phy; | 861 | fsl_otg_tc->phy.otg->usb_phy = &fsl_otg_tc->phy; |
| 861 | fsl_otg_tc->phy.otg->set_host = fsl_otg_set_host; | 862 | fsl_otg_tc->phy.otg->set_host = fsl_otg_set_host; |
| 862 | fsl_otg_tc->phy.otg->set_peripheral = fsl_otg_set_peripheral; | 863 | fsl_otg_tc->phy.otg->set_peripheral = fsl_otg_set_peripheral; |
| 863 | fsl_otg_tc->phy.otg->start_hnp = fsl_otg_start_hnp; | 864 | fsl_otg_tc->phy.otg->start_hnp = fsl_otg_start_hnp; |
| @@ -989,10 +990,10 @@ int usb_otg_start(struct platform_device *pdev) | |||
| 989 | * Also: record initial state of ID pin | 990 | * Also: record initial state of ID pin |
| 990 | */ | 991 | */ |
| 991 | if (fsl_readl(&p_otg->dr_mem_map->otgsc) & OTGSC_STS_USB_ID) { | 992 | if (fsl_readl(&p_otg->dr_mem_map->otgsc) & OTGSC_STS_USB_ID) { |
| 992 | p_otg->phy.state = OTG_STATE_UNDEFINED; | 993 | p_otg->phy.otg->state = OTG_STATE_UNDEFINED; |
| 993 | p_otg->fsm.id = 1; | 994 | p_otg->fsm.id = 1; |
| 994 | } else { | 995 | } else { |
| 995 | p_otg->phy.state = OTG_STATE_A_IDLE; | 996 | p_otg->phy.otg->state = OTG_STATE_A_IDLE; |
| 996 | p_otg->fsm.id = 0; | 997 | p_otg->fsm.id = 0; |
| 997 | } | 998 | } |
| 998 | 999 | ||
| @@ -1047,7 +1048,7 @@ static int show_fsl_usb2_otg_state(struct device *dev, | |||
| 1047 | /* State */ | 1048 | /* State */ |
| 1048 | t = scnprintf(next, size, | 1049 | t = scnprintf(next, size, |
| 1049 | "OTG state: %s\n\n", | 1050 | "OTG state: %s\n\n", |
| 1050 | usb_otg_state_string(fsl_otg_dev->phy.state)); | 1051 | usb_otg_state_string(fsl_otg_dev->phy.otg->state)); |
| 1051 | size -= t; | 1052 | size -= t; |
| 1052 | next += t; | 1053 | next += t; |
| 1053 | 1054 | ||
diff --git a/drivers/usb/phy/phy-fsl-usb.h b/drivers/usb/phy/phy-fsl-usb.h index 5986c96354df..23149954a09c 100644 --- a/drivers/usb/phy/phy-fsl-usb.h +++ b/drivers/usb/phy/phy-fsl-usb.h | |||
| @@ -298,7 +298,7 @@ | |||
| 298 | /* SE0 Time Before SRP */ | 298 | /* SE0 Time Before SRP */ |
| 299 | #define TB_SE0_SRP (2) /* b_idle,minimum 2 ms, section:5.3.2 */ | 299 | #define TB_SE0_SRP (2) /* b_idle,minimum 2 ms, section:5.3.2 */ |
| 300 | 300 | ||
| 301 | #define SET_OTG_STATE(otg_ptr, newstate) ((otg_ptr)->state = newstate) | 301 | #define SET_OTG_STATE(phy, newstate) ((phy)->otg->state = newstate) |
| 302 | 302 | ||
| 303 | struct usb_dr_mmap { | 303 | struct usb_dr_mmap { |
| 304 | /* Capability register */ | 304 | /* Capability register */ |
diff --git a/drivers/usb/phy/phy-generic.c b/drivers/usb/phy/phy-generic.c index 7594e5069ae5..4ba1f57220f6 100644 --- a/drivers/usb/phy/phy-generic.c +++ b/drivers/usb/phy/phy-generic.c | |||
| @@ -1,6 +1,4 @@ | |||
| 1 | /* | 1 | /* |
| 2 | * drivers/usb/otg/nop-usb-xceiv.c | ||
| 3 | * | ||
| 4 | * NOP USB transceiver for all USB transceiver which are either built-in | 2 | * NOP USB transceiver for all USB transceiver which are either built-in |
| 5 | * into USB IP or which are mostly autonomous. | 3 | * into USB IP or which are mostly autonomous. |
| 6 | * | 4 | * |
| @@ -123,7 +121,7 @@ static int nop_set_peripheral(struct usb_otg *otg, struct usb_gadget *gadget) | |||
| 123 | } | 121 | } |
| 124 | 122 | ||
| 125 | otg->gadget = gadget; | 123 | otg->gadget = gadget; |
| 126 | otg->phy->state = OTG_STATE_B_IDLE; | 124 | otg->state = OTG_STATE_B_IDLE; |
| 127 | return 0; | 125 | return 0; |
| 128 | } | 126 | } |
| 129 | 127 | ||
| @@ -225,10 +223,10 @@ int usb_phy_gen_create_phy(struct device *dev, struct usb_phy_generic *nop, | |||
| 225 | nop->phy.dev = nop->dev; | 223 | nop->phy.dev = nop->dev; |
| 226 | nop->phy.label = "nop-xceiv"; | 224 | nop->phy.label = "nop-xceiv"; |
| 227 | nop->phy.set_suspend = nop_set_suspend; | 225 | nop->phy.set_suspend = nop_set_suspend; |
| 228 | nop->phy.state = OTG_STATE_UNDEFINED; | ||
| 229 | nop->phy.type = type; | 226 | nop->phy.type = type; |
| 230 | 227 | ||
| 231 | nop->phy.otg->phy = &nop->phy; | 228 | nop->phy.otg->state = OTG_STATE_UNDEFINED; |
| 229 | nop->phy.otg->usb_phy = &nop->phy; | ||
| 232 | nop->phy.otg->set_host = nop_set_host; | 230 | nop->phy.otg->set_host = nop_set_host; |
| 233 | nop->phy.otg->set_peripheral = nop_set_peripheral; | 231 | nop->phy.otg->set_peripheral = nop_set_peripheral; |
| 234 | 232 | ||
diff --git a/drivers/usb/phy/phy-gpio-vbus-usb.c b/drivers/usb/phy/phy-gpio-vbus-usb.c index f4b14bd97e14..54511725caaf 100644 --- a/drivers/usb/phy/phy-gpio-vbus-usb.c +++ b/drivers/usb/phy/phy-gpio-vbus-usb.c | |||
| @@ -121,7 +121,7 @@ static void gpio_vbus_work(struct work_struct *work) | |||
| 121 | 121 | ||
| 122 | if (vbus) { | 122 | if (vbus) { |
| 123 | status = USB_EVENT_VBUS; | 123 | status = USB_EVENT_VBUS; |
| 124 | gpio_vbus->phy.state = OTG_STATE_B_PERIPHERAL; | 124 | gpio_vbus->phy.otg->state = OTG_STATE_B_PERIPHERAL; |
| 125 | gpio_vbus->phy.last_event = status; | 125 | gpio_vbus->phy.last_event = status; |
| 126 | usb_gadget_vbus_connect(gpio_vbus->phy.otg->gadget); | 126 | usb_gadget_vbus_connect(gpio_vbus->phy.otg->gadget); |
| 127 | 127 | ||
| @@ -134,6 +134,7 @@ static void gpio_vbus_work(struct work_struct *work) | |||
| 134 | 134 | ||
| 135 | atomic_notifier_call_chain(&gpio_vbus->phy.notifier, | 135 | atomic_notifier_call_chain(&gpio_vbus->phy.notifier, |
| 136 | status, gpio_vbus->phy.otg->gadget); | 136 | status, gpio_vbus->phy.otg->gadget); |
| 137 | usb_phy_set_event(&gpio_vbus->phy, USB_EVENT_ENUMERATED); | ||
| 137 | } else { | 138 | } else { |
| 138 | /* optionally disable D+ pullup */ | 139 | /* optionally disable D+ pullup */ |
| 139 | if (gpio_is_valid(gpio)) | 140 | if (gpio_is_valid(gpio)) |
| @@ -143,11 +144,12 @@ static void gpio_vbus_work(struct work_struct *work) | |||
| 143 | 144 | ||
| 144 | usb_gadget_vbus_disconnect(gpio_vbus->phy.otg->gadget); | 145 | usb_gadget_vbus_disconnect(gpio_vbus->phy.otg->gadget); |
| 145 | status = USB_EVENT_NONE; | 146 | status = USB_EVENT_NONE; |
| 146 | gpio_vbus->phy.state = OTG_STATE_B_IDLE; | 147 | gpio_vbus->phy.otg->state = OTG_STATE_B_IDLE; |
| 147 | gpio_vbus->phy.last_event = status; | 148 | gpio_vbus->phy.last_event = status; |
| 148 | 149 | ||
| 149 | atomic_notifier_call_chain(&gpio_vbus->phy.notifier, | 150 | atomic_notifier_call_chain(&gpio_vbus->phy.notifier, |
| 150 | status, gpio_vbus->phy.otg->gadget); | 151 | status, gpio_vbus->phy.otg->gadget); |
| 152 | usb_phy_set_event(&gpio_vbus->phy, USB_EVENT_NONE); | ||
| 151 | } | 153 | } |
| 152 | } | 154 | } |
| 153 | 155 | ||
| @@ -180,7 +182,7 @@ static int gpio_vbus_set_peripheral(struct usb_otg *otg, | |||
| 180 | struct platform_device *pdev; | 182 | struct platform_device *pdev; |
| 181 | int gpio; | 183 | int gpio; |
| 182 | 184 | ||
| 183 | gpio_vbus = container_of(otg->phy, struct gpio_vbus_data, phy); | 185 | gpio_vbus = container_of(otg->usb_phy, struct gpio_vbus_data, phy); |
| 184 | pdev = to_platform_device(gpio_vbus->dev); | 186 | pdev = to_platform_device(gpio_vbus->dev); |
| 185 | pdata = dev_get_platdata(gpio_vbus->dev); | 187 | pdata = dev_get_platdata(gpio_vbus->dev); |
| 186 | gpio = pdata->gpio_pullup; | 188 | gpio = pdata->gpio_pullup; |
| @@ -196,7 +198,7 @@ static int gpio_vbus_set_peripheral(struct usb_otg *otg, | |||
| 196 | set_vbus_draw(gpio_vbus, 0); | 198 | set_vbus_draw(gpio_vbus, 0); |
| 197 | 199 | ||
| 198 | usb_gadget_vbus_disconnect(otg->gadget); | 200 | usb_gadget_vbus_disconnect(otg->gadget); |
| 199 | otg->phy->state = OTG_STATE_UNDEFINED; | 201 | otg->state = OTG_STATE_UNDEFINED; |
| 200 | 202 | ||
| 201 | otg->gadget = NULL; | 203 | otg->gadget = NULL; |
| 202 | return 0; | 204 | return 0; |
| @@ -218,7 +220,7 @@ static int gpio_vbus_set_power(struct usb_phy *phy, unsigned mA) | |||
| 218 | 220 | ||
| 219 | gpio_vbus = container_of(phy, struct gpio_vbus_data, phy); | 221 | gpio_vbus = container_of(phy, struct gpio_vbus_data, phy); |
| 220 | 222 | ||
| 221 | if (phy->state == OTG_STATE_B_PERIPHERAL) | 223 | if (phy->otg->state == OTG_STATE_B_PERIPHERAL) |
| 222 | set_vbus_draw(gpio_vbus, mA); | 224 | set_vbus_draw(gpio_vbus, mA); |
| 223 | return 0; | 225 | return 0; |
| 224 | } | 226 | } |
| @@ -269,9 +271,9 @@ static int gpio_vbus_probe(struct platform_device *pdev) | |||
| 269 | gpio_vbus->phy.dev = gpio_vbus->dev; | 271 | gpio_vbus->phy.dev = gpio_vbus->dev; |
| 270 | gpio_vbus->phy.set_power = gpio_vbus_set_power; | 272 | gpio_vbus->phy.set_power = gpio_vbus_set_power; |
| 271 | gpio_vbus->phy.set_suspend = gpio_vbus_set_suspend; | 273 | gpio_vbus->phy.set_suspend = gpio_vbus_set_suspend; |
| 272 | gpio_vbus->phy.state = OTG_STATE_UNDEFINED; | ||
| 273 | 274 | ||
| 274 | gpio_vbus->phy.otg->phy = &gpio_vbus->phy; | 275 | gpio_vbus->phy.otg->state = OTG_STATE_UNDEFINED; |
| 276 | gpio_vbus->phy.otg->usb_phy = &gpio_vbus->phy; | ||
| 275 | gpio_vbus->phy.otg->set_peripheral = gpio_vbus_set_peripheral; | 277 | gpio_vbus->phy.otg->set_peripheral = gpio_vbus_set_peripheral; |
| 276 | 278 | ||
| 277 | err = devm_gpio_request(&pdev->dev, gpio, "vbus_detect"); | 279 | err = devm_gpio_request(&pdev->dev, gpio, "vbus_detect"); |
diff --git a/drivers/usb/phy/phy-isp1301-omap.c b/drivers/usb/phy/phy-isp1301-omap.c index 8eea56d3ded6..a2dfb2ae520e 100644 --- a/drivers/usb/phy/phy-isp1301-omap.c +++ b/drivers/usb/phy/phy-isp1301-omap.c | |||
| @@ -234,7 +234,7 @@ isp1301_clear_bits(struct isp1301 *isp, u8 reg, u8 bits) | |||
| 234 | 234 | ||
| 235 | static inline const char *state_name(struct isp1301 *isp) | 235 | static inline const char *state_name(struct isp1301 *isp) |
| 236 | { | 236 | { |
| 237 | return usb_otg_state_string(isp->phy.state); | 237 | return usb_otg_state_string(isp->phy.otg->state); |
| 238 | } | 238 | } |
| 239 | 239 | ||
| 240 | /*-------------------------------------------------------------------------*/ | 240 | /*-------------------------------------------------------------------------*/ |
| @@ -249,7 +249,7 @@ static inline const char *state_name(struct isp1301 *isp) | |||
| 249 | 249 | ||
| 250 | static void power_down(struct isp1301 *isp) | 250 | static void power_down(struct isp1301 *isp) |
| 251 | { | 251 | { |
| 252 | isp->phy.state = OTG_STATE_UNDEFINED; | 252 | isp->phy.otg->state = OTG_STATE_UNDEFINED; |
| 253 | 253 | ||
| 254 | // isp1301_set_bits(isp, ISP1301_MODE_CONTROL_2, MC2_GLOBAL_PWR_DN); | 254 | // isp1301_set_bits(isp, ISP1301_MODE_CONTROL_2, MC2_GLOBAL_PWR_DN); |
| 255 | isp1301_set_bits(isp, ISP1301_MODE_CONTROL_1, MC1_SUSPEND); | 255 | isp1301_set_bits(isp, ISP1301_MODE_CONTROL_1, MC1_SUSPEND); |
| @@ -339,7 +339,7 @@ static void a_idle(struct isp1301 *isp, const char *tag) | |||
| 339 | { | 339 | { |
| 340 | u32 l; | 340 | u32 l; |
| 341 | 341 | ||
| 342 | if (isp->phy.state == OTG_STATE_A_IDLE) | 342 | if (isp->phy.otg->state == OTG_STATE_A_IDLE) |
| 343 | return; | 343 | return; |
| 344 | 344 | ||
| 345 | isp->phy.otg->default_a = 1; | 345 | isp->phy.otg->default_a = 1; |
| @@ -351,7 +351,7 @@ static void a_idle(struct isp1301 *isp, const char *tag) | |||
| 351 | isp->phy.otg->gadget->is_a_peripheral = 1; | 351 | isp->phy.otg->gadget->is_a_peripheral = 1; |
| 352 | gadget_suspend(isp); | 352 | gadget_suspend(isp); |
| 353 | } | 353 | } |
| 354 | isp->phy.state = OTG_STATE_A_IDLE; | 354 | isp->phy.otg->state = OTG_STATE_A_IDLE; |
| 355 | l = omap_readl(OTG_CTRL) & OTG_XCEIV_OUTPUTS; | 355 | l = omap_readl(OTG_CTRL) & OTG_XCEIV_OUTPUTS; |
| 356 | omap_writel(l, OTG_CTRL); | 356 | omap_writel(l, OTG_CTRL); |
| 357 | isp->last_otg_ctrl = l; | 357 | isp->last_otg_ctrl = l; |
| @@ -363,7 +363,7 @@ static void b_idle(struct isp1301 *isp, const char *tag) | |||
| 363 | { | 363 | { |
| 364 | u32 l; | 364 | u32 l; |
| 365 | 365 | ||
| 366 | if (isp->phy.state == OTG_STATE_B_IDLE) | 366 | if (isp->phy.otg->state == OTG_STATE_B_IDLE) |
| 367 | return; | 367 | return; |
| 368 | 368 | ||
| 369 | isp->phy.otg->default_a = 0; | 369 | isp->phy.otg->default_a = 0; |
| @@ -375,7 +375,7 @@ static void b_idle(struct isp1301 *isp, const char *tag) | |||
| 375 | isp->phy.otg->gadget->is_a_peripheral = 0; | 375 | isp->phy.otg->gadget->is_a_peripheral = 0; |
| 376 | gadget_suspend(isp); | 376 | gadget_suspend(isp); |
| 377 | } | 377 | } |
| 378 | isp->phy.state = OTG_STATE_B_IDLE; | 378 | isp->phy.otg->state = OTG_STATE_B_IDLE; |
| 379 | l = omap_readl(OTG_CTRL) & OTG_XCEIV_OUTPUTS; | 379 | l = omap_readl(OTG_CTRL) & OTG_XCEIV_OUTPUTS; |
| 380 | omap_writel(l, OTG_CTRL); | 380 | omap_writel(l, OTG_CTRL); |
| 381 | isp->last_otg_ctrl = l; | 381 | isp->last_otg_ctrl = l; |
| @@ -474,7 +474,7 @@ static void check_state(struct isp1301 *isp, const char *tag) | |||
| 474 | default: | 474 | default: |
| 475 | break; | 475 | break; |
| 476 | } | 476 | } |
| 477 | if (isp->phy.state == state && !extra) | 477 | if (isp->phy.otg->state == state && !extra) |
| 478 | return; | 478 | return; |
| 479 | pr_debug("otg: %s FSM %s/%02x, %s, %06x\n", tag, | 479 | pr_debug("otg: %s FSM %s/%02x, %s, %06x\n", tag, |
| 480 | usb_otg_state_string(state), fsm, state_name(isp), | 480 | usb_otg_state_string(state), fsm, state_name(isp), |
| @@ -498,23 +498,23 @@ static void update_otg1(struct isp1301 *isp, u8 int_src) | |||
| 498 | 498 | ||
| 499 | if (int_src & INTR_SESS_VLD) | 499 | if (int_src & INTR_SESS_VLD) |
| 500 | otg_ctrl |= OTG_ASESSVLD; | 500 | otg_ctrl |= OTG_ASESSVLD; |
| 501 | else if (isp->phy.state == OTG_STATE_A_WAIT_VFALL) { | 501 | else if (isp->phy.otg->state == OTG_STATE_A_WAIT_VFALL) { |
| 502 | a_idle(isp, "vfall"); | 502 | a_idle(isp, "vfall"); |
| 503 | otg_ctrl &= ~OTG_CTRL_BITS; | 503 | otg_ctrl &= ~OTG_CTRL_BITS; |
| 504 | } | 504 | } |
| 505 | if (int_src & INTR_VBUS_VLD) | 505 | if (int_src & INTR_VBUS_VLD) |
| 506 | otg_ctrl |= OTG_VBUSVLD; | 506 | otg_ctrl |= OTG_VBUSVLD; |
| 507 | if (int_src & INTR_ID_GND) { /* default-A */ | 507 | if (int_src & INTR_ID_GND) { /* default-A */ |
| 508 | if (isp->phy.state == OTG_STATE_B_IDLE | 508 | if (isp->phy.otg->state == OTG_STATE_B_IDLE |
| 509 | || isp->phy.state | 509 | || isp->phy.otg->state |
| 510 | == OTG_STATE_UNDEFINED) { | 510 | == OTG_STATE_UNDEFINED) { |
| 511 | a_idle(isp, "init"); | 511 | a_idle(isp, "init"); |
| 512 | return; | 512 | return; |
| 513 | } | 513 | } |
| 514 | } else { /* default-B */ | 514 | } else { /* default-B */ |
| 515 | otg_ctrl |= OTG_ID; | 515 | otg_ctrl |= OTG_ID; |
| 516 | if (isp->phy.state == OTG_STATE_A_IDLE | 516 | if (isp->phy.otg->state == OTG_STATE_A_IDLE |
| 517 | || isp->phy.state == OTG_STATE_UNDEFINED) { | 517 | || isp->phy.otg->state == OTG_STATE_UNDEFINED) { |
| 518 | b_idle(isp, "init"); | 518 | b_idle(isp, "init"); |
| 519 | return; | 519 | return; |
| 520 | } | 520 | } |
| @@ -548,14 +548,14 @@ static void otg_update_isp(struct isp1301 *isp) | |||
| 548 | isp->last_otg_ctrl = otg_ctrl; | 548 | isp->last_otg_ctrl = otg_ctrl; |
| 549 | otg_ctrl = otg_ctrl & OTG_XCEIV_INPUTS; | 549 | otg_ctrl = otg_ctrl & OTG_XCEIV_INPUTS; |
| 550 | 550 | ||
| 551 | switch (isp->phy.state) { | 551 | switch (isp->phy.otg->state) { |
| 552 | case OTG_STATE_B_IDLE: | 552 | case OTG_STATE_B_IDLE: |
| 553 | case OTG_STATE_B_PERIPHERAL: | 553 | case OTG_STATE_B_PERIPHERAL: |
| 554 | case OTG_STATE_B_SRP_INIT: | 554 | case OTG_STATE_B_SRP_INIT: |
| 555 | if (!(otg_ctrl & OTG_PULLUP)) { | 555 | if (!(otg_ctrl & OTG_PULLUP)) { |
| 556 | // if (otg_ctrl & OTG_B_HNPEN) { | 556 | // if (otg_ctrl & OTG_B_HNPEN) { |
| 557 | if (isp->phy.otg->gadget->b_hnp_enable) { | 557 | if (isp->phy.otg->gadget->b_hnp_enable) { |
| 558 | isp->phy.state = OTG_STATE_B_WAIT_ACON; | 558 | isp->phy.otg->state = OTG_STATE_B_WAIT_ACON; |
| 559 | pr_debug(" --> b_wait_acon\n"); | 559 | pr_debug(" --> b_wait_acon\n"); |
| 560 | } | 560 | } |
| 561 | goto pulldown; | 561 | goto pulldown; |
| @@ -585,7 +585,7 @@ pulldown: | |||
| 585 | if (!(isp->phy.otg->host)) | 585 | if (!(isp->phy.otg->host)) |
| 586 | otg_ctrl &= ~OTG_DRV_VBUS; | 586 | otg_ctrl &= ~OTG_DRV_VBUS; |
| 587 | 587 | ||
| 588 | switch (isp->phy.state) { | 588 | switch (isp->phy.otg->state) { |
| 589 | case OTG_STATE_A_SUSPEND: | 589 | case OTG_STATE_A_SUSPEND: |
| 590 | if (otg_ctrl & OTG_DRV_VBUS) { | 590 | if (otg_ctrl & OTG_DRV_VBUS) { |
| 591 | set |= OTG1_VBUS_DRV; | 591 | set |= OTG1_VBUS_DRV; |
| @@ -596,7 +596,7 @@ pulldown: | |||
| 596 | 596 | ||
| 597 | /* FALLTHROUGH */ | 597 | /* FALLTHROUGH */ |
| 598 | case OTG_STATE_A_VBUS_ERR: | 598 | case OTG_STATE_A_VBUS_ERR: |
| 599 | isp->phy.state = OTG_STATE_A_WAIT_VFALL; | 599 | isp->phy.otg->state = OTG_STATE_A_WAIT_VFALL; |
| 600 | pr_debug(" --> a_wait_vfall\n"); | 600 | pr_debug(" --> a_wait_vfall\n"); |
| 601 | /* FALLTHROUGH */ | 601 | /* FALLTHROUGH */ |
| 602 | case OTG_STATE_A_WAIT_VFALL: | 602 | case OTG_STATE_A_WAIT_VFALL: |
| @@ -605,7 +605,7 @@ pulldown: | |||
| 605 | break; | 605 | break; |
| 606 | case OTG_STATE_A_IDLE: | 606 | case OTG_STATE_A_IDLE: |
| 607 | if (otg_ctrl & OTG_DRV_VBUS) { | 607 | if (otg_ctrl & OTG_DRV_VBUS) { |
| 608 | isp->phy.state = OTG_STATE_A_WAIT_VRISE; | 608 | isp->phy.otg->state = OTG_STATE_A_WAIT_VRISE; |
| 609 | pr_debug(" --> a_wait_vrise\n"); | 609 | pr_debug(" --> a_wait_vrise\n"); |
| 610 | } | 610 | } |
| 611 | /* FALLTHROUGH */ | 611 | /* FALLTHROUGH */ |
| @@ -625,17 +625,17 @@ pulldown: | |||
| 625 | if (otg_change & OTG_PULLUP) { | 625 | if (otg_change & OTG_PULLUP) { |
| 626 | u32 l; | 626 | u32 l; |
| 627 | 627 | ||
| 628 | switch (isp->phy.state) { | 628 | switch (isp->phy.otg->state) { |
| 629 | case OTG_STATE_B_IDLE: | 629 | case OTG_STATE_B_IDLE: |
| 630 | if (clr & OTG1_DP_PULLUP) | 630 | if (clr & OTG1_DP_PULLUP) |
| 631 | break; | 631 | break; |
| 632 | isp->phy.state = OTG_STATE_B_PERIPHERAL; | 632 | isp->phy.otg->state = OTG_STATE_B_PERIPHERAL; |
| 633 | pr_debug(" --> b_peripheral\n"); | 633 | pr_debug(" --> b_peripheral\n"); |
| 634 | break; | 634 | break; |
| 635 | case OTG_STATE_A_SUSPEND: | 635 | case OTG_STATE_A_SUSPEND: |
| 636 | if (clr & OTG1_DP_PULLUP) | 636 | if (clr & OTG1_DP_PULLUP) |
| 637 | break; | 637 | break; |
| 638 | isp->phy.state = OTG_STATE_A_PERIPHERAL; | 638 | isp->phy.otg->state = OTG_STATE_A_PERIPHERAL; |
| 639 | pr_debug(" --> a_peripheral\n"); | 639 | pr_debug(" --> a_peripheral\n"); |
| 640 | break; | 640 | break; |
| 641 | default: | 641 | default: |
| @@ -673,7 +673,7 @@ static irqreturn_t omap_otg_irq(int irq, void *_isp) | |||
| 673 | * remote wakeup (SRP, normal) using their own timer | 673 | * remote wakeup (SRP, normal) using their own timer |
| 674 | * to give "check cable and A-device" messages. | 674 | * to give "check cable and A-device" messages. |
| 675 | */ | 675 | */ |
| 676 | if (isp->phy.state == OTG_STATE_B_SRP_INIT) | 676 | if (isp->phy.otg->state == OTG_STATE_B_SRP_INIT) |
| 677 | b_idle(isp, "srp_timeout"); | 677 | b_idle(isp, "srp_timeout"); |
| 678 | 678 | ||
| 679 | omap_writew(B_SRP_TMROUT, OTG_IRQ_SRC); | 679 | omap_writew(B_SRP_TMROUT, OTG_IRQ_SRC); |
| @@ -691,7 +691,7 @@ static irqreturn_t omap_otg_irq(int irq, void *_isp) | |||
| 691 | omap_writel(otg_ctrl, OTG_CTRL); | 691 | omap_writel(otg_ctrl, OTG_CTRL); |
| 692 | 692 | ||
| 693 | /* subset of b_peripheral()... */ | 693 | /* subset of b_peripheral()... */ |
| 694 | isp->phy.state = OTG_STATE_B_PERIPHERAL; | 694 | isp->phy.otg->state = OTG_STATE_B_PERIPHERAL; |
| 695 | pr_debug(" --> b_peripheral\n"); | 695 | pr_debug(" --> b_peripheral\n"); |
| 696 | 696 | ||
| 697 | omap_writew(B_HNP_FAIL, OTG_IRQ_SRC); | 697 | omap_writew(B_HNP_FAIL, OTG_IRQ_SRC); |
| @@ -703,7 +703,7 @@ static irqreturn_t omap_otg_irq(int irq, void *_isp) | |||
| 703 | state_name(isp), omap_readl(OTG_CTRL)); | 703 | state_name(isp), omap_readl(OTG_CTRL)); |
| 704 | 704 | ||
| 705 | isp1301_defer_work(isp, WORK_UPDATE_OTG); | 705 | isp1301_defer_work(isp, WORK_UPDATE_OTG); |
| 706 | switch (isp->phy.state) { | 706 | switch (isp->phy.otg->state) { |
| 707 | case OTG_STATE_A_IDLE: | 707 | case OTG_STATE_A_IDLE: |
| 708 | if (!otg->host) | 708 | if (!otg->host) |
| 709 | break; | 709 | break; |
| @@ -734,7 +734,7 @@ static irqreturn_t omap_otg_irq(int irq, void *_isp) | |||
| 734 | otg_ctrl |= OTG_BUSDROP; | 734 | otg_ctrl |= OTG_BUSDROP; |
| 735 | otg_ctrl &= ~OTG_A_BUSREQ & OTG_CTRL_MASK & ~OTG_XCEIV_INPUTS; | 735 | otg_ctrl &= ~OTG_A_BUSREQ & OTG_CTRL_MASK & ~OTG_XCEIV_INPUTS; |
| 736 | omap_writel(otg_ctrl, OTG_CTRL); | 736 | omap_writel(otg_ctrl, OTG_CTRL); |
| 737 | isp->phy.state = OTG_STATE_A_WAIT_VFALL; | 737 | isp->phy.otg->state = OTG_STATE_A_WAIT_VFALL; |
| 738 | 738 | ||
| 739 | omap_writew(A_REQ_TMROUT, OTG_IRQ_SRC); | 739 | omap_writew(A_REQ_TMROUT, OTG_IRQ_SRC); |
| 740 | ret = IRQ_HANDLED; | 740 | ret = IRQ_HANDLED; |
| @@ -748,7 +748,7 @@ static irqreturn_t omap_otg_irq(int irq, void *_isp) | |||
| 748 | otg_ctrl |= OTG_BUSDROP; | 748 | otg_ctrl |= OTG_BUSDROP; |
| 749 | otg_ctrl &= ~OTG_A_BUSREQ & OTG_CTRL_MASK & ~OTG_XCEIV_INPUTS; | 749 | otg_ctrl &= ~OTG_A_BUSREQ & OTG_CTRL_MASK & ~OTG_XCEIV_INPUTS; |
| 750 | omap_writel(otg_ctrl, OTG_CTRL); | 750 | omap_writel(otg_ctrl, OTG_CTRL); |
| 751 | isp->phy.state = OTG_STATE_A_VBUS_ERR; | 751 | isp->phy.otg->state = OTG_STATE_A_VBUS_ERR; |
| 752 | 752 | ||
| 753 | omap_writew(A_VBUS_ERR, OTG_IRQ_SRC); | 753 | omap_writew(A_VBUS_ERR, OTG_IRQ_SRC); |
| 754 | ret = IRQ_HANDLED; | 754 | ret = IRQ_HANDLED; |
| @@ -769,7 +769,7 @@ static irqreturn_t omap_otg_irq(int irq, void *_isp) | |||
| 769 | 769 | ||
| 770 | /* role is peripheral */ | 770 | /* role is peripheral */ |
| 771 | if (otg_ctrl & OTG_DRIVER_SEL) { | 771 | if (otg_ctrl & OTG_DRIVER_SEL) { |
| 772 | switch (isp->phy.state) { | 772 | switch (isp->phy.otg->state) { |
| 773 | case OTG_STATE_A_IDLE: | 773 | case OTG_STATE_A_IDLE: |
| 774 | b_idle(isp, __func__); | 774 | b_idle(isp, __func__); |
| 775 | break; | 775 | break; |
| @@ -786,18 +786,18 @@ static irqreturn_t omap_otg_irq(int irq, void *_isp) | |||
| 786 | } | 786 | } |
| 787 | 787 | ||
| 788 | if (otg->host) { | 788 | if (otg->host) { |
| 789 | switch (isp->phy.state) { | 789 | switch (isp->phy.otg->state) { |
| 790 | case OTG_STATE_B_WAIT_ACON: | 790 | case OTG_STATE_B_WAIT_ACON: |
| 791 | isp->phy.state = OTG_STATE_B_HOST; | 791 | isp->phy.otg->state = OTG_STATE_B_HOST; |
| 792 | pr_debug(" --> b_host\n"); | 792 | pr_debug(" --> b_host\n"); |
| 793 | kick = 1; | 793 | kick = 1; |
| 794 | break; | 794 | break; |
| 795 | case OTG_STATE_A_WAIT_BCON: | 795 | case OTG_STATE_A_WAIT_BCON: |
| 796 | isp->phy.state = OTG_STATE_A_HOST; | 796 | isp->phy.otg->state = OTG_STATE_A_HOST; |
| 797 | pr_debug(" --> a_host\n"); | 797 | pr_debug(" --> a_host\n"); |
| 798 | break; | 798 | break; |
| 799 | case OTG_STATE_A_PERIPHERAL: | 799 | case OTG_STATE_A_PERIPHERAL: |
| 800 | isp->phy.state = OTG_STATE_A_WAIT_BCON; | 800 | isp->phy.otg->state = OTG_STATE_A_WAIT_BCON; |
| 801 | pr_debug(" --> a_wait_bcon\n"); | 801 | pr_debug(" --> a_wait_bcon\n"); |
| 802 | break; | 802 | break; |
| 803 | default: | 803 | default: |
| @@ -937,7 +937,7 @@ static void b_peripheral(struct isp1301 *isp) | |||
| 937 | /* UDC driver just set OTG_BSESSVLD */ | 937 | /* UDC driver just set OTG_BSESSVLD */ |
| 938 | isp1301_set_bits(isp, ISP1301_OTG_CONTROL_1, OTG1_DP_PULLUP); | 938 | isp1301_set_bits(isp, ISP1301_OTG_CONTROL_1, OTG1_DP_PULLUP); |
| 939 | isp1301_clear_bits(isp, ISP1301_OTG_CONTROL_1, OTG1_DP_PULLDOWN); | 939 | isp1301_clear_bits(isp, ISP1301_OTG_CONTROL_1, OTG1_DP_PULLDOWN); |
| 940 | isp->phy.state = OTG_STATE_B_PERIPHERAL; | 940 | isp->phy.otg->state = OTG_STATE_B_PERIPHERAL; |
| 941 | pr_debug(" --> b_peripheral\n"); | 941 | pr_debug(" --> b_peripheral\n"); |
| 942 | dump_regs(isp, "2periph"); | 942 | dump_regs(isp, "2periph"); |
| 943 | #endif | 943 | #endif |
| @@ -947,7 +947,7 @@ static void isp_update_otg(struct isp1301 *isp, u8 stat) | |||
| 947 | { | 947 | { |
| 948 | struct usb_otg *otg = isp->phy.otg; | 948 | struct usb_otg *otg = isp->phy.otg; |
| 949 | u8 isp_stat, isp_bstat; | 949 | u8 isp_stat, isp_bstat; |
| 950 | enum usb_otg_state state = isp->phy.state; | 950 | enum usb_otg_state state = isp->phy.otg->state; |
| 951 | 951 | ||
| 952 | if (stat & INTR_BDIS_ACON) | 952 | if (stat & INTR_BDIS_ACON) |
| 953 | pr_debug("OTG: BDIS_ACON, %s\n", state_name(isp)); | 953 | pr_debug("OTG: BDIS_ACON, %s\n", state_name(isp)); |
| @@ -970,7 +970,7 @@ static void isp_update_otg(struct isp1301 *isp, u8 stat) | |||
| 970 | * when HNP is used. | 970 | * when HNP is used. |
| 971 | */ | 971 | */ |
| 972 | if (isp_stat & INTR_VBUS_VLD) | 972 | if (isp_stat & INTR_VBUS_VLD) |
| 973 | isp->phy.state = OTG_STATE_A_HOST; | 973 | isp->phy.otg->state = OTG_STATE_A_HOST; |
| 974 | break; | 974 | break; |
| 975 | case OTG_STATE_A_WAIT_VFALL: | 975 | case OTG_STATE_A_WAIT_VFALL: |
| 976 | if (!(isp_stat & INTR_SESS_VLD)) | 976 | if (!(isp_stat & INTR_SESS_VLD)) |
| @@ -978,7 +978,7 @@ static void isp_update_otg(struct isp1301 *isp, u8 stat) | |||
| 978 | break; | 978 | break; |
| 979 | default: | 979 | default: |
| 980 | if (!(isp_stat & INTR_VBUS_VLD)) | 980 | if (!(isp_stat & INTR_VBUS_VLD)) |
| 981 | isp->phy.state = OTG_STATE_A_VBUS_ERR; | 981 | isp->phy.otg->state = OTG_STATE_A_VBUS_ERR; |
| 982 | break; | 982 | break; |
| 983 | } | 983 | } |
| 984 | isp_bstat = isp1301_get_u8(isp, ISP1301_OTG_STATUS); | 984 | isp_bstat = isp1301_get_u8(isp, ISP1301_OTG_STATUS); |
| @@ -1007,7 +1007,7 @@ static void isp_update_otg(struct isp1301 *isp, u8 stat) | |||
| 1007 | if (otg->default_a) { | 1007 | if (otg->default_a) { |
| 1008 | switch (state) { | 1008 | switch (state) { |
| 1009 | default: | 1009 | default: |
| 1010 | isp->phy.state = OTG_STATE_A_WAIT_VFALL; | 1010 | isp->phy.otg->state = OTG_STATE_A_WAIT_VFALL; |
| 1011 | break; | 1011 | break; |
| 1012 | case OTG_STATE_A_WAIT_VFALL: | 1012 | case OTG_STATE_A_WAIT_VFALL: |
| 1013 | state = OTG_STATE_A_IDLE; | 1013 | state = OTG_STATE_A_IDLE; |
| @@ -1020,7 +1020,7 @@ static void isp_update_otg(struct isp1301 *isp, u8 stat) | |||
| 1020 | host_suspend(isp); | 1020 | host_suspend(isp); |
| 1021 | isp1301_clear_bits(isp, ISP1301_MODE_CONTROL_1, | 1021 | isp1301_clear_bits(isp, ISP1301_MODE_CONTROL_1, |
| 1022 | MC1_BDIS_ACON_EN); | 1022 | MC1_BDIS_ACON_EN); |
| 1023 | isp->phy.state = OTG_STATE_B_IDLE; | 1023 | isp->phy.otg->state = OTG_STATE_B_IDLE; |
| 1024 | l = omap_readl(OTG_CTRL) & OTG_CTRL_MASK; | 1024 | l = omap_readl(OTG_CTRL) & OTG_CTRL_MASK; |
| 1025 | l &= ~OTG_CTRL_BITS; | 1025 | l &= ~OTG_CTRL_BITS; |
| 1026 | omap_writel(l, OTG_CTRL); | 1026 | omap_writel(l, OTG_CTRL); |
| @@ -1031,7 +1031,7 @@ static void isp_update_otg(struct isp1301 *isp, u8 stat) | |||
| 1031 | } | 1031 | } |
| 1032 | isp_bstat = isp1301_get_u8(isp, ISP1301_OTG_STATUS); | 1032 | isp_bstat = isp1301_get_u8(isp, ISP1301_OTG_STATUS); |
| 1033 | 1033 | ||
| 1034 | switch (isp->phy.state) { | 1034 | switch (isp->phy.otg->state) { |
| 1035 | case OTG_STATE_B_PERIPHERAL: | 1035 | case OTG_STATE_B_PERIPHERAL: |
| 1036 | case OTG_STATE_B_WAIT_ACON: | 1036 | case OTG_STATE_B_WAIT_ACON: |
| 1037 | case OTG_STATE_B_HOST: | 1037 | case OTG_STATE_B_HOST: |
| @@ -1071,7 +1071,7 @@ static void isp_update_otg(struct isp1301 *isp, u8 stat) | |||
| 1071 | } | 1071 | } |
| 1072 | } | 1072 | } |
| 1073 | 1073 | ||
| 1074 | if (state != isp->phy.state) | 1074 | if (state != isp->phy.otg->state) |
| 1075 | pr_debug(" isp, %s -> %s\n", | 1075 | pr_debug(" isp, %s -> %s\n", |
| 1076 | usb_otg_state_string(state), state_name(isp)); | 1076 | usb_otg_state_string(state), state_name(isp)); |
| 1077 | 1077 | ||
| @@ -1129,10 +1129,10 @@ isp1301_work(struct work_struct *work) | |||
| 1129 | * skip A_WAIT_VRISE; hc transitions invisibly | 1129 | * skip A_WAIT_VRISE; hc transitions invisibly |
| 1130 | * skip A_WAIT_BCON; same. | 1130 | * skip A_WAIT_BCON; same. |
| 1131 | */ | 1131 | */ |
| 1132 | switch (isp->phy.state) { | 1132 | switch (isp->phy.otg->state) { |
| 1133 | case OTG_STATE_A_WAIT_BCON: | 1133 | case OTG_STATE_A_WAIT_BCON: |
| 1134 | case OTG_STATE_A_WAIT_VRISE: | 1134 | case OTG_STATE_A_WAIT_VRISE: |
| 1135 | isp->phy.state = OTG_STATE_A_HOST; | 1135 | isp->phy.otg->state = OTG_STATE_A_HOST; |
| 1136 | pr_debug(" --> a_host\n"); | 1136 | pr_debug(" --> a_host\n"); |
| 1137 | otg_ctrl = omap_readl(OTG_CTRL); | 1137 | otg_ctrl = omap_readl(OTG_CTRL); |
| 1138 | otg_ctrl |= OTG_A_BUSREQ; | 1138 | otg_ctrl |= OTG_A_BUSREQ; |
| @@ -1141,7 +1141,7 @@ isp1301_work(struct work_struct *work) | |||
| 1141 | omap_writel(otg_ctrl, OTG_CTRL); | 1141 | omap_writel(otg_ctrl, OTG_CTRL); |
| 1142 | break; | 1142 | break; |
| 1143 | case OTG_STATE_B_WAIT_ACON: | 1143 | case OTG_STATE_B_WAIT_ACON: |
| 1144 | isp->phy.state = OTG_STATE_B_HOST; | 1144 | isp->phy.otg->state = OTG_STATE_B_HOST; |
| 1145 | pr_debug(" --> b_host (acon)\n"); | 1145 | pr_debug(" --> b_host (acon)\n"); |
| 1146 | break; | 1146 | break; |
| 1147 | case OTG_STATE_B_HOST: | 1147 | case OTG_STATE_B_HOST: |
| @@ -1275,7 +1275,7 @@ static int isp1301_otg_enable(struct isp1301 *isp) | |||
| 1275 | static int | 1275 | static int |
| 1276 | isp1301_set_host(struct usb_otg *otg, struct usb_bus *host) | 1276 | isp1301_set_host(struct usb_otg *otg, struct usb_bus *host) |
| 1277 | { | 1277 | { |
| 1278 | struct isp1301 *isp = container_of(otg->phy, struct isp1301, phy); | 1278 | struct isp1301 *isp = container_of(otg->usb_phy, struct isp1301, phy); |
| 1279 | 1279 | ||
| 1280 | if (isp != the_transceiver) | 1280 | if (isp != the_transceiver) |
| 1281 | return -ENODEV; | 1281 | return -ENODEV; |
| @@ -1331,7 +1331,7 @@ isp1301_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
| 1331 | static int | 1331 | static int |
| 1332 | isp1301_set_peripheral(struct usb_otg *otg, struct usb_gadget *gadget) | 1332 | isp1301_set_peripheral(struct usb_otg *otg, struct usb_gadget *gadget) |
| 1333 | { | 1333 | { |
| 1334 | struct isp1301 *isp = container_of(otg->phy, struct isp1301, phy); | 1334 | struct isp1301 *isp = container_of(otg->usb_phy, struct isp1301, phy); |
| 1335 | 1335 | ||
| 1336 | if (isp != the_transceiver) | 1336 | if (isp != the_transceiver) |
| 1337 | return -ENODEV; | 1337 | return -ENODEV; |
| @@ -1368,7 +1368,7 @@ isp1301_set_peripheral(struct usb_otg *otg, struct usb_gadget *gadget) | |||
| 1368 | } | 1368 | } |
| 1369 | 1369 | ||
| 1370 | power_up(isp); | 1370 | power_up(isp); |
| 1371 | isp->phy.state = OTG_STATE_B_IDLE; | 1371 | isp->phy.otg->state = OTG_STATE_B_IDLE; |
| 1372 | 1372 | ||
| 1373 | if (machine_is_omap_h2() || machine_is_omap_h3()) | 1373 | if (machine_is_omap_h2() || machine_is_omap_h3()) |
| 1374 | isp1301_set_bits(isp, ISP1301_MODE_CONTROL_1, MC1_DAT_SE0); | 1374 | isp1301_set_bits(isp, ISP1301_MODE_CONTROL_1, MC1_DAT_SE0); |
| @@ -1403,7 +1403,7 @@ isp1301_set_power(struct usb_phy *dev, unsigned mA) | |||
| 1403 | { | 1403 | { |
| 1404 | if (!the_transceiver) | 1404 | if (!the_transceiver) |
| 1405 | return -ENODEV; | 1405 | return -ENODEV; |
| 1406 | if (dev->state == OTG_STATE_B_PERIPHERAL) | 1406 | if (dev->otg->state == OTG_STATE_B_PERIPHERAL) |
| 1407 | enable_vbus_draw(the_transceiver, mA); | 1407 | enable_vbus_draw(the_transceiver, mA); |
| 1408 | return 0; | 1408 | return 0; |
| 1409 | } | 1409 | } |
| @@ -1411,10 +1411,10 @@ isp1301_set_power(struct usb_phy *dev, unsigned mA) | |||
| 1411 | static int | 1411 | static int |
| 1412 | isp1301_start_srp(struct usb_otg *otg) | 1412 | isp1301_start_srp(struct usb_otg *otg) |
| 1413 | { | 1413 | { |
| 1414 | struct isp1301 *isp = container_of(otg->phy, struct isp1301, phy); | 1414 | struct isp1301 *isp = container_of(otg->usb_phy, struct isp1301, phy); |
| 1415 | u32 otg_ctrl; | 1415 | u32 otg_ctrl; |
| 1416 | 1416 | ||
| 1417 | if (isp != the_transceiver || isp->phy.state != OTG_STATE_B_IDLE) | 1417 | if (isp != the_transceiver || isp->phy.otg->state != OTG_STATE_B_IDLE) |
| 1418 | return -ENODEV; | 1418 | return -ENODEV; |
| 1419 | 1419 | ||
| 1420 | otg_ctrl = omap_readl(OTG_CTRL); | 1420 | otg_ctrl = omap_readl(OTG_CTRL); |
| @@ -1424,7 +1424,7 @@ isp1301_start_srp(struct usb_otg *otg) | |||
| 1424 | otg_ctrl |= OTG_B_BUSREQ; | 1424 | otg_ctrl |= OTG_B_BUSREQ; |
| 1425 | otg_ctrl &= ~OTG_A_BUSREQ & OTG_CTRL_MASK; | 1425 | otg_ctrl &= ~OTG_A_BUSREQ & OTG_CTRL_MASK; |
| 1426 | omap_writel(otg_ctrl, OTG_CTRL); | 1426 | omap_writel(otg_ctrl, OTG_CTRL); |
| 1427 | isp->phy.state = OTG_STATE_B_SRP_INIT; | 1427 | isp->phy.otg->state = OTG_STATE_B_SRP_INIT; |
| 1428 | 1428 | ||
| 1429 | pr_debug("otg: SRP, %s ... %06x\n", state_name(isp), | 1429 | pr_debug("otg: SRP, %s ... %06x\n", state_name(isp), |
| 1430 | omap_readl(OTG_CTRL)); | 1430 | omap_readl(OTG_CTRL)); |
| @@ -1438,7 +1438,7 @@ static int | |||
| 1438 | isp1301_start_hnp(struct usb_otg *otg) | 1438 | isp1301_start_hnp(struct usb_otg *otg) |
| 1439 | { | 1439 | { |
| 1440 | #ifdef CONFIG_USB_OTG | 1440 | #ifdef CONFIG_USB_OTG |
| 1441 | struct isp1301 *isp = container_of(otg->phy, struct isp1301, phy); | 1441 | struct isp1301 *isp = container_of(otg->usb_phy, struct isp1301, phy); |
| 1442 | u32 l; | 1442 | u32 l; |
| 1443 | 1443 | ||
| 1444 | if (isp != the_transceiver) | 1444 | if (isp != the_transceiver) |
| @@ -1452,9 +1452,9 @@ isp1301_start_hnp(struct usb_otg *otg) | |||
| 1452 | /* We want hardware to manage most HNP protocol timings. | 1452 | /* We want hardware to manage most HNP protocol timings. |
| 1453 | * So do this part as early as possible... | 1453 | * So do this part as early as possible... |
| 1454 | */ | 1454 | */ |
| 1455 | switch (isp->phy.state) { | 1455 | switch (isp->phy.otg->state) { |
| 1456 | case OTG_STATE_B_HOST: | 1456 | case OTG_STATE_B_HOST: |
| 1457 | isp->phy.state = OTG_STATE_B_PERIPHERAL; | 1457 | isp->phy.otg->state = OTG_STATE_B_PERIPHERAL; |
| 1458 | /* caller will suspend next */ | 1458 | /* caller will suspend next */ |
| 1459 | break; | 1459 | break; |
| 1460 | case OTG_STATE_A_HOST: | 1460 | case OTG_STATE_A_HOST: |
| @@ -1583,7 +1583,7 @@ isp1301_probe(struct i2c_client *i2c, const struct i2c_device_id *id) | |||
| 1583 | isp->phy.label = DRIVER_NAME; | 1583 | isp->phy.label = DRIVER_NAME; |
| 1584 | isp->phy.set_power = isp1301_set_power, | 1584 | isp->phy.set_power = isp1301_set_power, |
| 1585 | 1585 | ||
| 1586 | isp->phy.otg->phy = &isp->phy; | 1586 | isp->phy.otg->usb_phy = &isp->phy; |
| 1587 | isp->phy.otg->set_host = isp1301_set_host, | 1587 | isp->phy.otg->set_host = isp1301_set_host, |
| 1588 | isp->phy.otg->set_peripheral = isp1301_set_peripheral, | 1588 | isp->phy.otg->set_peripheral = isp1301_set_peripheral, |
| 1589 | isp->phy.otg->start_srp = isp1301_start_srp, | 1589 | isp->phy.otg->start_srp = isp1301_start_srp, |
diff --git a/drivers/usb/phy/phy-msm-usb.c b/drivers/usb/phy/phy-msm-usb.c index 29be0e654ecc..000fd892455f 100644 --- a/drivers/usb/phy/phy-msm-usb.c +++ b/drivers/usb/phy/phy-msm-usb.c | |||
| @@ -708,7 +708,7 @@ static void msm_otg_start_host(struct usb_phy *phy, int on) | |||
| 708 | 708 | ||
| 709 | static int msm_otg_set_host(struct usb_otg *otg, struct usb_bus *host) | 709 | static int msm_otg_set_host(struct usb_otg *otg, struct usb_bus *host) |
| 710 | { | 710 | { |
| 711 | struct msm_otg *motg = container_of(otg->phy, struct msm_otg, phy); | 711 | struct msm_otg *motg = container_of(otg->usb_phy, struct msm_otg, phy); |
| 712 | struct usb_hcd *hcd; | 712 | struct usb_hcd *hcd; |
| 713 | 713 | ||
| 714 | /* | 714 | /* |
| @@ -716,16 +716,16 @@ static int msm_otg_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
| 716 | * only peripheral configuration. | 716 | * only peripheral configuration. |
| 717 | */ | 717 | */ |
| 718 | if (motg->pdata->mode == USB_DR_MODE_PERIPHERAL) { | 718 | if (motg->pdata->mode == USB_DR_MODE_PERIPHERAL) { |
| 719 | dev_info(otg->phy->dev, "Host mode is not supported\n"); | 719 | dev_info(otg->usb_phy->dev, "Host mode is not supported\n"); |
| 720 | return -ENODEV; | 720 | return -ENODEV; |
| 721 | } | 721 | } |
| 722 | 722 | ||
| 723 | if (!host) { | 723 | if (!host) { |
| 724 | if (otg->phy->state == OTG_STATE_A_HOST) { | 724 | if (otg->state == OTG_STATE_A_HOST) { |
| 725 | pm_runtime_get_sync(otg->phy->dev); | 725 | pm_runtime_get_sync(otg->usb_phy->dev); |
| 726 | msm_otg_start_host(otg->phy, 0); | 726 | msm_otg_start_host(otg->usb_phy, 0); |
| 727 | otg->host = NULL; | 727 | otg->host = NULL; |
| 728 | otg->phy->state = OTG_STATE_UNDEFINED; | 728 | otg->state = OTG_STATE_UNDEFINED; |
| 729 | schedule_work(&motg->sm_work); | 729 | schedule_work(&motg->sm_work); |
| 730 | } else { | 730 | } else { |
| 731 | otg->host = NULL; | 731 | otg->host = NULL; |
| @@ -738,14 +738,14 @@ static int msm_otg_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
| 738 | hcd->power_budget = motg->pdata->power_budget; | 738 | hcd->power_budget = motg->pdata->power_budget; |
| 739 | 739 | ||
| 740 | otg->host = host; | 740 | otg->host = host; |
| 741 | dev_dbg(otg->phy->dev, "host driver registered w/ tranceiver\n"); | 741 | dev_dbg(otg->usb_phy->dev, "host driver registered w/ tranceiver\n"); |
| 742 | 742 | ||
| 743 | /* | 743 | /* |
| 744 | * Kick the state machine work, if peripheral is not supported | 744 | * Kick the state machine work, if peripheral is not supported |
| 745 | * or peripheral is already registered with us. | 745 | * or peripheral is already registered with us. |
| 746 | */ | 746 | */ |
| 747 | if (motg->pdata->mode == USB_DR_MODE_HOST || otg->gadget) { | 747 | if (motg->pdata->mode == USB_DR_MODE_HOST || otg->gadget) { |
| 748 | pm_runtime_get_sync(otg->phy->dev); | 748 | pm_runtime_get_sync(otg->usb_phy->dev); |
| 749 | schedule_work(&motg->sm_work); | 749 | schedule_work(&motg->sm_work); |
| 750 | } | 750 | } |
| 751 | 751 | ||
| @@ -782,23 +782,23 @@ static void msm_otg_start_peripheral(struct usb_phy *phy, int on) | |||
| 782 | static int msm_otg_set_peripheral(struct usb_otg *otg, | 782 | static int msm_otg_set_peripheral(struct usb_otg *otg, |
| 783 | struct usb_gadget *gadget) | 783 | struct usb_gadget *gadget) |
| 784 | { | 784 | { |
| 785 | struct msm_otg *motg = container_of(otg->phy, struct msm_otg, phy); | 785 | struct msm_otg *motg = container_of(otg->usb_phy, struct msm_otg, phy); |
| 786 | 786 | ||
| 787 | /* | 787 | /* |
| 788 | * Fail peripheral registration if this board can support | 788 | * Fail peripheral registration if this board can support |
| 789 | * only host configuration. | 789 | * only host configuration. |
| 790 | */ | 790 | */ |
| 791 | if (motg->pdata->mode == USB_DR_MODE_HOST) { | 791 | if (motg->pdata->mode == USB_DR_MODE_HOST) { |
| 792 | dev_info(otg->phy->dev, "Peripheral mode is not supported\n"); | 792 | dev_info(otg->usb_phy->dev, "Peripheral mode is not supported\n"); |
| 793 | return -ENODEV; | 793 | return -ENODEV; |
| 794 | } | 794 | } |
| 795 | 795 | ||
| 796 | if (!gadget) { | 796 | if (!gadget) { |
| 797 | if (otg->phy->state == OTG_STATE_B_PERIPHERAL) { | 797 | if (otg->state == OTG_STATE_B_PERIPHERAL) { |
| 798 | pm_runtime_get_sync(otg->phy->dev); | 798 | pm_runtime_get_sync(otg->usb_phy->dev); |
| 799 | msm_otg_start_peripheral(otg->phy, 0); | 799 | msm_otg_start_peripheral(otg->usb_phy, 0); |
| 800 | otg->gadget = NULL; | 800 | otg->gadget = NULL; |
| 801 | otg->phy->state = OTG_STATE_UNDEFINED; | 801 | otg->state = OTG_STATE_UNDEFINED; |
| 802 | schedule_work(&motg->sm_work); | 802 | schedule_work(&motg->sm_work); |
| 803 | } else { | 803 | } else { |
| 804 | otg->gadget = NULL; | 804 | otg->gadget = NULL; |
| @@ -807,14 +807,15 @@ static int msm_otg_set_peripheral(struct usb_otg *otg, | |||
| 807 | return 0; | 807 | return 0; |
| 808 | } | 808 | } |
| 809 | otg->gadget = gadget; | 809 | otg->gadget = gadget; |
| 810 | dev_dbg(otg->phy->dev, "peripheral driver registered w/ tranceiver\n"); | 810 | dev_dbg(otg->usb_phy->dev, |
| 811 | "peripheral driver registered w/ tranceiver\n"); | ||
| 811 | 812 | ||
| 812 | /* | 813 | /* |
| 813 | * Kick the state machine work, if host is not supported | 814 | * Kick the state machine work, if host is not supported |
| 814 | * or host is already registered with us. | 815 | * or host is already registered with us. |
| 815 | */ | 816 | */ |
| 816 | if (motg->pdata->mode == USB_DR_MODE_PERIPHERAL || otg->host) { | 817 | if (motg->pdata->mode == USB_DR_MODE_PERIPHERAL || otg->host) { |
| 817 | pm_runtime_get_sync(otg->phy->dev); | 818 | pm_runtime_get_sync(otg->usb_phy->dev); |
| 818 | schedule_work(&motg->sm_work); | 819 | schedule_work(&motg->sm_work); |
| 819 | } | 820 | } |
| 820 | 821 | ||
| @@ -1170,20 +1171,20 @@ static void msm_otg_sm_work(struct work_struct *w) | |||
| 1170 | struct msm_otg *motg = container_of(w, struct msm_otg, sm_work); | 1171 | struct msm_otg *motg = container_of(w, struct msm_otg, sm_work); |
| 1171 | struct usb_otg *otg = motg->phy.otg; | 1172 | struct usb_otg *otg = motg->phy.otg; |
| 1172 | 1173 | ||
| 1173 | switch (otg->phy->state) { | 1174 | switch (otg->state) { |
| 1174 | case OTG_STATE_UNDEFINED: | 1175 | case OTG_STATE_UNDEFINED: |
| 1175 | dev_dbg(otg->phy->dev, "OTG_STATE_UNDEFINED state\n"); | 1176 | dev_dbg(otg->usb_phy->dev, "OTG_STATE_UNDEFINED state\n"); |
| 1176 | msm_otg_reset(otg->phy); | 1177 | msm_otg_reset(otg->usb_phy); |
| 1177 | msm_otg_init_sm(motg); | 1178 | msm_otg_init_sm(motg); |
| 1178 | otg->phy->state = OTG_STATE_B_IDLE; | 1179 | otg->state = OTG_STATE_B_IDLE; |
| 1179 | /* FALL THROUGH */ | 1180 | /* FALL THROUGH */ |
| 1180 | case OTG_STATE_B_IDLE: | 1181 | case OTG_STATE_B_IDLE: |
| 1181 | dev_dbg(otg->phy->dev, "OTG_STATE_B_IDLE state\n"); | 1182 | dev_dbg(otg->usb_phy->dev, "OTG_STATE_B_IDLE state\n"); |
| 1182 | if (!test_bit(ID, &motg->inputs) && otg->host) { | 1183 | if (!test_bit(ID, &motg->inputs) && otg->host) { |
| 1183 | /* disable BSV bit */ | 1184 | /* disable BSV bit */ |
| 1184 | writel(readl(USB_OTGSC) & ~OTGSC_BSVIE, USB_OTGSC); | 1185 | writel(readl(USB_OTGSC) & ~OTGSC_BSVIE, USB_OTGSC); |
| 1185 | msm_otg_start_host(otg->phy, 1); | 1186 | msm_otg_start_host(otg->usb_phy, 1); |
| 1186 | otg->phy->state = OTG_STATE_A_HOST; | 1187 | otg->state = OTG_STATE_A_HOST; |
| 1187 | } else if (test_bit(B_SESS_VLD, &motg->inputs)) { | 1188 | } else if (test_bit(B_SESS_VLD, &motg->inputs)) { |
| 1188 | switch (motg->chg_state) { | 1189 | switch (motg->chg_state) { |
| 1189 | case USB_CHG_STATE_UNDEFINED: | 1190 | case USB_CHG_STATE_UNDEFINED: |
| @@ -1198,14 +1199,16 @@ static void msm_otg_sm_work(struct work_struct *w) | |||
| 1198 | case USB_CDP_CHARGER: | 1199 | case USB_CDP_CHARGER: |
| 1199 | msm_otg_notify_charger(motg, | 1200 | msm_otg_notify_charger(motg, |
| 1200 | IDEV_CHG_MAX); | 1201 | IDEV_CHG_MAX); |
| 1201 | msm_otg_start_peripheral(otg->phy, 1); | 1202 | msm_otg_start_peripheral(otg->usb_phy, |
| 1202 | otg->phy->state | 1203 | 1); |
| 1204 | otg->state | ||
| 1203 | = OTG_STATE_B_PERIPHERAL; | 1205 | = OTG_STATE_B_PERIPHERAL; |
| 1204 | break; | 1206 | break; |
| 1205 | case USB_SDP_CHARGER: | 1207 | case USB_SDP_CHARGER: |
| 1206 | msm_otg_notify_charger(motg, IUNIT); | 1208 | msm_otg_notify_charger(motg, IUNIT); |
| 1207 | msm_otg_start_peripheral(otg->phy, 1); | 1209 | msm_otg_start_peripheral(otg->usb_phy, |
| 1208 | otg->phy->state | 1210 | 1); |
| 1211 | otg->state | ||
| 1209 | = OTG_STATE_B_PERIPHERAL; | 1212 | = OTG_STATE_B_PERIPHERAL; |
| 1210 | break; | 1213 | break; |
| 1211 | default: | 1214 | default: |
| @@ -1222,36 +1225,36 @@ static void msm_otg_sm_work(struct work_struct *w) | |||
| 1222 | * is incremented in charger detection work. | 1225 | * is incremented in charger detection work. |
| 1223 | */ | 1226 | */ |
| 1224 | if (cancel_delayed_work_sync(&motg->chg_work)) { | 1227 | if (cancel_delayed_work_sync(&motg->chg_work)) { |
| 1225 | pm_runtime_put_sync(otg->phy->dev); | 1228 | pm_runtime_put_sync(otg->usb_phy->dev); |
| 1226 | msm_otg_reset(otg->phy); | 1229 | msm_otg_reset(otg->usb_phy); |
| 1227 | } | 1230 | } |
| 1228 | msm_otg_notify_charger(motg, 0); | 1231 | msm_otg_notify_charger(motg, 0); |
| 1229 | motg->chg_state = USB_CHG_STATE_UNDEFINED; | 1232 | motg->chg_state = USB_CHG_STATE_UNDEFINED; |
| 1230 | motg->chg_type = USB_INVALID_CHARGER; | 1233 | motg->chg_type = USB_INVALID_CHARGER; |
| 1231 | } | 1234 | } |
| 1232 | 1235 | ||
| 1233 | if (otg->phy->state == OTG_STATE_B_IDLE) | 1236 | if (otg->state == OTG_STATE_B_IDLE) |
| 1234 | pm_runtime_put_sync(otg->phy->dev); | 1237 | pm_runtime_put_sync(otg->usb_phy->dev); |
| 1235 | break; | 1238 | break; |
| 1236 | case OTG_STATE_B_PERIPHERAL: | 1239 | case OTG_STATE_B_PERIPHERAL: |
| 1237 | dev_dbg(otg->phy->dev, "OTG_STATE_B_PERIPHERAL state\n"); | 1240 | dev_dbg(otg->usb_phy->dev, "OTG_STATE_B_PERIPHERAL state\n"); |
| 1238 | if (!test_bit(B_SESS_VLD, &motg->inputs) || | 1241 | if (!test_bit(B_SESS_VLD, &motg->inputs) || |
| 1239 | !test_bit(ID, &motg->inputs)) { | 1242 | !test_bit(ID, &motg->inputs)) { |
| 1240 | msm_otg_notify_charger(motg, 0); | 1243 | msm_otg_notify_charger(motg, 0); |
| 1241 | msm_otg_start_peripheral(otg->phy, 0); | 1244 | msm_otg_start_peripheral(otg->usb_phy, 0); |
| 1242 | motg->chg_state = USB_CHG_STATE_UNDEFINED; | 1245 | motg->chg_state = USB_CHG_STATE_UNDEFINED; |
| 1243 | motg->chg_type = USB_INVALID_CHARGER; | 1246 | motg->chg_type = USB_INVALID_CHARGER; |
| 1244 | otg->phy->state = OTG_STATE_B_IDLE; | 1247 | otg->state = OTG_STATE_B_IDLE; |
| 1245 | msm_otg_reset(otg->phy); | 1248 | msm_otg_reset(otg->usb_phy); |
| 1246 | schedule_work(w); | 1249 | schedule_work(w); |
| 1247 | } | 1250 | } |
| 1248 | break; | 1251 | break; |
| 1249 | case OTG_STATE_A_HOST: | 1252 | case OTG_STATE_A_HOST: |
| 1250 | dev_dbg(otg->phy->dev, "OTG_STATE_A_HOST state\n"); | 1253 | dev_dbg(otg->usb_phy->dev, "OTG_STATE_A_HOST state\n"); |
| 1251 | if (test_bit(ID, &motg->inputs)) { | 1254 | if (test_bit(ID, &motg->inputs)) { |
| 1252 | msm_otg_start_host(otg->phy, 0); | 1255 | msm_otg_start_host(otg->usb_phy, 0); |
| 1253 | otg->phy->state = OTG_STATE_B_IDLE; | 1256 | otg->state = OTG_STATE_B_IDLE; |
| 1254 | msm_otg_reset(otg->phy); | 1257 | msm_otg_reset(otg->usb_phy); |
| 1255 | schedule_work(w); | 1258 | schedule_work(w); |
| 1256 | } | 1259 | } |
| 1257 | break; | 1260 | break; |
| @@ -1303,7 +1306,7 @@ static int msm_otg_mode_show(struct seq_file *s, void *unused) | |||
| 1303 | struct msm_otg *motg = s->private; | 1306 | struct msm_otg *motg = s->private; |
| 1304 | struct usb_otg *otg = motg->phy.otg; | 1307 | struct usb_otg *otg = motg->phy.otg; |
| 1305 | 1308 | ||
| 1306 | switch (otg->phy->state) { | 1309 | switch (otg->state) { |
| 1307 | case OTG_STATE_A_HOST: | 1310 | case OTG_STATE_A_HOST: |
| 1308 | seq_puts(s, "host\n"); | 1311 | seq_puts(s, "host\n"); |
| 1309 | break; | 1312 | break; |
| @@ -1353,7 +1356,7 @@ static ssize_t msm_otg_mode_write(struct file *file, const char __user *ubuf, | |||
| 1353 | 1356 | ||
| 1354 | switch (req_mode) { | 1357 | switch (req_mode) { |
| 1355 | case USB_DR_MODE_UNKNOWN: | 1358 | case USB_DR_MODE_UNKNOWN: |
| 1356 | switch (otg->phy->state) { | 1359 | switch (otg->state) { |
| 1357 | case OTG_STATE_A_HOST: | 1360 | case OTG_STATE_A_HOST: |
| 1358 | case OTG_STATE_B_PERIPHERAL: | 1361 | case OTG_STATE_B_PERIPHERAL: |
| 1359 | set_bit(ID, &motg->inputs); | 1362 | set_bit(ID, &motg->inputs); |
| @@ -1364,7 +1367,7 @@ static ssize_t msm_otg_mode_write(struct file *file, const char __user *ubuf, | |||
| 1364 | } | 1367 | } |
| 1365 | break; | 1368 | break; |
| 1366 | case USB_DR_MODE_PERIPHERAL: | 1369 | case USB_DR_MODE_PERIPHERAL: |
| 1367 | switch (otg->phy->state) { | 1370 | switch (otg->state) { |
| 1368 | case OTG_STATE_B_IDLE: | 1371 | case OTG_STATE_B_IDLE: |
| 1369 | case OTG_STATE_A_HOST: | 1372 | case OTG_STATE_A_HOST: |
| 1370 | set_bit(ID, &motg->inputs); | 1373 | set_bit(ID, &motg->inputs); |
| @@ -1375,7 +1378,7 @@ static ssize_t msm_otg_mode_write(struct file *file, const char __user *ubuf, | |||
| 1375 | } | 1378 | } |
| 1376 | break; | 1379 | break; |
| 1377 | case USB_DR_MODE_HOST: | 1380 | case USB_DR_MODE_HOST: |
| 1378 | switch (otg->phy->state) { | 1381 | switch (otg->state) { |
| 1379 | case OTG_STATE_B_IDLE: | 1382 | case OTG_STATE_B_IDLE: |
| 1380 | case OTG_STATE_B_PERIPHERAL: | 1383 | case OTG_STATE_B_PERIPHERAL: |
| 1381 | clear_bit(ID, &motg->inputs); | 1384 | clear_bit(ID, &motg->inputs); |
| @@ -1388,7 +1391,7 @@ static ssize_t msm_otg_mode_write(struct file *file, const char __user *ubuf, | |||
| 1388 | goto out; | 1391 | goto out; |
| 1389 | } | 1392 | } |
| 1390 | 1393 | ||
| 1391 | pm_runtime_get_sync(otg->phy->dev); | 1394 | pm_runtime_get_sync(otg->usb_phy->dev); |
| 1392 | schedule_work(&motg->sm_work); | 1395 | schedule_work(&motg->sm_work); |
| 1393 | out: | 1396 | out: |
| 1394 | return status; | 1397 | return status; |
| @@ -1505,10 +1508,8 @@ static int msm_otg_read_dt(struct platform_device *pdev, struct msm_otg *motg) | |||
| 1505 | } | 1508 | } |
| 1506 | 1509 | ||
| 1507 | pdata->phy_init_seq = devm_kzalloc(&pdev->dev, len, GFP_KERNEL); | 1510 | pdata->phy_init_seq = devm_kzalloc(&pdev->dev, len, GFP_KERNEL); |
| 1508 | if (!pdata->phy_init_seq) { | 1511 | if (!pdata->phy_init_seq) |
| 1509 | dev_warn(&pdev->dev, "No space for PHY init sequence\n"); | ||
| 1510 | return 0; | 1512 | return 0; |
| 1511 | } | ||
| 1512 | 1513 | ||
| 1513 | ret = of_property_read_u32_array(node, "qcom,phy-init-sequence", | 1514 | ret = of_property_read_u32_array(node, "qcom,phy-init-sequence", |
| 1514 | pdata->phy_init_seq, words); | 1515 | pdata->phy_init_seq, words); |
| @@ -1530,10 +1531,8 @@ static int msm_otg_probe(struct platform_device *pdev) | |||
| 1530 | void __iomem *phy_select; | 1531 | void __iomem *phy_select; |
| 1531 | 1532 | ||
| 1532 | motg = devm_kzalloc(&pdev->dev, sizeof(struct msm_otg), GFP_KERNEL); | 1533 | motg = devm_kzalloc(&pdev->dev, sizeof(struct msm_otg), GFP_KERNEL); |
| 1533 | if (!motg) { | 1534 | if (!motg) |
| 1534 | dev_err(&pdev->dev, "unable to allocate msm_otg\n"); | ||
| 1535 | return -ENOMEM; | 1535 | return -ENOMEM; |
| 1536 | } | ||
| 1537 | 1536 | ||
| 1538 | pdata = dev_get_platdata(&pdev->dev); | 1537 | pdata = dev_get_platdata(&pdev->dev); |
| 1539 | if (!pdata) { | 1538 | if (!pdata) { |
| @@ -1546,10 +1545,8 @@ static int msm_otg_probe(struct platform_device *pdev) | |||
| 1546 | 1545 | ||
| 1547 | motg->phy.otg = devm_kzalloc(&pdev->dev, sizeof(struct usb_otg), | 1546 | motg->phy.otg = devm_kzalloc(&pdev->dev, sizeof(struct usb_otg), |
| 1548 | GFP_KERNEL); | 1547 | GFP_KERNEL); |
| 1549 | if (!motg->phy.otg) { | 1548 | if (!motg->phy.otg) |
| 1550 | dev_err(&pdev->dev, "unable to allocate msm_otg\n"); | ||
| 1551 | return -ENOMEM; | 1549 | return -ENOMEM; |
| 1552 | } | ||
| 1553 | 1550 | ||
| 1554 | phy = &motg->phy; | 1551 | phy = &motg->phy; |
| 1555 | phy->dev = &pdev->dev; | 1552 | phy->dev = &pdev->dev; |
| @@ -1674,7 +1671,7 @@ static int msm_otg_probe(struct platform_device *pdev) | |||
| 1674 | 1671 | ||
| 1675 | phy->io_ops = &msm_otg_io_ops; | 1672 | phy->io_ops = &msm_otg_io_ops; |
| 1676 | 1673 | ||
| 1677 | phy->otg->phy = &motg->phy; | 1674 | phy->otg->usb_phy = &motg->phy; |
| 1678 | phy->otg->set_host = msm_otg_set_host; | 1675 | phy->otg->set_host = msm_otg_set_host; |
| 1679 | phy->otg->set_peripheral = msm_otg_set_peripheral; | 1676 | phy->otg->set_peripheral = msm_otg_set_peripheral; |
| 1680 | 1677 | ||
| @@ -1775,7 +1772,7 @@ static int msm_otg_runtime_idle(struct device *dev) | |||
| 1775 | * This 1 sec delay also prevents entering into LPM immediately | 1772 | * This 1 sec delay also prevents entering into LPM immediately |
| 1776 | * after asynchronous interrupt. | 1773 | * after asynchronous interrupt. |
| 1777 | */ | 1774 | */ |
| 1778 | if (otg->phy->state != OTG_STATE_UNDEFINED) | 1775 | if (otg->state != OTG_STATE_UNDEFINED) |
| 1779 | pm_schedule_suspend(dev, 1000); | 1776 | pm_schedule_suspend(dev, 1000); |
| 1780 | 1777 | ||
| 1781 | return -EAGAIN; | 1778 | return -EAGAIN; |
diff --git a/drivers/usb/phy/phy-mv-usb.c b/drivers/usb/phy/phy-mv-usb.c index 7d80c54f0ac6..b234d46cd58b 100644 --- a/drivers/usb/phy/phy-mv-usb.c +++ b/drivers/usb/phy/phy-mv-usb.c | |||
| @@ -56,7 +56,7 @@ static char *state_string[] = { | |||
| 56 | 56 | ||
| 57 | static int mv_otg_set_vbus(struct usb_otg *otg, bool on) | 57 | static int mv_otg_set_vbus(struct usb_otg *otg, bool on) |
| 58 | { | 58 | { |
| 59 | struct mv_otg *mvotg = container_of(otg->phy, struct mv_otg, phy); | 59 | struct mv_otg *mvotg = container_of(otg->usb_phy, struct mv_otg, phy); |
| 60 | if (mvotg->pdata->set_vbus == NULL) | 60 | if (mvotg->pdata->set_vbus == NULL) |
| 61 | return -ENODEV; | 61 | return -ENODEV; |
| 62 | 62 | ||
| @@ -339,68 +339,68 @@ static void mv_otg_update_state(struct mv_otg *mvotg) | |||
| 339 | { | 339 | { |
| 340 | struct mv_otg_ctrl *otg_ctrl = &mvotg->otg_ctrl; | 340 | struct mv_otg_ctrl *otg_ctrl = &mvotg->otg_ctrl; |
| 341 | struct usb_phy *phy = &mvotg->phy; | 341 | struct usb_phy *phy = &mvotg->phy; |
| 342 | int old_state = phy->state; | 342 | int old_state = mvotg->phy.otg->state; |
| 343 | 343 | ||
| 344 | switch (old_state) { | 344 | switch (old_state) { |
| 345 | case OTG_STATE_UNDEFINED: | 345 | case OTG_STATE_UNDEFINED: |
| 346 | phy->state = OTG_STATE_B_IDLE; | 346 | mvotg->phy.otg->state = OTG_STATE_B_IDLE; |
| 347 | /* FALL THROUGH */ | 347 | /* FALL THROUGH */ |
| 348 | case OTG_STATE_B_IDLE: | 348 | case OTG_STATE_B_IDLE: |
| 349 | if (otg_ctrl->id == 0) | 349 | if (otg_ctrl->id == 0) |
| 350 | phy->state = OTG_STATE_A_IDLE; | 350 | mvotg->phy.otg->state = OTG_STATE_A_IDLE; |
| 351 | else if (otg_ctrl->b_sess_vld) | 351 | else if (otg_ctrl->b_sess_vld) |
| 352 | phy->state = OTG_STATE_B_PERIPHERAL; | 352 | mvotg->phy.otg->state = OTG_STATE_B_PERIPHERAL; |
| 353 | break; | 353 | break; |
| 354 | case OTG_STATE_B_PERIPHERAL: | 354 | case OTG_STATE_B_PERIPHERAL: |
| 355 | if (!otg_ctrl->b_sess_vld || otg_ctrl->id == 0) | 355 | if (!otg_ctrl->b_sess_vld || otg_ctrl->id == 0) |
| 356 | phy->state = OTG_STATE_B_IDLE; | 356 | mvotg->phy.otg->state = OTG_STATE_B_IDLE; |
| 357 | break; | 357 | break; |
| 358 | case OTG_STATE_A_IDLE: | 358 | case OTG_STATE_A_IDLE: |
| 359 | if (otg_ctrl->id) | 359 | if (otg_ctrl->id) |
| 360 | phy->state = OTG_STATE_B_IDLE; | 360 | mvotg->phy.otg->state = OTG_STATE_B_IDLE; |
| 361 | else if (!(otg_ctrl->a_bus_drop) && | 361 | else if (!(otg_ctrl->a_bus_drop) && |
| 362 | (otg_ctrl->a_bus_req || otg_ctrl->a_srp_det)) | 362 | (otg_ctrl->a_bus_req || otg_ctrl->a_srp_det)) |
| 363 | phy->state = OTG_STATE_A_WAIT_VRISE; | 363 | mvotg->phy.otg->state = OTG_STATE_A_WAIT_VRISE; |
| 364 | break; | 364 | break; |
| 365 | case OTG_STATE_A_WAIT_VRISE: | 365 | case OTG_STATE_A_WAIT_VRISE: |
| 366 | if (otg_ctrl->a_vbus_vld) | 366 | if (otg_ctrl->a_vbus_vld) |
| 367 | phy->state = OTG_STATE_A_WAIT_BCON; | 367 | mvotg->phy.otg->state = OTG_STATE_A_WAIT_BCON; |
| 368 | break; | 368 | break; |
| 369 | case OTG_STATE_A_WAIT_BCON: | 369 | case OTG_STATE_A_WAIT_BCON: |
| 370 | if (otg_ctrl->id || otg_ctrl->a_bus_drop | 370 | if (otg_ctrl->id || otg_ctrl->a_bus_drop |
| 371 | || otg_ctrl->a_wait_bcon_timeout) { | 371 | || otg_ctrl->a_wait_bcon_timeout) { |
| 372 | mv_otg_cancel_timer(mvotg, A_WAIT_BCON_TIMER); | 372 | mv_otg_cancel_timer(mvotg, A_WAIT_BCON_TIMER); |
| 373 | mvotg->otg_ctrl.a_wait_bcon_timeout = 0; | 373 | mvotg->otg_ctrl.a_wait_bcon_timeout = 0; |
| 374 | phy->state = OTG_STATE_A_WAIT_VFALL; | 374 | mvotg->phy.otg->state = OTG_STATE_A_WAIT_VFALL; |
| 375 | otg_ctrl->a_bus_req = 0; | 375 | otg_ctrl->a_bus_req = 0; |
| 376 | } else if (!otg_ctrl->a_vbus_vld) { | 376 | } else if (!otg_ctrl->a_vbus_vld) { |
| 377 | mv_otg_cancel_timer(mvotg, A_WAIT_BCON_TIMER); | 377 | mv_otg_cancel_timer(mvotg, A_WAIT_BCON_TIMER); |
| 378 | mvotg->otg_ctrl.a_wait_bcon_timeout = 0; | 378 | mvotg->otg_ctrl.a_wait_bcon_timeout = 0; |
| 379 | phy->state = OTG_STATE_A_VBUS_ERR; | 379 | mvotg->phy.otg->state = OTG_STATE_A_VBUS_ERR; |
| 380 | } else if (otg_ctrl->b_conn) { | 380 | } else if (otg_ctrl->b_conn) { |
| 381 | mv_otg_cancel_timer(mvotg, A_WAIT_BCON_TIMER); | 381 | mv_otg_cancel_timer(mvotg, A_WAIT_BCON_TIMER); |
| 382 | mvotg->otg_ctrl.a_wait_bcon_timeout = 0; | 382 | mvotg->otg_ctrl.a_wait_bcon_timeout = 0; |
| 383 | phy->state = OTG_STATE_A_HOST; | 383 | mvotg->phy.otg->state = OTG_STATE_A_HOST; |
| 384 | } | 384 | } |
| 385 | break; | 385 | break; |
| 386 | case OTG_STATE_A_HOST: | 386 | case OTG_STATE_A_HOST: |
| 387 | if (otg_ctrl->id || !otg_ctrl->b_conn | 387 | if (otg_ctrl->id || !otg_ctrl->b_conn |
| 388 | || otg_ctrl->a_bus_drop) | 388 | || otg_ctrl->a_bus_drop) |
| 389 | phy->state = OTG_STATE_A_WAIT_BCON; | 389 | mvotg->phy.otg->state = OTG_STATE_A_WAIT_BCON; |
| 390 | else if (!otg_ctrl->a_vbus_vld) | 390 | else if (!otg_ctrl->a_vbus_vld) |
| 391 | phy->state = OTG_STATE_A_VBUS_ERR; | 391 | mvotg->phy.otg->state = OTG_STATE_A_VBUS_ERR; |
| 392 | break; | 392 | break; |
| 393 | case OTG_STATE_A_WAIT_VFALL: | 393 | case OTG_STATE_A_WAIT_VFALL: |
| 394 | if (otg_ctrl->id | 394 | if (otg_ctrl->id |
| 395 | || (!otg_ctrl->b_conn && otg_ctrl->a_sess_vld) | 395 | || (!otg_ctrl->b_conn && otg_ctrl->a_sess_vld) |
| 396 | || otg_ctrl->a_bus_req) | 396 | || otg_ctrl->a_bus_req) |
| 397 | phy->state = OTG_STATE_A_IDLE; | 397 | mvotg->phy.otg->state = OTG_STATE_A_IDLE; |
| 398 | break; | 398 | break; |
| 399 | case OTG_STATE_A_VBUS_ERR: | 399 | case OTG_STATE_A_VBUS_ERR: |
| 400 | if (otg_ctrl->id || otg_ctrl->a_clr_err | 400 | if (otg_ctrl->id || otg_ctrl->a_clr_err |
| 401 | || otg_ctrl->a_bus_drop) { | 401 | || otg_ctrl->a_bus_drop) { |
| 402 | otg_ctrl->a_clr_err = 0; | 402 | otg_ctrl->a_clr_err = 0; |
| 403 | phy->state = OTG_STATE_A_WAIT_VFALL; | 403 | mvotg->phy.otg->state = OTG_STATE_A_WAIT_VFALL; |
| 404 | } | 404 | } |
| 405 | break; | 405 | break; |
| 406 | default: | 406 | default: |
| @@ -420,8 +420,8 @@ static void mv_otg_work(struct work_struct *work) | |||
| 420 | run: | 420 | run: |
| 421 | /* work queue is single thread, or we need spin_lock to protect */ | 421 | /* work queue is single thread, or we need spin_lock to protect */ |
| 422 | phy = &mvotg->phy; | 422 | phy = &mvotg->phy; |
| 423 | otg = phy->otg; | 423 | otg = mvotg->phy.otg; |
| 424 | old_state = phy->state; | 424 | old_state = otg->state; |
| 425 | 425 | ||
| 426 | if (!mvotg->active) | 426 | if (!mvotg->active) |
| 427 | return; | 427 | return; |
| @@ -429,22 +429,24 @@ run: | |||
| 429 | mv_otg_update_inputs(mvotg); | 429 | mv_otg_update_inputs(mvotg); |
| 430 | mv_otg_update_state(mvotg); | 430 | mv_otg_update_state(mvotg); |
| 431 | 431 | ||
| 432 | if (old_state != phy->state) { | 432 | if (old_state != mvotg->phy.otg->state) { |
| 433 | dev_info(&mvotg->pdev->dev, "change from state %s to %s\n", | 433 | dev_info(&mvotg->pdev->dev, "change from state %s to %s\n", |
| 434 | state_string[old_state], | 434 | state_string[old_state], |
| 435 | state_string[phy->state]); | 435 | state_string[mvotg->phy.otg->state]); |
| 436 | 436 | ||
| 437 | switch (phy->state) { | 437 | switch (mvotg->phy.otg->state) { |
| 438 | case OTG_STATE_B_IDLE: | 438 | case OTG_STATE_B_IDLE: |
| 439 | otg->default_a = 0; | 439 | otg->default_a = 0; |
| 440 | if (old_state == OTG_STATE_B_PERIPHERAL) | 440 | if (old_state == OTG_STATE_B_PERIPHERAL) |
| 441 | mv_otg_start_periphrals(mvotg, 0); | 441 | mv_otg_start_periphrals(mvotg, 0); |
| 442 | mv_otg_reset(mvotg); | 442 | mv_otg_reset(mvotg); |
| 443 | mv_otg_disable(mvotg); | 443 | mv_otg_disable(mvotg); |
| 444 | usb_phy_set_event(&mvotg->phy, USB_EVENT_NONE); | ||
| 444 | break; | 445 | break; |
| 445 | case OTG_STATE_B_PERIPHERAL: | 446 | case OTG_STATE_B_PERIPHERAL: |
| 446 | mv_otg_enable(mvotg); | 447 | mv_otg_enable(mvotg); |
| 447 | mv_otg_start_periphrals(mvotg, 1); | 448 | mv_otg_start_periphrals(mvotg, 1); |
| 449 | usb_phy_set_event(&mvotg->phy, USB_EVENT_ENUMERATED); | ||
| 448 | break; | 450 | break; |
| 449 | case OTG_STATE_A_IDLE: | 451 | case OTG_STATE_A_IDLE: |
| 450 | otg->default_a = 1; | 452 | otg->default_a = 1; |
| @@ -545,8 +547,8 @@ set_a_bus_req(struct device *dev, struct device_attribute *attr, | |||
| 545 | return -1; | 547 | return -1; |
| 546 | 548 | ||
| 547 | /* We will use this interface to change to A device */ | 549 | /* We will use this interface to change to A device */ |
| 548 | if (mvotg->phy.state != OTG_STATE_B_IDLE | 550 | if (mvotg->phy.otg->state != OTG_STATE_B_IDLE |
| 549 | && mvotg->phy.state != OTG_STATE_A_IDLE) | 551 | && mvotg->phy.otg->state != OTG_STATE_A_IDLE) |
| 550 | return -1; | 552 | return -1; |
| 551 | 553 | ||
| 552 | /* The clock may disabled and we need to set irq for ID detected */ | 554 | /* The clock may disabled and we need to set irq for ID detected */ |
| @@ -686,10 +688,8 @@ static int mv_otg_probe(struct platform_device *pdev) | |||
| 686 | } | 688 | } |
| 687 | 689 | ||
| 688 | mvotg = devm_kzalloc(&pdev->dev, sizeof(*mvotg), GFP_KERNEL); | 690 | mvotg = devm_kzalloc(&pdev->dev, sizeof(*mvotg), GFP_KERNEL); |
| 689 | if (!mvotg) { | 691 | if (!mvotg) |
| 690 | dev_err(&pdev->dev, "failed to allocate memory!\n"); | ||
| 691 | return -ENOMEM; | 692 | return -ENOMEM; |
| 692 | } | ||
| 693 | 693 | ||
| 694 | otg = devm_kzalloc(&pdev->dev, sizeof(*otg), GFP_KERNEL); | 694 | otg = devm_kzalloc(&pdev->dev, sizeof(*otg), GFP_KERNEL); |
| 695 | if (!otg) | 695 | if (!otg) |
| @@ -717,9 +717,9 @@ static int mv_otg_probe(struct platform_device *pdev) | |||
| 717 | mvotg->phy.dev = &pdev->dev; | 717 | mvotg->phy.dev = &pdev->dev; |
| 718 | mvotg->phy.otg = otg; | 718 | mvotg->phy.otg = otg; |
| 719 | mvotg->phy.label = driver_name; | 719 | mvotg->phy.label = driver_name; |
| 720 | mvotg->phy.state = OTG_STATE_UNDEFINED; | ||
| 721 | 720 | ||
| 722 | otg->phy = &mvotg->phy; | 721 | otg->state = OTG_STATE_UNDEFINED; |
| 722 | otg->usb_phy = &mvotg->phy; | ||
| 723 | otg->set_host = mv_otg_set_host; | 723 | otg->set_host = mv_otg_set_host; |
| 724 | otg->set_peripheral = mv_otg_set_peripheral; | 724 | otg->set_peripheral = mv_otg_set_peripheral; |
| 725 | otg->set_vbus = mv_otg_set_vbus; | 725 | otg->set_vbus = mv_otg_set_vbus; |
diff --git a/drivers/usb/phy/phy-mxs-usb.c b/drivers/usb/phy/phy-mxs-usb.c index 0e0c41587a08..a55dadcd47f3 100644 --- a/drivers/usb/phy/phy-mxs-usb.c +++ b/drivers/usb/phy/phy-mxs-usb.c | |||
| @@ -390,10 +390,8 @@ static int mxs_phy_probe(struct platform_device *pdev) | |||
| 390 | } | 390 | } |
| 391 | 391 | ||
| 392 | mxs_phy = devm_kzalloc(&pdev->dev, sizeof(*mxs_phy), GFP_KERNEL); | 392 | mxs_phy = devm_kzalloc(&pdev->dev, sizeof(*mxs_phy), GFP_KERNEL); |
| 393 | if (!mxs_phy) { | 393 | if (!mxs_phy) |
| 394 | dev_err(&pdev->dev, "Failed to allocate USB PHY structure!\n"); | ||
| 395 | return -ENOMEM; | 394 | return -ENOMEM; |
| 396 | } | ||
| 397 | 395 | ||
| 398 | /* Some SoCs don't have anatop registers */ | 396 | /* Some SoCs don't have anatop registers */ |
| 399 | if (of_get_property(np, "fsl,anatop", NULL)) { | 397 | if (of_get_property(np, "fsl,anatop", NULL)) { |
diff --git a/drivers/usb/phy/phy-rcar-gen2-usb.c b/drivers/usb/phy/phy-rcar-gen2-usb.c index 388d89f6b141..f83808413ba2 100644 --- a/drivers/usb/phy/phy-rcar-gen2-usb.c +++ b/drivers/usb/phy/phy-rcar-gen2-usb.c | |||
| @@ -195,10 +195,8 @@ static int rcar_gen2_usb_phy_probe(struct platform_device *pdev) | |||
| 195 | return PTR_ERR(base); | 195 | return PTR_ERR(base); |
| 196 | 196 | ||
| 197 | priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); | 197 | priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); |
| 198 | if (!priv) { | 198 | if (!priv) |
| 199 | dev_err(dev, "Memory allocation failed\n"); | ||
| 200 | return -ENOMEM; | 199 | return -ENOMEM; |
| 201 | } | ||
| 202 | 200 | ||
| 203 | spin_lock_init(&priv->lock); | 201 | spin_lock_init(&priv->lock); |
| 204 | priv->clk = clk; | 202 | priv->clk = clk; |
diff --git a/drivers/usb/phy/phy-rcar-usb.c b/drivers/usb/phy/phy-rcar-usb.c index 33265a5b2cdf..1e09b8377885 100644 --- a/drivers/usb/phy/phy-rcar-usb.c +++ b/drivers/usb/phy/phy-rcar-usb.c | |||
| @@ -195,17 +195,13 @@ static int rcar_usb_phy_probe(struct platform_device *pdev) | |||
| 195 | return PTR_ERR(reg0); | 195 | return PTR_ERR(reg0); |
| 196 | 196 | ||
| 197 | res1 = platform_get_resource(pdev, IORESOURCE_MEM, 1); | 197 | res1 = platform_get_resource(pdev, IORESOURCE_MEM, 1); |
| 198 | if (res1) { | 198 | reg1 = devm_ioremap_resource(dev, res1); |
| 199 | reg1 = devm_ioremap_resource(dev, res1); | 199 | if (IS_ERR(reg1)) |
| 200 | if (IS_ERR(reg1)) | 200 | return PTR_ERR(reg1); |
| 201 | return PTR_ERR(reg1); | ||
| 202 | } | ||
| 203 | 201 | ||
| 204 | priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); | 202 | priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); |
| 205 | if (!priv) { | 203 | if (!priv) |
| 206 | dev_err(dev, "priv data allocation error\n"); | ||
| 207 | return -ENOMEM; | 204 | return -ENOMEM; |
| 208 | } | ||
| 209 | 205 | ||
| 210 | priv->reg0 = reg0; | 206 | priv->reg0 = reg0; |
| 211 | priv->reg1 = reg1; | 207 | priv->reg1 = reg1; |
diff --git a/drivers/usb/phy/phy-tahvo.c b/drivers/usb/phy/phy-tahvo.c index cc61ee44b911..d391c79a542a 100644 --- a/drivers/usb/phy/phy-tahvo.c +++ b/drivers/usb/phy/phy-tahvo.c | |||
| @@ -81,33 +81,35 @@ static void check_vbus_state(struct tahvo_usb *tu) | |||
| 81 | 81 | ||
| 82 | reg = retu_read(rdev, TAHVO_REG_IDSR); | 82 | reg = retu_read(rdev, TAHVO_REG_IDSR); |
| 83 | if (reg & TAHVO_STAT_VBUS) { | 83 | if (reg & TAHVO_STAT_VBUS) { |
| 84 | switch (tu->phy.state) { | 84 | switch (tu->phy.otg->state) { |
| 85 | case OTG_STATE_B_IDLE: | 85 | case OTG_STATE_B_IDLE: |
| 86 | /* Enable the gadget driver */ | 86 | /* Enable the gadget driver */ |
| 87 | if (tu->phy.otg->gadget) | 87 | if (tu->phy.otg->gadget) |
| 88 | usb_gadget_vbus_connect(tu->phy.otg->gadget); | 88 | usb_gadget_vbus_connect(tu->phy.otg->gadget); |
| 89 | tu->phy.state = OTG_STATE_B_PERIPHERAL; | 89 | tu->phy.otg->state = OTG_STATE_B_PERIPHERAL; |
| 90 | usb_phy_set_event(&tu->phy, USB_EVENT_ENUMERATED); | ||
| 90 | break; | 91 | break; |
| 91 | case OTG_STATE_A_IDLE: | 92 | case OTG_STATE_A_IDLE: |
| 92 | /* | 93 | /* |
| 93 | * Session is now valid assuming the USB hub is driving | 94 | * Session is now valid assuming the USB hub is driving |
| 94 | * Vbus. | 95 | * Vbus. |
| 95 | */ | 96 | */ |
| 96 | tu->phy.state = OTG_STATE_A_HOST; | 97 | tu->phy.otg->state = OTG_STATE_A_HOST; |
| 97 | break; | 98 | break; |
| 98 | default: | 99 | default: |
| 99 | break; | 100 | break; |
| 100 | } | 101 | } |
| 101 | dev_info(&tu->pt_dev->dev, "USB cable connected\n"); | 102 | dev_info(&tu->pt_dev->dev, "USB cable connected\n"); |
| 102 | } else { | 103 | } else { |
| 103 | switch (tu->phy.state) { | 104 | switch (tu->phy.otg->state) { |
| 104 | case OTG_STATE_B_PERIPHERAL: | 105 | case OTG_STATE_B_PERIPHERAL: |
| 105 | if (tu->phy.otg->gadget) | 106 | if (tu->phy.otg->gadget) |
| 106 | usb_gadget_vbus_disconnect(tu->phy.otg->gadget); | 107 | usb_gadget_vbus_disconnect(tu->phy.otg->gadget); |
| 107 | tu->phy.state = OTG_STATE_B_IDLE; | 108 | tu->phy.otg->state = OTG_STATE_B_IDLE; |
| 109 | usb_phy_set_event(&tu->phy, USB_EVENT_NONE); | ||
| 108 | break; | 110 | break; |
| 109 | case OTG_STATE_A_HOST: | 111 | case OTG_STATE_A_HOST: |
| 110 | tu->phy.state = OTG_STATE_A_IDLE; | 112 | tu->phy.otg->state = OTG_STATE_A_IDLE; |
| 111 | break; | 113 | break; |
| 112 | default: | 114 | default: |
| 113 | break; | 115 | break; |
| @@ -132,14 +134,14 @@ static void tahvo_usb_become_host(struct tahvo_usb *tu) | |||
| 132 | /* Power up the transceiver in USB host mode */ | 134 | /* Power up the transceiver in USB host mode */ |
| 133 | retu_write(rdev, TAHVO_REG_USBR, USBR_REGOUT | USBR_NSUSPEND | | 135 | retu_write(rdev, TAHVO_REG_USBR, USBR_REGOUT | USBR_NSUSPEND | |
| 134 | USBR_MASTER_SW2 | USBR_MASTER_SW1); | 136 | USBR_MASTER_SW2 | USBR_MASTER_SW1); |
| 135 | tu->phy.state = OTG_STATE_A_IDLE; | 137 | tu->phy.otg->state = OTG_STATE_A_IDLE; |
| 136 | 138 | ||
| 137 | check_vbus_state(tu); | 139 | check_vbus_state(tu); |
| 138 | } | 140 | } |
| 139 | 141 | ||
| 140 | static void tahvo_usb_stop_host(struct tahvo_usb *tu) | 142 | static void tahvo_usb_stop_host(struct tahvo_usb *tu) |
| 141 | { | 143 | { |
| 142 | tu->phy.state = OTG_STATE_A_IDLE; | 144 | tu->phy.otg->state = OTG_STATE_A_IDLE; |
| 143 | } | 145 | } |
| 144 | 146 | ||
| 145 | static void tahvo_usb_become_peripheral(struct tahvo_usb *tu) | 147 | static void tahvo_usb_become_peripheral(struct tahvo_usb *tu) |
| @@ -151,7 +153,7 @@ static void tahvo_usb_become_peripheral(struct tahvo_usb *tu) | |||
| 151 | /* Power up transceiver and set it in USB peripheral mode */ | 153 | /* Power up transceiver and set it in USB peripheral mode */ |
| 152 | retu_write(rdev, TAHVO_REG_USBR, USBR_SLAVE_CONTROL | USBR_REGOUT | | 154 | retu_write(rdev, TAHVO_REG_USBR, USBR_SLAVE_CONTROL | USBR_REGOUT | |
| 153 | USBR_NSUSPEND | USBR_SLAVE_SW); | 155 | USBR_NSUSPEND | USBR_SLAVE_SW); |
| 154 | tu->phy.state = OTG_STATE_B_IDLE; | 156 | tu->phy.otg->state = OTG_STATE_B_IDLE; |
| 155 | 157 | ||
| 156 | check_vbus_state(tu); | 158 | check_vbus_state(tu); |
| 157 | } | 159 | } |
| @@ -160,7 +162,7 @@ static void tahvo_usb_stop_peripheral(struct tahvo_usb *tu) | |||
| 160 | { | 162 | { |
| 161 | if (tu->phy.otg->gadget) | 163 | if (tu->phy.otg->gadget) |
| 162 | usb_gadget_vbus_disconnect(tu->phy.otg->gadget); | 164 | usb_gadget_vbus_disconnect(tu->phy.otg->gadget); |
| 163 | tu->phy.state = OTG_STATE_B_IDLE; | 165 | tu->phy.otg->state = OTG_STATE_B_IDLE; |
| 164 | } | 166 | } |
| 165 | 167 | ||
| 166 | static void tahvo_usb_power_off(struct tahvo_usb *tu) | 168 | static void tahvo_usb_power_off(struct tahvo_usb *tu) |
| @@ -173,7 +175,7 @@ static void tahvo_usb_power_off(struct tahvo_usb *tu) | |||
| 173 | 175 | ||
| 174 | /* Power off transceiver */ | 176 | /* Power off transceiver */ |
| 175 | retu_write(rdev, TAHVO_REG_USBR, 0); | 177 | retu_write(rdev, TAHVO_REG_USBR, 0); |
| 176 | tu->phy.state = OTG_STATE_UNDEFINED; | 178 | tu->phy.otg->state = OTG_STATE_UNDEFINED; |
| 177 | } | 179 | } |
| 178 | 180 | ||
| 179 | static int tahvo_usb_set_suspend(struct usb_phy *dev, int suspend) | 181 | static int tahvo_usb_set_suspend(struct usb_phy *dev, int suspend) |
| @@ -196,7 +198,8 @@ static int tahvo_usb_set_suspend(struct usb_phy *dev, int suspend) | |||
| 196 | 198 | ||
| 197 | static int tahvo_usb_set_host(struct usb_otg *otg, struct usb_bus *host) | 199 | static int tahvo_usb_set_host(struct usb_otg *otg, struct usb_bus *host) |
| 198 | { | 200 | { |
| 199 | struct tahvo_usb *tu = container_of(otg->phy, struct tahvo_usb, phy); | 201 | struct tahvo_usb *tu = container_of(otg->usb_phy, struct tahvo_usb, |
| 202 | phy); | ||
| 200 | 203 | ||
| 201 | dev_dbg(&tu->pt_dev->dev, "%s %p\n", __func__, host); | 204 | dev_dbg(&tu->pt_dev->dev, "%s %p\n", __func__, host); |
| 202 | 205 | ||
| @@ -225,7 +228,8 @@ static int tahvo_usb_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
| 225 | static int tahvo_usb_set_peripheral(struct usb_otg *otg, | 228 | static int tahvo_usb_set_peripheral(struct usb_otg *otg, |
| 226 | struct usb_gadget *gadget) | 229 | struct usb_gadget *gadget) |
| 227 | { | 230 | { |
| 228 | struct tahvo_usb *tu = container_of(otg->phy, struct tahvo_usb, phy); | 231 | struct tahvo_usb *tu = container_of(otg->usb_phy, struct tahvo_usb, |
| 232 | phy); | ||
| 229 | 233 | ||
| 230 | dev_dbg(&tu->pt_dev->dev, "%s %p\n", __func__, gadget); | 234 | dev_dbg(&tu->pt_dev->dev, "%s %p\n", __func__, gadget); |
| 231 | 235 | ||
| @@ -379,11 +383,11 @@ static int tahvo_usb_probe(struct platform_device *pdev) | |||
| 379 | /* Create OTG interface */ | 383 | /* Create OTG interface */ |
| 380 | tahvo_usb_power_off(tu); | 384 | tahvo_usb_power_off(tu); |
| 381 | tu->phy.dev = &pdev->dev; | 385 | tu->phy.dev = &pdev->dev; |
| 382 | tu->phy.state = OTG_STATE_UNDEFINED; | 386 | tu->phy.otg->state = OTG_STATE_UNDEFINED; |
| 383 | tu->phy.label = DRIVER_NAME; | 387 | tu->phy.label = DRIVER_NAME; |
| 384 | tu->phy.set_suspend = tahvo_usb_set_suspend; | 388 | tu->phy.set_suspend = tahvo_usb_set_suspend; |
| 385 | 389 | ||
| 386 | tu->phy.otg->phy = &tu->phy; | 390 | tu->phy.otg->usb_phy = &tu->phy; |
| 387 | tu->phy.otg->set_host = tahvo_usb_set_host; | 391 | tu->phy.otg->set_host = tahvo_usb_set_host; |
| 388 | tu->phy.otg->set_peripheral = tahvo_usb_set_peripheral; | 392 | tu->phy.otg->set_peripheral = tahvo_usb_set_peripheral; |
| 389 | 393 | ||
diff --git a/drivers/usb/phy/phy-tegra-usb.c b/drivers/usb/phy/phy-tegra-usb.c index 886f1807a67b..fa2bfa4ee34e 100644 --- a/drivers/usb/phy/phy-tegra-usb.c +++ b/drivers/usb/phy/phy-tegra-usb.c | |||
| @@ -880,11 +880,8 @@ static int utmi_phy_probe(struct tegra_usb_phy *tegra_phy, | |||
| 880 | 880 | ||
| 881 | tegra_phy->config = devm_kzalloc(&pdev->dev, sizeof(*config), | 881 | tegra_phy->config = devm_kzalloc(&pdev->dev, sizeof(*config), |
| 882 | GFP_KERNEL); | 882 | GFP_KERNEL); |
| 883 | if (!tegra_phy->config) { | 883 | if (!tegra_phy->config) |
| 884 | dev_err(&pdev->dev, | ||
| 885 | "unable to allocate memory for USB UTMIP config\n"); | ||
| 886 | return -ENOMEM; | 884 | return -ENOMEM; |
| 887 | } | ||
| 888 | 885 | ||
| 889 | config = tegra_phy->config; | 886 | config = tegra_phy->config; |
| 890 | 887 | ||
| @@ -979,10 +976,8 @@ static int tegra_usb_phy_probe(struct platform_device *pdev) | |||
| 979 | int err; | 976 | int err; |
| 980 | 977 | ||
| 981 | tegra_phy = devm_kzalloc(&pdev->dev, sizeof(*tegra_phy), GFP_KERNEL); | 978 | tegra_phy = devm_kzalloc(&pdev->dev, sizeof(*tegra_phy), GFP_KERNEL); |
| 982 | if (!tegra_phy) { | 979 | if (!tegra_phy) |
| 983 | dev_err(&pdev->dev, "unable to allocate memory for USB2 PHY\n"); | ||
| 984 | return -ENOMEM; | 980 | return -ENOMEM; |
| 985 | } | ||
| 986 | 981 | ||
| 987 | match = of_match_device(tegra_usb_phy_id_table, &pdev->dev); | 982 | match = of_match_device(tegra_usb_phy_id_table, &pdev->dev); |
| 988 | if (!match) { | 983 | if (!match) { |
diff --git a/drivers/usb/phy/phy-ulpi.c b/drivers/usb/phy/phy-ulpi.c index 4e3877c329f2..f48a7a21e3c2 100644 --- a/drivers/usb/phy/phy-ulpi.c +++ b/drivers/usb/phy/phy-ulpi.c | |||
| @@ -211,7 +211,7 @@ static int ulpi_init(struct usb_phy *phy) | |||
| 211 | 211 | ||
| 212 | static int ulpi_set_host(struct usb_otg *otg, struct usb_bus *host) | 212 | static int ulpi_set_host(struct usb_otg *otg, struct usb_bus *host) |
| 213 | { | 213 | { |
| 214 | struct usb_phy *phy = otg->phy; | 214 | struct usb_phy *phy = otg->usb_phy; |
| 215 | unsigned int flags = usb_phy_io_read(phy, ULPI_IFC_CTRL); | 215 | unsigned int flags = usb_phy_io_read(phy, ULPI_IFC_CTRL); |
| 216 | 216 | ||
| 217 | if (!host) { | 217 | if (!host) { |
| @@ -237,7 +237,7 @@ static int ulpi_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
| 237 | 237 | ||
| 238 | static int ulpi_set_vbus(struct usb_otg *otg, bool on) | 238 | static int ulpi_set_vbus(struct usb_otg *otg, bool on) |
| 239 | { | 239 | { |
| 240 | struct usb_phy *phy = otg->phy; | 240 | struct usb_phy *phy = otg->usb_phy; |
| 241 | unsigned int flags = usb_phy_io_read(phy, ULPI_OTG_CTRL); | 241 | unsigned int flags = usb_phy_io_read(phy, ULPI_OTG_CTRL); |
| 242 | 242 | ||
| 243 | flags &= ~(ULPI_OTG_CTRL_DRVVBUS | ULPI_OTG_CTRL_DRVVBUS_EXT); | 243 | flags &= ~(ULPI_OTG_CTRL_DRVVBUS | ULPI_OTG_CTRL_DRVVBUS_EXT); |
| @@ -276,7 +276,7 @@ otg_ulpi_create(struct usb_phy_io_ops *ops, | |||
| 276 | phy->otg = otg; | 276 | phy->otg = otg; |
| 277 | phy->init = ulpi_init; | 277 | phy->init = ulpi_init; |
| 278 | 278 | ||
| 279 | otg->phy = phy; | 279 | otg->usb_phy = phy; |
| 280 | otg->set_host = ulpi_set_host; | 280 | otg->set_host = ulpi_set_host; |
| 281 | otg->set_vbus = ulpi_set_vbus; | 281 | otg->set_vbus = ulpi_set_vbus; |
| 282 | 282 | ||
diff --git a/drivers/usb/phy/phy.c b/drivers/usb/phy/phy.c index 045cd309367a..b4066a001ba0 100644 --- a/drivers/usb/phy/phy.c +++ b/drivers/usb/phy/phy.c | |||
| @@ -191,7 +191,9 @@ struct usb_phy *devm_usb_get_phy_by_phandle(struct device *dev, | |||
| 191 | 191 | ||
| 192 | phy = __of_usb_find_phy(node); | 192 | phy = __of_usb_find_phy(node); |
| 193 | if (IS_ERR(phy) || !try_module_get(phy->dev->driver->owner)) { | 193 | if (IS_ERR(phy) || !try_module_get(phy->dev->driver->owner)) { |
| 194 | phy = ERR_PTR(-EPROBE_DEFER); | 194 | if (!IS_ERR(phy)) |
| 195 | phy = ERR_PTR(-EPROBE_DEFER); | ||
| 196 | |||
| 195 | devres_free(ptr); | 197 | devres_free(ptr); |
| 196 | goto err1; | 198 | goto err1; |
| 197 | } | 199 | } |
| @@ -444,3 +446,15 @@ int usb_bind_phy(const char *dev_name, u8 index, | |||
| 444 | return 0; | 446 | return 0; |
| 445 | } | 447 | } |
| 446 | EXPORT_SYMBOL_GPL(usb_bind_phy); | 448 | EXPORT_SYMBOL_GPL(usb_bind_phy); |
| 449 | |||
| 450 | /** | ||
| 451 | * usb_phy_set_event - set event to phy event | ||
| 452 | * @x: the phy returned by usb_get_phy(); | ||
| 453 | * | ||
| 454 | * This sets event to phy event | ||
| 455 | */ | ||
| 456 | void usb_phy_set_event(struct usb_phy *x, unsigned long event) | ||
| 457 | { | ||
| 458 | x->last_event = event; | ||
| 459 | } | ||
| 460 | EXPORT_SYMBOL_GPL(usb_phy_set_event); | ||
diff --git a/drivers/usb/renesas_usbhs/common.c b/drivers/usb/renesas_usbhs/common.c index b3b6813ab270..371478704899 100644 --- a/drivers/usb/renesas_usbhs/common.c +++ b/drivers/usb/renesas_usbhs/common.c | |||
| @@ -126,13 +126,15 @@ void usbhs_sys_host_ctrl(struct usbhs_priv *priv, int enable) | |||
| 126 | void usbhs_sys_function_ctrl(struct usbhs_priv *priv, int enable) | 126 | void usbhs_sys_function_ctrl(struct usbhs_priv *priv, int enable) |
| 127 | { | 127 | { |
| 128 | u16 mask = DCFM | DRPD | DPRPU | HSE | USBE; | 128 | u16 mask = DCFM | DRPD | DPRPU | HSE | USBE; |
| 129 | u16 val = DPRPU | HSE | USBE; | 129 | u16 val = HSE | USBE; |
| 130 | 130 | ||
| 131 | /* | 131 | /* |
| 132 | * if enable | 132 | * if enable |
| 133 | * | 133 | * |
| 134 | * - select Function mode | 134 | * - select Function mode |
| 135 | * - D+ Line Pull-up | 135 | * - D+ Line Pull-up is disabled |
| 136 | * When D+ Line Pull-up is enabled, | ||
| 137 | * calling usbhs_sys_function_pullup(,1) | ||
| 136 | */ | 138 | */ |
| 137 | usbhs_bset(priv, SYSCFG, mask, enable ? val : 0); | 139 | usbhs_bset(priv, SYSCFG, mask, enable ? val : 0); |
| 138 | } | 140 | } |
| @@ -496,20 +498,18 @@ static int usbhs_probe(struct platform_device *pdev) | |||
| 496 | } | 498 | } |
| 497 | 499 | ||
| 498 | /* platform data */ | 500 | /* platform data */ |
| 499 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 500 | irq_res = platform_get_resource(pdev, IORESOURCE_IRQ, 0); | 501 | irq_res = platform_get_resource(pdev, IORESOURCE_IRQ, 0); |
| 501 | if (!res || !irq_res) { | 502 | if (!irq_res) { |
| 502 | dev_err(&pdev->dev, "Not enough Renesas USB platform resources.\n"); | 503 | dev_err(&pdev->dev, "Not enough Renesas USB platform resources.\n"); |
| 503 | return -ENODEV; | 504 | return -ENODEV; |
| 504 | } | 505 | } |
| 505 | 506 | ||
| 506 | /* usb private data */ | 507 | /* usb private data */ |
| 507 | priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL); | 508 | priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL); |
| 508 | if (!priv) { | 509 | if (!priv) |
| 509 | dev_err(&pdev->dev, "Could not allocate priv\n"); | ||
| 510 | return -ENOMEM; | 510 | return -ENOMEM; |
| 511 | } | ||
| 512 | 511 | ||
| 512 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
| 513 | priv->base = devm_ioremap_resource(&pdev->dev, res); | 513 | priv->base = devm_ioremap_resource(&pdev->dev, res); |
| 514 | if (IS_ERR(priv->base)) | 514 | if (IS_ERR(priv->base)) |
| 515 | return PTR_ERR(priv->base); | 515 | return PTR_ERR(priv->base); |
diff --git a/drivers/usb/renesas_usbhs/common.h b/drivers/usb/renesas_usbhs/common.h index a7996da6a1bd..0427cdd1a483 100644 --- a/drivers/usb/renesas_usbhs/common.h +++ b/drivers/usb/renesas_usbhs/common.h | |||
| @@ -102,6 +102,10 @@ struct usbhs_priv; | |||
| 102 | #define DEVADD8 0x00E0 | 102 | #define DEVADD8 0x00E0 |
| 103 | #define DEVADD9 0x00E2 | 103 | #define DEVADD9 0x00E2 |
| 104 | #define DEVADDA 0x00E4 | 104 | #define DEVADDA 0x00E4 |
| 105 | #define D2FIFOSEL 0x00F0 /* for R-Car Gen2 */ | ||
| 106 | #define D2FIFOCTR 0x00F2 /* for R-Car Gen2 */ | ||
| 107 | #define D3FIFOSEL 0x00F4 /* for R-Car Gen2 */ | ||
| 108 | #define D3FIFOCTR 0x00F6 /* for R-Car Gen2 */ | ||
| 105 | 109 | ||
| 106 | /* SYSCFG */ | 110 | /* SYSCFG */ |
| 107 | #define SCKE (1 << 10) /* USB Module Clock Enable */ | 111 | #define SCKE (1 << 10) /* USB Module Clock Enable */ |
| @@ -269,7 +273,8 @@ struct usbhs_priv { | |||
| 269 | */ | 273 | */ |
| 270 | struct usbhs_fifo_info fifo_info; | 274 | struct usbhs_fifo_info fifo_info; |
| 271 | 275 | ||
| 272 | struct usb_phy *phy; | 276 | struct usb_phy *usb_phy; |
| 277 | struct phy *phy; | ||
| 273 | }; | 278 | }; |
| 274 | 279 | ||
| 275 | /* | 280 | /* |
diff --git a/drivers/usb/renesas_usbhs/fifo.c b/drivers/usb/renesas_usbhs/fifo.c index b0c97a3f1bfe..f46271ce1b15 100644 --- a/drivers/usb/renesas_usbhs/fifo.c +++ b/drivers/usb/renesas_usbhs/fifo.c | |||
| @@ -21,8 +21,6 @@ | |||
| 21 | #include "pipe.h" | 21 | #include "pipe.h" |
| 22 | 22 | ||
| 23 | #define usbhsf_get_cfifo(p) (&((p)->fifo_info.cfifo)) | 23 | #define usbhsf_get_cfifo(p) (&((p)->fifo_info.cfifo)) |
| 24 | #define usbhsf_get_d0fifo(p) (&((p)->fifo_info.d0fifo)) | ||
| 25 | #define usbhsf_get_d1fifo(p) (&((p)->fifo_info.d1fifo)) | ||
| 26 | #define usbhsf_is_cfifo(p, f) (usbhsf_get_cfifo(p) == f) | 24 | #define usbhsf_is_cfifo(p, f) (usbhsf_get_cfifo(p) == f) |
| 27 | 25 | ||
| 28 | #define usbhsf_fifo_is_busy(f) ((f)->pipe) /* see usbhs_pipe_select_fifo */ | 26 | #define usbhsf_fifo_is_busy(f) ((f)->pipe) /* see usbhs_pipe_select_fifo */ |
| @@ -577,14 +575,6 @@ static int usbhsf_pio_try_push(struct usbhs_pkt *pkt, int *is_done) | |||
| 577 | usbhs_pipe_number(pipe), | 575 | usbhs_pipe_number(pipe), |
| 578 | pkt->length, pkt->actual, *is_done, pkt->zero); | 576 | pkt->length, pkt->actual, *is_done, pkt->zero); |
| 579 | 577 | ||
| 580 | /* | ||
| 581 | * Transmission end | ||
| 582 | */ | ||
| 583 | if (*is_done) { | ||
| 584 | if (usbhs_pipe_is_dcp(pipe)) | ||
| 585 | usbhs_dcp_control_transfer_done(pipe); | ||
| 586 | } | ||
| 587 | |||
| 588 | usbhsf_fifo_unselect(pipe, fifo); | 578 | usbhsf_fifo_unselect(pipe, fifo); |
| 589 | 579 | ||
| 590 | return 0; | 580 | return 0; |
| @@ -722,14 +712,6 @@ usbhs_fifo_read_end: | |||
| 722 | usbhs_pipe_number(pipe), | 712 | usbhs_pipe_number(pipe), |
| 723 | pkt->length, pkt->actual, *is_done, pkt->zero); | 713 | pkt->length, pkt->actual, *is_done, pkt->zero); |
| 724 | 714 | ||
| 725 | /* | ||
| 726 | * Transmission end | ||
| 727 | */ | ||
| 728 | if (*is_done) { | ||
| 729 | if (usbhs_pipe_is_dcp(pipe)) | ||
| 730 | usbhs_dcp_control_transfer_done(pipe); | ||
| 731 | } | ||
| 732 | |||
| 733 | usbhs_fifo_read_busy: | 715 | usbhs_fifo_read_busy: |
| 734 | usbhsf_fifo_unselect(pipe, fifo); | 716 | usbhsf_fifo_unselect(pipe, fifo); |
| 735 | 717 | ||
| @@ -777,18 +759,13 @@ static struct usbhs_fifo *usbhsf_get_dma_fifo(struct usbhs_priv *priv, | |||
| 777 | struct usbhs_pkt *pkt) | 759 | struct usbhs_pkt *pkt) |
| 778 | { | 760 | { |
| 779 | struct usbhs_fifo *fifo; | 761 | struct usbhs_fifo *fifo; |
| 762 | int i; | ||
| 780 | 763 | ||
| 781 | /* DMA :: D0FIFO */ | 764 | usbhs_for_each_dfifo(priv, fifo, i) { |
| 782 | fifo = usbhsf_get_d0fifo(priv); | 765 | if (usbhsf_dma_chan_get(fifo, pkt) && |
| 783 | if (usbhsf_dma_chan_get(fifo, pkt) && | 766 | !usbhsf_fifo_is_busy(fifo)) |
| 784 | !usbhsf_fifo_is_busy(fifo)) | 767 | return fifo; |
| 785 | return fifo; | 768 | } |
| 786 | |||
| 787 | /* DMA :: D1FIFO */ | ||
| 788 | fifo = usbhsf_get_d1fifo(priv); | ||
| 789 | if (usbhsf_dma_chan_get(fifo, pkt) && | ||
| 790 | !usbhsf_fifo_is_busy(fifo)) | ||
| 791 | return fifo; | ||
| 792 | 769 | ||
| 793 | return NULL; | 770 | return NULL; |
| 794 | } | 771 | } |
| @@ -1176,6 +1153,24 @@ static void usbhsf_dma_complete(void *arg) | |||
| 1176 | usbhs_pipe_number(pipe), ret); | 1153 | usbhs_pipe_number(pipe), ret); |
| 1177 | } | 1154 | } |
| 1178 | 1155 | ||
| 1156 | void usbhs_fifo_clear_dcp(struct usbhs_pipe *pipe) | ||
| 1157 | { | ||
| 1158 | struct usbhs_priv *priv = usbhs_pipe_to_priv(pipe); | ||
| 1159 | struct usbhs_fifo *fifo = usbhsf_get_cfifo(priv); /* CFIFO */ | ||
| 1160 | |||
| 1161 | /* clear DCP FIFO of transmission */ | ||
| 1162 | if (usbhsf_fifo_select(pipe, fifo, 1) < 0) | ||
| 1163 | return; | ||
| 1164 | usbhsf_fifo_clear(pipe, fifo); | ||
| 1165 | usbhsf_fifo_unselect(pipe, fifo); | ||
| 1166 | |||
| 1167 | /* clear DCP FIFO of reception */ | ||
| 1168 | if (usbhsf_fifo_select(pipe, fifo, 0) < 0) | ||
| 1169 | return; | ||
| 1170 | usbhsf_fifo_clear(pipe, fifo); | ||
| 1171 | usbhsf_fifo_unselect(pipe, fifo); | ||
| 1172 | } | ||
| 1173 | |||
| 1179 | /* | 1174 | /* |
| 1180 | * fifo init | 1175 | * fifo init |
| 1181 | */ | 1176 | */ |
| @@ -1183,8 +1178,8 @@ void usbhs_fifo_init(struct usbhs_priv *priv) | |||
| 1183 | { | 1178 | { |
| 1184 | struct usbhs_mod *mod = usbhs_mod_get_current(priv); | 1179 | struct usbhs_mod *mod = usbhs_mod_get_current(priv); |
| 1185 | struct usbhs_fifo *cfifo = usbhsf_get_cfifo(priv); | 1180 | struct usbhs_fifo *cfifo = usbhsf_get_cfifo(priv); |
| 1186 | struct usbhs_fifo *d0fifo = usbhsf_get_d0fifo(priv); | 1181 | struct usbhs_fifo *dfifo; |
| 1187 | struct usbhs_fifo *d1fifo = usbhsf_get_d1fifo(priv); | 1182 | int i; |
| 1188 | 1183 | ||
| 1189 | mod->irq_empty = usbhsf_irq_empty; | 1184 | mod->irq_empty = usbhsf_irq_empty; |
| 1190 | mod->irq_ready = usbhsf_irq_ready; | 1185 | mod->irq_ready = usbhsf_irq_ready; |
| @@ -1192,8 +1187,8 @@ void usbhs_fifo_init(struct usbhs_priv *priv) | |||
| 1192 | mod->irq_brdysts = 0; | 1187 | mod->irq_brdysts = 0; |
| 1193 | 1188 | ||
| 1194 | cfifo->pipe = NULL; | 1189 | cfifo->pipe = NULL; |
| 1195 | d0fifo->pipe = NULL; | 1190 | usbhs_for_each_dfifo(priv, dfifo, i) |
| 1196 | d1fifo->pipe = NULL; | 1191 | dfifo->pipe = NULL; |
| 1197 | } | 1192 | } |
| 1198 | 1193 | ||
| 1199 | void usbhs_fifo_quit(struct usbhs_priv *priv) | 1194 | void usbhs_fifo_quit(struct usbhs_priv *priv) |
| @@ -1206,6 +1201,25 @@ void usbhs_fifo_quit(struct usbhs_priv *priv) | |||
| 1206 | mod->irq_brdysts = 0; | 1201 | mod->irq_brdysts = 0; |
| 1207 | } | 1202 | } |
| 1208 | 1203 | ||
| 1204 | #define __USBHS_DFIFO_INIT(priv, fifo, channel, fifo_port) \ | ||
| 1205 | do { \ | ||
| 1206 | fifo = usbhsf_get_dnfifo(priv, channel); \ | ||
| 1207 | fifo->name = "D"#channel"FIFO"; \ | ||
| 1208 | fifo->port = fifo_port; \ | ||
| 1209 | fifo->sel = D##channel##FIFOSEL; \ | ||
| 1210 | fifo->ctr = D##channel##FIFOCTR; \ | ||
| 1211 | fifo->tx_slave.shdma_slave.slave_id = \ | ||
| 1212 | usbhs_get_dparam(priv, d##channel##_tx_id); \ | ||
| 1213 | fifo->rx_slave.shdma_slave.slave_id = \ | ||
| 1214 | usbhs_get_dparam(priv, d##channel##_rx_id); \ | ||
| 1215 | usbhsf_dma_init(priv, fifo); \ | ||
| 1216 | } while (0) | ||
| 1217 | |||
| 1218 | #define USBHS_DFIFO_INIT(priv, fifo, channel) \ | ||
| 1219 | __USBHS_DFIFO_INIT(priv, fifo, channel, D##channel##FIFO) | ||
| 1220 | #define USBHS_DFIFO_INIT_NO_PORT(priv, fifo, channel) \ | ||
| 1221 | __USBHS_DFIFO_INIT(priv, fifo, channel, 0) | ||
| 1222 | |||
| 1209 | int usbhs_fifo_probe(struct usbhs_priv *priv) | 1223 | int usbhs_fifo_probe(struct usbhs_priv *priv) |
| 1210 | { | 1224 | { |
| 1211 | struct usbhs_fifo *fifo; | 1225 | struct usbhs_fifo *fifo; |
| @@ -1217,31 +1231,20 @@ int usbhs_fifo_probe(struct usbhs_priv *priv) | |||
| 1217 | fifo->sel = CFIFOSEL; | 1231 | fifo->sel = CFIFOSEL; |
| 1218 | fifo->ctr = CFIFOCTR; | 1232 | fifo->ctr = CFIFOCTR; |
| 1219 | 1233 | ||
| 1220 | /* D0FIFO */ | 1234 | /* DFIFO */ |
| 1221 | fifo = usbhsf_get_d0fifo(priv); | 1235 | USBHS_DFIFO_INIT(priv, fifo, 0); |
| 1222 | fifo->name = "D0FIFO"; | 1236 | USBHS_DFIFO_INIT(priv, fifo, 1); |
| 1223 | fifo->port = D0FIFO; | 1237 | USBHS_DFIFO_INIT_NO_PORT(priv, fifo, 2); |
| 1224 | fifo->sel = D0FIFOSEL; | 1238 | USBHS_DFIFO_INIT_NO_PORT(priv, fifo, 3); |
| 1225 | fifo->ctr = D0FIFOCTR; | ||
| 1226 | fifo->tx_slave.shdma_slave.slave_id = usbhs_get_dparam(priv, d0_tx_id); | ||
| 1227 | fifo->rx_slave.shdma_slave.slave_id = usbhs_get_dparam(priv, d0_rx_id); | ||
| 1228 | usbhsf_dma_init(priv, fifo); | ||
| 1229 | |||
| 1230 | /* D1FIFO */ | ||
| 1231 | fifo = usbhsf_get_d1fifo(priv); | ||
| 1232 | fifo->name = "D1FIFO"; | ||
| 1233 | fifo->port = D1FIFO; | ||
| 1234 | fifo->sel = D1FIFOSEL; | ||
| 1235 | fifo->ctr = D1FIFOCTR; | ||
| 1236 | fifo->tx_slave.shdma_slave.slave_id = usbhs_get_dparam(priv, d1_tx_id); | ||
| 1237 | fifo->rx_slave.shdma_slave.slave_id = usbhs_get_dparam(priv, d1_rx_id); | ||
| 1238 | usbhsf_dma_init(priv, fifo); | ||
| 1239 | 1239 | ||
| 1240 | return 0; | 1240 | return 0; |
| 1241 | } | 1241 | } |
| 1242 | 1242 | ||
| 1243 | void usbhs_fifo_remove(struct usbhs_priv *priv) | 1243 | void usbhs_fifo_remove(struct usbhs_priv *priv) |
| 1244 | { | 1244 | { |
| 1245 | usbhsf_dma_quit(priv, usbhsf_get_d0fifo(priv)); | 1245 | struct usbhs_fifo *fifo; |
| 1246 | usbhsf_dma_quit(priv, usbhsf_get_d1fifo(priv)); | 1246 | int i; |
| 1247 | |||
| 1248 | usbhs_for_each_dfifo(priv, fifo, i) | ||
| 1249 | usbhsf_dma_quit(priv, fifo); | ||
| 1247 | } | 1250 | } |
diff --git a/drivers/usb/renesas_usbhs/fifo.h b/drivers/usb/renesas_usbhs/fifo.h index a168a1760fce..f07037c1185f 100644 --- a/drivers/usb/renesas_usbhs/fifo.h +++ b/drivers/usb/renesas_usbhs/fifo.h | |||
| @@ -38,11 +38,16 @@ struct usbhs_fifo { | |||
| 38 | struct sh_dmae_slave rx_slave; | 38 | struct sh_dmae_slave rx_slave; |
| 39 | }; | 39 | }; |
| 40 | 40 | ||
| 41 | #define USBHS_MAX_NUM_DFIFO 4 | ||
| 41 | struct usbhs_fifo_info { | 42 | struct usbhs_fifo_info { |
| 42 | struct usbhs_fifo cfifo; | 43 | struct usbhs_fifo cfifo; |
| 43 | struct usbhs_fifo d0fifo; | 44 | struct usbhs_fifo dfifo[USBHS_MAX_NUM_DFIFO]; |
| 44 | struct usbhs_fifo d1fifo; | ||
| 45 | }; | 45 | }; |
| 46 | #define usbhsf_get_dnfifo(p, n) (&((p)->fifo_info.dfifo[n])) | ||
| 47 | #define usbhs_for_each_dfifo(priv, dfifo, i) \ | ||
| 48 | for ((i) = 0, dfifo = usbhsf_get_dnfifo(priv, (i)); \ | ||
| 49 | ((i) < USBHS_MAX_NUM_DFIFO); \ | ||
| 50 | (i)++, dfifo = usbhsf_get_dnfifo(priv, (i))) | ||
| 46 | 51 | ||
| 47 | struct usbhs_pkt_handle; | 52 | struct usbhs_pkt_handle; |
| 48 | struct usbhs_pkt { | 53 | struct usbhs_pkt { |
| @@ -74,6 +79,7 @@ int usbhs_fifo_probe(struct usbhs_priv *priv); | |||
| 74 | void usbhs_fifo_remove(struct usbhs_priv *priv); | 79 | void usbhs_fifo_remove(struct usbhs_priv *priv); |
| 75 | void usbhs_fifo_init(struct usbhs_priv *priv); | 80 | void usbhs_fifo_init(struct usbhs_priv *priv); |
| 76 | void usbhs_fifo_quit(struct usbhs_priv *priv); | 81 | void usbhs_fifo_quit(struct usbhs_priv *priv); |
| 82 | void usbhs_fifo_clear_dcp(struct usbhs_pipe *pipe); | ||
| 77 | 83 | ||
| 78 | /* | 84 | /* |
| 79 | * packet info | 85 | * packet info |
diff --git a/drivers/usb/renesas_usbhs/mod_gadget.c b/drivers/usb/renesas_usbhs/mod_gadget.c index 2d17c10a0428..8697e6efcabf 100644 --- a/drivers/usb/renesas_usbhs/mod_gadget.c +++ b/drivers/usb/renesas_usbhs/mod_gadget.c | |||
| @@ -56,6 +56,7 @@ struct usbhsg_gpriv { | |||
| 56 | #define USBHSG_STATUS_REGISTERD (1 << 1) | 56 | #define USBHSG_STATUS_REGISTERD (1 << 1) |
| 57 | #define USBHSG_STATUS_WEDGE (1 << 2) | 57 | #define USBHSG_STATUS_WEDGE (1 << 2) |
| 58 | #define USBHSG_STATUS_SELF_POWERED (1 << 3) | 58 | #define USBHSG_STATUS_SELF_POWERED (1 << 3) |
| 59 | #define USBHSG_STATUS_SOFT_CONNECT (1 << 4) | ||
| 59 | }; | 60 | }; |
| 60 | 61 | ||
| 61 | struct usbhsg_recip_handle { | 62 | struct usbhsg_recip_handle { |
| @@ -484,6 +485,9 @@ static int usbhsg_irq_ctrl_stage(struct usbhs_priv *priv, | |||
| 484 | case NODATA_STATUS_STAGE: | 485 | case NODATA_STATUS_STAGE: |
| 485 | pipe->handler = &usbhs_ctrl_stage_end_handler; | 486 | pipe->handler = &usbhs_ctrl_stage_end_handler; |
| 486 | break; | 487 | break; |
| 488 | case READ_STATUS_STAGE: | ||
| 489 | case WRITE_STATUS_STAGE: | ||
| 490 | usbhs_dcp_control_transfer_done(pipe); | ||
| 487 | default: | 491 | default: |
| 488 | return ret; | 492 | return ret; |
| 489 | } | 493 | } |
| @@ -602,6 +606,9 @@ static int usbhsg_ep_disable(struct usb_ep *ep) | |||
| 602 | struct usbhsg_uep *uep = usbhsg_ep_to_uep(ep); | 606 | struct usbhsg_uep *uep = usbhsg_ep_to_uep(ep); |
| 603 | struct usbhs_pipe *pipe = usbhsg_uep_to_pipe(uep); | 607 | struct usbhs_pipe *pipe = usbhsg_uep_to_pipe(uep); |
| 604 | 608 | ||
| 609 | if (!pipe) | ||
| 610 | return -EINVAL; | ||
| 611 | |||
| 605 | usbhsg_pipe_disable(uep); | 612 | usbhsg_pipe_disable(uep); |
| 606 | usbhs_pipe_free(pipe); | 613 | usbhs_pipe_free(pipe); |
| 607 | 614 | ||
| @@ -723,6 +730,25 @@ static struct usb_ep_ops usbhsg_ep_ops = { | |||
| 723 | }; | 730 | }; |
| 724 | 731 | ||
| 725 | /* | 732 | /* |
| 733 | * pullup control | ||
| 734 | */ | ||
| 735 | static int usbhsg_can_pullup(struct usbhs_priv *priv) | ||
| 736 | { | ||
| 737 | struct usbhsg_gpriv *gpriv = usbhsg_priv_to_gpriv(priv); | ||
| 738 | |||
| 739 | return gpriv->driver && | ||
| 740 | usbhsg_status_has(gpriv, USBHSG_STATUS_SOFT_CONNECT); | ||
| 741 | } | ||
| 742 | |||
| 743 | static void usbhsg_update_pullup(struct usbhs_priv *priv) | ||
| 744 | { | ||
| 745 | if (usbhsg_can_pullup(priv)) | ||
| 746 | usbhs_sys_function_pullup(priv, 1); | ||
| 747 | else | ||
| 748 | usbhs_sys_function_pullup(priv, 0); | ||
| 749 | } | ||
| 750 | |||
| 751 | /* | ||
| 726 | * usb module start/end | 752 | * usb module start/end |
| 727 | */ | 753 | */ |
| 728 | static int usbhsg_try_start(struct usbhs_priv *priv, u32 status) | 754 | static int usbhsg_try_start(struct usbhs_priv *priv, u32 status) |
| @@ -756,9 +782,9 @@ static int usbhsg_try_start(struct usbhs_priv *priv, u32 status) | |||
| 756 | /* | 782 | /* |
| 757 | * pipe initialize and enable DCP | 783 | * pipe initialize and enable DCP |
| 758 | */ | 784 | */ |
| 785 | usbhs_fifo_init(priv); | ||
| 759 | usbhs_pipe_init(priv, | 786 | usbhs_pipe_init(priv, |
| 760 | usbhsg_dma_map_ctrl); | 787 | usbhsg_dma_map_ctrl); |
| 761 | usbhs_fifo_init(priv); | ||
| 762 | 788 | ||
| 763 | /* dcp init instead of usbhsg_ep_enable() */ | 789 | /* dcp init instead of usbhsg_ep_enable() */ |
| 764 | dcp->pipe = usbhs_dcp_malloc(priv); | 790 | dcp->pipe = usbhs_dcp_malloc(priv); |
| @@ -772,6 +798,7 @@ static int usbhsg_try_start(struct usbhs_priv *priv, u32 status) | |||
| 772 | * - usb module | 798 | * - usb module |
| 773 | */ | 799 | */ |
| 774 | usbhs_sys_function_ctrl(priv, 1); | 800 | usbhs_sys_function_ctrl(priv, 1); |
| 801 | usbhsg_update_pullup(priv); | ||
| 775 | 802 | ||
| 776 | /* | 803 | /* |
| 777 | * enable irq callback | 804 | * enable irq callback |
| @@ -851,8 +878,7 @@ static int usbhsg_gadget_start(struct usb_gadget *gadget, | |||
| 851 | return usbhsg_try_start(priv, USBHSG_STATUS_REGISTERD); | 878 | return usbhsg_try_start(priv, USBHSG_STATUS_REGISTERD); |
| 852 | } | 879 | } |
| 853 | 880 | ||
| 854 | static int usbhsg_gadget_stop(struct usb_gadget *gadget, | 881 | static int usbhsg_gadget_stop(struct usb_gadget *gadget) |
| 855 | struct usb_gadget_driver *driver) | ||
| 856 | { | 882 | { |
| 857 | struct usbhsg_gpriv *gpriv = usbhsg_gadget_to_gpriv(gadget); | 883 | struct usbhsg_gpriv *gpriv = usbhsg_gadget_to_gpriv(gadget); |
| 858 | struct usbhs_priv *priv = usbhsg_gpriv_to_priv(gpriv); | 884 | struct usbhs_priv *priv = usbhsg_gpriv_to_priv(gpriv); |
| @@ -878,8 +904,15 @@ static int usbhsg_pullup(struct usb_gadget *gadget, int is_on) | |||
| 878 | { | 904 | { |
| 879 | struct usbhsg_gpriv *gpriv = usbhsg_gadget_to_gpriv(gadget); | 905 | struct usbhsg_gpriv *gpriv = usbhsg_gadget_to_gpriv(gadget); |
| 880 | struct usbhs_priv *priv = usbhsg_gpriv_to_priv(gpriv); | 906 | struct usbhs_priv *priv = usbhsg_gpriv_to_priv(gpriv); |
| 907 | unsigned long flags; | ||
| 881 | 908 | ||
| 882 | usbhs_sys_function_pullup(priv, is_on); | 909 | usbhs_lock(priv, flags); |
| 910 | if (is_on) | ||
| 911 | usbhsg_status_set(gpriv, USBHSG_STATUS_SOFT_CONNECT); | ||
| 912 | else | ||
| 913 | usbhsg_status_clr(gpriv, USBHSG_STATUS_SOFT_CONNECT); | ||
| 914 | usbhsg_update_pullup(priv); | ||
| 915 | usbhs_unlock(priv, flags); | ||
| 883 | 916 | ||
| 884 | return 0; | 917 | return 0; |
| 885 | } | 918 | } |
diff --git a/drivers/usb/renesas_usbhs/mod_host.c b/drivers/usb/renesas_usbhs/mod_host.c index 10e1ded9c9cc..f0d323125871 100644 --- a/drivers/usb/renesas_usbhs/mod_host.c +++ b/drivers/usb/renesas_usbhs/mod_host.c | |||
| @@ -1474,9 +1474,9 @@ static int usbhsh_start(struct usbhs_priv *priv) | |||
| 1474 | /* | 1474 | /* |
| 1475 | * pipe initialize and enable DCP | 1475 | * pipe initialize and enable DCP |
| 1476 | */ | 1476 | */ |
| 1477 | usbhs_fifo_init(priv); | ||
| 1477 | usbhs_pipe_init(priv, | 1478 | usbhs_pipe_init(priv, |
| 1478 | usbhsh_dma_map_ctrl); | 1479 | usbhsh_dma_map_ctrl); |
| 1479 | usbhs_fifo_init(priv); | ||
| 1480 | usbhsh_pipe_init_for_host(priv); | 1480 | usbhsh_pipe_init_for_host(priv); |
| 1481 | 1481 | ||
| 1482 | /* | 1482 | /* |
diff --git a/drivers/usb/renesas_usbhs/pipe.c b/drivers/usb/renesas_usbhs/pipe.c index 040bcefcb040..007f45abe96c 100644 --- a/drivers/usb/renesas_usbhs/pipe.c +++ b/drivers/usb/renesas_usbhs/pipe.c | |||
| @@ -618,8 +618,12 @@ void usbhs_pipe_data_sequence(struct usbhs_pipe *pipe, int sequence) | |||
| 618 | 618 | ||
| 619 | void usbhs_pipe_clear(struct usbhs_pipe *pipe) | 619 | void usbhs_pipe_clear(struct usbhs_pipe *pipe) |
| 620 | { | 620 | { |
| 621 | usbhsp_pipectrl_set(pipe, ACLRM, ACLRM); | 621 | if (usbhs_pipe_is_dcp(pipe)) { |
| 622 | usbhsp_pipectrl_set(pipe, ACLRM, 0); | 622 | usbhs_fifo_clear_dcp(pipe); |
| 623 | } else { | ||
| 624 | usbhsp_pipectrl_set(pipe, ACLRM, ACLRM); | ||
| 625 | usbhsp_pipectrl_set(pipe, ACLRM, 0); | ||
| 626 | } | ||
| 623 | } | 627 | } |
| 624 | 628 | ||
| 625 | static struct usbhs_pipe *usbhsp_get_pipe(struct usbhs_priv *priv, u32 type) | 629 | static struct usbhs_pipe *usbhsp_get_pipe(struct usbhs_priv *priv, u32 type) |
diff --git a/drivers/usb/renesas_usbhs/rcar2.c b/drivers/usb/renesas_usbhs/rcar2.c index e6b9dcc1c289..8fc15c0ba339 100644 --- a/drivers/usb/renesas_usbhs/rcar2.c +++ b/drivers/usb/renesas_usbhs/rcar2.c | |||
| @@ -12,6 +12,7 @@ | |||
| 12 | 12 | ||
| 13 | #include <linux/gpio.h> | 13 | #include <linux/gpio.h> |
| 14 | #include <linux/of_gpio.h> | 14 | #include <linux/of_gpio.h> |
| 15 | #include <linux/phy/phy.h> | ||
| 15 | #include <linux/platform_data/gpio-rcar.h> | 16 | #include <linux/platform_data/gpio-rcar.h> |
| 16 | #include <linux/usb/phy.h> | 17 | #include <linux/usb/phy.h> |
| 17 | #include "common.h" | 18 | #include "common.h" |
| @@ -20,25 +21,43 @@ | |||
| 20 | static int usbhs_rcar2_hardware_init(struct platform_device *pdev) | 21 | static int usbhs_rcar2_hardware_init(struct platform_device *pdev) |
| 21 | { | 22 | { |
| 22 | struct usbhs_priv *priv = usbhs_pdev_to_priv(pdev); | 23 | struct usbhs_priv *priv = usbhs_pdev_to_priv(pdev); |
| 23 | struct usb_phy *phy; | ||
| 24 | 24 | ||
| 25 | phy = usb_get_phy_dev(&pdev->dev, 0); | 25 | if (IS_ENABLED(CONFIG_GENERIC_PHY)) { |
| 26 | if (IS_ERR(phy)) | 26 | struct phy *phy = phy_get(&pdev->dev, "usb"); |
| 27 | return PTR_ERR(phy); | ||
| 28 | 27 | ||
| 29 | priv->phy = phy; | 28 | if (IS_ERR(phy)) |
| 30 | return 0; | 29 | return PTR_ERR(phy); |
| 30 | |||
| 31 | priv->phy = phy; | ||
| 32 | return 0; | ||
| 33 | } | ||
| 34 | |||
| 35 | if (IS_ENABLED(CONFIG_USB_PHY)) { | ||
| 36 | struct usb_phy *usb_phy = usb_get_phy_dev(&pdev->dev, 0); | ||
| 37 | |||
| 38 | if (IS_ERR(usb_phy)) | ||
| 39 | return PTR_ERR(usb_phy); | ||
| 40 | |||
| 41 | priv->usb_phy = usb_phy; | ||
| 42 | return 0; | ||
| 43 | } | ||
| 44 | |||
| 45 | return -ENXIO; | ||
| 31 | } | 46 | } |
| 32 | 47 | ||
| 33 | static int usbhs_rcar2_hardware_exit(struct platform_device *pdev) | 48 | static int usbhs_rcar2_hardware_exit(struct platform_device *pdev) |
| 34 | { | 49 | { |
| 35 | struct usbhs_priv *priv = usbhs_pdev_to_priv(pdev); | 50 | struct usbhs_priv *priv = usbhs_pdev_to_priv(pdev); |
| 36 | 51 | ||
| 37 | if (!priv->phy) | 52 | if (priv->phy) { |
| 38 | return 0; | 53 | phy_put(priv->phy); |
| 54 | priv->phy = NULL; | ||
| 55 | } | ||
| 39 | 56 | ||
| 40 | usb_put_phy(priv->phy); | 57 | if (priv->usb_phy) { |
| 41 | priv->phy = NULL; | 58 | usb_put_phy(priv->usb_phy); |
| 59 | priv->usb_phy = NULL; | ||
| 60 | } | ||
| 42 | 61 | ||
| 43 | return 0; | 62 | return 0; |
| 44 | } | 63 | } |
| @@ -47,21 +66,35 @@ static int usbhs_rcar2_power_ctrl(struct platform_device *pdev, | |||
| 47 | void __iomem *base, int enable) | 66 | void __iomem *base, int enable) |
| 48 | { | 67 | { |
| 49 | struct usbhs_priv *priv = usbhs_pdev_to_priv(pdev); | 68 | struct usbhs_priv *priv = usbhs_pdev_to_priv(pdev); |
| 69 | int retval = -ENODEV; | ||
| 70 | |||
| 71 | if (priv->phy) { | ||
| 72 | if (enable) { | ||
| 73 | retval = phy_init(priv->phy); | ||
| 50 | 74 | ||
| 51 | if (!priv->phy) | 75 | if (!retval) |
| 52 | return -ENODEV; | 76 | retval = phy_power_on(priv->phy); |
| 77 | } else { | ||
| 78 | phy_power_off(priv->phy); | ||
| 79 | phy_exit(priv->phy); | ||
| 80 | retval = 0; | ||
| 81 | } | ||
| 82 | } | ||
| 53 | 83 | ||
| 54 | if (enable) { | 84 | if (priv->usb_phy) { |
| 55 | int retval = usb_phy_init(priv->phy); | 85 | if (enable) { |
| 86 | retval = usb_phy_init(priv->usb_phy); | ||
| 56 | 87 | ||
| 57 | if (!retval) | 88 | if (!retval) |
| 58 | retval = usb_phy_set_suspend(priv->phy, 0); | 89 | retval = usb_phy_set_suspend(priv->usb_phy, 0); |
| 59 | return retval; | 90 | } else { |
| 91 | usb_phy_set_suspend(priv->usb_phy, 1); | ||
| 92 | usb_phy_shutdown(priv->usb_phy); | ||
| 93 | retval = 0; | ||
| 94 | } | ||
| 60 | } | 95 | } |
| 61 | 96 | ||
| 62 | usb_phy_set_suspend(priv->phy, 1); | 97 | return retval; |
| 63 | usb_phy_shutdown(priv->phy); | ||
| 64 | return 0; | ||
| 65 | } | 98 | } |
| 66 | 99 | ||
| 67 | static int usbhs_rcar2_get_id(struct platform_device *pdev) | 100 | static int usbhs_rcar2_get_id(struct platform_device *pdev) |
diff --git a/drivers/usb/serial/Kconfig b/drivers/usb/serial/Kconfig index a69f7cd9d0bf..b7cf1982d1d9 100644 --- a/drivers/usb/serial/Kconfig +++ b/drivers/usb/serial/Kconfig | |||
| @@ -60,6 +60,7 @@ config USB_SERIAL_SIMPLE | |||
| 60 | - Suunto ANT+ USB device. | 60 | - Suunto ANT+ USB device. |
| 61 | - Medtronic CareLink USB device | 61 | - Medtronic CareLink USB device |
| 62 | - Fundamental Software dongle. | 62 | - Fundamental Software dongle. |
| 63 | - Google USB serial devices | ||
| 63 | - HP4x calculators | 64 | - HP4x calculators |
| 64 | - a number of Motorola phones | 65 | - a number of Motorola phones |
| 65 | - Novatel Wireless GPS receivers | 66 | - Novatel Wireless GPS receivers |
| @@ -606,10 +607,10 @@ config USB_SERIAL_CYBERJACK | |||
| 606 | If unsure, say N. | 607 | If unsure, say N. |
| 607 | 608 | ||
| 608 | config USB_SERIAL_XIRCOM | 609 | config USB_SERIAL_XIRCOM |
| 609 | tristate "USB Xircom / Entregra Single Port Serial Driver" | 610 | tristate "USB Xircom / Entrega Single Port Serial Driver" |
| 610 | select USB_EZUSB_FX2 | 611 | select USB_EZUSB_FX2 |
| 611 | help | 612 | help |
| 612 | Say Y here if you want to use a Xircom or Entregra single port USB to | 613 | Say Y here if you want to use a Xircom or Entrega single port USB to |
| 613 | serial converter device. This driver makes use of firmware | 614 | serial converter device. This driver makes use of firmware |
| 614 | developed from scratch by Brian Warner. | 615 | developed from scratch by Brian Warner. |
| 615 | 616 | ||
diff --git a/drivers/usb/serial/keyspan_pda.c b/drivers/usb/serial/keyspan_pda.c index 742d827f876c..dd97d8b572c3 100644 --- a/drivers/usb/serial/keyspan_pda.c +++ b/drivers/usb/serial/keyspan_pda.c | |||
| @@ -1,5 +1,5 @@ | |||
| 1 | /* | 1 | /* |
| 2 | * USB Keyspan PDA / Xircom / Entregra Converter driver | 2 | * USB Keyspan PDA / Xircom / Entrega Converter driver |
| 3 | * | 3 | * |
| 4 | * Copyright (C) 1999 - 2001 Greg Kroah-Hartman <greg@kroah.com> | 4 | * Copyright (C) 1999 - 2001 Greg Kroah-Hartman <greg@kroah.com> |
| 5 | * Copyright (C) 1999, 2000 Brian Warner <warner@lothar.com> | 5 | * Copyright (C) 1999, 2000 Brian Warner <warner@lothar.com> |
| @@ -58,11 +58,11 @@ struct keyspan_pda_private { | |||
| 58 | #define KEYSPAN_PDA_FAKE_ID 0x0103 | 58 | #define KEYSPAN_PDA_FAKE_ID 0x0103 |
| 59 | #define KEYSPAN_PDA_ID 0x0104 /* no clue */ | 59 | #define KEYSPAN_PDA_ID 0x0104 /* no clue */ |
| 60 | 60 | ||
| 61 | /* For Xircom PGSDB9 and older Entregra version of the same device */ | 61 | /* For Xircom PGSDB9 and older Entrega version of the same device */ |
| 62 | #define XIRCOM_VENDOR_ID 0x085a | 62 | #define XIRCOM_VENDOR_ID 0x085a |
| 63 | #define XIRCOM_FAKE_ID 0x8027 | 63 | #define XIRCOM_FAKE_ID 0x8027 |
| 64 | #define ENTREGRA_VENDOR_ID 0x1645 | 64 | #define ENTREGA_VENDOR_ID 0x1645 |
| 65 | #define ENTREGRA_FAKE_ID 0x8093 | 65 | #define ENTREGA_FAKE_ID 0x8093 |
| 66 | 66 | ||
| 67 | static const struct usb_device_id id_table_combined[] = { | 67 | static const struct usb_device_id id_table_combined[] = { |
| 68 | #ifdef KEYSPAN | 68 | #ifdef KEYSPAN |
| @@ -70,7 +70,7 @@ static const struct usb_device_id id_table_combined[] = { | |||
| 70 | #endif | 70 | #endif |
| 71 | #ifdef XIRCOM | 71 | #ifdef XIRCOM |
| 72 | { USB_DEVICE(XIRCOM_VENDOR_ID, XIRCOM_FAKE_ID) }, | 72 | { USB_DEVICE(XIRCOM_VENDOR_ID, XIRCOM_FAKE_ID) }, |
| 73 | { USB_DEVICE(ENTREGRA_VENDOR_ID, ENTREGRA_FAKE_ID) }, | 73 | { USB_DEVICE(ENTREGA_VENDOR_ID, ENTREGA_FAKE_ID) }, |
| 74 | #endif | 74 | #endif |
| 75 | { USB_DEVICE(KEYSPAN_VENDOR_ID, KEYSPAN_PDA_ID) }, | 75 | { USB_DEVICE(KEYSPAN_VENDOR_ID, KEYSPAN_PDA_ID) }, |
| 76 | { } /* Terminating entry */ | 76 | { } /* Terminating entry */ |
| @@ -93,7 +93,7 @@ static const struct usb_device_id id_table_fake[] = { | |||
| 93 | #ifdef XIRCOM | 93 | #ifdef XIRCOM |
| 94 | static const struct usb_device_id id_table_fake_xircom[] = { | 94 | static const struct usb_device_id id_table_fake_xircom[] = { |
| 95 | { USB_DEVICE(XIRCOM_VENDOR_ID, XIRCOM_FAKE_ID) }, | 95 | { USB_DEVICE(XIRCOM_VENDOR_ID, XIRCOM_FAKE_ID) }, |
| 96 | { USB_DEVICE(ENTREGRA_VENDOR_ID, ENTREGRA_FAKE_ID) }, | 96 | { USB_DEVICE(ENTREGA_VENDOR_ID, ENTREGA_FAKE_ID) }, |
| 97 | { } | 97 | { } |
| 98 | }; | 98 | }; |
| 99 | #endif | 99 | #endif |
| @@ -667,7 +667,7 @@ static int keyspan_pda_fake_startup(struct usb_serial *serial) | |||
| 667 | #endif | 667 | #endif |
| 668 | #ifdef XIRCOM | 668 | #ifdef XIRCOM |
| 669 | else if ((le16_to_cpu(serial->dev->descriptor.idVendor) == XIRCOM_VENDOR_ID) || | 669 | else if ((le16_to_cpu(serial->dev->descriptor.idVendor) == XIRCOM_VENDOR_ID) || |
| 670 | (le16_to_cpu(serial->dev->descriptor.idVendor) == ENTREGRA_VENDOR_ID)) | 670 | (le16_to_cpu(serial->dev->descriptor.idVendor) == ENTREGA_VENDOR_ID)) |
| 671 | fw_name = "keyspan_pda/xircom_pgs.fw"; | 671 | fw_name = "keyspan_pda/xircom_pgs.fw"; |
| 672 | #endif | 672 | #endif |
| 673 | else { | 673 | else { |
| @@ -744,7 +744,7 @@ static struct usb_serial_driver xircom_pgs_fake_device = { | |||
| 744 | .owner = THIS_MODULE, | 744 | .owner = THIS_MODULE, |
| 745 | .name = "xircom_no_firm", | 745 | .name = "xircom_no_firm", |
| 746 | }, | 746 | }, |
| 747 | .description = "Xircom / Entregra PGS - (prerenumeration)", | 747 | .description = "Xircom / Entrega PGS - (prerenumeration)", |
| 748 | .id_table = id_table_fake_xircom, | 748 | .id_table = id_table_fake_xircom, |
| 749 | .num_ports = 1, | 749 | .num_ports = 1, |
| 750 | .attach = keyspan_pda_fake_startup, | 750 | .attach = keyspan_pda_fake_startup, |
diff --git a/drivers/usb/serial/kobil_sct.c b/drivers/usb/serial/kobil_sct.c index 02c420af251e..2363654cafc9 100644 --- a/drivers/usb/serial/kobil_sct.c +++ b/drivers/usb/serial/kobil_sct.c | |||
| @@ -244,7 +244,7 @@ static int kobil_open(struct tty_struct *tty, struct usb_serial_port *port) | |||
| 244 | priv->device_type == KOBIL_ADAPTER_B_PRODUCT_ID || | 244 | priv->device_type == KOBIL_ADAPTER_B_PRODUCT_ID || |
| 245 | priv->device_type == KOBIL_KAAN_SIM_PRODUCT_ID) { | 245 | priv->device_type == KOBIL_KAAN_SIM_PRODUCT_ID) { |
| 246 | /* start reading (Adapter B 'cause PNP string) */ | 246 | /* start reading (Adapter B 'cause PNP string) */ |
| 247 | result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC); | 247 | result = usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL); |
| 248 | dev_dbg(dev, "%s - Send read URB returns: %i\n", __func__, result); | 248 | dev_dbg(dev, "%s - Send read URB returns: %i\n", __func__, result); |
| 249 | } | 249 | } |
| 250 | 250 | ||
diff --git a/drivers/usb/serial/mos7720.c b/drivers/usb/serial/mos7720.c index dfd728a263d2..4f70df33975a 100644 --- a/drivers/usb/serial/mos7720.c +++ b/drivers/usb/serial/mos7720.c | |||
| @@ -1299,8 +1299,6 @@ static void mos7720_throttle(struct tty_struct *tty) | |||
| 1299 | mos7720_port->shadowMCR &= ~UART_MCR_RTS; | 1299 | mos7720_port->shadowMCR &= ~UART_MCR_RTS; |
| 1300 | write_mos_reg(port->serial, port->port_number, MCR, | 1300 | write_mos_reg(port->serial, port->port_number, MCR, |
| 1301 | mos7720_port->shadowMCR); | 1301 | mos7720_port->shadowMCR); |
| 1302 | if (status != 0) | ||
| 1303 | return; | ||
| 1304 | } | 1302 | } |
| 1305 | } | 1303 | } |
| 1306 | 1304 | ||
| @@ -1331,8 +1329,6 @@ static void mos7720_unthrottle(struct tty_struct *tty) | |||
| 1331 | mos7720_port->shadowMCR |= UART_MCR_RTS; | 1329 | mos7720_port->shadowMCR |= UART_MCR_RTS; |
| 1332 | write_mos_reg(port->serial, port->port_number, MCR, | 1330 | write_mos_reg(port->serial, port->port_number, MCR, |
| 1333 | mos7720_port->shadowMCR); | 1331 | mos7720_port->shadowMCR); |
| 1334 | if (status != 0) | ||
| 1335 | return; | ||
| 1336 | } | 1332 | } |
| 1337 | } | 1333 | } |
| 1338 | 1334 | ||
| @@ -1657,7 +1653,7 @@ static void change_port_settings(struct tty_struct *tty, | |||
| 1657 | write_mos_reg(serial, port_number, IER, 0x0c); | 1653 | write_mos_reg(serial, port_number, IER, 0x0c); |
| 1658 | 1654 | ||
| 1659 | if (port->read_urb->status != -EINPROGRESS) { | 1655 | if (port->read_urb->status != -EINPROGRESS) { |
| 1660 | status = usb_submit_urb(port->read_urb, GFP_ATOMIC); | 1656 | status = usb_submit_urb(port->read_urb, GFP_KERNEL); |
| 1661 | if (status) | 1657 | if (status) |
| 1662 | dev_dbg(&port->dev, "usb_submit_urb(read bulk) failed, status = %d\n", status); | 1658 | dev_dbg(&port->dev, "usb_submit_urb(read bulk) failed, status = %d\n", status); |
| 1663 | } | 1659 | } |
| @@ -1702,7 +1698,7 @@ static void mos7720_set_termios(struct tty_struct *tty, | |||
| 1702 | change_port_settings(tty, mos7720_port, old_termios); | 1698 | change_port_settings(tty, mos7720_port, old_termios); |
| 1703 | 1699 | ||
| 1704 | if (port->read_urb->status != -EINPROGRESS) { | 1700 | if (port->read_urb->status != -EINPROGRESS) { |
| 1705 | status = usb_submit_urb(port->read_urb, GFP_ATOMIC); | 1701 | status = usb_submit_urb(port->read_urb, GFP_KERNEL); |
| 1706 | if (status) | 1702 | if (status) |
| 1707 | dev_dbg(&port->dev, "usb_submit_urb(read bulk) failed, status = %d\n", status); | 1703 | dev_dbg(&port->dev, "usb_submit_urb(read bulk) failed, status = %d\n", status); |
| 1708 | } | 1704 | } |
diff --git a/drivers/usb/serial/mos7840.c b/drivers/usb/serial/mos7840.c index 3d88eefdf1d1..220b4be89641 100644 --- a/drivers/usb/serial/mos7840.c +++ b/drivers/usb/serial/mos7840.c | |||
| @@ -1904,7 +1904,7 @@ static void mos7840_change_port_settings(struct tty_struct *tty, | |||
| 1904 | 1904 | ||
| 1905 | if (mos7840_port->read_urb_busy == false) { | 1905 | if (mos7840_port->read_urb_busy == false) { |
| 1906 | mos7840_port->read_urb_busy = true; | 1906 | mos7840_port->read_urb_busy = true; |
| 1907 | status = usb_submit_urb(mos7840_port->read_urb, GFP_ATOMIC); | 1907 | status = usb_submit_urb(mos7840_port->read_urb, GFP_KERNEL); |
| 1908 | if (status) { | 1908 | if (status) { |
| 1909 | dev_dbg(&port->dev, "usb_submit_urb(read bulk) failed, status = %d\n", | 1909 | dev_dbg(&port->dev, "usb_submit_urb(read bulk) failed, status = %d\n", |
| 1910 | status); | 1910 | status); |
| @@ -1968,7 +1968,7 @@ static void mos7840_set_termios(struct tty_struct *tty, | |||
| 1968 | 1968 | ||
| 1969 | if (mos7840_port->read_urb_busy == false) { | 1969 | if (mos7840_port->read_urb_busy == false) { |
| 1970 | mos7840_port->read_urb_busy = true; | 1970 | mos7840_port->read_urb_busy = true; |
| 1971 | status = usb_submit_urb(mos7840_port->read_urb, GFP_ATOMIC); | 1971 | status = usb_submit_urb(mos7840_port->read_urb, GFP_KERNEL); |
| 1972 | if (status) { | 1972 | if (status) { |
| 1973 | dev_dbg(&port->dev, "usb_submit_urb(read bulk) failed, status = %d\n", | 1973 | dev_dbg(&port->dev, "usb_submit_urb(read bulk) failed, status = %d\n", |
| 1974 | status); | 1974 | status); |
diff --git a/drivers/usb/serial/qcserial.c b/drivers/usb/serial/qcserial.c index b2aa003bf411..cb3e14780a7e 100644 --- a/drivers/usb/serial/qcserial.c +++ b/drivers/usb/serial/qcserial.c | |||
| @@ -27,12 +27,15 @@ enum qcserial_layouts { | |||
| 27 | QCSERIAL_G2K = 0, /* Gobi 2000 */ | 27 | QCSERIAL_G2K = 0, /* Gobi 2000 */ |
| 28 | QCSERIAL_G1K = 1, /* Gobi 1000 */ | 28 | QCSERIAL_G1K = 1, /* Gobi 1000 */ |
| 29 | QCSERIAL_SWI = 2, /* Sierra Wireless */ | 29 | QCSERIAL_SWI = 2, /* Sierra Wireless */ |
| 30 | QCSERIAL_HWI = 3, /* Huawei */ | ||
| 30 | }; | 31 | }; |
| 31 | 32 | ||
| 32 | #define DEVICE_G1K(v, p) \ | 33 | #define DEVICE_G1K(v, p) \ |
| 33 | USB_DEVICE(v, p), .driver_info = QCSERIAL_G1K | 34 | USB_DEVICE(v, p), .driver_info = QCSERIAL_G1K |
| 34 | #define DEVICE_SWI(v, p) \ | 35 | #define DEVICE_SWI(v, p) \ |
| 35 | USB_DEVICE(v, p), .driver_info = QCSERIAL_SWI | 36 | USB_DEVICE(v, p), .driver_info = QCSERIAL_SWI |
| 37 | #define DEVICE_HWI(v, p) \ | ||
| 38 | USB_DEVICE(v, p), .driver_info = QCSERIAL_HWI | ||
| 36 | 39 | ||
| 37 | static const struct usb_device_id id_table[] = { | 40 | static const struct usb_device_id id_table[] = { |
| 38 | /* Gobi 1000 devices */ | 41 | /* Gobi 1000 devices */ |
| @@ -157,6 +160,9 @@ static const struct usb_device_id id_table[] = { | |||
| 157 | {DEVICE_SWI(0x413c, 0x81a8)}, /* Dell Wireless 5808 Gobi(TM) 4G LTE Mobile Broadband Card */ | 160 | {DEVICE_SWI(0x413c, 0x81a8)}, /* Dell Wireless 5808 Gobi(TM) 4G LTE Mobile Broadband Card */ |
| 158 | {DEVICE_SWI(0x413c, 0x81a9)}, /* Dell Wireless 5808e Gobi(TM) 4G LTE Mobile Broadband Card */ | 161 | {DEVICE_SWI(0x413c, 0x81a9)}, /* Dell Wireless 5808e Gobi(TM) 4G LTE Mobile Broadband Card */ |
| 159 | 162 | ||
| 163 | /* Huawei devices */ | ||
| 164 | {DEVICE_HWI(0x03f0, 0x581d)}, /* HP lt4112 LTE/HSPA+ Gobi 4G Modem (Huawei me906e) */ | ||
| 165 | |||
| 160 | { } /* Terminating entry */ | 166 | { } /* Terminating entry */ |
| 161 | }; | 167 | }; |
| 162 | MODULE_DEVICE_TABLE(usb, id_table); | 168 | MODULE_DEVICE_TABLE(usb, id_table); |
| @@ -287,6 +293,33 @@ static int qcprobe(struct usb_serial *serial, const struct usb_device_id *id) | |||
| 287 | break; | 293 | break; |
| 288 | } | 294 | } |
| 289 | break; | 295 | break; |
| 296 | case QCSERIAL_HWI: | ||
| 297 | /* | ||
| 298 | * Huawei layout: | ||
| 299 | * 0: AT-capable modem port | ||
| 300 | * 1: DM/DIAG | ||
| 301 | * 2: AT-capable modem port | ||
| 302 | * 3: CCID-compatible PCSC interface | ||
| 303 | * 4: QMI/net | ||
| 304 | * 5: NMEA | ||
| 305 | */ | ||
| 306 | switch (ifnum) { | ||
| 307 | case 0: | ||
| 308 | case 2: | ||
| 309 | dev_dbg(dev, "Modem port found\n"); | ||
| 310 | break; | ||
| 311 | case 1: | ||
| 312 | dev_dbg(dev, "DM/DIAG interface found\n"); | ||
| 313 | break; | ||
| 314 | case 5: | ||
| 315 | dev_dbg(dev, "NMEA GPS interface found\n"); | ||
| 316 | break; | ||
| 317 | default: | ||
| 318 | /* don't claim any unsupported interface */ | ||
| 319 | altsetting = -1; | ||
| 320 | break; | ||
| 321 | } | ||
| 322 | break; | ||
| 290 | default: | 323 | default: |
| 291 | dev_err(dev, "unsupported device layout type: %lu\n", | 324 | dev_err(dev, "unsupported device layout type: %lu\n", |
| 292 | id->driver_info); | 325 | id->driver_info); |
diff --git a/drivers/usb/serial/usb-serial-simple.c b/drivers/usb/serial/usb-serial-simple.c index 8bfc47c29828..3658662898fc 100644 --- a/drivers/usb/serial/usb-serial-simple.c +++ b/drivers/usb/serial/usb-serial-simple.c | |||
| @@ -56,6 +56,14 @@ DEVICE(funsoft, FUNSOFT_IDS); | |||
| 56 | { USB_DEVICE(0x8087, 0x0716) } | 56 | { USB_DEVICE(0x8087, 0x0716) } |
| 57 | DEVICE(flashloader, FLASHLOADER_IDS); | 57 | DEVICE(flashloader, FLASHLOADER_IDS); |
| 58 | 58 | ||
| 59 | /* Google Serial USB SubClass */ | ||
| 60 | #define GOOGLE_IDS() \ | ||
| 61 | { USB_VENDOR_AND_INTERFACE_INFO(0x18d1, \ | ||
| 62 | USB_CLASS_VENDOR_SPEC, \ | ||
| 63 | 0x50, \ | ||
| 64 | 0x01) } | ||
| 65 | DEVICE(google, GOOGLE_IDS); | ||
| 66 | |||
| 59 | /* ViVOpay USB Serial Driver */ | 67 | /* ViVOpay USB Serial Driver */ |
| 60 | #define VIVOPAY_IDS() \ | 68 | #define VIVOPAY_IDS() \ |
| 61 | { USB_DEVICE(0x1d5f, 0x1004) } /* ViVOpay 8800 */ | 69 | { USB_DEVICE(0x1d5f, 0x1004) } /* ViVOpay 8800 */ |
| @@ -97,6 +105,7 @@ static struct usb_serial_driver * const serial_drivers[] = { | |||
| 97 | &zio_device, | 105 | &zio_device, |
| 98 | &funsoft_device, | 106 | &funsoft_device, |
| 99 | &flashloader_device, | 107 | &flashloader_device, |
| 108 | &google_device, | ||
| 100 | &vivopay_device, | 109 | &vivopay_device, |
| 101 | &moto_modem_device, | 110 | &moto_modem_device, |
| 102 | &novatel_gps_device, | 111 | &novatel_gps_device, |
| @@ -111,6 +120,7 @@ static const struct usb_device_id id_table[] = { | |||
| 111 | ZIO_IDS(), | 120 | ZIO_IDS(), |
| 112 | FUNSOFT_IDS(), | 121 | FUNSOFT_IDS(), |
| 113 | FLASHLOADER_IDS(), | 122 | FLASHLOADER_IDS(), |
| 123 | GOOGLE_IDS(), | ||
| 114 | VIVOPAY_IDS(), | 124 | VIVOPAY_IDS(), |
| 115 | MOTO_IDS(), | 125 | MOTO_IDS(), |
| 116 | NOVATEL_IDS(), | 126 | NOVATEL_IDS(), |
diff --git a/drivers/usb/storage/debug.c b/drivers/usb/storage/debug.c index 2d81e1d8ee30..57bf3ad41fb6 100644 --- a/drivers/usb/storage/debug.c +++ b/drivers/usb/storage/debug.c | |||
| @@ -181,17 +181,14 @@ void usb_stor_show_sense(const struct us_data *us, | |||
| 181 | US_DEBUGPX("%s\n", what); | 181 | US_DEBUGPX("%s\n", what); |
| 182 | } | 182 | } |
| 183 | 183 | ||
| 184 | int usb_stor_dbg(const struct us_data *us, const char *fmt, ...) | 184 | void usb_stor_dbg(const struct us_data *us, const char *fmt, ...) |
| 185 | { | 185 | { |
| 186 | va_list args; | 186 | va_list args; |
| 187 | int r; | ||
| 188 | 187 | ||
| 189 | va_start(args, fmt); | 188 | va_start(args, fmt); |
| 190 | 189 | ||
| 191 | r = dev_vprintk_emit(LOGLEVEL_DEBUG, &us->pusb_dev->dev, fmt, args); | 190 | dev_vprintk_emit(LOGLEVEL_DEBUG, &us->pusb_dev->dev, fmt, args); |
| 192 | 191 | ||
| 193 | va_end(args); | 192 | va_end(args); |
| 194 | |||
| 195 | return r; | ||
| 196 | } | 193 | } |
| 197 | EXPORT_SYMBOL_GPL(usb_stor_dbg); | 194 | EXPORT_SYMBOL_GPL(usb_stor_dbg); |
diff --git a/drivers/usb/storage/debug.h b/drivers/usb/storage/debug.h index b1273f03e223..f52520306e1a 100644 --- a/drivers/usb/storage/debug.h +++ b/drivers/usb/storage/debug.h | |||
| @@ -50,15 +50,17 @@ | |||
| 50 | void usb_stor_show_command(const struct us_data *us, struct scsi_cmnd *srb); | 50 | void usb_stor_show_command(const struct us_data *us, struct scsi_cmnd *srb); |
| 51 | void usb_stor_show_sense(const struct us_data *us, unsigned char key, | 51 | void usb_stor_show_sense(const struct us_data *us, unsigned char key, |
| 52 | unsigned char asc, unsigned char ascq); | 52 | unsigned char asc, unsigned char ascq); |
| 53 | __printf(2, 3) int usb_stor_dbg(const struct us_data *us, | 53 | __printf(2, 3) void usb_stor_dbg(const struct us_data *us, |
| 54 | const char *fmt, ...); | 54 | const char *fmt, ...); |
| 55 | 55 | ||
| 56 | #define US_DEBUGPX(fmt, ...) printk(fmt, ##__VA_ARGS__) | 56 | #define US_DEBUGPX(fmt, ...) printk(fmt, ##__VA_ARGS__) |
| 57 | #define US_DEBUG(x) x | 57 | #define US_DEBUG(x) x |
| 58 | #else | 58 | #else |
| 59 | __printf(2, 3) | 59 | __printf(2, 3) |
| 60 | static inline int _usb_stor_dbg(const struct us_data *us, | 60 | static inline void _usb_stor_dbg(const struct us_data *us, |
| 61 | const char *fmt, ...) {return 1;} | 61 | const char *fmt, ...) |
| 62 | { | ||
| 63 | } | ||
| 62 | #define usb_stor_dbg(us, fmt, ...) \ | 64 | #define usb_stor_dbg(us, fmt, ...) \ |
| 63 | do { if (0) _usb_stor_dbg(us, fmt, ##__VA_ARGS__); } while (0) | 65 | do { if (0) _usb_stor_dbg(us, fmt, ##__VA_ARGS__); } while (0) |
| 64 | #define US_DEBUGPX(fmt, ...) \ | 66 | #define US_DEBUGPX(fmt, ...) \ |
diff --git a/drivers/usb/storage/initializers.c b/drivers/usb/storage/initializers.c index 73f125e0cb58..31fa2e92065b 100644 --- a/drivers/usb/storage/initializers.c +++ b/drivers/usb/storage/initializers.c | |||
| @@ -49,10 +49,9 @@ int usb_stor_euscsi_init(struct us_data *us) | |||
| 49 | int result; | 49 | int result; |
| 50 | 50 | ||
| 51 | usb_stor_dbg(us, "Attempting to init eUSCSI bridge...\n"); | 51 | usb_stor_dbg(us, "Attempting to init eUSCSI bridge...\n"); |
| 52 | us->iobuf[0] = 0x1; | ||
| 53 | result = usb_stor_control_msg(us, us->send_ctrl_pipe, | 52 | result = usb_stor_control_msg(us, us->send_ctrl_pipe, |
| 54 | 0x0C, USB_RECIP_INTERFACE | USB_TYPE_VENDOR, | 53 | 0x0C, USB_RECIP_INTERFACE | USB_TYPE_VENDOR, |
| 55 | 0x01, 0x0, us->iobuf, 0x1, 5 * HZ); | 54 | 0x01, 0x0, NULL, 0x0, 5 * HZ); |
| 56 | usb_stor_dbg(us, "-- result is %d\n", result); | 55 | usb_stor_dbg(us, "-- result is %d\n", result); |
| 57 | 56 | ||
| 58 | return 0; | 57 | return 0; |
diff --git a/drivers/usb/storage/transport.c b/drivers/usb/storage/transport.c index b1d815eb6d0b..540add24a12f 100644 --- a/drivers/usb/storage/transport.c +++ b/drivers/usb/storage/transport.c | |||
| @@ -1035,9 +1035,20 @@ int usb_stor_Bulk_max_lun(struct us_data *us) | |||
| 1035 | usb_stor_dbg(us, "GetMaxLUN command result is %d, data is %d\n", | 1035 | usb_stor_dbg(us, "GetMaxLUN command result is %d, data is %d\n", |
| 1036 | result, us->iobuf[0]); | 1036 | result, us->iobuf[0]); |
| 1037 | 1037 | ||
| 1038 | /* if we have a successful request, return the result */ | 1038 | /* |
| 1039 | if (result > 0) | 1039 | * If we have a successful request, return the result if valid. The |
| 1040 | return us->iobuf[0]; | 1040 | * CBW LUN field is 4 bits wide, so the value reported by the device |
| 1041 | * should fit into that. | ||
| 1042 | */ | ||
| 1043 | if (result > 0) { | ||
| 1044 | if (us->iobuf[0] < 16) { | ||
| 1045 | return us->iobuf[0]; | ||
| 1046 | } else { | ||
| 1047 | dev_info(&us->pusb_intf->dev, | ||
| 1048 | "Max LUN %d is not valid, using 0 instead", | ||
| 1049 | us->iobuf[0]); | ||
| 1050 | } | ||
| 1051 | } | ||
| 1041 | 1052 | ||
| 1042 | /* | 1053 | /* |
| 1043 | * Some devices don't like GetMaxLUN. They may STALL the control | 1054 | * Some devices don't like GetMaxLUN. They may STALL the control |
diff --git a/drivers/usb/storage/uas.c b/drivers/usb/storage/uas.c index 4047edfb64e1..6cdabdc119a7 100644 --- a/drivers/usb/storage/uas.c +++ b/drivers/usb/storage/uas.c | |||
| @@ -66,7 +66,7 @@ enum { | |||
| 66 | /* Overrides scsi_pointer */ | 66 | /* Overrides scsi_pointer */ |
| 67 | struct uas_cmd_info { | 67 | struct uas_cmd_info { |
| 68 | unsigned int state; | 68 | unsigned int state; |
| 69 | unsigned int stream; | 69 | unsigned int uas_tag; |
| 70 | struct urb *cmd_urb; | 70 | struct urb *cmd_urb; |
| 71 | struct urb *data_in_urb; | 71 | struct urb *data_in_urb; |
| 72 | struct urb *data_out_urb; | 72 | struct urb *data_out_urb; |
| @@ -173,30 +173,15 @@ static void uas_sense(struct urb *urb, struct scsi_cmnd *cmnd) | |||
| 173 | cmnd->result = sense_iu->status; | 173 | cmnd->result = sense_iu->status; |
| 174 | } | 174 | } |
| 175 | 175 | ||
| 176 | /* | ||
| 177 | * scsi-tags go from 0 - (nr_tags - 1), uas tags need to match stream-ids, | ||
| 178 | * which go from 1 - nr_streams. And we use 1 for untagged commands. | ||
| 179 | */ | ||
| 180 | static int uas_get_tag(struct scsi_cmnd *cmnd) | ||
| 181 | { | ||
| 182 | int tag; | ||
| 183 | |||
| 184 | if (cmnd->flags & SCMD_TAGGED) | ||
| 185 | tag = cmnd->request->tag + 2; | ||
| 186 | else | ||
| 187 | tag = 1; | ||
| 188 | |||
| 189 | return tag; | ||
| 190 | } | ||
| 191 | |||
| 192 | static void uas_log_cmd_state(struct scsi_cmnd *cmnd, const char *prefix, | 176 | static void uas_log_cmd_state(struct scsi_cmnd *cmnd, const char *prefix, |
| 193 | int status) | 177 | int status) |
| 194 | { | 178 | { |
| 195 | struct uas_cmd_info *ci = (void *)&cmnd->SCp; | 179 | struct uas_cmd_info *ci = (void *)&cmnd->SCp; |
| 180 | struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp; | ||
| 196 | 181 | ||
| 197 | scmd_printk(KERN_INFO, cmnd, | 182 | scmd_printk(KERN_INFO, cmnd, |
| 198 | "%s %d tag %d inflight:%s%s%s%s%s%s%s%s%s%s%s%s ", | 183 | "%s %d uas-tag %d inflight:%s%s%s%s%s%s%s%s%s%s%s%s ", |
| 199 | prefix, status, uas_get_tag(cmnd), | 184 | prefix, status, cmdinfo->uas_tag, |
| 200 | (ci->state & SUBMIT_STATUS_URB) ? " s-st" : "", | 185 | (ci->state & SUBMIT_STATUS_URB) ? " s-st" : "", |
| 201 | (ci->state & ALLOC_DATA_IN_URB) ? " a-in" : "", | 186 | (ci->state & ALLOC_DATA_IN_URB) ? " a-in" : "", |
| 202 | (ci->state & SUBMIT_DATA_IN_URB) ? " s-in" : "", | 187 | (ci->state & SUBMIT_DATA_IN_URB) ? " s-in" : "", |
| @@ -242,7 +227,7 @@ static int uas_try_complete(struct scsi_cmnd *cmnd, const char *caller) | |||
| 242 | DATA_OUT_URB_INFLIGHT | | 227 | DATA_OUT_URB_INFLIGHT | |
| 243 | COMMAND_ABORTED)) | 228 | COMMAND_ABORTED)) |
| 244 | return -EBUSY; | 229 | return -EBUSY; |
| 245 | devinfo->cmnd[uas_get_tag(cmnd) - 1] = NULL; | 230 | devinfo->cmnd[cmdinfo->uas_tag - 1] = NULL; |
| 246 | uas_free_unsubmitted_urbs(cmnd); | 231 | uas_free_unsubmitted_urbs(cmnd); |
| 247 | cmnd->scsi_done(cmnd); | 232 | cmnd->scsi_done(cmnd); |
| 248 | return 0; | 233 | return 0; |
| @@ -289,7 +274,7 @@ static void uas_stat_cmplt(struct urb *urb) | |||
| 289 | idx = be16_to_cpup(&iu->tag) - 1; | 274 | idx = be16_to_cpup(&iu->tag) - 1; |
| 290 | if (idx >= MAX_CMNDS || !devinfo->cmnd[idx]) { | 275 | if (idx >= MAX_CMNDS || !devinfo->cmnd[idx]) { |
| 291 | dev_err(&urb->dev->dev, | 276 | dev_err(&urb->dev->dev, |
| 292 | "stat urb: no pending cmd for tag %d\n", idx + 1); | 277 | "stat urb: no pending cmd for uas-tag %d\n", idx + 1); |
| 293 | goto out; | 278 | goto out; |
| 294 | } | 279 | } |
| 295 | 280 | ||
| @@ -427,7 +412,8 @@ static struct urb *uas_alloc_data_urb(struct uas_dev_info *devinfo, gfp_t gfp, | |||
| 427 | goto out; | 412 | goto out; |
| 428 | usb_fill_bulk_urb(urb, udev, pipe, NULL, sdb->length, | 413 | usb_fill_bulk_urb(urb, udev, pipe, NULL, sdb->length, |
| 429 | uas_data_cmplt, cmnd); | 414 | uas_data_cmplt, cmnd); |
| 430 | urb->stream_id = cmdinfo->stream; | 415 | if (devinfo->use_streams) |
| 416 | urb->stream_id = cmdinfo->uas_tag; | ||
| 431 | urb->num_sgs = udev->bus->sg_tablesize ? sdb->table.nents : 0; | 417 | urb->num_sgs = udev->bus->sg_tablesize ? sdb->table.nents : 0; |
| 432 | urb->sg = sdb->table.sgl; | 418 | urb->sg = sdb->table.sgl; |
| 433 | out: | 419 | out: |
| @@ -451,7 +437,8 @@ static struct urb *uas_alloc_sense_urb(struct uas_dev_info *devinfo, gfp_t gfp, | |||
| 451 | 437 | ||
| 452 | usb_fill_bulk_urb(urb, udev, devinfo->status_pipe, iu, sizeof(*iu), | 438 | usb_fill_bulk_urb(urb, udev, devinfo->status_pipe, iu, sizeof(*iu), |
| 453 | uas_stat_cmplt, cmnd->device->host); | 439 | uas_stat_cmplt, cmnd->device->host); |
| 454 | urb->stream_id = cmdinfo->stream; | 440 | if (devinfo->use_streams) |
| 441 | urb->stream_id = cmdinfo->uas_tag; | ||
| 455 | urb->transfer_flags |= URB_FREE_BUFFER; | 442 | urb->transfer_flags |= URB_FREE_BUFFER; |
| 456 | out: | 443 | out: |
| 457 | return urb; | 444 | return urb; |
| @@ -465,6 +452,7 @@ static struct urb *uas_alloc_cmd_urb(struct uas_dev_info *devinfo, gfp_t gfp, | |||
| 465 | { | 452 | { |
| 466 | struct usb_device *udev = devinfo->udev; | 453 | struct usb_device *udev = devinfo->udev; |
| 467 | struct scsi_device *sdev = cmnd->device; | 454 | struct scsi_device *sdev = cmnd->device; |
| 455 | struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp; | ||
| 468 | struct urb *urb = usb_alloc_urb(0, gfp); | 456 | struct urb *urb = usb_alloc_urb(0, gfp); |
| 469 | struct command_iu *iu; | 457 | struct command_iu *iu; |
| 470 | int len; | 458 | int len; |
| @@ -481,7 +469,7 @@ static struct urb *uas_alloc_cmd_urb(struct uas_dev_info *devinfo, gfp_t gfp, | |||
| 481 | goto free; | 469 | goto free; |
| 482 | 470 | ||
| 483 | iu->iu_id = IU_ID_COMMAND; | 471 | iu->iu_id = IU_ID_COMMAND; |
| 484 | iu->tag = cpu_to_be16(uas_get_tag(cmnd)); | 472 | iu->tag = cpu_to_be16(cmdinfo->uas_tag); |
| 485 | iu->prio_attr = UAS_SIMPLE_TAG; | 473 | iu->prio_attr = UAS_SIMPLE_TAG; |
| 486 | iu->len = len; | 474 | iu->len = len; |
| 487 | int_to_scsilun(sdev->lun, &iu->lun); | 475 | int_to_scsilun(sdev->lun, &iu->lun); |
| @@ -608,8 +596,7 @@ static int uas_queuecommand_lck(struct scsi_cmnd *cmnd, | |||
| 608 | struct uas_dev_info *devinfo = sdev->hostdata; | 596 | struct uas_dev_info *devinfo = sdev->hostdata; |
| 609 | struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp; | 597 | struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp; |
| 610 | unsigned long flags; | 598 | unsigned long flags; |
| 611 | unsigned int stream; | 599 | int idx, err; |
| 612 | int err; | ||
| 613 | 600 | ||
| 614 | BUILD_BUG_ON(sizeof(struct uas_cmd_info) > sizeof(struct scsi_pointer)); | 601 | BUILD_BUG_ON(sizeof(struct uas_cmd_info) > sizeof(struct scsi_pointer)); |
| 615 | 602 | ||
| @@ -635,8 +622,12 @@ static int uas_queuecommand_lck(struct scsi_cmnd *cmnd, | |||
| 635 | return 0; | 622 | return 0; |
| 636 | } | 623 | } |
| 637 | 624 | ||
| 638 | stream = uas_get_tag(cmnd); | 625 | /* Find a free uas-tag */ |
| 639 | if (devinfo->cmnd[stream - 1]) { | 626 | for (idx = 0; idx < devinfo->qdepth; idx++) { |
| 627 | if (!devinfo->cmnd[idx]) | ||
| 628 | break; | ||
| 629 | } | ||
| 630 | if (idx == devinfo->qdepth) { | ||
| 640 | spin_unlock_irqrestore(&devinfo->lock, flags); | 631 | spin_unlock_irqrestore(&devinfo->lock, flags); |
| 641 | return SCSI_MLQUEUE_DEVICE_BUSY; | 632 | return SCSI_MLQUEUE_DEVICE_BUSY; |
| 642 | } | 633 | } |
| @@ -644,7 +635,7 @@ static int uas_queuecommand_lck(struct scsi_cmnd *cmnd, | |||
| 644 | cmnd->scsi_done = done; | 635 | cmnd->scsi_done = done; |
| 645 | 636 | ||
| 646 | memset(cmdinfo, 0, sizeof(*cmdinfo)); | 637 | memset(cmdinfo, 0, sizeof(*cmdinfo)); |
| 647 | cmdinfo->stream = stream; | 638 | cmdinfo->uas_tag = idx + 1; /* uas-tag == usb-stream-id, so 1 based */ |
| 648 | cmdinfo->state = SUBMIT_STATUS_URB | ALLOC_CMD_URB | SUBMIT_CMD_URB; | 639 | cmdinfo->state = SUBMIT_STATUS_URB | ALLOC_CMD_URB | SUBMIT_CMD_URB; |
| 649 | 640 | ||
| 650 | switch (cmnd->sc_data_direction) { | 641 | switch (cmnd->sc_data_direction) { |
| @@ -659,10 +650,8 @@ static int uas_queuecommand_lck(struct scsi_cmnd *cmnd, | |||
| 659 | break; | 650 | break; |
| 660 | } | 651 | } |
| 661 | 652 | ||
| 662 | if (!devinfo->use_streams) { | 653 | if (!devinfo->use_streams) |
| 663 | cmdinfo->state &= ~(SUBMIT_DATA_IN_URB | SUBMIT_DATA_OUT_URB); | 654 | cmdinfo->state &= ~(SUBMIT_DATA_IN_URB | SUBMIT_DATA_OUT_URB); |
| 664 | cmdinfo->stream = 0; | ||
| 665 | } | ||
| 666 | 655 | ||
| 667 | err = uas_submit_urbs(cmnd, devinfo, GFP_ATOMIC); | 656 | err = uas_submit_urbs(cmnd, devinfo, GFP_ATOMIC); |
| 668 | if (err) { | 657 | if (err) { |
| @@ -674,7 +663,7 @@ static int uas_queuecommand_lck(struct scsi_cmnd *cmnd, | |||
| 674 | uas_add_work(cmdinfo); | 663 | uas_add_work(cmdinfo); |
| 675 | } | 664 | } |
| 676 | 665 | ||
| 677 | devinfo->cmnd[stream - 1] = cmnd; | 666 | devinfo->cmnd[idx] = cmnd; |
| 678 | spin_unlock_irqrestore(&devinfo->lock, flags); | 667 | spin_unlock_irqrestore(&devinfo->lock, flags); |
| 679 | return 0; | 668 | return 0; |
| 680 | } | 669 | } |
| @@ -702,7 +691,7 @@ static int uas_eh_abort_handler(struct scsi_cmnd *cmnd) | |||
| 702 | cmdinfo->state |= COMMAND_ABORTED; | 691 | cmdinfo->state |= COMMAND_ABORTED; |
| 703 | 692 | ||
| 704 | /* Drop all refs to this cmnd, kill data urbs to break their ref */ | 693 | /* Drop all refs to this cmnd, kill data urbs to break their ref */ |
| 705 | devinfo->cmnd[uas_get_tag(cmnd) - 1] = NULL; | 694 | devinfo->cmnd[cmdinfo->uas_tag - 1] = NULL; |
| 706 | if (cmdinfo->state & DATA_IN_URB_INFLIGHT) | 695 | if (cmdinfo->state & DATA_IN_URB_INFLIGHT) |
| 707 | data_in_urb = usb_get_urb(cmdinfo->data_in_urb); | 696 | data_in_urb = usb_get_urb(cmdinfo->data_in_urb); |
| 708 | if (cmdinfo->state & DATA_OUT_URB_INFLIGHT) | 697 | if (cmdinfo->state & DATA_OUT_URB_INFLIGHT) |
| @@ -816,13 +805,6 @@ static struct scsi_host_template uas_host_template = { | |||
| 816 | .sg_tablesize = SG_NONE, | 805 | .sg_tablesize = SG_NONE, |
| 817 | .cmd_per_lun = 1, /* until we override it */ | 806 | .cmd_per_lun = 1, /* until we override it */ |
| 818 | .skip_settle_delay = 1, | 807 | .skip_settle_delay = 1, |
| 819 | |||
| 820 | /* | ||
| 821 | * The uas drivers expects tags not to be bigger than the maximum | ||
| 822 | * per-device queue depth, which is not true with the blk-mq tag | ||
| 823 | * allocator. | ||
| 824 | */ | ||
| 825 | .disable_blk_mq = true, | ||
| 826 | .use_blk_tags = 1, | 808 | .use_blk_tags = 1, |
| 827 | }; | 809 | }; |
| 828 | 810 | ||
diff --git a/drivers/usb/storage/usb.c b/drivers/usb/storage/usb.c index 9d66ce62542e..d468d02179f4 100644 --- a/drivers/usb/storage/usb.c +++ b/drivers/usb/storage/usb.c | |||
| @@ -884,7 +884,9 @@ static void usb_stor_scan_dwork(struct work_struct *work) | |||
| 884 | dev_dbg(dev, "starting scan\n"); | 884 | dev_dbg(dev, "starting scan\n"); |
| 885 | 885 | ||
| 886 | /* For bulk-only devices, determine the max LUN value */ | 886 | /* For bulk-only devices, determine the max LUN value */ |
| 887 | if (us->protocol == USB_PR_BULK && !(us->fflags & US_FL_SINGLE_LUN)) { | 887 | if (us->protocol == USB_PR_BULK && |
| 888 | !(us->fflags & US_FL_SINGLE_LUN) && | ||
| 889 | !(us->fflags & US_FL_SCM_MULT_TARG)) { | ||
| 888 | mutex_lock(&us->dev_mutex); | 890 | mutex_lock(&us->dev_mutex); |
| 889 | us->max_lun = usb_stor_Bulk_max_lun(us); | 891 | us->max_lun = usb_stor_Bulk_max_lun(us); |
| 890 | mutex_unlock(&us->dev_mutex); | 892 | mutex_unlock(&us->dev_mutex); |
| @@ -983,21 +985,31 @@ int usb_stor_probe2(struct us_data *us) | |||
| 983 | usb_stor_dbg(us, "Transport: %s\n", us->transport_name); | 985 | usb_stor_dbg(us, "Transport: %s\n", us->transport_name); |
| 984 | usb_stor_dbg(us, "Protocol: %s\n", us->protocol_name); | 986 | usb_stor_dbg(us, "Protocol: %s\n", us->protocol_name); |
| 985 | 987 | ||
| 988 | if (us->fflags & US_FL_SCM_MULT_TARG) { | ||
| 989 | /* | ||
| 990 | * SCM eUSCSI bridge devices can have different numbers | ||
| 991 | * of LUNs on different targets; allow all to be probed. | ||
| 992 | */ | ||
| 993 | us->max_lun = 7; | ||
| 994 | /* The eUSCSI itself has ID 7, so avoid scanning that */ | ||
| 995 | us_to_host(us)->this_id = 7; | ||
| 996 | /* max_id is 8 initially, so no need to set it here */ | ||
| 997 | } else { | ||
| 998 | /* In the normal case there is only a single target */ | ||
| 999 | us_to_host(us)->max_id = 1; | ||
| 1000 | /* | ||
| 1001 | * Like Windows, we won't store the LUN bits in CDB[1] for | ||
| 1002 | * SCSI-2 devices using the Bulk-Only transport (even though | ||
| 1003 | * this violates the SCSI spec). | ||
| 1004 | */ | ||
| 1005 | if (us->transport == usb_stor_Bulk_transport) | ||
| 1006 | us_to_host(us)->no_scsi2_lun_in_cdb = 1; | ||
| 1007 | } | ||
| 1008 | |||
| 986 | /* fix for single-lun devices */ | 1009 | /* fix for single-lun devices */ |
| 987 | if (us->fflags & US_FL_SINGLE_LUN) | 1010 | if (us->fflags & US_FL_SINGLE_LUN) |
| 988 | us->max_lun = 0; | 1011 | us->max_lun = 0; |
| 989 | 1012 | ||
| 990 | if (!(us->fflags & US_FL_SCM_MULT_TARG)) | ||
| 991 | us_to_host(us)->max_id = 1; | ||
| 992 | |||
| 993 | /* | ||
| 994 | * Like Windows, we won't store the LUN bits in CDB[1] for SCSI-2 | ||
| 995 | * devices using the Bulk-Only transport (even though this violates | ||
| 996 | * the SCSI spec). | ||
| 997 | */ | ||
| 998 | if (us->transport == usb_stor_Bulk_transport) | ||
| 999 | us_to_host(us)->no_scsi2_lun_in_cdb = 1; | ||
| 1000 | |||
| 1001 | /* Find the endpoints and calculate pipe values */ | 1013 | /* Find the endpoints and calculate pipe values */ |
| 1002 | result = get_pipes(us); | 1014 | result = get_pipes(us); |
| 1003 | if (result) | 1015 | if (result) |
diff --git a/drivers/usb/usbip/stub_dev.c b/drivers/usb/usbip/stub_dev.c index fac20e0434c0..a3ec49bdc1e6 100644 --- a/drivers/usb/usbip/stub_dev.c +++ b/drivers/usb/usbip/stub_dev.c | |||
| @@ -311,7 +311,6 @@ static int stub_probe(struct usb_device *udev) | |||
| 311 | { | 311 | { |
| 312 | struct stub_device *sdev = NULL; | 312 | struct stub_device *sdev = NULL; |
| 313 | const char *udev_busid = dev_name(&udev->dev); | 313 | const char *udev_busid = dev_name(&udev->dev); |
| 314 | int err = 0; | ||
| 315 | struct bus_id_priv *busid_priv; | 314 | struct bus_id_priv *busid_priv; |
| 316 | int rc; | 315 | int rc; |
| 317 | 316 | ||
| @@ -372,23 +371,28 @@ static int stub_probe(struct usb_device *udev) | |||
| 372 | (struct usb_dev_state *) udev); | 371 | (struct usb_dev_state *) udev); |
| 373 | if (rc) { | 372 | if (rc) { |
| 374 | dev_dbg(&udev->dev, "unable to claim port\n"); | 373 | dev_dbg(&udev->dev, "unable to claim port\n"); |
| 375 | return rc; | 374 | goto err_port; |
| 376 | } | 375 | } |
| 377 | 376 | ||
| 378 | err = stub_add_files(&udev->dev); | 377 | rc = stub_add_files(&udev->dev); |
| 379 | if (err) { | 378 | if (rc) { |
| 380 | dev_err(&udev->dev, "stub_add_files for %s\n", udev_busid); | 379 | dev_err(&udev->dev, "stub_add_files for %s\n", udev_busid); |
| 381 | dev_set_drvdata(&udev->dev, NULL); | 380 | goto err_files; |
| 382 | usb_put_dev(udev); | ||
| 383 | kthread_stop_put(sdev->ud.eh); | ||
| 384 | |||
| 385 | busid_priv->sdev = NULL; | ||
| 386 | stub_device_free(sdev); | ||
| 387 | return err; | ||
| 388 | } | 381 | } |
| 389 | busid_priv->status = STUB_BUSID_ALLOC; | 382 | busid_priv->status = STUB_BUSID_ALLOC; |
| 390 | 383 | ||
| 391 | return 0; | 384 | return 0; |
| 385 | err_files: | ||
| 386 | usb_hub_release_port(udev->parent, udev->portnum, | ||
| 387 | (struct usb_dev_state *) udev); | ||
| 388 | err_port: | ||
| 389 | dev_set_drvdata(&udev->dev, NULL); | ||
| 390 | usb_put_dev(udev); | ||
| 391 | kthread_stop_put(sdev->ud.eh); | ||
| 392 | |||
| 393 | busid_priv->sdev = NULL; | ||
| 394 | stub_device_free(sdev); | ||
| 395 | return rc; | ||
| 392 | } | 396 | } |
| 393 | 397 | ||
| 394 | static void shutdown_busid(struct bus_id_priv *busid_priv) | 398 | static void shutdown_busid(struct bus_id_priv *busid_priv) |
diff --git a/drivers/usb/usbip/vhci_hcd.c b/drivers/usb/usbip/vhci_hcd.c index c02374b6049c..cc1b03eccf4a 100644 --- a/drivers/usb/usbip/vhci_hcd.c +++ b/drivers/usb/usbip/vhci_hcd.c | |||
| @@ -518,8 +518,7 @@ static int vhci_urb_enqueue(struct usb_hcd *hcd, struct urb *urb, | |||
| 518 | dev_info(dev, "SetAddress Request (%d) to port %d\n", | 518 | dev_info(dev, "SetAddress Request (%d) to port %d\n", |
| 519 | ctrlreq->wValue, vdev->rhport); | 519 | ctrlreq->wValue, vdev->rhport); |
| 520 | 520 | ||
| 521 | if (vdev->udev) | 521 | usb_put_dev(vdev->udev); |
| 522 | usb_put_dev(vdev->udev); | ||
| 523 | vdev->udev = usb_get_dev(urb->dev); | 522 | vdev->udev = usb_get_dev(urb->dev); |
| 524 | 523 | ||
| 525 | spin_lock(&vdev->ud.lock); | 524 | spin_lock(&vdev->ud.lock); |
| @@ -539,8 +538,7 @@ static int vhci_urb_enqueue(struct usb_hcd *hcd, struct urb *urb, | |||
| 539 | usbip_dbg_vhci_hc( | 538 | usbip_dbg_vhci_hc( |
| 540 | "Not yet?:Get_Descriptor to device 0 (get max pipe size)\n"); | 539 | "Not yet?:Get_Descriptor to device 0 (get max pipe size)\n"); |
| 541 | 540 | ||
| 542 | if (vdev->udev) | 541 | usb_put_dev(vdev->udev); |
| 543 | usb_put_dev(vdev->udev); | ||
| 544 | vdev->udev = usb_get_dev(urb->dev); | 542 | vdev->udev = usb_get_dev(urb->dev); |
| 545 | goto out; | 543 | goto out; |
| 546 | 544 | ||
| @@ -831,8 +829,7 @@ static void vhci_device_reset(struct usbip_device *ud) | |||
| 831 | vdev->speed = 0; | 829 | vdev->speed = 0; |
| 832 | vdev->devid = 0; | 830 | vdev->devid = 0; |
| 833 | 831 | ||
| 834 | if (vdev->udev) | 832 | usb_put_dev(vdev->udev); |
| 835 | usb_put_dev(vdev->udev); | ||
| 836 | vdev->udev = NULL; | 833 | vdev->udev = NULL; |
| 837 | 834 | ||
| 838 | if (ud->tcp_socket) { | 835 | if (ud->tcp_socket) { |
diff --git a/drivers/usb/wusbcore/dev-sysfs.c b/drivers/usb/wusbcore/dev-sysfs.c index 101834576236..415b14002a61 100644 --- a/drivers/usb/wusbcore/dev-sysfs.c +++ b/drivers/usb/wusbcore/dev-sysfs.c | |||
| @@ -101,7 +101,7 @@ static ssize_t wusb_ck_store(struct device *dev, | |||
| 101 | if (wusbhc == NULL) | 101 | if (wusbhc == NULL) |
| 102 | return -ENODEV; | 102 | return -ENODEV; |
| 103 | result = wusb_dev_4way_handshake(wusbhc, usb_dev->wusb_dev, &ck); | 103 | result = wusb_dev_4way_handshake(wusbhc, usb_dev->wusb_dev, &ck); |
| 104 | memset(&ck, 0, sizeof(ck)); | 104 | memzero_explicit(&ck, sizeof(ck)); |
| 105 | wusbhc_put(wusbhc); | 105 | wusbhc_put(wusbhc); |
| 106 | return result < 0 ? result : size; | 106 | return result < 0 ? result : size; |
| 107 | } | 107 | } |
diff --git a/drivers/usb/wusbcore/security.c b/drivers/usb/wusbcore/security.c index cc74d669c802..b66faaf3e842 100644 --- a/drivers/usb/wusbcore/security.c +++ b/drivers/usb/wusbcore/security.c | |||
| @@ -522,10 +522,10 @@ error_hs3: | |||
| 522 | error_hs2: | 522 | error_hs2: |
| 523 | error_hs1: | 523 | error_hs1: |
| 524 | memset(hs, 0, 3*sizeof(hs[0])); | 524 | memset(hs, 0, 3*sizeof(hs[0])); |
| 525 | memset(&keydvt_out, 0, sizeof(keydvt_out)); | 525 | memzero_explicit(&keydvt_out, sizeof(keydvt_out)); |
| 526 | memset(&keydvt_in, 0, sizeof(keydvt_in)); | 526 | memzero_explicit(&keydvt_in, sizeof(keydvt_in)); |
| 527 | memset(&ccm_n, 0, sizeof(ccm_n)); | 527 | memzero_explicit(&ccm_n, sizeof(ccm_n)); |
| 528 | memset(mic, 0, sizeof(mic)); | 528 | memzero_explicit(mic, sizeof(mic)); |
| 529 | if (result < 0) | 529 | if (result < 0) |
| 530 | wusb_dev_set_encryption(usb_dev, 0); | 530 | wusb_dev_set_encryption(usb_dev, 0); |
| 531 | error_dev_set_encryption: | 531 | error_dev_set_encryption: |
diff --git a/drivers/uwb/rsv.c b/drivers/uwb/rsv.c index 0887ae982783..536ad42b0a4b 100644 --- a/drivers/uwb/rsv.c +++ b/drivers/uwb/rsv.c | |||
| @@ -213,7 +213,7 @@ void uwb_rsv_backoff_win_timer(unsigned long arg) | |||
| 213 | bow->total_expired = 0; | 213 | bow->total_expired = 0; |
| 214 | bow->window = UWB_DRP_BACKOFF_WIN_MIN >> 1; | 214 | bow->window = UWB_DRP_BACKOFF_WIN_MIN >> 1; |
| 215 | } | 215 | } |
| 216 | dev_dbg(dev, "backoff_win_timer total_expired=%d, n=%d\n: ", bow->total_expired, bow->n); | 216 | dev_dbg(dev, "backoff_win_timer total_expired=%d, n=%d\n", bow->total_expired, bow->n); |
| 217 | 217 | ||
| 218 | /* try to relocate all the "to be moved" relocations */ | 218 | /* try to relocate all the "to be moved" relocations */ |
| 219 | uwb_rsv_handle_drp_avail_change(rc); | 219 | uwb_rsv_handle_drp_avail_change(rc); |
| @@ -234,7 +234,7 @@ void uwb_rsv_backoff_win_increment(struct uwb_rc *rc) | |||
| 234 | 234 | ||
| 235 | bow->window <<= 1; | 235 | bow->window <<= 1; |
| 236 | bow->n = prandom_u32() & (bow->window - 1); | 236 | bow->n = prandom_u32() & (bow->window - 1); |
| 237 | dev_dbg(dev, "new_window=%d, n=%d\n: ", bow->window, bow->n); | 237 | dev_dbg(dev, "new_window=%d, n=%d\n", bow->window, bow->n); |
| 238 | 238 | ||
| 239 | /* reset the timer associated variables */ | 239 | /* reset the timer associated variables */ |
| 240 | timeout_us = bow->n * UWB_SUPERFRAME_LENGTH_US; | 240 | timeout_us = bow->n * UWB_SUPERFRAME_LENGTH_US; |
diff --git a/include/dt-bindings/phy/phy.h b/include/dt-bindings/phy/phy.h new file mode 100644 index 000000000000..6c901930eb3e --- /dev/null +++ b/include/dt-bindings/phy/phy.h | |||
| @@ -0,0 +1,19 @@ | |||
| 1 | /* | ||
| 2 | * | ||
| 3 | * This header provides constants for the phy framework | ||
| 4 | * | ||
| 5 | * Copyright (C) 2014 STMicroelectronics | ||
| 6 | * Author: Gabriel Fernandez <gabriel.fernandez@st.com> | ||
| 7 | * License terms: GNU General Public License (GPL), version 2 | ||
| 8 | */ | ||
| 9 | |||
| 10 | #ifndef _DT_BINDINGS_PHY | ||
| 11 | #define _DT_BINDINGS_PHY | ||
| 12 | |||
| 13 | #define PHY_NONE 0 | ||
| 14 | #define PHY_TYPE_SATA 1 | ||
| 15 | #define PHY_TYPE_PCIE 2 | ||
| 16 | #define PHY_TYPE_USB2 3 | ||
| 17 | #define PHY_TYPE_USB3 4 | ||
| 18 | |||
| 19 | #endif /* _DT_BINDINGS_PHY */ | ||
diff --git a/include/linux/i2c/twl.h b/include/linux/i2c/twl.h index 8cfb50f38529..0bc03f100d04 100644 --- a/include/linux/i2c/twl.h +++ b/include/linux/i2c/twl.h | |||
| @@ -26,7 +26,6 @@ | |||
| 26 | #define __TWL_H_ | 26 | #define __TWL_H_ |
| 27 | 27 | ||
| 28 | #include <linux/types.h> | 28 | #include <linux/types.h> |
| 29 | #include <linux/phy/phy.h> | ||
| 30 | #include <linux/input/matrix_keypad.h> | 29 | #include <linux/input/matrix_keypad.h> |
| 31 | 30 | ||
| 32 | /* | 31 | /* |
| @@ -634,7 +633,6 @@ enum twl4030_usb_mode { | |||
| 634 | struct twl4030_usb_data { | 633 | struct twl4030_usb_data { |
| 635 | enum twl4030_usb_mode usb_mode; | 634 | enum twl4030_usb_mode usb_mode; |
| 636 | unsigned long features; | 635 | unsigned long features; |
| 637 | struct phy_init_data *init_data; | ||
| 638 | 636 | ||
| 639 | int (*phy_init)(struct device *dev); | 637 | int (*phy_init)(struct device *dev); |
| 640 | int (*phy_exit)(struct device *dev); | 638 | int (*phy_exit)(struct device *dev); |
diff --git a/include/linux/pci_ids.h b/include/linux/pci_ids.h index 97fb9f69aaed..e63c02a93f6b 100644 --- a/include/linux/pci_ids.h +++ b/include/linux/pci_ids.h | |||
| @@ -564,6 +564,7 @@ | |||
| 564 | #define PCI_DEVICE_ID_AMD_8131_BRIDGE 0x7450 | 564 | #define PCI_DEVICE_ID_AMD_8131_BRIDGE 0x7450 |
| 565 | #define PCI_DEVICE_ID_AMD_8131_APIC 0x7451 | 565 | #define PCI_DEVICE_ID_AMD_8131_APIC 0x7451 |
| 566 | #define PCI_DEVICE_ID_AMD_8132_BRIDGE 0x7458 | 566 | #define PCI_DEVICE_ID_AMD_8132_BRIDGE 0x7458 |
| 567 | #define PCI_DEVICE_ID_AMD_NL_USB 0x7912 | ||
| 567 | #define PCI_DEVICE_ID_AMD_CS5535_IDE 0x208F | 568 | #define PCI_DEVICE_ID_AMD_CS5535_IDE 0x208F |
| 568 | #define PCI_DEVICE_ID_AMD_CS5536_ISA 0x2090 | 569 | #define PCI_DEVICE_ID_AMD_CS5536_ISA 0x2090 |
| 569 | #define PCI_DEVICE_ID_AMD_CS5536_FLASH 0x2091 | 570 | #define PCI_DEVICE_ID_AMD_CS5536_FLASH 0x2091 |
diff --git a/include/linux/phy/phy.h b/include/linux/phy/phy.h index 8cb6f815475b..a0197fa1b116 100644 --- a/include/linux/phy/phy.h +++ b/include/linux/phy/phy.h | |||
| @@ -61,7 +61,6 @@ struct phy { | |||
| 61 | struct device dev; | 61 | struct device dev; |
| 62 | int id; | 62 | int id; |
| 63 | const struct phy_ops *ops; | 63 | const struct phy_ops *ops; |
| 64 | struct phy_init_data *init_data; | ||
| 65 | struct mutex mutex; | 64 | struct mutex mutex; |
| 66 | int init_count; | 65 | int init_count; |
| 67 | int power_count; | 66 | int power_count; |
| @@ -84,33 +83,14 @@ struct phy_provider { | |||
| 84 | struct of_phandle_args *args); | 83 | struct of_phandle_args *args); |
| 85 | }; | 84 | }; |
| 86 | 85 | ||
| 87 | /** | 86 | struct phy_lookup { |
| 88 | * struct phy_consumer - represents the phy consumer | 87 | struct list_head node; |
| 89 | * @dev_name: the device name of the controller that will use this PHY device | 88 | const char *dev_id; |
| 90 | * @port: name given to the consumer port | 89 | const char *con_id; |
| 91 | */ | 90 | struct phy *phy; |
| 92 | struct phy_consumer { | ||
| 93 | const char *dev_name; | ||
| 94 | const char *port; | ||
| 95 | }; | ||
| 96 | |||
| 97 | /** | ||
| 98 | * struct phy_init_data - contains the list of PHY consumers | ||
| 99 | * @num_consumers: number of consumers for this PHY device | ||
| 100 | * @consumers: list of PHY consumers | ||
| 101 | */ | ||
| 102 | struct phy_init_data { | ||
| 103 | unsigned int num_consumers; | ||
| 104 | struct phy_consumer *consumers; | ||
| 105 | }; | 91 | }; |
| 106 | 92 | ||
| 107 | #define PHY_CONSUMER(_dev_name, _port) \ | 93 | #define to_phy(a) (container_of((a), struct phy, dev)) |
| 108 | { \ | ||
| 109 | .dev_name = _dev_name, \ | ||
| 110 | .port = _port, \ | ||
| 111 | } | ||
| 112 | |||
| 113 | #define to_phy(dev) (container_of((dev), struct phy, dev)) | ||
| 114 | 94 | ||
| 115 | #define of_phy_provider_register(dev, xlate) \ | 95 | #define of_phy_provider_register(dev, xlate) \ |
| 116 | __of_phy_provider_register((dev), THIS_MODULE, (xlate)) | 96 | __of_phy_provider_register((dev), THIS_MODULE, (xlate)) |
| @@ -159,10 +139,9 @@ struct phy *of_phy_get(struct device_node *np, const char *con_id); | |||
| 159 | struct phy *of_phy_simple_xlate(struct device *dev, | 139 | struct phy *of_phy_simple_xlate(struct device *dev, |
| 160 | struct of_phandle_args *args); | 140 | struct of_phandle_args *args); |
| 161 | struct phy *phy_create(struct device *dev, struct device_node *node, | 141 | struct phy *phy_create(struct device *dev, struct device_node *node, |
| 162 | const struct phy_ops *ops, | 142 | const struct phy_ops *ops); |
| 163 | struct phy_init_data *init_data); | ||
| 164 | struct phy *devm_phy_create(struct device *dev, struct device_node *node, | 143 | struct phy *devm_phy_create(struct device *dev, struct device_node *node, |
| 165 | const struct phy_ops *ops, struct phy_init_data *init_data); | 144 | const struct phy_ops *ops); |
| 166 | void phy_destroy(struct phy *phy); | 145 | void phy_destroy(struct phy *phy); |
| 167 | void devm_phy_destroy(struct device *dev, struct phy *phy); | 146 | void devm_phy_destroy(struct device *dev, struct phy *phy); |
| 168 | struct phy_provider *__of_phy_provider_register(struct device *dev, | 147 | struct phy_provider *__of_phy_provider_register(struct device *dev, |
| @@ -174,6 +153,8 @@ struct phy_provider *__devm_of_phy_provider_register(struct device *dev, | |||
| 174 | void of_phy_provider_unregister(struct phy_provider *phy_provider); | 153 | void of_phy_provider_unregister(struct phy_provider *phy_provider); |
| 175 | void devm_of_phy_provider_unregister(struct device *dev, | 154 | void devm_of_phy_provider_unregister(struct device *dev, |
| 176 | struct phy_provider *phy_provider); | 155 | struct phy_provider *phy_provider); |
| 156 | int phy_create_lookup(struct phy *phy, const char *con_id, const char *dev_id); | ||
| 157 | void phy_remove_lookup(struct phy *phy, const char *con_id, const char *dev_id); | ||
| 177 | #else | 158 | #else |
| 178 | static inline int phy_pm_runtime_get(struct phy *phy) | 159 | static inline int phy_pm_runtime_get(struct phy *phy) |
| 179 | { | 160 | { |
| @@ -301,16 +282,14 @@ static inline struct phy *of_phy_simple_xlate(struct device *dev, | |||
| 301 | 282 | ||
| 302 | static inline struct phy *phy_create(struct device *dev, | 283 | static inline struct phy *phy_create(struct device *dev, |
| 303 | struct device_node *node, | 284 | struct device_node *node, |
| 304 | const struct phy_ops *ops, | 285 | const struct phy_ops *ops) |
| 305 | struct phy_init_data *init_data) | ||
| 306 | { | 286 | { |
| 307 | return ERR_PTR(-ENOSYS); | 287 | return ERR_PTR(-ENOSYS); |
| 308 | } | 288 | } |
| 309 | 289 | ||
| 310 | static inline struct phy *devm_phy_create(struct device *dev, | 290 | static inline struct phy *devm_phy_create(struct device *dev, |
| 311 | struct device_node *node, | 291 | struct device_node *node, |
| 312 | const struct phy_ops *ops, | 292 | const struct phy_ops *ops) |
| 313 | struct phy_init_data *init_data) | ||
| 314 | { | 293 | { |
| 315 | return ERR_PTR(-ENOSYS); | 294 | return ERR_PTR(-ENOSYS); |
| 316 | } | 295 | } |
| @@ -345,6 +324,13 @@ static inline void devm_of_phy_provider_unregister(struct device *dev, | |||
| 345 | struct phy_provider *phy_provider) | 324 | struct phy_provider *phy_provider) |
| 346 | { | 325 | { |
| 347 | } | 326 | } |
| 327 | static inline int | ||
| 328 | phy_create_lookup(struct phy *phy, const char *con_id, const char *dev_id) | ||
| 329 | { | ||
| 330 | return 0; | ||
| 331 | } | ||
| 332 | static inline void phy_remove_lookup(struct phy *phy, const char *con_id, | ||
| 333 | const char *dev_id) { } | ||
| 348 | #endif | 334 | #endif |
| 349 | 335 | ||
| 350 | #endif /* __DRIVERS_PHY_H */ | 336 | #endif /* __DRIVERS_PHY_H */ |
diff --git a/include/linux/platform_data/dwc3-exynos.h b/include/linux/platform_data/dwc3-exynos.h deleted file mode 100644 index 5eb7da9b3772..000000000000 --- a/include/linux/platform_data/dwc3-exynos.h +++ /dev/null | |||
| @@ -1,24 +0,0 @@ | |||
| 1 | /** | ||
| 2 | * dwc3-exynos.h - Samsung EXYNOS DWC3 Specific Glue layer, header. | ||
| 3 | * | ||
| 4 | * Copyright (c) 2012 Samsung Electronics Co., Ltd. | ||
| 5 | * http://www.samsung.com | ||
| 6 | * | ||
| 7 | * Author: Anton Tikhomirov <av.tikhomirov@samsung.com> | ||
| 8 | * | ||
| 9 | * This program is free software; you can redistribute it and/or modify | ||
| 10 | * it under the terms of the GNU General Public License as published by | ||
| 11 | * the Free Software Foundation; either version 2 of the License, or | ||
| 12 | * (at your option) any later version. | ||
| 13 | */ | ||
| 14 | |||
| 15 | #ifndef _DWC3_EXYNOS_H_ | ||
| 16 | #define _DWC3_EXYNOS_H_ | ||
| 17 | |||
| 18 | struct dwc3_exynos_data { | ||
| 19 | int phy_type; | ||
| 20 | int (*phy_init)(struct platform_device *pdev, int type); | ||
| 21 | int (*phy_exit)(struct platform_device *pdev, int type); | ||
| 22 | }; | ||
| 23 | |||
| 24 | #endif /* _DWC3_EXYNOS_H_ */ | ||
diff --git a/include/linux/usb/chipidea.h b/include/linux/usb/chipidea.h index e14c09a45c5a..535997a6681b 100644 --- a/include/linux/usb/chipidea.h +++ b/include/linux/usb/chipidea.h | |||
| @@ -13,11 +13,12 @@ struct ci_hdrc_platform_data { | |||
| 13 | /* offset of the capability registers */ | 13 | /* offset of the capability registers */ |
| 14 | uintptr_t capoffset; | 14 | uintptr_t capoffset; |
| 15 | unsigned power_budget; | 15 | unsigned power_budget; |
| 16 | struct usb_phy *phy; | 16 | struct phy *phy; |
| 17 | /* old usb_phy interface */ | ||
| 18 | struct usb_phy *usb_phy; | ||
| 17 | enum usb_phy_interface phy_mode; | 19 | enum usb_phy_interface phy_mode; |
| 18 | unsigned long flags; | 20 | unsigned long flags; |
| 19 | #define CI_HDRC_REGS_SHARED BIT(0) | 21 | #define CI_HDRC_REGS_SHARED BIT(0) |
| 20 | #define CI_HDRC_REQUIRE_TRANSCEIVER BIT(1) | ||
| 21 | #define CI_HDRC_DISABLE_STREAMING BIT(3) | 22 | #define CI_HDRC_DISABLE_STREAMING BIT(3) |
| 22 | /* | 23 | /* |
| 23 | * Only set it when DCCPARAMS.DC==1 and DCCPARAMS.HC==1, | 24 | * Only set it when DCCPARAMS.DC==1 and DCCPARAMS.HC==1, |
diff --git a/include/linux/usb/composite.h b/include/linux/usb/composite.h index c330f5ef42cf..3d87defcc527 100644 --- a/include/linux/usb/composite.h +++ b/include/linux/usb/composite.h | |||
| @@ -427,6 +427,8 @@ static inline struct usb_composite_driver *to_cdriver( | |||
| 427 | * @b_vendor_code: bMS_VendorCode part of the OS string | 427 | * @b_vendor_code: bMS_VendorCode part of the OS string |
| 428 | * @use_os_string: false by default, interested gadgets set it | 428 | * @use_os_string: false by default, interested gadgets set it |
| 429 | * @os_desc_config: the configuration to be used with OS descriptors | 429 | * @os_desc_config: the configuration to be used with OS descriptors |
| 430 | * @setup_pending: true when setup request is queued but not completed | ||
| 431 | * @os_desc_pending: true when os_desc request is queued but not completed | ||
| 430 | * | 432 | * |
| 431 | * One of these devices is allocated and initialized before the | 433 | * One of these devices is allocated and initialized before the |
| 432 | * associated device driver's bind() is called. | 434 | * associated device driver's bind() is called. |
| @@ -488,6 +490,9 @@ struct usb_composite_dev { | |||
| 488 | 490 | ||
| 489 | /* protects deactivations and delayed_status counts*/ | 491 | /* protects deactivations and delayed_status counts*/ |
| 490 | spinlock_t lock; | 492 | spinlock_t lock; |
| 493 | |||
| 494 | unsigned setup_pending:1; | ||
| 495 | unsigned os_desc_pending:1; | ||
| 491 | }; | 496 | }; |
| 492 | 497 | ||
| 493 | extern int usb_string_id(struct usb_composite_dev *c); | 498 | extern int usb_string_id(struct usb_composite_dev *c); |
| @@ -501,6 +506,8 @@ extern int usb_string_ids_n(struct usb_composite_dev *c, unsigned n); | |||
| 501 | extern void composite_disconnect(struct usb_gadget *gadget); | 506 | extern void composite_disconnect(struct usb_gadget *gadget); |
| 502 | extern int composite_setup(struct usb_gadget *gadget, | 507 | extern int composite_setup(struct usb_gadget *gadget, |
| 503 | const struct usb_ctrlrequest *ctrl); | 508 | const struct usb_ctrlrequest *ctrl); |
| 509 | extern void composite_suspend(struct usb_gadget *gadget); | ||
| 510 | extern void composite_resume(struct usb_gadget *gadget); | ||
| 504 | 511 | ||
| 505 | /* | 512 | /* |
| 506 | * Some systems will need runtime overrides for the product identifiers | 513 | * Some systems will need runtime overrides for the product identifiers |
diff --git a/include/linux/usb/ehci-dbgp.h b/include/linux/usb/ehci-dbgp.h new file mode 100644 index 000000000000..7344d9e591cc --- /dev/null +++ b/include/linux/usb/ehci-dbgp.h | |||
| @@ -0,0 +1,83 @@ | |||
| 1 | /* | ||
| 2 | * Standalone EHCI usb debug driver | ||
| 3 | * | ||
| 4 | * Originally written by: | ||
| 5 | * Eric W. Biederman" <ebiederm@xmission.com> and | ||
| 6 | * Yinghai Lu <yhlu.kernel@gmail.com> | ||
| 7 | * | ||
| 8 | * Changes for early/late printk and HW errata: | ||
| 9 | * Jason Wessel <jason.wessel@windriver.com> | ||
| 10 | * Copyright (C) 2009 Wind River Systems, Inc. | ||
| 11 | * | ||
| 12 | */ | ||
| 13 | |||
| 14 | #ifndef __LINUX_USB_EHCI_DBGP_H | ||
| 15 | #define __LINUX_USB_EHCI_DBGP_H | ||
| 16 | |||
| 17 | #include <linux/console.h> | ||
| 18 | #include <linux/types.h> | ||
| 19 | |||
| 20 | /* Appendix C, Debug port ... intended for use with special "debug devices" | ||
| 21 | * that can help if there's no serial console. (nonstandard enumeration.) | ||
| 22 | */ | ||
| 23 | struct ehci_dbg_port { | ||
| 24 | u32 control; | ||
| 25 | #define DBGP_OWNER (1<<30) | ||
| 26 | #define DBGP_ENABLED (1<<28) | ||
| 27 | #define DBGP_DONE (1<<16) | ||
| 28 | #define DBGP_INUSE (1<<10) | ||
| 29 | #define DBGP_ERRCODE(x) (((x)>>7)&0x07) | ||
| 30 | # define DBGP_ERR_BAD 1 | ||
| 31 | # define DBGP_ERR_SIGNAL 2 | ||
| 32 | #define DBGP_ERROR (1<<6) | ||
| 33 | #define DBGP_GO (1<<5) | ||
| 34 | #define DBGP_OUT (1<<4) | ||
| 35 | #define DBGP_LEN(x) (((x)>>0)&0x0f) | ||
| 36 | u32 pids; | ||
| 37 | #define DBGP_PID_GET(x) (((x)>>16)&0xff) | ||
| 38 | #define DBGP_PID_SET(data, tok) (((data)<<8)|(tok)) | ||
| 39 | u32 data03; | ||
| 40 | u32 data47; | ||
| 41 | u32 address; | ||
| 42 | #define DBGP_EPADDR(dev, ep) (((dev)<<8)|(ep)) | ||
| 43 | }; | ||
| 44 | |||
| 45 | #ifdef CONFIG_EARLY_PRINTK_DBGP | ||
| 46 | extern int early_dbgp_init(char *s); | ||
| 47 | extern struct console early_dbgp_console; | ||
| 48 | #endif /* CONFIG_EARLY_PRINTK_DBGP */ | ||
| 49 | |||
| 50 | struct usb_hcd; | ||
| 51 | |||
| 52 | #ifdef CONFIG_XEN_DOM0 | ||
| 53 | extern int xen_dbgp_reset_prep(struct usb_hcd *); | ||
| 54 | extern int xen_dbgp_external_startup(struct usb_hcd *); | ||
| 55 | #else | ||
| 56 | static inline int xen_dbgp_reset_prep(struct usb_hcd *hcd) | ||
| 57 | { | ||
| 58 | return 1; /* Shouldn't this be 0? */ | ||
| 59 | } | ||
| 60 | |||
| 61 | static inline int xen_dbgp_external_startup(struct usb_hcd *hcd) | ||
| 62 | { | ||
| 63 | return -1; | ||
| 64 | } | ||
| 65 | #endif | ||
| 66 | |||
| 67 | #ifdef CONFIG_EARLY_PRINTK_DBGP | ||
| 68 | /* Call backs from ehci host driver to ehci debug driver */ | ||
| 69 | extern int dbgp_external_startup(struct usb_hcd *); | ||
| 70 | extern int dbgp_reset_prep(struct usb_hcd *); | ||
| 71 | #else | ||
| 72 | static inline int dbgp_reset_prep(struct usb_hcd *hcd) | ||
| 73 | { | ||
| 74 | return xen_dbgp_reset_prep(hcd); | ||
| 75 | } | ||
| 76 | |||
| 77 | static inline int dbgp_external_startup(struct usb_hcd *hcd) | ||
| 78 | { | ||
| 79 | return xen_dbgp_external_startup(hcd); | ||
| 80 | } | ||
| 81 | #endif | ||
| 82 | |||
| 83 | #endif /* __LINUX_USB_EHCI_DBGP_H */ | ||
diff --git a/include/linux/usb/ehci_def.h b/include/linux/usb/ehci_def.h index daec99af5d54..966889a20ea3 100644 --- a/include/linux/usb/ehci_def.h +++ b/include/linux/usb/ehci_def.h | |||
| @@ -19,6 +19,8 @@ | |||
| 19 | #ifndef __LINUX_USB_EHCI_DEF_H | 19 | #ifndef __LINUX_USB_EHCI_DEF_H |
| 20 | #define __LINUX_USB_EHCI_DEF_H | 20 | #define __LINUX_USB_EHCI_DEF_H |
| 21 | 21 | ||
| 22 | #include <linux/usb/ehci-dbgp.h> | ||
| 23 | |||
| 22 | /* EHCI register interface, corresponds to EHCI Revision 0.95 specification */ | 24 | /* EHCI register interface, corresponds to EHCI Revision 0.95 specification */ |
| 23 | 25 | ||
| 24 | /* Section 2.2 Host Controller Capability Registers */ | 26 | /* Section 2.2 Host Controller Capability Registers */ |
| @@ -190,67 +192,4 @@ struct ehci_regs { | |||
| 190 | #define USBMODE_EX_HC (3<<0) /* host controller mode */ | 192 | #define USBMODE_EX_HC (3<<0) /* host controller mode */ |
| 191 | }; | 193 | }; |
| 192 | 194 | ||
| 193 | /* Appendix C, Debug port ... intended for use with special "debug devices" | ||
| 194 | * that can help if there's no serial console. (nonstandard enumeration.) | ||
| 195 | */ | ||
| 196 | struct ehci_dbg_port { | ||
| 197 | u32 control; | ||
| 198 | #define DBGP_OWNER (1<<30) | ||
| 199 | #define DBGP_ENABLED (1<<28) | ||
| 200 | #define DBGP_DONE (1<<16) | ||
| 201 | #define DBGP_INUSE (1<<10) | ||
| 202 | #define DBGP_ERRCODE(x) (((x)>>7)&0x07) | ||
| 203 | # define DBGP_ERR_BAD 1 | ||
| 204 | # define DBGP_ERR_SIGNAL 2 | ||
| 205 | #define DBGP_ERROR (1<<6) | ||
| 206 | #define DBGP_GO (1<<5) | ||
| 207 | #define DBGP_OUT (1<<4) | ||
| 208 | #define DBGP_LEN(x) (((x)>>0)&0x0f) | ||
| 209 | u32 pids; | ||
| 210 | #define DBGP_PID_GET(x) (((x)>>16)&0xff) | ||
| 211 | #define DBGP_PID_SET(data, tok) (((data)<<8)|(tok)) | ||
| 212 | u32 data03; | ||
| 213 | u32 data47; | ||
| 214 | u32 address; | ||
| 215 | #define DBGP_EPADDR(dev, ep) (((dev)<<8)|(ep)) | ||
| 216 | }; | ||
| 217 | |||
| 218 | #ifdef CONFIG_EARLY_PRINTK_DBGP | ||
| 219 | #include <linux/init.h> | ||
| 220 | extern int __init early_dbgp_init(char *s); | ||
| 221 | extern struct console early_dbgp_console; | ||
| 222 | #endif /* CONFIG_EARLY_PRINTK_DBGP */ | ||
| 223 | |||
| 224 | struct usb_hcd; | ||
| 225 | |||
| 226 | #ifdef CONFIG_XEN_DOM0 | ||
| 227 | extern int xen_dbgp_reset_prep(struct usb_hcd *); | ||
| 228 | extern int xen_dbgp_external_startup(struct usb_hcd *); | ||
| 229 | #else | ||
| 230 | static inline int xen_dbgp_reset_prep(struct usb_hcd *hcd) | ||
| 231 | { | ||
| 232 | return 1; /* Shouldn't this be 0? */ | ||
| 233 | } | ||
| 234 | |||
| 235 | static inline int xen_dbgp_external_startup(struct usb_hcd *hcd) | ||
| 236 | { | ||
| 237 | return -1; | ||
| 238 | } | ||
| 239 | #endif | ||
| 240 | |||
| 241 | #ifdef CONFIG_EARLY_PRINTK_DBGP | ||
| 242 | /* Call backs from ehci host driver to ehci debug driver */ | ||
| 243 | extern int dbgp_external_startup(struct usb_hcd *); | ||
| 244 | extern int dbgp_reset_prep(struct usb_hcd *hcd); | ||
| 245 | #else | ||
| 246 | static inline int dbgp_reset_prep(struct usb_hcd *hcd) | ||
| 247 | { | ||
| 248 | return xen_dbgp_reset_prep(hcd); | ||
| 249 | } | ||
| 250 | static inline int dbgp_external_startup(struct usb_hcd *hcd) | ||
| 251 | { | ||
| 252 | return xen_dbgp_external_startup(hcd); | ||
| 253 | } | ||
| 254 | #endif | ||
| 255 | |||
| 256 | #endif /* __LINUX_USB_EHCI_DEF_H */ | 195 | #endif /* __LINUX_USB_EHCI_DEF_H */ |
diff --git a/include/linux/usb/gadget.h b/include/linux/usb/gadget.h index 522cafe26790..70ddb3943b62 100644 --- a/include/linux/usb/gadget.h +++ b/include/linux/usb/gadget.h | |||
| @@ -490,8 +490,7 @@ struct usb_gadget_ops { | |||
| 490 | void (*get_config_params)(struct usb_dcd_config_params *); | 490 | void (*get_config_params)(struct usb_dcd_config_params *); |
| 491 | int (*udc_start)(struct usb_gadget *, | 491 | int (*udc_start)(struct usb_gadget *, |
| 492 | struct usb_gadget_driver *); | 492 | struct usb_gadget_driver *); |
| 493 | int (*udc_stop)(struct usb_gadget *, | 493 | int (*udc_stop)(struct usb_gadget *); |
| 494 | struct usb_gadget_driver *); | ||
| 495 | }; | 494 | }; |
| 496 | 495 | ||
| 497 | /** | 496 | /** |
| @@ -925,7 +924,7 @@ extern int usb_add_gadget_udc_release(struct device *parent, | |||
| 925 | struct usb_gadget *gadget, void (*release)(struct device *dev)); | 924 | struct usb_gadget *gadget, void (*release)(struct device *dev)); |
| 926 | extern int usb_add_gadget_udc(struct device *parent, struct usb_gadget *gadget); | 925 | extern int usb_add_gadget_udc(struct device *parent, struct usb_gadget *gadget); |
| 927 | extern void usb_del_gadget_udc(struct usb_gadget *gadget); | 926 | extern void usb_del_gadget_udc(struct usb_gadget *gadget); |
| 928 | extern int udc_attach_driver(const char *name, | 927 | extern int usb_udc_attach_driver(const char *name, |
| 929 | struct usb_gadget_driver *driver); | 928 | struct usb_gadget_driver *driver); |
| 930 | 929 | ||
| 931 | /*-------------------------------------------------------------------------*/ | 930 | /*-------------------------------------------------------------------------*/ |
diff --git a/include/linux/usb/hcd.h b/include/linux/usb/hcd.h index 668898e29d0e..086bf13307e6 100644 --- a/include/linux/usb/hcd.h +++ b/include/linux/usb/hcd.h | |||
| @@ -379,6 +379,9 @@ struct hc_driver { | |||
| 379 | int (*disable_usb3_lpm_timeout)(struct usb_hcd *, | 379 | int (*disable_usb3_lpm_timeout)(struct usb_hcd *, |
| 380 | struct usb_device *, enum usb3_link_state state); | 380 | struct usb_device *, enum usb3_link_state state); |
| 381 | int (*find_raw_port_number)(struct usb_hcd *, int); | 381 | int (*find_raw_port_number)(struct usb_hcd *, int); |
| 382 | /* Call for power on/off the port if necessary */ | ||
| 383 | int (*port_power)(struct usb_hcd *hcd, int portnum, bool enable); | ||
| 384 | |||
| 382 | }; | 385 | }; |
| 383 | 386 | ||
| 384 | static inline int hcd_giveback_urb_in_bh(struct usb_hcd *hcd) | 387 | static inline int hcd_giveback_urb_in_bh(struct usb_hcd *hcd) |
diff --git a/include/linux/usb/otg.h b/include/linux/usb/otg.h index 154332b7c8c0..52661c5da690 100644 --- a/include/linux/usb/otg.h +++ b/include/linux/usb/otg.h | |||
| @@ -9,15 +9,20 @@ | |||
| 9 | #ifndef __LINUX_USB_OTG_H | 9 | #ifndef __LINUX_USB_OTG_H |
| 10 | #define __LINUX_USB_OTG_H | 10 | #define __LINUX_USB_OTG_H |
| 11 | 11 | ||
| 12 | #include <linux/phy/phy.h> | ||
| 12 | #include <linux/usb/phy.h> | 13 | #include <linux/usb/phy.h> |
| 13 | 14 | ||
| 14 | struct usb_otg { | 15 | struct usb_otg { |
| 15 | u8 default_a; | 16 | u8 default_a; |
| 16 | 17 | ||
| 17 | struct usb_phy *phy; | 18 | struct phy *phy; |
| 19 | /* old usb_phy interface */ | ||
| 20 | struct usb_phy *usb_phy; | ||
| 18 | struct usb_bus *host; | 21 | struct usb_bus *host; |
| 19 | struct usb_gadget *gadget; | 22 | struct usb_gadget *gadget; |
| 20 | 23 | ||
| 24 | enum usb_otg_state state; | ||
| 25 | |||
| 21 | /* bind/unbind the host controller */ | 26 | /* bind/unbind the host controller */ |
| 22 | int (*set_host)(struct usb_otg *otg, struct usb_bus *host); | 27 | int (*set_host)(struct usb_otg *otg, struct usb_bus *host); |
| 23 | 28 | ||
diff --git a/include/linux/usb/phy.h b/include/linux/usb/phy.h index 353053a33f21..f499c23e6342 100644 --- a/include/linux/usb/phy.h +++ b/include/linux/usb/phy.h | |||
| @@ -77,7 +77,6 @@ struct usb_phy { | |||
| 77 | unsigned int flags; | 77 | unsigned int flags; |
| 78 | 78 | ||
| 79 | enum usb_phy_type type; | 79 | enum usb_phy_type type; |
| 80 | enum usb_otg_state state; | ||
| 81 | enum usb_phy_events last_event; | 80 | enum usb_phy_events last_event; |
| 82 | 81 | ||
| 83 | struct usb_otg *otg; | 82 | struct usb_otg *otg; |
| @@ -210,6 +209,7 @@ extern void usb_put_phy(struct usb_phy *); | |||
| 210 | extern void devm_usb_put_phy(struct device *dev, struct usb_phy *x); | 209 | extern void devm_usb_put_phy(struct device *dev, struct usb_phy *x); |
| 211 | extern int usb_bind_phy(const char *dev_name, u8 index, | 210 | extern int usb_bind_phy(const char *dev_name, u8 index, |
| 212 | const char *phy_dev_name); | 211 | const char *phy_dev_name); |
| 212 | extern void usb_phy_set_event(struct usb_phy *x, unsigned long event); | ||
| 213 | #else | 213 | #else |
| 214 | static inline struct usb_phy *usb_get_phy(enum usb_phy_type type) | 214 | static inline struct usb_phy *usb_get_phy(enum usb_phy_type type) |
| 215 | { | 215 | { |
| @@ -251,6 +251,10 @@ static inline int usb_bind_phy(const char *dev_name, u8 index, | |||
| 251 | { | 251 | { |
| 252 | return -EOPNOTSUPP; | 252 | return -EOPNOTSUPP; |
| 253 | } | 253 | } |
| 254 | |||
| 255 | static inline void usb_phy_set_event(struct usb_phy *x, unsigned long event) | ||
| 256 | { | ||
| 257 | } | ||
| 254 | #endif | 258 | #endif |
| 255 | 259 | ||
| 256 | static inline int | 260 | static inline int |
diff --git a/include/linux/usb/renesas_usbhs.h b/include/linux/usb/renesas_usbhs.h index d5952bb66752..9fd9e481ea98 100644 --- a/include/linux/usb/renesas_usbhs.h +++ b/include/linux/usb/renesas_usbhs.h | |||
| @@ -145,6 +145,10 @@ struct renesas_usbhs_driver_param { | |||
| 145 | int d0_rx_id; | 145 | int d0_rx_id; |
| 146 | int d1_tx_id; | 146 | int d1_tx_id; |
| 147 | int d1_rx_id; | 147 | int d1_rx_id; |
| 148 | int d2_tx_id; | ||
| 149 | int d2_rx_id; | ||
| 150 | int d3_tx_id; | ||
| 151 | int d3_rx_id; | ||
| 148 | 152 | ||
| 149 | /* | 153 | /* |
| 150 | * option: | 154 | * option: |
diff --git a/tools/usb/usbip/src/usbipd.c b/tools/usb/usbip/src/usbipd.c index 2f87f2d348ba..2a7cd2b8d966 100644 --- a/tools/usb/usbip/src/usbipd.c +++ b/tools/usb/usbip/src/usbipd.c | |||
| @@ -91,7 +91,6 @@ static void usbipd_help(void) | |||
| 91 | static int recv_request_import(int sockfd) | 91 | static int recv_request_import(int sockfd) |
| 92 | { | 92 | { |
| 93 | struct op_import_request req; | 93 | struct op_import_request req; |
| 94 | struct op_common reply; | ||
| 95 | struct usbip_exported_device *edev; | 94 | struct usbip_exported_device *edev; |
| 96 | struct usbip_usb_device pdu_udev; | 95 | struct usbip_usb_device pdu_udev; |
| 97 | struct list_head *i; | 96 | struct list_head *i; |
| @@ -100,7 +99,6 @@ static int recv_request_import(int sockfd) | |||
| 100 | int rc; | 99 | int rc; |
| 101 | 100 | ||
| 102 | memset(&req, 0, sizeof(req)); | 101 | memset(&req, 0, sizeof(req)); |
| 103 | memset(&reply, 0, sizeof(reply)); | ||
| 104 | 102 | ||
| 105 | rc = usbip_net_recv(sockfd, &req, sizeof(req)); | 103 | rc = usbip_net_recv(sockfd, &req, sizeof(req)); |
| 106 | if (rc < 0) { | 104 | if (rc < 0) { |
