diff options
Diffstat (limited to 'drivers/usb/phy')
23 files changed, 807 insertions, 327 deletions
diff --git a/drivers/usb/phy/Kconfig b/drivers/usb/phy/Kconfig index 3622fff8b798..d5589f9c60a9 100644 --- a/drivers/usb/phy/Kconfig +++ b/drivers/usb/phy/Kconfig | |||
@@ -1,22 +1,10 @@ | |||
1 | # | 1 | # |
2 | # Physical Layer USB driver configuration | 2 | # Physical Layer USB driver configuration |
3 | # | 3 | # |
4 | menuconfig USB_PHY | 4 | menu "USB Physical Layer drivers" |
5 | bool "USB Physical Layer drivers" | ||
6 | help | ||
7 | Most USB controllers have the physical layer signalling part | ||
8 | (commonly called a PHY) built in. However, dual-role devices | ||
9 | (a.k.a. USB on-the-go) which support being USB master or slave | ||
10 | with the same connector often use an external PHY. | ||
11 | |||
12 | The drivers in this submenu add support for such PHY devices. | ||
13 | They are not needed for standard master-only (or the vast | ||
14 | majority of slave-only) USB interfaces. | ||
15 | 5 | ||
16 | If you're not sure if this applies to you, it probably doesn't; | 6 | config USB_PHY |
17 | say N here. | 7 | def_bool n |
18 | |||
19 | if USB_PHY | ||
20 | 8 | ||
21 | # | 9 | # |
22 | # USB Transceiver Drivers | 10 | # USB Transceiver Drivers |
@@ -24,6 +12,7 @@ if USB_PHY | |||
24 | config AB8500_USB | 12 | config AB8500_USB |
25 | tristate "AB8500 USB Transceiver Driver" | 13 | tristate "AB8500 USB Transceiver Driver" |
26 | depends on AB8500_CORE | 14 | depends on AB8500_CORE |
15 | select USB_PHY | ||
27 | help | 16 | help |
28 | Enable this to support the USB OTG transceiver in AB8500 chip. | 17 | Enable this to support the USB OTG transceiver in AB8500 chip. |
29 | This transceiver supports high and full speed devices plus, | 18 | This transceiver supports high and full speed devices plus, |
@@ -33,12 +22,14 @@ config FSL_USB2_OTG | |||
33 | bool "Freescale USB OTG Transceiver Driver" | 22 | bool "Freescale USB OTG Transceiver Driver" |
34 | depends on USB_EHCI_FSL && USB_FSL_USB2 && PM_RUNTIME | 23 | depends on USB_EHCI_FSL && USB_FSL_USB2 && PM_RUNTIME |
35 | select USB_OTG | 24 | select USB_OTG |
25 | select USB_PHY | ||
36 | help | 26 | help |
37 | Enable this to support Freescale USB OTG transceiver. | 27 | Enable this to support Freescale USB OTG transceiver. |
38 | 28 | ||
39 | config ISP1301_OMAP | 29 | config ISP1301_OMAP |
40 | tristate "Philips ISP1301 with OMAP OTG" | 30 | tristate "Philips ISP1301 with OMAP OTG" |
41 | depends on I2C && ARCH_OMAP_OTG | 31 | depends on I2C && ARCH_OMAP_OTG |
32 | select USB_PHY | ||
42 | help | 33 | help |
43 | If you say yes here you get support for the Philips ISP1301 | 34 | If you say yes here you get support for the Philips ISP1301 |
44 | USB-On-The-Go transceiver working with the OMAP OTG controller. | 35 | USB-On-The-Go transceiver working with the OMAP OTG controller. |
@@ -52,12 +43,14 @@ config ISP1301_OMAP | |||
52 | config MV_U3D_PHY | 43 | config MV_U3D_PHY |
53 | bool "Marvell USB 3.0 PHY controller Driver" | 44 | bool "Marvell USB 3.0 PHY controller Driver" |
54 | depends on CPU_MMP3 | 45 | depends on CPU_MMP3 |
46 | select USB_PHY | ||
55 | help | 47 | help |
56 | Enable this to support Marvell USB 3.0 phy controller for Marvell | 48 | Enable this to support Marvell USB 3.0 phy controller for Marvell |
57 | SoC. | 49 | SoC. |
58 | 50 | ||
59 | config NOP_USB_XCEIV | 51 | config NOP_USB_XCEIV |
60 | tristate "NOP USB Transceiver Driver" | 52 | tristate "NOP USB Transceiver Driver" |
53 | select USB_PHY | ||
61 | help | 54 | help |
62 | This driver is to be used by all the usb transceiver which are either | 55 | This driver is to be used by all the usb transceiver which are either |
63 | built-in with usb ip or which are autonomous and doesn't require any | 56 | built-in with usb ip or which are autonomous and doesn't require any |
@@ -65,6 +58,7 @@ config NOP_USB_XCEIV | |||
65 | 58 | ||
66 | config OMAP_CONTROL_USB | 59 | config OMAP_CONTROL_USB |
67 | tristate "OMAP CONTROL USB Driver" | 60 | tristate "OMAP CONTROL USB Driver" |
61 | depends on ARCH_OMAP2PLUS || COMPILE_TEST | ||
68 | help | 62 | help |
69 | Enable this to add support for the USB part present in the control | 63 | Enable this to add support for the USB part present in the control |
70 | module. This driver has API to power on the USB2 PHY and to write to | 64 | module. This driver has API to power on the USB2 PHY and to write to |
@@ -76,6 +70,7 @@ config OMAP_USB2 | |||
76 | tristate "OMAP USB2 PHY Driver" | 70 | tristate "OMAP USB2 PHY Driver" |
77 | depends on ARCH_OMAP2PLUS | 71 | depends on ARCH_OMAP2PLUS |
78 | select OMAP_CONTROL_USB | 72 | select OMAP_CONTROL_USB |
73 | select USB_PHY | ||
79 | help | 74 | help |
80 | Enable this to support the transceiver that is part of SOC. This | 75 | Enable this to support the transceiver that is part of SOC. This |
81 | driver takes care of all the PHY functionality apart from comparator. | 76 | driver takes care of all the PHY functionality apart from comparator. |
@@ -84,13 +79,27 @@ config OMAP_USB2 | |||
84 | 79 | ||
85 | config OMAP_USB3 | 80 | config OMAP_USB3 |
86 | tristate "OMAP USB3 PHY Driver" | 81 | tristate "OMAP USB3 PHY Driver" |
82 | depends on ARCH_OMAP2PLUS || COMPILE_TEST | ||
87 | select OMAP_CONTROL_USB | 83 | select OMAP_CONTROL_USB |
84 | select USB_PHY | ||
88 | help | 85 | help |
89 | Enable this to support the USB3 PHY that is part of SOC. This | 86 | Enable this to support the USB3 PHY that is part of SOC. This |
90 | driver takes care of all the PHY functionality apart from comparator. | 87 | driver takes care of all the PHY functionality apart from comparator. |
91 | This driver interacts with the "OMAP Control USB Driver" to power | 88 | This driver interacts with the "OMAP Control USB Driver" to power |
92 | on/off the PHY. | 89 | on/off the PHY. |
93 | 90 | ||
91 | config AM335X_CONTROL_USB | ||
92 | tristate | ||
93 | |||
94 | config AM335X_PHY_USB | ||
95 | tristate "AM335x USB PHY Driver" | ||
96 | select USB_PHY | ||
97 | select AM335X_CONTROL_USB | ||
98 | select NOP_USB_XCEIV | ||
99 | help | ||
100 | This driver provides PHY support for that phy which part for the | ||
101 | AM335x SoC. | ||
102 | |||
94 | config SAMSUNG_USBPHY | 103 | config SAMSUNG_USBPHY |
95 | tristate | 104 | tristate |
96 | help | 105 | help |
@@ -101,6 +110,7 @@ config SAMSUNG_USBPHY | |||
101 | config SAMSUNG_USB2PHY | 110 | config SAMSUNG_USB2PHY |
102 | tristate "Samsung USB 2.0 PHY controller Driver" | 111 | tristate "Samsung USB 2.0 PHY controller Driver" |
103 | select SAMSUNG_USBPHY | 112 | select SAMSUNG_USBPHY |
113 | select USB_PHY | ||
104 | help | 114 | help |
105 | Enable this to support Samsung USB 2.0 (High Speed) PHY controller | 115 | Enable this to support Samsung USB 2.0 (High Speed) PHY controller |
106 | driver for Samsung SoCs. | 116 | driver for Samsung SoCs. |
@@ -108,6 +118,7 @@ config SAMSUNG_USB2PHY | |||
108 | config SAMSUNG_USB3PHY | 118 | config SAMSUNG_USB3PHY |
109 | tristate "Samsung USB 3.0 PHY controller Driver" | 119 | tristate "Samsung USB 3.0 PHY controller Driver" |
110 | select SAMSUNG_USBPHY | 120 | select SAMSUNG_USBPHY |
121 | select USB_PHY | ||
111 | help | 122 | help |
112 | Enable this to support Samsung USB 3.0 (Super Speed) phy controller | 123 | Enable this to support Samsung USB 3.0 (Super Speed) phy controller |
113 | for samsung SoCs. | 124 | for samsung SoCs. |
@@ -115,6 +126,7 @@ config SAMSUNG_USB3PHY | |||
115 | config TWL4030_USB | 126 | config TWL4030_USB |
116 | tristate "TWL4030 USB Transceiver Driver" | 127 | tristate "TWL4030 USB Transceiver Driver" |
117 | depends on TWL4030_CORE && REGULATOR_TWL4030 && USB_MUSB_OMAP2PLUS | 128 | depends on TWL4030_CORE && REGULATOR_TWL4030 && USB_MUSB_OMAP2PLUS |
129 | select USB_PHY | ||
118 | help | 130 | help |
119 | Enable this to support the USB OTG transceiver on TWL4030 | 131 | Enable this to support the USB OTG transceiver on TWL4030 |
120 | family chips (including the TWL5030 and TPS659x0 devices). | 132 | family chips (including the TWL5030 and TPS659x0 devices). |
@@ -135,6 +147,7 @@ config TWL6030_USB | |||
135 | config USB_GPIO_VBUS | 147 | config USB_GPIO_VBUS |
136 | tristate "GPIO based peripheral-only VBUS sensing 'transceiver'" | 148 | tristate "GPIO based peripheral-only VBUS sensing 'transceiver'" |
137 | depends on GPIOLIB | 149 | depends on GPIOLIB |
150 | select USB_PHY | ||
138 | help | 151 | help |
139 | Provides simple GPIO VBUS sensing for controllers with an | 152 | Provides simple GPIO VBUS sensing for controllers with an |
140 | internal transceiver via the usb_phy interface, and | 153 | internal transceiver via the usb_phy interface, and |
@@ -145,6 +158,7 @@ config USB_ISP1301 | |||
145 | tristate "NXP ISP1301 USB transceiver support" | 158 | tristate "NXP ISP1301 USB transceiver support" |
146 | depends on USB || USB_GADGET | 159 | depends on USB || USB_GADGET |
147 | depends on I2C | 160 | depends on I2C |
161 | select USB_PHY | ||
148 | help | 162 | help |
149 | Say Y here to add support for the NXP ISP1301 USB transceiver driver. | 163 | Say Y here to add support for the NXP ISP1301 USB transceiver driver. |
150 | This chip is typically used as USB transceiver for USB host, gadget | 164 | This chip is typically used as USB transceiver for USB host, gadget |
@@ -156,6 +170,7 @@ config USB_ISP1301 | |||
156 | config USB_MSM_OTG | 170 | config USB_MSM_OTG |
157 | tristate "OTG support for Qualcomm on-chip USB controller" | 171 | tristate "OTG support for Qualcomm on-chip USB controller" |
158 | depends on (USB || USB_GADGET) && ARCH_MSM | 172 | depends on (USB || USB_GADGET) && ARCH_MSM |
173 | select USB_PHY | ||
159 | help | 174 | help |
160 | Enable this to support the USB OTG transceiver on MSM chips. It | 175 | Enable this to support the USB OTG transceiver on MSM chips. It |
161 | handles PHY initialization, clock management, and workarounds | 176 | handles PHY initialization, clock management, and workarounds |
@@ -169,6 +184,7 @@ config USB_MV_OTG | |||
169 | tristate "Marvell USB OTG support" | 184 | tristate "Marvell USB OTG support" |
170 | depends on USB_EHCI_MV && USB_MV_UDC && PM_RUNTIME | 185 | depends on USB_EHCI_MV && USB_MV_UDC && PM_RUNTIME |
171 | select USB_OTG | 186 | select USB_OTG |
187 | select USB_PHY | ||
172 | help | 188 | help |
173 | Say Y here if you want to build Marvell USB OTG transciever | 189 | Say Y here if you want to build Marvell USB OTG transciever |
174 | driver in kernel (including PXA and MMP series). This driver | 190 | driver in kernel (including PXA and MMP series). This driver |
@@ -180,6 +196,7 @@ config USB_MXS_PHY | |||
180 | tristate "Freescale MXS USB PHY support" | 196 | tristate "Freescale MXS USB PHY support" |
181 | depends on ARCH_MXC || ARCH_MXS | 197 | depends on ARCH_MXC || ARCH_MXS |
182 | select STMP_DEVICE | 198 | select STMP_DEVICE |
199 | select USB_PHY | ||
183 | help | 200 | help |
184 | Enable this to support the Freescale MXS USB PHY. | 201 | Enable this to support the Freescale MXS USB PHY. |
185 | 202 | ||
@@ -188,6 +205,7 @@ config USB_MXS_PHY | |||
188 | config USB_RCAR_PHY | 205 | config USB_RCAR_PHY |
189 | tristate "Renesas R-Car USB PHY support" | 206 | tristate "Renesas R-Car USB PHY support" |
190 | depends on USB || USB_GADGET | 207 | depends on USB || USB_GADGET |
208 | select USB_PHY | ||
191 | help | 209 | help |
192 | Say Y here to add support for the Renesas R-Car USB common PHY driver. | 210 | Say Y here to add support for the Renesas R-Car USB common PHY driver. |
193 | This chip is typically used as USB PHY for USB host, gadget. | 211 | This chip is typically used as USB PHY for USB host, gadget. |
@@ -210,4 +228,4 @@ config USB_ULPI_VIEWPORT | |||
210 | Provides read/write operations to the ULPI phy register set for | 228 | Provides read/write operations to the ULPI phy register set for |
211 | controllers with a viewport register (e.g. Chipidea/ARC controllers). | 229 | controllers with a viewport register (e.g. Chipidea/ARC controllers). |
212 | 230 | ||
213 | endif # USB_PHY | 231 | endmenu |
diff --git a/drivers/usb/phy/Makefile b/drivers/usb/phy/Makefile index 070eca3af18b..2135e85f46ed 100644 --- a/drivers/usb/phy/Makefile +++ b/drivers/usb/phy/Makefile | |||
@@ -1,9 +1,6 @@ | |||
1 | # | 1 | # |
2 | # Makefile for physical layer USB drivers | 2 | # Makefile for physical layer USB drivers |
3 | # | 3 | # |
4 | |||
5 | ccflags-$(CONFIG_USB_DEBUG) := -DDEBUG | ||
6 | |||
7 | obj-$(CONFIG_USB_PHY) += phy.o | 4 | obj-$(CONFIG_USB_PHY) += phy.o |
8 | obj-$(CONFIG_OF) += of.o | 5 | obj-$(CONFIG_OF) += of.o |
9 | 6 | ||
@@ -14,8 +11,10 @@ phy-fsl-usb2-objs := phy-fsl-usb.o phy-fsm-usb.o | |||
14 | obj-$(CONFIG_FSL_USB2_OTG) += phy-fsl-usb2.o | 11 | obj-$(CONFIG_FSL_USB2_OTG) += phy-fsl-usb2.o |
15 | obj-$(CONFIG_ISP1301_OMAP) += phy-isp1301-omap.o | 12 | obj-$(CONFIG_ISP1301_OMAP) += phy-isp1301-omap.o |
16 | obj-$(CONFIG_MV_U3D_PHY) += phy-mv-u3d-usb.o | 13 | obj-$(CONFIG_MV_U3D_PHY) += phy-mv-u3d-usb.o |
17 | obj-$(CONFIG_NOP_USB_XCEIV) += phy-nop.o | 14 | obj-$(CONFIG_NOP_USB_XCEIV) += phy-generic.o |
18 | obj-$(CONFIG_OMAP_CONTROL_USB) += phy-omap-control.o | 15 | obj-$(CONFIG_OMAP_CONTROL_USB) += phy-omap-control.o |
16 | obj-$(CONFIG_AM335X_CONTROL_USB) += phy-am335x-control.o | ||
17 | obj-$(CONFIG_AM335X_PHY_USB) += phy-am335x.o | ||
19 | obj-$(CONFIG_OMAP_USB2) += phy-omap-usb2.o | 18 | obj-$(CONFIG_OMAP_USB2) += phy-omap-usb2.o |
20 | obj-$(CONFIG_OMAP_USB3) += phy-omap-usb3.o | 19 | obj-$(CONFIG_OMAP_USB3) += phy-omap-usb3.o |
21 | obj-$(CONFIG_SAMSUNG_USBPHY) += phy-samsung-usb.o | 20 | obj-$(CONFIG_SAMSUNG_USBPHY) += phy-samsung-usb.o |
diff --git a/drivers/usb/phy/am35x-phy-control.h b/drivers/usb/phy/am35x-phy-control.h new file mode 100644 index 000000000000..b96594d1962c --- /dev/null +++ b/drivers/usb/phy/am35x-phy-control.h | |||
@@ -0,0 +1,21 @@ | |||
1 | #ifndef _AM335x_PHY_CONTROL_H_ | ||
2 | #define _AM335x_PHY_CONTROL_H_ | ||
3 | |||
4 | struct phy_control { | ||
5 | void (*phy_power)(struct phy_control *phy_ctrl, u32 id, bool on); | ||
6 | void (*phy_wkup)(struct phy_control *phy_ctrl, u32 id, bool on); | ||
7 | }; | ||
8 | |||
9 | static inline void phy_ctrl_power(struct phy_control *phy_ctrl, u32 id, bool on) | ||
10 | { | ||
11 | phy_ctrl->phy_power(phy_ctrl, id, on); | ||
12 | } | ||
13 | |||
14 | static inline void phy_ctrl_wkup(struct phy_control *phy_ctrl, u32 id, bool on) | ||
15 | { | ||
16 | phy_ctrl->phy_wkup(phy_ctrl, id, on); | ||
17 | } | ||
18 | |||
19 | struct phy_control *am335x_get_phy_control(struct device *dev); | ||
20 | |||
21 | #endif | ||
diff --git a/drivers/usb/phy/phy-am335x-control.c b/drivers/usb/phy/phy-am335x-control.c new file mode 100644 index 000000000000..759754521426 --- /dev/null +++ b/drivers/usb/phy/phy-am335x-control.c | |||
@@ -0,0 +1,137 @@ | |||
1 | #include <linux/module.h> | ||
2 | #include <linux/platform_device.h> | ||
3 | #include <linux/err.h> | ||
4 | #include <linux/of.h> | ||
5 | #include <linux/io.h> | ||
6 | |||
7 | struct phy_control { | ||
8 | void (*phy_power)(struct phy_control *phy_ctrl, u32 id, bool on); | ||
9 | void (*phy_wkup)(struct phy_control *phy_ctrl, u32 id, bool on); | ||
10 | }; | ||
11 | |||
12 | struct am335x_control_usb { | ||
13 | struct device *dev; | ||
14 | void __iomem *phy_reg; | ||
15 | void __iomem *wkup; | ||
16 | spinlock_t lock; | ||
17 | struct phy_control phy_ctrl; | ||
18 | }; | ||
19 | |||
20 | #define AM335X_USB0_CTRL 0x0 | ||
21 | #define AM335X_USB1_CTRL 0x8 | ||
22 | #define AM335x_USB_WKUP 0x0 | ||
23 | |||
24 | #define USBPHY_CM_PWRDN (1 << 0) | ||
25 | #define USBPHY_OTG_PWRDN (1 << 1) | ||
26 | #define USBPHY_OTGVDET_EN (1 << 19) | ||
27 | #define USBPHY_OTGSESSEND_EN (1 << 20) | ||
28 | |||
29 | static void am335x_phy_power(struct phy_control *phy_ctrl, u32 id, bool on) | ||
30 | { | ||
31 | struct am335x_control_usb *usb_ctrl; | ||
32 | u32 val; | ||
33 | u32 reg; | ||
34 | |||
35 | usb_ctrl = container_of(phy_ctrl, struct am335x_control_usb, phy_ctrl); | ||
36 | |||
37 | switch (id) { | ||
38 | case 0: | ||
39 | reg = AM335X_USB0_CTRL; | ||
40 | break; | ||
41 | case 1: | ||
42 | reg = AM335X_USB1_CTRL; | ||
43 | break; | ||
44 | default: | ||
45 | __WARN(); | ||
46 | return; | ||
47 | } | ||
48 | |||
49 | val = readl(usb_ctrl->phy_reg + reg); | ||
50 | if (on) { | ||
51 | val &= ~(USBPHY_CM_PWRDN | USBPHY_OTG_PWRDN); | ||
52 | val |= USBPHY_OTGVDET_EN | USBPHY_OTGSESSEND_EN; | ||
53 | } else { | ||
54 | val |= USBPHY_CM_PWRDN | USBPHY_OTG_PWRDN; | ||
55 | } | ||
56 | |||
57 | writel(val, usb_ctrl->phy_reg + reg); | ||
58 | } | ||
59 | |||
60 | static const struct phy_control ctrl_am335x = { | ||
61 | .phy_power = am335x_phy_power, | ||
62 | }; | ||
63 | |||
64 | static const struct of_device_id omap_control_usb_id_table[] = { | ||
65 | { .compatible = "ti,am335x-usb-ctrl-module", .data = &ctrl_am335x }, | ||
66 | {} | ||
67 | }; | ||
68 | MODULE_DEVICE_TABLE(of, omap_control_usb_id_table); | ||
69 | |||
70 | static struct platform_driver am335x_control_driver; | ||
71 | static int match(struct device *dev, void *data) | ||
72 | { | ||
73 | struct device_node *node = (struct device_node *)data; | ||
74 | return dev->of_node == node && | ||
75 | dev->driver == &am335x_control_driver.driver; | ||
76 | } | ||
77 | |||
78 | struct phy_control *am335x_get_phy_control(struct device *dev) | ||
79 | { | ||
80 | struct device_node *node; | ||
81 | struct am335x_control_usb *ctrl_usb; | ||
82 | |||
83 | node = of_parse_phandle(dev->of_node, "ti,ctrl_mod", 0); | ||
84 | if (!node) | ||
85 | return NULL; | ||
86 | |||
87 | dev = bus_find_device(&platform_bus_type, NULL, node, match); | ||
88 | ctrl_usb = dev_get_drvdata(dev); | ||
89 | if (!ctrl_usb) | ||
90 | return NULL; | ||
91 | return &ctrl_usb->phy_ctrl; | ||
92 | } | ||
93 | EXPORT_SYMBOL_GPL(am335x_get_phy_control); | ||
94 | |||
95 | static int am335x_control_usb_probe(struct platform_device *pdev) | ||
96 | { | ||
97 | struct resource *res; | ||
98 | struct am335x_control_usb *ctrl_usb; | ||
99 | const struct of_device_id *of_id; | ||
100 | const struct phy_control *phy_ctrl; | ||
101 | |||
102 | of_id = of_match_node(omap_control_usb_id_table, pdev->dev.of_node); | ||
103 | if (!of_id) | ||
104 | return -EINVAL; | ||
105 | |||
106 | phy_ctrl = of_id->data; | ||
107 | |||
108 | ctrl_usb = devm_kzalloc(&pdev->dev, sizeof(*ctrl_usb), GFP_KERNEL); | ||
109 | if (!ctrl_usb) { | ||
110 | dev_err(&pdev->dev, "unable to alloc memory for control usb\n"); | ||
111 | return -ENOMEM; | ||
112 | } | ||
113 | |||
114 | ctrl_usb->dev = &pdev->dev; | ||
115 | |||
116 | res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "phy_ctrl"); | ||
117 | ctrl_usb->phy_reg = devm_ioremap_resource(&pdev->dev, res); | ||
118 | if (IS_ERR(ctrl_usb->phy_reg)) | ||
119 | return PTR_ERR(ctrl_usb->phy_reg); | ||
120 | spin_lock_init(&ctrl_usb->lock); | ||
121 | ctrl_usb->phy_ctrl = *phy_ctrl; | ||
122 | |||
123 | dev_set_drvdata(ctrl_usb->dev, ctrl_usb); | ||
124 | return 0; | ||
125 | } | ||
126 | |||
127 | static struct platform_driver am335x_control_driver = { | ||
128 | .probe = am335x_control_usb_probe, | ||
129 | .driver = { | ||
130 | .name = "am335x-control-usb", | ||
131 | .owner = THIS_MODULE, | ||
132 | .of_match_table = of_match_ptr(omap_control_usb_id_table), | ||
133 | }, | ||
134 | }; | ||
135 | |||
136 | module_platform_driver(am335x_control_driver); | ||
137 | MODULE_LICENSE("GPL v2"); | ||
diff --git a/drivers/usb/phy/phy-am335x.c b/drivers/usb/phy/phy-am335x.c new file mode 100644 index 000000000000..c4d614d1f173 --- /dev/null +++ b/drivers/usb/phy/phy-am335x.c | |||
@@ -0,0 +1,99 @@ | |||
1 | #include <linux/module.h> | ||
2 | #include <linux/platform_device.h> | ||
3 | #include <linux/dma-mapping.h> | ||
4 | #include <linux/usb/otg.h> | ||
5 | #include <linux/usb/usb_phy_gen_xceiv.h> | ||
6 | #include <linux/slab.h> | ||
7 | #include <linux/clk.h> | ||
8 | #include <linux/regulator/consumer.h> | ||
9 | #include <linux/of.h> | ||
10 | #include <linux/of_address.h> | ||
11 | |||
12 | #include "am35x-phy-control.h" | ||
13 | #include "phy-generic.h" | ||
14 | |||
15 | struct am335x_phy { | ||
16 | struct usb_phy_gen_xceiv usb_phy_gen; | ||
17 | struct phy_control *phy_ctrl; | ||
18 | int id; | ||
19 | }; | ||
20 | |||
21 | static int am335x_init(struct usb_phy *phy) | ||
22 | { | ||
23 | struct am335x_phy *am_phy = dev_get_drvdata(phy->dev); | ||
24 | |||
25 | phy_ctrl_power(am_phy->phy_ctrl, am_phy->id, true); | ||
26 | return 0; | ||
27 | } | ||
28 | |||
29 | static void am335x_shutdown(struct usb_phy *phy) | ||
30 | { | ||
31 | struct am335x_phy *am_phy = dev_get_drvdata(phy->dev); | ||
32 | |||
33 | phy_ctrl_power(am_phy->phy_ctrl, am_phy->id, false); | ||
34 | } | ||
35 | |||
36 | static int am335x_phy_probe(struct platform_device *pdev) | ||
37 | { | ||
38 | struct am335x_phy *am_phy; | ||
39 | struct device *dev = &pdev->dev; | ||
40 | int ret; | ||
41 | |||
42 | am_phy = devm_kzalloc(dev, sizeof(*am_phy), GFP_KERNEL); | ||
43 | if (!am_phy) | ||
44 | return -ENOMEM; | ||
45 | |||
46 | am_phy->phy_ctrl = am335x_get_phy_control(dev); | ||
47 | if (!am_phy->phy_ctrl) | ||
48 | return -EPROBE_DEFER; | ||
49 | am_phy->id = of_alias_get_id(pdev->dev.of_node, "phy"); | ||
50 | if (am_phy->id < 0) { | ||
51 | dev_err(&pdev->dev, "Missing PHY id: %d\n", am_phy->id); | ||
52 | return am_phy->id; | ||
53 | } | ||
54 | |||
55 | ret = usb_phy_gen_create_phy(dev, &am_phy->usb_phy_gen, | ||
56 | USB_PHY_TYPE_USB2, 0, false, false); | ||
57 | if (ret) | ||
58 | return ret; | ||
59 | |||
60 | ret = usb_add_phy_dev(&am_phy->usb_phy_gen.phy); | ||
61 | if (ret) | ||
62 | goto err_add; | ||
63 | am_phy->usb_phy_gen.phy.init = am335x_init; | ||
64 | am_phy->usb_phy_gen.phy.shutdown = am335x_shutdown; | ||
65 | |||
66 | platform_set_drvdata(pdev, am_phy); | ||
67 | return 0; | ||
68 | |||
69 | err_add: | ||
70 | usb_phy_gen_cleanup_phy(&am_phy->usb_phy_gen); | ||
71 | return ret; | ||
72 | } | ||
73 | |||
74 | static int am335x_phy_remove(struct platform_device *pdev) | ||
75 | { | ||
76 | struct am335x_phy *am_phy = platform_get_drvdata(pdev); | ||
77 | |||
78 | usb_remove_phy(&am_phy->usb_phy_gen.phy); | ||
79 | return 0; | ||
80 | } | ||
81 | |||
82 | static const struct of_device_id am335x_phy_ids[] = { | ||
83 | { .compatible = "ti,am335x-usb-phy" }, | ||
84 | { } | ||
85 | }; | ||
86 | MODULE_DEVICE_TABLE(of, am335x_phy_ids); | ||
87 | |||
88 | static struct platform_driver am335x_phy_driver = { | ||
89 | .probe = am335x_phy_probe, | ||
90 | .remove = am335x_phy_remove, | ||
91 | .driver = { | ||
92 | .name = "am335x-phy-driver", | ||
93 | .owner = THIS_MODULE, | ||
94 | .of_match_table = of_match_ptr(am335x_phy_ids), | ||
95 | }, | ||
96 | }; | ||
97 | |||
98 | module_platform_driver(am335x_phy_driver); | ||
99 | MODULE_LICENSE("GPL v2"); | ||
diff --git a/drivers/usb/phy/phy-fsl-usb.c b/drivers/usb/phy/phy-fsl-usb.c index e771bafb9f1d..fa7c9f9628b5 100644 --- a/drivers/usb/phy/phy-fsl-usb.c +++ b/drivers/usb/phy/phy-fsl-usb.c | |||
@@ -611,7 +611,7 @@ static int fsl_otg_set_peripheral(struct usb_otg *otg, | |||
611 | otg_dev->fsm.b_bus_req = 1; | 611 | otg_dev->fsm.b_bus_req = 1; |
612 | 612 | ||
613 | /* start the gadget right away if the ID pin says Mini-B */ | 613 | /* start the gadget right away if the ID pin says Mini-B */ |
614 | DBG("ID pin=%d\n", otg_dev->fsm.id); | 614 | pr_debug("ID pin=%d\n", otg_dev->fsm.id); |
615 | if (otg_dev->fsm.id == 1) { | 615 | if (otg_dev->fsm.id == 1) { |
616 | fsl_otg_start_host(&otg_dev->fsm, 0); | 616 | fsl_otg_start_host(&otg_dev->fsm, 0); |
617 | otg_drv_vbus(&otg_dev->fsm, 0); | 617 | otg_drv_vbus(&otg_dev->fsm, 0); |
@@ -684,7 +684,7 @@ static int fsl_otg_start_hnp(struct usb_otg *otg) | |||
684 | if (otg_dev != fsl_otg_dev) | 684 | if (otg_dev != fsl_otg_dev) |
685 | return -ENODEV; | 685 | return -ENODEV; |
686 | 686 | ||
687 | DBG("start_hnp...n"); | 687 | pr_debug("start_hnp...\n"); |
688 | 688 | ||
689 | /* clear a_bus_req to enter a_suspend state */ | 689 | /* clear a_bus_req to enter a_suspend state */ |
690 | otg_dev->fsm.a_bus_req = 0; | 690 | otg_dev->fsm.a_bus_req = 0; |
@@ -834,7 +834,7 @@ int usb_otg_start(struct platform_device *pdev) | |||
834 | int status; | 834 | int status; |
835 | struct resource *res; | 835 | struct resource *res; |
836 | u32 temp; | 836 | u32 temp; |
837 | struct fsl_usb2_platform_data *pdata = pdev->dev.platform_data; | 837 | struct fsl_usb2_platform_data *pdata = dev_get_platdata(&pdev->dev); |
838 | 838 | ||
839 | p_otg = container_of(otg_trans, struct fsl_otg, phy); | 839 | p_otg = container_of(otg_trans, struct fsl_otg, phy); |
840 | fsm = &p_otg->fsm; | 840 | fsm = &p_otg->fsm; |
@@ -941,7 +941,7 @@ int usb_otg_start(struct platform_device *pdev) | |||
941 | p_otg->fsm.id = 0; | 941 | p_otg->fsm.id = 0; |
942 | } | 942 | } |
943 | 943 | ||
944 | DBG("initial ID pin=%d\n", p_otg->fsm.id); | 944 | pr_debug("initial ID pin=%d\n", p_otg->fsm.id); |
945 | 945 | ||
946 | /* enable OTG ID pin interrupt */ | 946 | /* enable OTG ID pin interrupt */ |
947 | temp = fsl_readl(&p_otg->dr_mem_map->otgsc); | 947 | temp = fsl_readl(&p_otg->dr_mem_map->otgsc); |
@@ -1105,7 +1105,7 @@ static int fsl_otg_probe(struct platform_device *pdev) | |||
1105 | { | 1105 | { |
1106 | int ret; | 1106 | int ret; |
1107 | 1107 | ||
1108 | if (!pdev->dev.platform_data) | 1108 | if (!dev_get_platdata(&pdev->dev)) |
1109 | return -ENODEV; | 1109 | return -ENODEV; |
1110 | 1110 | ||
1111 | /* configure the OTG */ | 1111 | /* configure the OTG */ |
@@ -1137,7 +1137,7 @@ static int fsl_otg_probe(struct platform_device *pdev) | |||
1137 | 1137 | ||
1138 | static int fsl_otg_remove(struct platform_device *pdev) | 1138 | static int fsl_otg_remove(struct platform_device *pdev) |
1139 | { | 1139 | { |
1140 | struct fsl_usb2_platform_data *pdata = pdev->dev.platform_data; | 1140 | struct fsl_usb2_platform_data *pdata = dev_get_platdata(&pdev->dev); |
1141 | 1141 | ||
1142 | usb_remove_phy(&fsl_otg_dev->phy); | 1142 | usb_remove_phy(&fsl_otg_dev->phy); |
1143 | free_irq(fsl_otg_dev->irq, fsl_otg_dev); | 1143 | free_irq(fsl_otg_dev->irq, fsl_otg_dev); |
diff --git a/drivers/usb/phy/phy-fsm-usb.h b/drivers/usb/phy/phy-fsm-usb.h index c30a2e1d9e46..fbe586206f33 100644 --- a/drivers/usb/phy/phy-fsm-usb.h +++ b/drivers/usb/phy/phy-fsm-usb.h | |||
@@ -15,18 +15,11 @@ | |||
15 | * 675 Mass Ave, Cambridge, MA 02139, USA. | 15 | * 675 Mass Ave, Cambridge, MA 02139, USA. |
16 | */ | 16 | */ |
17 | 17 | ||
18 | #undef DEBUG | ||
19 | #undef VERBOSE | 18 | #undef VERBOSE |
20 | 19 | ||
21 | #ifdef DEBUG | ||
22 | #define DBG(fmt, args...) printk(KERN_DEBUG "[%s] " fmt , \ | ||
23 | __func__, ## args) | ||
24 | #else | ||
25 | #define DBG(fmt, args...) do {} while (0) | ||
26 | #endif | ||
27 | |||
28 | #ifdef VERBOSE | 20 | #ifdef VERBOSE |
29 | #define VDBG DBG | 21 | #define VDBG(fmt, args...) pr_debug("[%s] " fmt , \ |
22 | __func__, ## args) | ||
30 | #else | 23 | #else |
31 | #define VDBG(stuff...) do {} while (0) | 24 | #define VDBG(stuff...) do {} while (0) |
32 | #endif | 25 | #endif |
diff --git a/drivers/usb/phy/phy-nop.c b/drivers/usb/phy/phy-generic.c index 55445e5d72e5..efe59f3f7fda 100644 --- a/drivers/usb/phy/phy-nop.c +++ b/drivers/usb/phy/phy-generic.c | |||
@@ -30,19 +30,13 @@ | |||
30 | #include <linux/platform_device.h> | 30 | #include <linux/platform_device.h> |
31 | #include <linux/dma-mapping.h> | 31 | #include <linux/dma-mapping.h> |
32 | #include <linux/usb/otg.h> | 32 | #include <linux/usb/otg.h> |
33 | #include <linux/usb/nop-usb-xceiv.h> | 33 | #include <linux/usb/usb_phy_gen_xceiv.h> |
34 | #include <linux/slab.h> | 34 | #include <linux/slab.h> |
35 | #include <linux/clk.h> | 35 | #include <linux/clk.h> |
36 | #include <linux/regulator/consumer.h> | 36 | #include <linux/regulator/consumer.h> |
37 | #include <linux/of.h> | 37 | #include <linux/of.h> |
38 | 38 | ||
39 | struct nop_usb_xceiv { | 39 | #include "phy-generic.h" |
40 | struct usb_phy phy; | ||
41 | struct device *dev; | ||
42 | struct clk *clk; | ||
43 | struct regulator *vcc; | ||
44 | struct regulator *reset; | ||
45 | }; | ||
46 | 40 | ||
47 | static struct platform_device *pd; | 41 | static struct platform_device *pd; |
48 | 42 | ||
@@ -50,9 +44,9 @@ void usb_nop_xceiv_register(void) | |||
50 | { | 44 | { |
51 | if (pd) | 45 | if (pd) |
52 | return; | 46 | return; |
53 | pd = platform_device_register_simple("nop_usb_xceiv", -1, NULL, 0); | 47 | pd = platform_device_register_simple("usb_phy_gen_xceiv", -1, NULL, 0); |
54 | if (!pd) { | 48 | if (!pd) { |
55 | printk(KERN_ERR "Unable to register usb nop transceiver\n"); | 49 | pr_err("Unable to register generic usb transceiver\n"); |
56 | return; | 50 | return; |
57 | } | 51 | } |
58 | } | 52 | } |
@@ -70,9 +64,9 @@ static int nop_set_suspend(struct usb_phy *x, int suspend) | |||
70 | return 0; | 64 | return 0; |
71 | } | 65 | } |
72 | 66 | ||
73 | static int nop_init(struct usb_phy *phy) | 67 | int usb_gen_phy_init(struct usb_phy *phy) |
74 | { | 68 | { |
75 | struct nop_usb_xceiv *nop = dev_get_drvdata(phy->dev); | 69 | struct usb_phy_gen_xceiv *nop = dev_get_drvdata(phy->dev); |
76 | 70 | ||
77 | if (!IS_ERR(nop->vcc)) { | 71 | if (!IS_ERR(nop->vcc)) { |
78 | if (regulator_enable(nop->vcc)) | 72 | if (regulator_enable(nop->vcc)) |
@@ -90,10 +84,11 @@ static int nop_init(struct usb_phy *phy) | |||
90 | 84 | ||
91 | return 0; | 85 | return 0; |
92 | } | 86 | } |
87 | EXPORT_SYMBOL_GPL(usb_gen_phy_init); | ||
93 | 88 | ||
94 | static void nop_shutdown(struct usb_phy *phy) | 89 | void usb_gen_phy_shutdown(struct usb_phy *phy) |
95 | { | 90 | { |
96 | struct nop_usb_xceiv *nop = dev_get_drvdata(phy->dev); | 91 | struct usb_phy_gen_xceiv *nop = dev_get_drvdata(phy->dev); |
97 | 92 | ||
98 | if (!IS_ERR(nop->reset)) { | 93 | if (!IS_ERR(nop->reset)) { |
99 | /* Assert RESET */ | 94 | /* Assert RESET */ |
@@ -109,6 +104,7 @@ static void nop_shutdown(struct usb_phy *phy) | |||
109 | dev_err(phy->dev, "Failed to disable power\n"); | 104 | dev_err(phy->dev, "Failed to disable power\n"); |
110 | } | 105 | } |
111 | } | 106 | } |
107 | EXPORT_SYMBOL_GPL(usb_gen_phy_shutdown); | ||
112 | 108 | ||
113 | static int nop_set_peripheral(struct usb_otg *otg, struct usb_gadget *gadget) | 109 | static int nop_set_peripheral(struct usb_otg *otg, struct usb_gadget *gadget) |
114 | { | 110 | { |
@@ -139,52 +135,27 @@ static int nop_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
139 | return 0; | 135 | return 0; |
140 | } | 136 | } |
141 | 137 | ||
142 | static int nop_usb_xceiv_probe(struct platform_device *pdev) | 138 | int usb_phy_gen_create_phy(struct device *dev, struct usb_phy_gen_xceiv *nop, |
139 | enum usb_phy_type type, u32 clk_rate, bool needs_vcc, | ||
140 | bool needs_reset) | ||
143 | { | 141 | { |
144 | struct device *dev = &pdev->dev; | ||
145 | struct nop_usb_xceiv_platform_data *pdata = pdev->dev.platform_data; | ||
146 | struct nop_usb_xceiv *nop; | ||
147 | enum usb_phy_type type = USB_PHY_TYPE_USB2; | ||
148 | int err; | 142 | int err; |
149 | u32 clk_rate = 0; | ||
150 | bool needs_vcc = false; | ||
151 | bool needs_reset = false; | ||
152 | |||
153 | nop = devm_kzalloc(&pdev->dev, sizeof(*nop), GFP_KERNEL); | ||
154 | if (!nop) | ||
155 | return -ENOMEM; | ||
156 | 143 | ||
157 | nop->phy.otg = devm_kzalloc(&pdev->dev, sizeof(*nop->phy.otg), | 144 | nop->phy.otg = devm_kzalloc(dev, sizeof(*nop->phy.otg), |
158 | GFP_KERNEL); | 145 | GFP_KERNEL); |
159 | if (!nop->phy.otg) | 146 | if (!nop->phy.otg) |
160 | return -ENOMEM; | 147 | return -ENOMEM; |
161 | 148 | ||
162 | if (dev->of_node) { | 149 | nop->clk = devm_clk_get(dev, "main_clk"); |
163 | struct device_node *node = dev->of_node; | ||
164 | |||
165 | if (of_property_read_u32(node, "clock-frequency", &clk_rate)) | ||
166 | clk_rate = 0; | ||
167 | |||
168 | needs_vcc = of_property_read_bool(node, "vcc-supply"); | ||
169 | needs_reset = of_property_read_bool(node, "reset-supply"); | ||
170 | |||
171 | } else if (pdata) { | ||
172 | type = pdata->type; | ||
173 | clk_rate = pdata->clk_rate; | ||
174 | needs_vcc = pdata->needs_vcc; | ||
175 | needs_reset = pdata->needs_reset; | ||
176 | } | ||
177 | |||
178 | nop->clk = devm_clk_get(&pdev->dev, "main_clk"); | ||
179 | if (IS_ERR(nop->clk)) { | 150 | if (IS_ERR(nop->clk)) { |
180 | dev_dbg(&pdev->dev, "Can't get phy clock: %ld\n", | 151 | dev_dbg(dev, "Can't get phy clock: %ld\n", |
181 | PTR_ERR(nop->clk)); | 152 | PTR_ERR(nop->clk)); |
182 | } | 153 | } |
183 | 154 | ||
184 | if (!IS_ERR(nop->clk) && clk_rate) { | 155 | if (!IS_ERR(nop->clk) && clk_rate) { |
185 | err = clk_set_rate(nop->clk, clk_rate); | 156 | err = clk_set_rate(nop->clk, clk_rate); |
186 | if (err) { | 157 | if (err) { |
187 | dev_err(&pdev->dev, "Error setting clock rate\n"); | 158 | dev_err(dev, "Error setting clock rate\n"); |
188 | return err; | 159 | return err; |
189 | } | 160 | } |
190 | } | 161 | } |
@@ -192,33 +163,31 @@ static int nop_usb_xceiv_probe(struct platform_device *pdev) | |||
192 | if (!IS_ERR(nop->clk)) { | 163 | if (!IS_ERR(nop->clk)) { |
193 | err = clk_prepare(nop->clk); | 164 | err = clk_prepare(nop->clk); |
194 | if (err) { | 165 | if (err) { |
195 | dev_err(&pdev->dev, "Error preparing clock\n"); | 166 | dev_err(dev, "Error preparing clock\n"); |
196 | return err; | 167 | return err; |
197 | } | 168 | } |
198 | } | 169 | } |
199 | 170 | ||
200 | nop->vcc = devm_regulator_get(&pdev->dev, "vcc"); | 171 | nop->vcc = devm_regulator_get(dev, "vcc"); |
201 | if (IS_ERR(nop->vcc)) { | 172 | if (IS_ERR(nop->vcc)) { |
202 | dev_dbg(&pdev->dev, "Error getting vcc regulator: %ld\n", | 173 | dev_dbg(dev, "Error getting vcc regulator: %ld\n", |
203 | PTR_ERR(nop->vcc)); | 174 | PTR_ERR(nop->vcc)); |
204 | if (needs_vcc) | 175 | if (needs_vcc) |
205 | return -EPROBE_DEFER; | 176 | return -EPROBE_DEFER; |
206 | } | 177 | } |
207 | 178 | ||
208 | nop->reset = devm_regulator_get(&pdev->dev, "reset"); | 179 | nop->reset = devm_regulator_get(dev, "reset"); |
209 | if (IS_ERR(nop->reset)) { | 180 | if (IS_ERR(nop->reset)) { |
210 | dev_dbg(&pdev->dev, "Error getting reset regulator: %ld\n", | 181 | dev_dbg(dev, "Error getting reset regulator: %ld\n", |
211 | PTR_ERR(nop->reset)); | 182 | PTR_ERR(nop->reset)); |
212 | if (needs_reset) | 183 | if (needs_reset) |
213 | return -EPROBE_DEFER; | 184 | return -EPROBE_DEFER; |
214 | } | 185 | } |
215 | 186 | ||
216 | nop->dev = &pdev->dev; | 187 | nop->dev = dev; |
217 | nop->phy.dev = nop->dev; | 188 | nop->phy.dev = nop->dev; |
218 | nop->phy.label = "nop-xceiv"; | 189 | nop->phy.label = "nop-xceiv"; |
219 | nop->phy.set_suspend = nop_set_suspend; | 190 | nop->phy.set_suspend = nop_set_suspend; |
220 | nop->phy.init = nop_init; | ||
221 | nop->phy.shutdown = nop_shutdown; | ||
222 | nop->phy.state = OTG_STATE_UNDEFINED; | 191 | nop->phy.state = OTG_STATE_UNDEFINED; |
223 | nop->phy.type = type; | 192 | nop->phy.type = type; |
224 | 193 | ||
@@ -226,6 +195,59 @@ static int nop_usb_xceiv_probe(struct platform_device *pdev) | |||
226 | nop->phy.otg->set_host = nop_set_host; | 195 | nop->phy.otg->set_host = nop_set_host; |
227 | nop->phy.otg->set_peripheral = nop_set_peripheral; | 196 | nop->phy.otg->set_peripheral = nop_set_peripheral; |
228 | 197 | ||
198 | ATOMIC_INIT_NOTIFIER_HEAD(&nop->phy.notifier); | ||
199 | return 0; | ||
200 | } | ||
201 | EXPORT_SYMBOL_GPL(usb_phy_gen_create_phy); | ||
202 | |||
203 | void usb_phy_gen_cleanup_phy(struct usb_phy_gen_xceiv *nop) | ||
204 | { | ||
205 | if (!IS_ERR(nop->clk)) | ||
206 | clk_unprepare(nop->clk); | ||
207 | } | ||
208 | EXPORT_SYMBOL_GPL(usb_phy_gen_cleanup_phy); | ||
209 | |||
210 | static int usb_phy_gen_xceiv_probe(struct platform_device *pdev) | ||
211 | { | ||
212 | struct device *dev = &pdev->dev; | ||
213 | struct usb_phy_gen_xceiv_platform_data *pdata = | ||
214 | dev_get_platdata(&pdev->dev); | ||
215 | struct usb_phy_gen_xceiv *nop; | ||
216 | enum usb_phy_type type = USB_PHY_TYPE_USB2; | ||
217 | int err; | ||
218 | u32 clk_rate = 0; | ||
219 | bool needs_vcc = false; | ||
220 | bool needs_reset = false; | ||
221 | |||
222 | if (dev->of_node) { | ||
223 | struct device_node *node = dev->of_node; | ||
224 | |||
225 | if (of_property_read_u32(node, "clock-frequency", &clk_rate)) | ||
226 | clk_rate = 0; | ||
227 | |||
228 | needs_vcc = of_property_read_bool(node, "vcc-supply"); | ||
229 | needs_reset = of_property_read_bool(node, "reset-supply"); | ||
230 | |||
231 | } else if (pdata) { | ||
232 | type = pdata->type; | ||
233 | clk_rate = pdata->clk_rate; | ||
234 | needs_vcc = pdata->needs_vcc; | ||
235 | needs_reset = pdata->needs_reset; | ||
236 | } | ||
237 | |||
238 | nop = devm_kzalloc(dev, sizeof(*nop), GFP_KERNEL); | ||
239 | if (!nop) | ||
240 | return -ENOMEM; | ||
241 | |||
242 | |||
243 | err = usb_phy_gen_create_phy(dev, nop, type, clk_rate, needs_vcc, | ||
244 | needs_reset); | ||
245 | if (err) | ||
246 | return err; | ||
247 | |||
248 | nop->phy.init = usb_gen_phy_init; | ||
249 | nop->phy.shutdown = usb_gen_phy_shutdown; | ||
250 | |||
229 | err = usb_add_phy_dev(&nop->phy); | 251 | err = usb_add_phy_dev(&nop->phy); |
230 | if (err) { | 252 | if (err) { |
231 | dev_err(&pdev->dev, "can't register transceiver, err: %d\n", | 253 | dev_err(&pdev->dev, "can't register transceiver, err: %d\n", |
@@ -235,23 +257,18 @@ static int nop_usb_xceiv_probe(struct platform_device *pdev) | |||
235 | 257 | ||
236 | platform_set_drvdata(pdev, nop); | 258 | platform_set_drvdata(pdev, nop); |
237 | 259 | ||
238 | ATOMIC_INIT_NOTIFIER_HEAD(&nop->phy.notifier); | ||
239 | |||
240 | return 0; | 260 | return 0; |
241 | 261 | ||
242 | err_add: | 262 | err_add: |
243 | if (!IS_ERR(nop->clk)) | 263 | usb_phy_gen_cleanup_phy(nop); |
244 | clk_unprepare(nop->clk); | ||
245 | return err; | 264 | return err; |
246 | } | 265 | } |
247 | 266 | ||
248 | static int nop_usb_xceiv_remove(struct platform_device *pdev) | 267 | static int usb_phy_gen_xceiv_remove(struct platform_device *pdev) |
249 | { | 268 | { |
250 | struct nop_usb_xceiv *nop = platform_get_drvdata(pdev); | 269 | struct usb_phy_gen_xceiv *nop = platform_get_drvdata(pdev); |
251 | |||
252 | if (!IS_ERR(nop->clk)) | ||
253 | clk_unprepare(nop->clk); | ||
254 | 270 | ||
271 | usb_phy_gen_cleanup_phy(nop); | ||
255 | usb_remove_phy(&nop->phy); | 272 | usb_remove_phy(&nop->phy); |
256 | 273 | ||
257 | return 0; | 274 | return 0; |
@@ -264,29 +281,29 @@ static const struct of_device_id nop_xceiv_dt_ids[] = { | |||
264 | 281 | ||
265 | MODULE_DEVICE_TABLE(of, nop_xceiv_dt_ids); | 282 | MODULE_DEVICE_TABLE(of, nop_xceiv_dt_ids); |
266 | 283 | ||
267 | static struct platform_driver nop_usb_xceiv_driver = { | 284 | static struct platform_driver usb_phy_gen_xceiv_driver = { |
268 | .probe = nop_usb_xceiv_probe, | 285 | .probe = usb_phy_gen_xceiv_probe, |
269 | .remove = nop_usb_xceiv_remove, | 286 | .remove = usb_phy_gen_xceiv_remove, |
270 | .driver = { | 287 | .driver = { |
271 | .name = "nop_usb_xceiv", | 288 | .name = "usb_phy_gen_xceiv", |
272 | .owner = THIS_MODULE, | 289 | .owner = THIS_MODULE, |
273 | .of_match_table = nop_xceiv_dt_ids, | 290 | .of_match_table = nop_xceiv_dt_ids, |
274 | }, | 291 | }, |
275 | }; | 292 | }; |
276 | 293 | ||
277 | static int __init nop_usb_xceiv_init(void) | 294 | static int __init usb_phy_gen_xceiv_init(void) |
278 | { | 295 | { |
279 | return platform_driver_register(&nop_usb_xceiv_driver); | 296 | return platform_driver_register(&usb_phy_gen_xceiv_driver); |
280 | } | 297 | } |
281 | subsys_initcall(nop_usb_xceiv_init); | 298 | subsys_initcall(usb_phy_gen_xceiv_init); |
282 | 299 | ||
283 | static void __exit nop_usb_xceiv_exit(void) | 300 | static void __exit usb_phy_gen_xceiv_exit(void) |
284 | { | 301 | { |
285 | platform_driver_unregister(&nop_usb_xceiv_driver); | 302 | platform_driver_unregister(&usb_phy_gen_xceiv_driver); |
286 | } | 303 | } |
287 | module_exit(nop_usb_xceiv_exit); | 304 | module_exit(usb_phy_gen_xceiv_exit); |
288 | 305 | ||
289 | MODULE_ALIAS("platform:nop_usb_xceiv"); | 306 | MODULE_ALIAS("platform:usb_phy_gen_xceiv"); |
290 | MODULE_AUTHOR("Texas Instruments Inc"); | 307 | MODULE_AUTHOR("Texas Instruments Inc"); |
291 | MODULE_DESCRIPTION("NOP USB Transceiver driver"); | 308 | MODULE_DESCRIPTION("NOP USB Transceiver driver"); |
292 | MODULE_LICENSE("GPL"); | 309 | MODULE_LICENSE("GPL"); |
diff --git a/drivers/usb/phy/phy-generic.h b/drivers/usb/phy/phy-generic.h new file mode 100644 index 000000000000..61687d5a965b --- /dev/null +++ b/drivers/usb/phy/phy-generic.h | |||
@@ -0,0 +1,20 @@ | |||
1 | #ifndef _PHY_GENERIC_H_ | ||
2 | #define _PHY_GENERIC_H_ | ||
3 | |||
4 | struct usb_phy_gen_xceiv { | ||
5 | struct usb_phy phy; | ||
6 | struct device *dev; | ||
7 | struct clk *clk; | ||
8 | struct regulator *vcc; | ||
9 | struct regulator *reset; | ||
10 | }; | ||
11 | |||
12 | int usb_gen_phy_init(struct usb_phy *phy); | ||
13 | void usb_gen_phy_shutdown(struct usb_phy *phy); | ||
14 | |||
15 | int usb_phy_gen_create_phy(struct device *dev, struct usb_phy_gen_xceiv *nop, | ||
16 | enum usb_phy_type type, u32 clk_rate, bool needs_vcc, | ||
17 | bool needs_reset); | ||
18 | void usb_phy_gen_cleanup_phy(struct usb_phy_gen_xceiv *nop); | ||
19 | |||
20 | #endif | ||
diff --git a/drivers/usb/phy/phy-gpio-vbus-usb.c b/drivers/usb/phy/phy-gpio-vbus-usb.c index 8443335c2ea0..b2f29c9aebbf 100644 --- a/drivers/usb/phy/phy-gpio-vbus-usb.c +++ b/drivers/usb/phy/phy-gpio-vbus-usb.c | |||
@@ -101,7 +101,7 @@ static void gpio_vbus_work(struct work_struct *work) | |||
101 | { | 101 | { |
102 | struct gpio_vbus_data *gpio_vbus = | 102 | struct gpio_vbus_data *gpio_vbus = |
103 | container_of(work, struct gpio_vbus_data, work.work); | 103 | container_of(work, struct gpio_vbus_data, work.work); |
104 | struct gpio_vbus_mach_info *pdata = gpio_vbus->dev->platform_data; | 104 | struct gpio_vbus_mach_info *pdata = dev_get_platdata(gpio_vbus->dev); |
105 | int gpio, status, vbus; | 105 | int gpio, status, vbus; |
106 | 106 | ||
107 | if (!gpio_vbus->phy.otg->gadget) | 107 | if (!gpio_vbus->phy.otg->gadget) |
@@ -155,7 +155,7 @@ static void gpio_vbus_work(struct work_struct *work) | |||
155 | static irqreturn_t gpio_vbus_irq(int irq, void *data) | 155 | static irqreturn_t gpio_vbus_irq(int irq, void *data) |
156 | { | 156 | { |
157 | struct platform_device *pdev = data; | 157 | struct platform_device *pdev = data; |
158 | struct gpio_vbus_mach_info *pdata = pdev->dev.platform_data; | 158 | struct gpio_vbus_mach_info *pdata = dev_get_platdata(&pdev->dev); |
159 | struct gpio_vbus_data *gpio_vbus = platform_get_drvdata(pdev); | 159 | struct gpio_vbus_data *gpio_vbus = platform_get_drvdata(pdev); |
160 | struct usb_otg *otg = gpio_vbus->phy.otg; | 160 | struct usb_otg *otg = gpio_vbus->phy.otg; |
161 | 161 | ||
@@ -182,7 +182,7 @@ static int gpio_vbus_set_peripheral(struct usb_otg *otg, | |||
182 | 182 | ||
183 | gpio_vbus = container_of(otg->phy, struct gpio_vbus_data, phy); | 183 | gpio_vbus = container_of(otg->phy, struct gpio_vbus_data, phy); |
184 | pdev = to_platform_device(gpio_vbus->dev); | 184 | pdev = to_platform_device(gpio_vbus->dev); |
185 | pdata = gpio_vbus->dev->platform_data; | 185 | pdata = dev_get_platdata(gpio_vbus->dev); |
186 | gpio = pdata->gpio_pullup; | 186 | gpio = pdata->gpio_pullup; |
187 | 187 | ||
188 | if (!gadget) { | 188 | if (!gadget) { |
@@ -243,7 +243,7 @@ static int gpio_vbus_set_suspend(struct usb_phy *phy, int suspend) | |||
243 | 243 | ||
244 | static int __init gpio_vbus_probe(struct platform_device *pdev) | 244 | static int __init gpio_vbus_probe(struct platform_device *pdev) |
245 | { | 245 | { |
246 | struct gpio_vbus_mach_info *pdata = pdev->dev.platform_data; | 246 | struct gpio_vbus_mach_info *pdata = dev_get_platdata(&pdev->dev); |
247 | struct gpio_vbus_data *gpio_vbus; | 247 | struct gpio_vbus_data *gpio_vbus; |
248 | struct resource *res; | 248 | struct resource *res; |
249 | int err, gpio, irq; | 249 | int err, gpio, irq; |
@@ -352,7 +352,7 @@ err_gpio: | |||
352 | static int __exit gpio_vbus_remove(struct platform_device *pdev) | 352 | static int __exit gpio_vbus_remove(struct platform_device *pdev) |
353 | { | 353 | { |
354 | struct gpio_vbus_data *gpio_vbus = platform_get_drvdata(pdev); | 354 | struct gpio_vbus_data *gpio_vbus = platform_get_drvdata(pdev); |
355 | struct gpio_vbus_mach_info *pdata = pdev->dev.platform_data; | 355 | struct gpio_vbus_mach_info *pdata = dev_get_platdata(&pdev->dev); |
356 | int gpio = pdata->gpio_vbus; | 356 | int gpio = pdata->gpio_vbus; |
357 | 357 | ||
358 | device_init_wakeup(&pdev->dev, 0); | 358 | device_init_wakeup(&pdev->dev, 0); |
diff --git a/drivers/usb/phy/phy-isp1301-omap.c b/drivers/usb/phy/phy-isp1301-omap.c index ae481afcb3ec..d3a5160e4cc7 100644 --- a/drivers/usb/phy/phy-isp1301-omap.c +++ b/drivers/usb/phy/phy-isp1301-omap.c | |||
@@ -40,9 +40,7 @@ | |||
40 | 40 | ||
41 | #include <mach/usb.h> | 41 | #include <mach/usb.h> |
42 | 42 | ||
43 | #ifndef DEBUG | 43 | #undef VERBOSE |
44 | #undef VERBOSE | ||
45 | #endif | ||
46 | 44 | ||
47 | 45 | ||
48 | #define DRIVER_VERSION "24 August 2004" | 46 | #define DRIVER_VERSION "24 August 2004" |
@@ -387,7 +385,6 @@ static void b_idle(struct isp1301 *isp, const char *tag) | |||
387 | static void | 385 | static void |
388 | dump_regs(struct isp1301 *isp, const char *label) | 386 | dump_regs(struct isp1301 *isp, const char *label) |
389 | { | 387 | { |
390 | #ifdef DEBUG | ||
391 | u8 ctrl = isp1301_get_u8(isp, ISP1301_OTG_CONTROL_1); | 388 | u8 ctrl = isp1301_get_u8(isp, ISP1301_OTG_CONTROL_1); |
392 | u8 status = isp1301_get_u8(isp, ISP1301_OTG_STATUS); | 389 | u8 status = isp1301_get_u8(isp, ISP1301_OTG_STATUS); |
393 | u8 src = isp1301_get_u8(isp, ISP1301_INTERRUPT_SOURCE); | 390 | u8 src = isp1301_get_u8(isp, ISP1301_INTERRUPT_SOURCE); |
@@ -396,7 +393,6 @@ dump_regs(struct isp1301 *isp, const char *label) | |||
396 | omap_readl(OTG_CTRL), label, state_name(isp), | 393 | omap_readl(OTG_CTRL), label, state_name(isp), |
397 | ctrl, status, src); | 394 | ctrl, status, src); |
398 | /* mode control and irq enables don't change much */ | 395 | /* mode control and irq enables don't change much */ |
399 | #endif | ||
400 | } | 396 | } |
401 | 397 | ||
402 | /*-------------------------------------------------------------------------*/ | 398 | /*-------------------------------------------------------------------------*/ |
diff --git a/drivers/usb/phy/phy-msm-usb.c b/drivers/usb/phy/phy-msm-usb.c index d08f33435e96..e9d4cd960ecd 100644 --- a/drivers/usb/phy/phy-msm-usb.c +++ b/drivers/usb/phy/phy-msm-usb.c | |||
@@ -1419,7 +1419,7 @@ static int __init msm_otg_probe(struct platform_device *pdev) | |||
1419 | struct usb_phy *phy; | 1419 | struct usb_phy *phy; |
1420 | 1420 | ||
1421 | dev_info(&pdev->dev, "msm_otg probe\n"); | 1421 | dev_info(&pdev->dev, "msm_otg probe\n"); |
1422 | if (!pdev->dev.platform_data) { | 1422 | if (!dev_get_platdata(&pdev->dev)) { |
1423 | dev_err(&pdev->dev, "No platform data given. Bailing out\n"); | 1423 | dev_err(&pdev->dev, "No platform data given. Bailing out\n"); |
1424 | return -ENODEV; | 1424 | return -ENODEV; |
1425 | } | 1425 | } |
@@ -1436,7 +1436,7 @@ static int __init msm_otg_probe(struct platform_device *pdev) | |||
1436 | return -ENOMEM; | 1436 | return -ENOMEM; |
1437 | } | 1437 | } |
1438 | 1438 | ||
1439 | motg->pdata = pdev->dev.platform_data; | 1439 | motg->pdata = dev_get_platdata(&pdev->dev); |
1440 | phy = &motg->phy; | 1440 | phy = &motg->phy; |
1441 | phy->dev = &pdev->dev; | 1441 | phy->dev = &pdev->dev; |
1442 | 1442 | ||
diff --git a/drivers/usb/phy/phy-mv-u3d-usb.c b/drivers/usb/phy/phy-mv-u3d-usb.c index 1568ea63e338..d317903022bf 100644 --- a/drivers/usb/phy/phy-mv-u3d-usb.c +++ b/drivers/usb/phy/phy-mv-u3d-usb.c | |||
@@ -82,7 +82,7 @@ static void mv_u3d_phy_write(void __iomem *base, u32 reg, u32 value) | |||
82 | writel_relaxed(value, data); | 82 | writel_relaxed(value, data); |
83 | } | 83 | } |
84 | 84 | ||
85 | void mv_u3d_phy_shutdown(struct usb_phy *phy) | 85 | static void mv_u3d_phy_shutdown(struct usb_phy *phy) |
86 | { | 86 | { |
87 | struct mv_u3d_phy *mv_u3d_phy; | 87 | struct mv_u3d_phy *mv_u3d_phy; |
88 | void __iomem *base; | 88 | void __iomem *base; |
@@ -271,7 +271,7 @@ static int mv_u3d_phy_probe(struct platform_device *pdev) | |||
271 | void __iomem *phy_base; | 271 | void __iomem *phy_base; |
272 | int ret; | 272 | int ret; |
273 | 273 | ||
274 | pdata = pdev->dev.platform_data; | 274 | pdata = dev_get_platdata(&pdev->dev); |
275 | if (!pdata) { | 275 | if (!pdata) { |
276 | dev_err(&pdev->dev, "%s: no platform data defined\n", __func__); | 276 | dev_err(&pdev->dev, "%s: no platform data defined\n", __func__); |
277 | return -EINVAL; | 277 | return -EINVAL; |
diff --git a/drivers/usb/phy/phy-mv-usb.c b/drivers/usb/phy/phy-mv-usb.c index 4a6b03c73876..98f6ac6a78ea 100644 --- a/drivers/usb/phy/phy-mv-usb.c +++ b/drivers/usb/phy/phy-mv-usb.c | |||
@@ -653,7 +653,7 @@ static struct attribute_group inputs_attr_group = { | |||
653 | .attrs = inputs_attrs, | 653 | .attrs = inputs_attrs, |
654 | }; | 654 | }; |
655 | 655 | ||
656 | int mv_otg_remove(struct platform_device *pdev) | 656 | static int mv_otg_remove(struct platform_device *pdev) |
657 | { | 657 | { |
658 | struct mv_otg *mvotg = platform_get_drvdata(pdev); | 658 | struct mv_otg *mvotg = platform_get_drvdata(pdev); |
659 | 659 | ||
@@ -673,7 +673,7 @@ int mv_otg_remove(struct platform_device *pdev) | |||
673 | 673 | ||
674 | static int mv_otg_probe(struct platform_device *pdev) | 674 | static int mv_otg_probe(struct platform_device *pdev) |
675 | { | 675 | { |
676 | struct mv_usb_platform_data *pdata = pdev->dev.platform_data; | 676 | struct mv_usb_platform_data *pdata = dev_get_platdata(&pdev->dev); |
677 | struct mv_otg *mvotg; | 677 | struct mv_otg *mvotg; |
678 | struct usb_otg *otg; | 678 | struct usb_otg *otg; |
679 | struct resource *r; | 679 | struct resource *r; |
@@ -893,7 +893,7 @@ static int mv_otg_resume(struct platform_device *pdev) | |||
893 | 893 | ||
894 | static struct platform_driver mv_otg_driver = { | 894 | static struct platform_driver mv_otg_driver = { |
895 | .probe = mv_otg_probe, | 895 | .probe = mv_otg_probe, |
896 | .remove = __exit_p(mv_otg_remove), | 896 | .remove = mv_otg_remove, |
897 | .driver = { | 897 | .driver = { |
898 | .owner = THIS_MODULE, | 898 | .owner = THIS_MODULE, |
899 | .name = driver_name, | 899 | .name = driver_name, |
diff --git a/drivers/usb/phy/phy-mxs-usb.c b/drivers/usb/phy/phy-mxs-usb.c index bd601c537c8d..fdd33b44dbd3 100644 --- a/drivers/usb/phy/phy-mxs-usb.c +++ b/drivers/usb/phy/phy-mxs-usb.c | |||
@@ -41,11 +41,14 @@ struct mxs_phy { | |||
41 | 41 | ||
42 | #define to_mxs_phy(p) container_of((p), struct mxs_phy, phy) | 42 | #define to_mxs_phy(p) container_of((p), struct mxs_phy, phy) |
43 | 43 | ||
44 | static void mxs_phy_hw_init(struct mxs_phy *mxs_phy) | 44 | static int mxs_phy_hw_init(struct mxs_phy *mxs_phy) |
45 | { | 45 | { |
46 | int ret; | ||
46 | void __iomem *base = mxs_phy->phy.io_priv; | 47 | void __iomem *base = mxs_phy->phy.io_priv; |
47 | 48 | ||
48 | stmp_reset_block(base + HW_USBPHY_CTRL); | 49 | ret = stmp_reset_block(base + HW_USBPHY_CTRL); |
50 | if (ret) | ||
51 | return ret; | ||
49 | 52 | ||
50 | /* Power up the PHY */ | 53 | /* Power up the PHY */ |
51 | writel(0, base + HW_USBPHY_PWD); | 54 | writel(0, base + HW_USBPHY_PWD); |
@@ -54,6 +57,8 @@ static void mxs_phy_hw_init(struct mxs_phy *mxs_phy) | |||
54 | writel(BM_USBPHY_CTRL_ENUTMILEVEL2 | | 57 | writel(BM_USBPHY_CTRL_ENUTMILEVEL2 | |
55 | BM_USBPHY_CTRL_ENUTMILEVEL3, | 58 | BM_USBPHY_CTRL_ENUTMILEVEL3, |
56 | base + HW_USBPHY_CTRL_SET); | 59 | base + HW_USBPHY_CTRL_SET); |
60 | |||
61 | return 0; | ||
57 | } | 62 | } |
58 | 63 | ||
59 | static int mxs_phy_init(struct usb_phy *phy) | 64 | static int mxs_phy_init(struct usb_phy *phy) |
@@ -61,9 +66,7 @@ static int mxs_phy_init(struct usb_phy *phy) | |||
61 | struct mxs_phy *mxs_phy = to_mxs_phy(phy); | 66 | struct mxs_phy *mxs_phy = to_mxs_phy(phy); |
62 | 67 | ||
63 | clk_prepare_enable(mxs_phy->clk); | 68 | clk_prepare_enable(mxs_phy->clk); |
64 | mxs_phy_hw_init(mxs_phy); | 69 | return mxs_phy_hw_init(mxs_phy); |
65 | |||
66 | return 0; | ||
67 | } | 70 | } |
68 | 71 | ||
69 | static void mxs_phy_shutdown(struct usb_phy *phy) | 72 | static void mxs_phy_shutdown(struct usb_phy *phy) |
diff --git a/drivers/usb/phy/phy-omap-control.c b/drivers/usb/phy/phy-omap-control.c index 1419ceda9759..a4dda8e12562 100644 --- a/drivers/usb/phy/phy-omap-control.c +++ b/drivers/usb/phy/phy-omap-control.c | |||
@@ -197,7 +197,8 @@ static int omap_control_usb_probe(struct platform_device *pdev) | |||
197 | { | 197 | { |
198 | struct resource *res; | 198 | struct resource *res; |
199 | struct device_node *np = pdev->dev.of_node; | 199 | struct device_node *np = pdev->dev.of_node; |
200 | struct omap_control_usb_platform_data *pdata = pdev->dev.platform_data; | 200 | struct omap_control_usb_platform_data *pdata = |
201 | dev_get_platdata(&pdev->dev); | ||
201 | 202 | ||
202 | control_usb = devm_kzalloc(&pdev->dev, sizeof(*control_usb), | 203 | control_usb = devm_kzalloc(&pdev->dev, sizeof(*control_usb), |
203 | GFP_KERNEL); | 204 | GFP_KERNEL); |
diff --git a/drivers/usb/phy/phy-omap-usb3.c b/drivers/usb/phy/phy-omap-usb3.c index a2fb30bbb971..fc15694d3031 100644 --- a/drivers/usb/phy/phy-omap-usb3.c +++ b/drivers/usb/phy/phy-omap-usb3.c | |||
@@ -27,7 +27,6 @@ | |||
27 | #include <linux/delay.h> | 27 | #include <linux/delay.h> |
28 | #include <linux/usb/omap_control_usb.h> | 28 | #include <linux/usb/omap_control_usb.h> |
29 | 29 | ||
30 | #define NUM_SYS_CLKS 6 | ||
31 | #define PLL_STATUS 0x00000004 | 30 | #define PLL_STATUS 0x00000004 |
32 | #define PLL_GO 0x00000008 | 31 | #define PLL_GO 0x00000008 |
33 | #define PLL_CONFIGURATION1 0x0000000C | 32 | #define PLL_CONFIGURATION1 0x0000000C |
@@ -57,26 +56,32 @@ | |||
57 | */ | 56 | */ |
58 | # define PLL_IDLE_TIME 100; | 57 | # define PLL_IDLE_TIME 100; |
59 | 58 | ||
60 | enum sys_clk_rate { | 59 | struct usb_dpll_map { |
61 | CLK_RATE_UNDEFINED = -1, | 60 | unsigned long rate; |
62 | CLK_RATE_12MHZ, | 61 | struct usb_dpll_params params; |
63 | CLK_RATE_16MHZ, | ||
64 | CLK_RATE_19MHZ, | ||
65 | CLK_RATE_20MHZ, | ||
66 | CLK_RATE_26MHZ, | ||
67 | CLK_RATE_38MHZ | ||
68 | }; | 62 | }; |
69 | 63 | ||
70 | static struct usb_dpll_params omap_usb3_dpll_params[NUM_SYS_CLKS] = { | 64 | static struct usb_dpll_map dpll_map[] = { |
71 | {1250, 5, 4, 20, 0}, /* 12 MHz */ | 65 | {12000000, {1250, 5, 4, 20, 0} }, /* 12 MHz */ |
72 | {3125, 20, 4, 20, 0}, /* 16.8 MHz */ | 66 | {16800000, {3125, 20, 4, 20, 0} }, /* 16.8 MHz */ |
73 | {1172, 8, 4, 20, 65537}, /* 19.2 MHz */ | 67 | {19200000, {1172, 8, 4, 20, 65537} }, /* 19.2 MHz */ |
74 | {1000, 7, 4, 10, 0}, /* 20 MHz */ | 68 | {20000000, {1000, 7, 4, 10, 0} }, /* 20 MHz */ |
75 | {1250, 12, 4, 20, 0}, /* 26 MHz */ | 69 | {26000000, {1250, 12, 4, 20, 0} }, /* 26 MHz */ |
76 | {3125, 47, 4, 20, 92843}, /* 38.4 MHz */ | 70 | {38400000, {3125, 47, 4, 20, 92843} }, /* 38.4 MHz */ |
77 | |||
78 | }; | 71 | }; |
79 | 72 | ||
73 | static struct usb_dpll_params *omap_usb3_get_dpll_params(unsigned long rate) | ||
74 | { | ||
75 | int i; | ||
76 | |||
77 | for (i = 0; i < ARRAY_SIZE(dpll_map); i++) { | ||
78 | if (rate == dpll_map[i].rate) | ||
79 | return &dpll_map[i].params; | ||
80 | } | ||
81 | |||
82 | return 0; | ||
83 | } | ||
84 | |||
80 | static int omap_usb3_suspend(struct usb_phy *x, int suspend) | 85 | static int omap_usb3_suspend(struct usb_phy *x, int suspend) |
81 | { | 86 | { |
82 | struct omap_usb *phy = phy_to_omapusb(x); | 87 | struct omap_usb *phy = phy_to_omapusb(x); |
@@ -116,26 +121,6 @@ static int omap_usb3_suspend(struct usb_phy *x, int suspend) | |||
116 | return 0; | 121 | return 0; |
117 | } | 122 | } |
118 | 123 | ||
119 | static inline enum sys_clk_rate __get_sys_clk_index(unsigned long rate) | ||
120 | { | ||
121 | switch (rate) { | ||
122 | case 12000000: | ||
123 | return CLK_RATE_12MHZ; | ||
124 | case 16800000: | ||
125 | return CLK_RATE_16MHZ; | ||
126 | case 19200000: | ||
127 | return CLK_RATE_19MHZ; | ||
128 | case 20000000: | ||
129 | return CLK_RATE_20MHZ; | ||
130 | case 26000000: | ||
131 | return CLK_RATE_26MHZ; | ||
132 | case 38400000: | ||
133 | return CLK_RATE_38MHZ; | ||
134 | default: | ||
135 | return CLK_RATE_UNDEFINED; | ||
136 | } | ||
137 | } | ||
138 | |||
139 | static void omap_usb_dpll_relock(struct omap_usb *phy) | 124 | static void omap_usb_dpll_relock(struct omap_usb *phy) |
140 | { | 125 | { |
141 | u32 val; | 126 | u32 val; |
@@ -155,39 +140,39 @@ static int omap_usb_dpll_lock(struct omap_usb *phy) | |||
155 | { | 140 | { |
156 | u32 val; | 141 | u32 val; |
157 | unsigned long rate; | 142 | unsigned long rate; |
158 | enum sys_clk_rate clk_index; | 143 | struct usb_dpll_params *dpll_params; |
159 | |||
160 | rate = clk_get_rate(phy->sys_clk); | ||
161 | clk_index = __get_sys_clk_index(rate); | ||
162 | 144 | ||
163 | if (clk_index == CLK_RATE_UNDEFINED) { | 145 | rate = clk_get_rate(phy->sys_clk); |
164 | pr_err("dpll cannot be locked for sys clk freq:%luHz\n", rate); | 146 | dpll_params = omap_usb3_get_dpll_params(rate); |
147 | if (!dpll_params) { | ||
148 | dev_err(phy->dev, | ||
149 | "No DPLL configuration for %lu Hz SYS CLK\n", rate); | ||
165 | return -EINVAL; | 150 | return -EINVAL; |
166 | } | 151 | } |
167 | 152 | ||
168 | val = omap_usb_readl(phy->pll_ctrl_base, PLL_CONFIGURATION1); | 153 | val = omap_usb_readl(phy->pll_ctrl_base, PLL_CONFIGURATION1); |
169 | val &= ~PLL_REGN_MASK; | 154 | val &= ~PLL_REGN_MASK; |
170 | val |= omap_usb3_dpll_params[clk_index].n << PLL_REGN_SHIFT; | 155 | val |= dpll_params->n << PLL_REGN_SHIFT; |
171 | omap_usb_writel(phy->pll_ctrl_base, PLL_CONFIGURATION1, val); | 156 | omap_usb_writel(phy->pll_ctrl_base, PLL_CONFIGURATION1, val); |
172 | 157 | ||
173 | val = omap_usb_readl(phy->pll_ctrl_base, PLL_CONFIGURATION2); | 158 | val = omap_usb_readl(phy->pll_ctrl_base, PLL_CONFIGURATION2); |
174 | val &= ~PLL_SELFREQDCO_MASK; | 159 | val &= ~PLL_SELFREQDCO_MASK; |
175 | val |= omap_usb3_dpll_params[clk_index].freq << PLL_SELFREQDCO_SHIFT; | 160 | val |= dpll_params->freq << PLL_SELFREQDCO_SHIFT; |
176 | omap_usb_writel(phy->pll_ctrl_base, PLL_CONFIGURATION2, val); | 161 | omap_usb_writel(phy->pll_ctrl_base, PLL_CONFIGURATION2, val); |
177 | 162 | ||
178 | val = omap_usb_readl(phy->pll_ctrl_base, PLL_CONFIGURATION1); | 163 | val = omap_usb_readl(phy->pll_ctrl_base, PLL_CONFIGURATION1); |
179 | val &= ~PLL_REGM_MASK; | 164 | val &= ~PLL_REGM_MASK; |
180 | val |= omap_usb3_dpll_params[clk_index].m << PLL_REGM_SHIFT; | 165 | val |= dpll_params->m << PLL_REGM_SHIFT; |
181 | omap_usb_writel(phy->pll_ctrl_base, PLL_CONFIGURATION1, val); | 166 | omap_usb_writel(phy->pll_ctrl_base, PLL_CONFIGURATION1, val); |
182 | 167 | ||
183 | val = omap_usb_readl(phy->pll_ctrl_base, PLL_CONFIGURATION4); | 168 | val = omap_usb_readl(phy->pll_ctrl_base, PLL_CONFIGURATION4); |
184 | val &= ~PLL_REGM_F_MASK; | 169 | val &= ~PLL_REGM_F_MASK; |
185 | val |= omap_usb3_dpll_params[clk_index].mf << PLL_REGM_F_SHIFT; | 170 | val |= dpll_params->mf << PLL_REGM_F_SHIFT; |
186 | omap_usb_writel(phy->pll_ctrl_base, PLL_CONFIGURATION4, val); | 171 | omap_usb_writel(phy->pll_ctrl_base, PLL_CONFIGURATION4, val); |
187 | 172 | ||
188 | val = omap_usb_readl(phy->pll_ctrl_base, PLL_CONFIGURATION3); | 173 | val = omap_usb_readl(phy->pll_ctrl_base, PLL_CONFIGURATION3); |
189 | val &= ~PLL_SD_MASK; | 174 | val &= ~PLL_SD_MASK; |
190 | val |= omap_usb3_dpll_params[clk_index].sd << PLL_SD_SHIFT; | 175 | val |= dpll_params->sd << PLL_SD_SHIFT; |
191 | omap_usb_writel(phy->pll_ctrl_base, PLL_CONFIGURATION3, val); | 176 | omap_usb_writel(phy->pll_ctrl_base, PLL_CONFIGURATION3, val); |
192 | 177 | ||
193 | omap_usb_dpll_relock(phy); | 178 | omap_usb_dpll_relock(phy); |
@@ -198,8 +183,12 @@ static int omap_usb_dpll_lock(struct omap_usb *phy) | |||
198 | static int omap_usb3_init(struct usb_phy *x) | 183 | static int omap_usb3_init(struct usb_phy *x) |
199 | { | 184 | { |
200 | struct omap_usb *phy = phy_to_omapusb(x); | 185 | struct omap_usb *phy = phy_to_omapusb(x); |
186 | int ret; | ||
187 | |||
188 | ret = omap_usb_dpll_lock(phy); | ||
189 | if (ret) | ||
190 | return ret; | ||
201 | 191 | ||
202 | omap_usb_dpll_lock(phy); | ||
203 | omap_control_usb3_phy_power(phy->control_dev, 1); | 192 | omap_control_usb3_phy_power(phy->control_dev, 1); |
204 | 193 | ||
205 | return 0; | 194 | return 0; |
diff --git a/drivers/usb/phy/phy-rcar-usb.c b/drivers/usb/phy/phy-rcar-usb.c index ae909408958d..33265a5b2cdf 100644 --- a/drivers/usb/phy/phy-rcar-usb.c +++ b/drivers/usb/phy/phy-rcar-usb.c | |||
@@ -83,7 +83,7 @@ static int rcar_usb_phy_init(struct usb_phy *phy) | |||
83 | { | 83 | { |
84 | struct rcar_usb_phy_priv *priv = usb_phy_to_priv(phy); | 84 | struct rcar_usb_phy_priv *priv = usb_phy_to_priv(phy); |
85 | struct device *dev = phy->dev; | 85 | struct device *dev = phy->dev; |
86 | struct rcar_phy_platform_data *pdata = dev->platform_data; | 86 | struct rcar_phy_platform_data *pdata = dev_get_platdata(dev); |
87 | void __iomem *reg0 = priv->reg0; | 87 | void __iomem *reg0 = priv->reg0; |
88 | void __iomem *reg1 = priv->reg1; | 88 | void __iomem *reg1 = priv->reg1; |
89 | static const u8 ovcn_act[] = { OVC0_ACT, OVC1_ACT, OVC2_ACT }; | 89 | static const u8 ovcn_act[] = { OVC0_ACT, OVC1_ACT, OVC2_ACT }; |
@@ -184,17 +184,12 @@ static int rcar_usb_phy_probe(struct platform_device *pdev) | |||
184 | void __iomem *reg0, *reg1 = NULL; | 184 | void __iomem *reg0, *reg1 = NULL; |
185 | int ret; | 185 | int ret; |
186 | 186 | ||
187 | if (!pdev->dev.platform_data) { | 187 | if (!dev_get_platdata(&pdev->dev)) { |
188 | dev_err(dev, "No platform data\n"); | 188 | dev_err(dev, "No platform data\n"); |
189 | return -EINVAL; | 189 | return -EINVAL; |
190 | } | 190 | } |
191 | 191 | ||
192 | res0 = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 192 | res0 = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
193 | if (!res0) { | ||
194 | dev_err(dev, "Not enough platform resources\n"); | ||
195 | return -EINVAL; | ||
196 | } | ||
197 | |||
198 | reg0 = devm_ioremap_resource(dev, res0); | 193 | reg0 = devm_ioremap_resource(dev, res0); |
199 | if (IS_ERR(reg0)) | 194 | if (IS_ERR(reg0)) |
200 | return PTR_ERR(reg0); | 195 | return PTR_ERR(reg0); |
diff --git a/drivers/usb/phy/phy-samsung-usb2.c b/drivers/usb/phy/phy-samsung-usb2.c index 758b86d0fcb3..ff70e4b19b97 100644 --- a/drivers/usb/phy/phy-samsung-usb2.c +++ b/drivers/usb/phy/phy-samsung-usb2.c | |||
@@ -359,7 +359,7 @@ static int samsung_usb2phy_probe(struct platform_device *pdev) | |||
359 | { | 359 | { |
360 | struct samsung_usbphy *sphy; | 360 | struct samsung_usbphy *sphy; |
361 | struct usb_otg *otg; | 361 | struct usb_otg *otg; |
362 | struct samsung_usbphy_data *pdata = pdev->dev.platform_data; | 362 | struct samsung_usbphy_data *pdata = dev_get_platdata(&pdev->dev); |
363 | const struct samsung_usbphy_drvdata *drv_data; | 363 | const struct samsung_usbphy_drvdata *drv_data; |
364 | struct device *dev = &pdev->dev; | 364 | struct device *dev = &pdev->dev; |
365 | struct resource *phy_mem; | 365 | struct resource *phy_mem; |
diff --git a/drivers/usb/phy/phy-samsung-usb3.c b/drivers/usb/phy/phy-samsung-usb3.c index 300e0cf5e31f..c6eb22213de6 100644 --- a/drivers/usb/phy/phy-samsung-usb3.c +++ b/drivers/usb/phy/phy-samsung-usb3.c | |||
@@ -231,7 +231,7 @@ static void samsung_usb3phy_shutdown(struct usb_phy *phy) | |||
231 | static int samsung_usb3phy_probe(struct platform_device *pdev) | 231 | static int samsung_usb3phy_probe(struct platform_device *pdev) |
232 | { | 232 | { |
233 | struct samsung_usbphy *sphy; | 233 | struct samsung_usbphy *sphy; |
234 | struct samsung_usbphy_data *pdata = pdev->dev.platform_data; | 234 | struct samsung_usbphy_data *pdata = dev_get_platdata(&pdev->dev); |
235 | struct device *dev = &pdev->dev; | 235 | struct device *dev = &pdev->dev; |
236 | struct resource *phy_mem; | 236 | struct resource *phy_mem; |
237 | void __iomem *phy_base; | 237 | void __iomem *phy_base; |
diff --git a/drivers/usb/phy/phy-tegra-usb.c b/drivers/usb/phy/phy-tegra-usb.c index cec0855ed248..3bfb3d1957c1 100644 --- a/drivers/usb/phy/phy-tegra-usb.c +++ b/drivers/usb/phy/phy-tegra-usb.c | |||
@@ -28,20 +28,28 @@ | |||
28 | #include <linux/io.h> | 28 | #include <linux/io.h> |
29 | #include <linux/gpio.h> | 29 | #include <linux/gpio.h> |
30 | #include <linux/of.h> | 30 | #include <linux/of.h> |
31 | #include <linux/of_device.h> | ||
31 | #include <linux/of_gpio.h> | 32 | #include <linux/of_gpio.h> |
32 | #include <linux/usb/otg.h> | 33 | #include <linux/usb/otg.h> |
33 | #include <linux/usb/ulpi.h> | 34 | #include <linux/usb/ulpi.h> |
35 | #include <linux/usb/of.h> | ||
34 | #include <asm/mach-types.h> | 36 | #include <asm/mach-types.h> |
35 | #include <linux/usb/ehci_def.h> | 37 | #include <linux/usb/ehci_def.h> |
36 | #include <linux/usb/tegra_usb_phy.h> | 38 | #include <linux/usb/tegra_usb_phy.h> |
39 | #include <linux/regulator/consumer.h> | ||
37 | 40 | ||
38 | #define ULPI_VIEWPORT 0x170 | 41 | #define ULPI_VIEWPORT 0x170 |
39 | 42 | ||
40 | /* PORTSC registers */ | 43 | /* PORTSC PTS/PHCD bits, Tegra20 only */ |
41 | #define TEGRA_USB_PORTSC1 0x184 | 44 | #define TEGRA_USB_PORTSC1 0x184 |
42 | #define TEGRA_USB_PORTSC1_PTS(x) (((x) & 0x3) << 30) | 45 | #define TEGRA_USB_PORTSC1_PTS(x) (((x) & 0x3) << 30) |
43 | #define TEGRA_USB_PORTSC1_PHCD (1 << 23) | 46 | #define TEGRA_USB_PORTSC1_PHCD (1 << 23) |
44 | 47 | ||
48 | /* HOSTPC1 PTS/PHCD bits, Tegra30 and above */ | ||
49 | #define TEGRA_USB_HOSTPC1_DEVLC 0x1b4 | ||
50 | #define TEGRA_USB_HOSTPC1_DEVLC_PTS(x) (((x) & 0x7) << 29) | ||
51 | #define TEGRA_USB_HOSTPC1_DEVLC_PHCD (1 << 22) | ||
52 | |||
45 | /* Bits of PORTSC1, which will get cleared by writing 1 into them */ | 53 | /* Bits of PORTSC1, which will get cleared by writing 1 into them */ |
46 | #define TEGRA_PORTSC1_RWC_BITS (PORT_CSC | PORT_PEC | PORT_OCC) | 54 | #define TEGRA_PORTSC1_RWC_BITS (PORT_CSC | PORT_PEC | PORT_OCC) |
47 | 55 | ||
@@ -84,16 +92,22 @@ | |||
84 | 92 | ||
85 | #define UTMIP_XCVR_CFG0 0x808 | 93 | #define UTMIP_XCVR_CFG0 0x808 |
86 | #define UTMIP_XCVR_SETUP(x) (((x) & 0xf) << 0) | 94 | #define UTMIP_XCVR_SETUP(x) (((x) & 0xf) << 0) |
95 | #define UTMIP_XCVR_SETUP_MSB(x) ((((x) & 0x70) >> 4) << 22) | ||
87 | #define UTMIP_XCVR_LSRSLEW(x) (((x) & 0x3) << 8) | 96 | #define UTMIP_XCVR_LSRSLEW(x) (((x) & 0x3) << 8) |
88 | #define UTMIP_XCVR_LSFSLEW(x) (((x) & 0x3) << 10) | 97 | #define UTMIP_XCVR_LSFSLEW(x) (((x) & 0x3) << 10) |
89 | #define UTMIP_FORCE_PD_POWERDOWN (1 << 14) | 98 | #define UTMIP_FORCE_PD_POWERDOWN (1 << 14) |
90 | #define UTMIP_FORCE_PD2_POWERDOWN (1 << 16) | 99 | #define UTMIP_FORCE_PD2_POWERDOWN (1 << 16) |
91 | #define UTMIP_FORCE_PDZI_POWERDOWN (1 << 18) | 100 | #define UTMIP_FORCE_PDZI_POWERDOWN (1 << 18) |
92 | #define UTMIP_XCVR_HSSLEW_MSB(x) (((x) & 0x7f) << 25) | 101 | #define UTMIP_XCVR_LSBIAS_SEL (1 << 21) |
102 | #define UTMIP_XCVR_HSSLEW(x) (((x) & 0x3) << 4) | ||
103 | #define UTMIP_XCVR_HSSLEW_MSB(x) ((((x) & 0x1fc) >> 2) << 25) | ||
93 | 104 | ||
94 | #define UTMIP_BIAS_CFG0 0x80c | 105 | #define UTMIP_BIAS_CFG0 0x80c |
95 | #define UTMIP_OTGPD (1 << 11) | 106 | #define UTMIP_OTGPD (1 << 11) |
96 | #define UTMIP_BIASPD (1 << 10) | 107 | #define UTMIP_BIASPD (1 << 10) |
108 | #define UTMIP_HSSQUELCH_LEVEL(x) (((x) & 0x3) << 0) | ||
109 | #define UTMIP_HSDISCON_LEVEL(x) (((x) & 0x3) << 2) | ||
110 | #define UTMIP_HSDISCON_LEVEL_MSB(x) ((((x) & 0x4) >> 2) << 24) | ||
97 | 111 | ||
98 | #define UTMIP_HSRX_CFG0 0x810 | 112 | #define UTMIP_HSRX_CFG0 0x810 |
99 | #define UTMIP_ELASTIC_LIMIT(x) (((x) & 0x1f) << 10) | 113 | #define UTMIP_ELASTIC_LIMIT(x) (((x) & 0x1f) << 10) |
@@ -137,6 +151,12 @@ | |||
137 | #define UTMIP_BIAS_CFG1 0x83c | 151 | #define UTMIP_BIAS_CFG1 0x83c |
138 | #define UTMIP_BIAS_PDTRK_COUNT(x) (((x) & 0x1f) << 3) | 152 | #define UTMIP_BIAS_PDTRK_COUNT(x) (((x) & 0x1f) << 3) |
139 | 153 | ||
154 | /* For Tegra30 and above only, the address is different in Tegra20 */ | ||
155 | #define USB_USBMODE 0x1f8 | ||
156 | #define USB_USBMODE_MASK (3 << 0) | ||
157 | #define USB_USBMODE_HOST (3 << 0) | ||
158 | #define USB_USBMODE_DEVICE (2 << 0) | ||
159 | |||
140 | static DEFINE_SPINLOCK(utmip_pad_lock); | 160 | static DEFINE_SPINLOCK(utmip_pad_lock); |
141 | static int utmip_pad_count; | 161 | static int utmip_pad_count; |
142 | 162 | ||
@@ -184,36 +204,22 @@ static const struct tegra_xtal_freq tegra_freq_table[] = { | |||
184 | }, | 204 | }, |
185 | }; | 205 | }; |
186 | 206 | ||
187 | static struct tegra_utmip_config utmip_default[] = { | ||
188 | [0] = { | ||
189 | .hssync_start_delay = 9, | ||
190 | .idle_wait_delay = 17, | ||
191 | .elastic_limit = 16, | ||
192 | .term_range_adj = 6, | ||
193 | .xcvr_setup = 9, | ||
194 | .xcvr_lsfslew = 1, | ||
195 | .xcvr_lsrslew = 1, | ||
196 | }, | ||
197 | [2] = { | ||
198 | .hssync_start_delay = 9, | ||
199 | .idle_wait_delay = 17, | ||
200 | .elastic_limit = 16, | ||
201 | .term_range_adj = 6, | ||
202 | .xcvr_setup = 9, | ||
203 | .xcvr_lsfslew = 2, | ||
204 | .xcvr_lsrslew = 2, | ||
205 | }, | ||
206 | }; | ||
207 | |||
208 | static void set_pts(struct tegra_usb_phy *phy, u8 pts_val) | 207 | static void set_pts(struct tegra_usb_phy *phy, u8 pts_val) |
209 | { | 208 | { |
210 | void __iomem *base = phy->regs; | 209 | void __iomem *base = phy->regs; |
211 | unsigned long val; | 210 | unsigned long val; |
212 | 211 | ||
213 | val = readl(base + TEGRA_USB_PORTSC1) & ~TEGRA_PORTSC1_RWC_BITS; | 212 | if (phy->soc_config->has_hostpc) { |
214 | val &= ~TEGRA_USB_PORTSC1_PTS(3); | 213 | val = readl(base + TEGRA_USB_HOSTPC1_DEVLC); |
215 | val |= TEGRA_USB_PORTSC1_PTS(pts_val & 3); | 214 | val &= ~TEGRA_USB_HOSTPC1_DEVLC_PTS(~0); |
216 | writel(val, base + TEGRA_USB_PORTSC1); | 215 | val |= TEGRA_USB_HOSTPC1_DEVLC_PTS(pts_val); |
216 | writel(val, base + TEGRA_USB_HOSTPC1_DEVLC); | ||
217 | } else { | ||
218 | val = readl(base + TEGRA_USB_PORTSC1) & ~TEGRA_PORTSC1_RWC_BITS; | ||
219 | val &= ~TEGRA_USB_PORTSC1_PTS(~0); | ||
220 | val |= TEGRA_USB_PORTSC1_PTS(pts_val); | ||
221 | writel(val, base + TEGRA_USB_PORTSC1); | ||
222 | } | ||
217 | } | 223 | } |
218 | 224 | ||
219 | static void set_phcd(struct tegra_usb_phy *phy, bool enable) | 225 | static void set_phcd(struct tegra_usb_phy *phy, bool enable) |
@@ -221,17 +227,26 @@ static void set_phcd(struct tegra_usb_phy *phy, bool enable) | |||
221 | void __iomem *base = phy->regs; | 227 | void __iomem *base = phy->regs; |
222 | unsigned long val; | 228 | unsigned long val; |
223 | 229 | ||
224 | val = readl(base + TEGRA_USB_PORTSC1) & ~TEGRA_PORTSC1_RWC_BITS; | 230 | if (phy->soc_config->has_hostpc) { |
225 | if (enable) | 231 | val = readl(base + TEGRA_USB_HOSTPC1_DEVLC); |
226 | val |= TEGRA_USB_PORTSC1_PHCD; | 232 | if (enable) |
227 | else | 233 | val |= TEGRA_USB_HOSTPC1_DEVLC_PHCD; |
228 | val &= ~TEGRA_USB_PORTSC1_PHCD; | 234 | else |
229 | writel(val, base + TEGRA_USB_PORTSC1); | 235 | val &= ~TEGRA_USB_HOSTPC1_DEVLC_PHCD; |
236 | writel(val, base + TEGRA_USB_HOSTPC1_DEVLC); | ||
237 | } else { | ||
238 | val = readl(base + TEGRA_USB_PORTSC1) & ~PORT_RWC_BITS; | ||
239 | if (enable) | ||
240 | val |= TEGRA_USB_PORTSC1_PHCD; | ||
241 | else | ||
242 | val &= ~TEGRA_USB_PORTSC1_PHCD; | ||
243 | writel(val, base + TEGRA_USB_PORTSC1); | ||
244 | } | ||
230 | } | 245 | } |
231 | 246 | ||
232 | static int utmip_pad_open(struct tegra_usb_phy *phy) | 247 | static int utmip_pad_open(struct tegra_usb_phy *phy) |
233 | { | 248 | { |
234 | phy->pad_clk = devm_clk_get(phy->dev, "utmi-pads"); | 249 | phy->pad_clk = devm_clk_get(phy->u_phy.dev, "utmi-pads"); |
235 | if (IS_ERR(phy->pad_clk)) { | 250 | if (IS_ERR(phy->pad_clk)) { |
236 | pr_err("%s: can't get utmip pad clock\n", __func__); | 251 | pr_err("%s: can't get utmip pad clock\n", __func__); |
237 | return PTR_ERR(phy->pad_clk); | 252 | return PTR_ERR(phy->pad_clk); |
@@ -244,6 +259,7 @@ static void utmip_pad_power_on(struct tegra_usb_phy *phy) | |||
244 | { | 259 | { |
245 | unsigned long val, flags; | 260 | unsigned long val, flags; |
246 | void __iomem *base = phy->pad_regs; | 261 | void __iomem *base = phy->pad_regs; |
262 | struct tegra_utmip_config *config = phy->config; | ||
247 | 263 | ||
248 | clk_prepare_enable(phy->pad_clk); | 264 | clk_prepare_enable(phy->pad_clk); |
249 | 265 | ||
@@ -252,6 +268,16 @@ static void utmip_pad_power_on(struct tegra_usb_phy *phy) | |||
252 | if (utmip_pad_count++ == 0) { | 268 | if (utmip_pad_count++ == 0) { |
253 | val = readl(base + UTMIP_BIAS_CFG0); | 269 | val = readl(base + UTMIP_BIAS_CFG0); |
254 | val &= ~(UTMIP_OTGPD | UTMIP_BIASPD); | 270 | val &= ~(UTMIP_OTGPD | UTMIP_BIASPD); |
271 | |||
272 | if (phy->soc_config->requires_extra_tuning_parameters) { | ||
273 | val &= ~(UTMIP_HSSQUELCH_LEVEL(~0) | | ||
274 | UTMIP_HSDISCON_LEVEL(~0) | | ||
275 | UTMIP_HSDISCON_LEVEL_MSB(~0)); | ||
276 | |||
277 | val |= UTMIP_HSSQUELCH_LEVEL(config->hssquelch_level); | ||
278 | val |= UTMIP_HSDISCON_LEVEL(config->hsdiscon_level); | ||
279 | val |= UTMIP_HSDISCON_LEVEL_MSB(config->hsdiscon_level); | ||
280 | } | ||
255 | writel(val, base + UTMIP_BIAS_CFG0); | 281 | writel(val, base + UTMIP_BIAS_CFG0); |
256 | } | 282 | } |
257 | 283 | ||
@@ -361,7 +387,7 @@ static int utmi_phy_power_on(struct tegra_usb_phy *phy) | |||
361 | } | 387 | } |
362 | 388 | ||
363 | val = readl(base + UTMIP_TX_CFG0); | 389 | val = readl(base + UTMIP_TX_CFG0); |
364 | val &= ~UTMIP_FS_PREABMLE_J; | 390 | val |= UTMIP_FS_PREABMLE_J; |
365 | writel(val, base + UTMIP_TX_CFG0); | 391 | writel(val, base + UTMIP_TX_CFG0); |
366 | 392 | ||
367 | val = readl(base + UTMIP_HSRX_CFG0); | 393 | val = readl(base + UTMIP_HSRX_CFG0); |
@@ -384,34 +410,56 @@ static int utmi_phy_power_on(struct tegra_usb_phy *phy) | |||
384 | val &= ~UTMIP_SUSPEND_EXIT_ON_EDGE; | 410 | val &= ~UTMIP_SUSPEND_EXIT_ON_EDGE; |
385 | writel(val, base + UTMIP_MISC_CFG0); | 411 | writel(val, base + UTMIP_MISC_CFG0); |
386 | 412 | ||
387 | val = readl(base + UTMIP_MISC_CFG1); | 413 | if (!phy->soc_config->utmi_pll_config_in_car_module) { |
388 | val &= ~(UTMIP_PLL_ACTIVE_DLY_COUNT(~0) | UTMIP_PLLU_STABLE_COUNT(~0)); | 414 | val = readl(base + UTMIP_MISC_CFG1); |
389 | val |= UTMIP_PLL_ACTIVE_DLY_COUNT(phy->freq->active_delay) | | 415 | val &= ~(UTMIP_PLL_ACTIVE_DLY_COUNT(~0) | |
390 | UTMIP_PLLU_STABLE_COUNT(phy->freq->stable_count); | 416 | UTMIP_PLLU_STABLE_COUNT(~0)); |
391 | writel(val, base + UTMIP_MISC_CFG1); | 417 | val |= UTMIP_PLL_ACTIVE_DLY_COUNT(phy->freq->active_delay) | |
392 | 418 | UTMIP_PLLU_STABLE_COUNT(phy->freq->stable_count); | |
393 | val = readl(base + UTMIP_PLL_CFG1); | 419 | writel(val, base + UTMIP_MISC_CFG1); |
394 | val &= ~(UTMIP_XTAL_FREQ_COUNT(~0) | UTMIP_PLLU_ENABLE_DLY_COUNT(~0)); | 420 | |
395 | val |= UTMIP_XTAL_FREQ_COUNT(phy->freq->xtal_freq_count) | | 421 | val = readl(base + UTMIP_PLL_CFG1); |
396 | UTMIP_PLLU_ENABLE_DLY_COUNT(phy->freq->enable_delay); | 422 | val &= ~(UTMIP_XTAL_FREQ_COUNT(~0) | |
397 | writel(val, base + UTMIP_PLL_CFG1); | 423 | UTMIP_PLLU_ENABLE_DLY_COUNT(~0)); |
424 | val |= UTMIP_XTAL_FREQ_COUNT(phy->freq->xtal_freq_count) | | ||
425 | UTMIP_PLLU_ENABLE_DLY_COUNT(phy->freq->enable_delay); | ||
426 | writel(val, base + UTMIP_PLL_CFG1); | ||
427 | } | ||
398 | 428 | ||
399 | if (phy->mode == TEGRA_USB_PHY_MODE_DEVICE) { | 429 | if (phy->mode == USB_DR_MODE_PERIPHERAL) { |
400 | val = readl(base + USB_SUSP_CTRL); | 430 | val = readl(base + USB_SUSP_CTRL); |
401 | val &= ~(USB_WAKE_ON_CNNT_EN_DEV | USB_WAKE_ON_DISCON_EN_DEV); | 431 | val &= ~(USB_WAKE_ON_CNNT_EN_DEV | USB_WAKE_ON_DISCON_EN_DEV); |
402 | writel(val, base + USB_SUSP_CTRL); | 432 | writel(val, base + USB_SUSP_CTRL); |
433 | |||
434 | val = readl(base + UTMIP_BAT_CHRG_CFG0); | ||
435 | val &= ~UTMIP_PD_CHRG; | ||
436 | writel(val, base + UTMIP_BAT_CHRG_CFG0); | ||
437 | } else { | ||
438 | val = readl(base + UTMIP_BAT_CHRG_CFG0); | ||
439 | val |= UTMIP_PD_CHRG; | ||
440 | writel(val, base + UTMIP_BAT_CHRG_CFG0); | ||
403 | } | 441 | } |
404 | 442 | ||
405 | utmip_pad_power_on(phy); | 443 | utmip_pad_power_on(phy); |
406 | 444 | ||
407 | val = readl(base + UTMIP_XCVR_CFG0); | 445 | val = readl(base + UTMIP_XCVR_CFG0); |
408 | val &= ~(UTMIP_FORCE_PD_POWERDOWN | UTMIP_FORCE_PD2_POWERDOWN | | 446 | val &= ~(UTMIP_FORCE_PD_POWERDOWN | UTMIP_FORCE_PD2_POWERDOWN | |
409 | UTMIP_FORCE_PDZI_POWERDOWN | UTMIP_XCVR_SETUP(~0) | | 447 | UTMIP_FORCE_PDZI_POWERDOWN | UTMIP_XCVR_LSBIAS_SEL | |
410 | UTMIP_XCVR_LSFSLEW(~0) | UTMIP_XCVR_LSRSLEW(~0) | | 448 | UTMIP_XCVR_SETUP(~0) | UTMIP_XCVR_SETUP_MSB(~0) | |
411 | UTMIP_XCVR_HSSLEW_MSB(~0)); | 449 | UTMIP_XCVR_LSFSLEW(~0) | UTMIP_XCVR_LSRSLEW(~0)); |
412 | val |= UTMIP_XCVR_SETUP(config->xcvr_setup); | 450 | |
451 | if (!config->xcvr_setup_use_fuses) { | ||
452 | val |= UTMIP_XCVR_SETUP(config->xcvr_setup); | ||
453 | val |= UTMIP_XCVR_SETUP_MSB(config->xcvr_setup); | ||
454 | } | ||
413 | val |= UTMIP_XCVR_LSFSLEW(config->xcvr_lsfslew); | 455 | val |= UTMIP_XCVR_LSFSLEW(config->xcvr_lsfslew); |
414 | val |= UTMIP_XCVR_LSRSLEW(config->xcvr_lsrslew); | 456 | val |= UTMIP_XCVR_LSRSLEW(config->xcvr_lsrslew); |
457 | |||
458 | if (phy->soc_config->requires_extra_tuning_parameters) { | ||
459 | val &= ~(UTMIP_XCVR_HSSLEW(~0) | UTMIP_XCVR_HSSLEW_MSB(~0)); | ||
460 | val |= UTMIP_XCVR_HSSLEW(config->xcvr_hsslew); | ||
461 | val |= UTMIP_XCVR_HSSLEW_MSB(config->xcvr_hsslew); | ||
462 | } | ||
415 | writel(val, base + UTMIP_XCVR_CFG0); | 463 | writel(val, base + UTMIP_XCVR_CFG0); |
416 | 464 | ||
417 | val = readl(base + UTMIP_XCVR_CFG1); | 465 | val = readl(base + UTMIP_XCVR_CFG1); |
@@ -420,23 +468,19 @@ static int utmi_phy_power_on(struct tegra_usb_phy *phy) | |||
420 | val |= UTMIP_XCVR_TERM_RANGE_ADJ(config->term_range_adj); | 468 | val |= UTMIP_XCVR_TERM_RANGE_ADJ(config->term_range_adj); |
421 | writel(val, base + UTMIP_XCVR_CFG1); | 469 | writel(val, base + UTMIP_XCVR_CFG1); |
422 | 470 | ||
423 | val = readl(base + UTMIP_BAT_CHRG_CFG0); | ||
424 | val &= ~UTMIP_PD_CHRG; | ||
425 | writel(val, base + UTMIP_BAT_CHRG_CFG0); | ||
426 | |||
427 | val = readl(base + UTMIP_BIAS_CFG1); | 471 | val = readl(base + UTMIP_BIAS_CFG1); |
428 | val &= ~UTMIP_BIAS_PDTRK_COUNT(~0); | 472 | val &= ~UTMIP_BIAS_PDTRK_COUNT(~0); |
429 | val |= UTMIP_BIAS_PDTRK_COUNT(0x5); | 473 | val |= UTMIP_BIAS_PDTRK_COUNT(0x5); |
430 | writel(val, base + UTMIP_BIAS_CFG1); | 474 | writel(val, base + UTMIP_BIAS_CFG1); |
431 | 475 | ||
432 | if (phy->is_legacy_phy) { | 476 | val = readl(base + UTMIP_SPARE_CFG0); |
433 | val = readl(base + UTMIP_SPARE_CFG0); | 477 | if (config->xcvr_setup_use_fuses) |
434 | if (phy->mode == TEGRA_USB_PHY_MODE_DEVICE) | 478 | val |= FUSE_SETUP_SEL; |
435 | val &= ~FUSE_SETUP_SEL; | 479 | else |
436 | else | 480 | val &= ~FUSE_SETUP_SEL; |
437 | val |= FUSE_SETUP_SEL; | 481 | writel(val, base + UTMIP_SPARE_CFG0); |
438 | writel(val, base + UTMIP_SPARE_CFG0); | 482 | |
439 | } else { | 483 | if (!phy->is_legacy_phy) { |
440 | val = readl(base + USB_SUSP_CTRL); | 484 | val = readl(base + USB_SUSP_CTRL); |
441 | val |= UTMIP_PHY_ENABLE; | 485 | val |= UTMIP_PHY_ENABLE; |
442 | writel(val, base + USB_SUSP_CTRL); | 486 | writel(val, base + USB_SUSP_CTRL); |
@@ -459,6 +503,16 @@ static int utmi_phy_power_on(struct tegra_usb_phy *phy) | |||
459 | 503 | ||
460 | utmi_phy_clk_enable(phy); | 504 | utmi_phy_clk_enable(phy); |
461 | 505 | ||
506 | if (phy->soc_config->requires_usbmode_setup) { | ||
507 | val = readl(base + USB_USBMODE); | ||
508 | val &= ~USB_USBMODE_MASK; | ||
509 | if (phy->mode == USB_DR_MODE_HOST) | ||
510 | val |= USB_USBMODE_HOST; | ||
511 | else | ||
512 | val |= USB_USBMODE_DEVICE; | ||
513 | writel(val, base + USB_USBMODE); | ||
514 | } | ||
515 | |||
462 | if (!phy->is_legacy_phy) | 516 | if (!phy->is_legacy_phy) |
463 | set_pts(phy, 0); | 517 | set_pts(phy, 0); |
464 | 518 | ||
@@ -472,7 +526,7 @@ static int utmi_phy_power_off(struct tegra_usb_phy *phy) | |||
472 | 526 | ||
473 | utmi_phy_clk_disable(phy); | 527 | utmi_phy_clk_disable(phy); |
474 | 528 | ||
475 | if (phy->mode == TEGRA_USB_PHY_MODE_DEVICE) { | 529 | if (phy->mode == USB_DR_MODE_PERIPHERAL) { |
476 | val = readl(base + USB_SUSP_CTRL); | 530 | val = readl(base + USB_SUSP_CTRL); |
477 | val &= ~USB_WAKEUP_DEBOUNCE_COUNT(~0); | 531 | val &= ~USB_WAKEUP_DEBOUNCE_COUNT(~0); |
478 | val |= USB_WAKE_ON_CNNT_EN_DEV | USB_WAKEUP_DEBOUNCE_COUNT(5); | 532 | val |= USB_WAKE_ON_CNNT_EN_DEV | USB_WAKEUP_DEBOUNCE_COUNT(5); |
@@ -560,13 +614,15 @@ static int ulpi_phy_power_on(struct tegra_usb_phy *phy) | |||
560 | 614 | ||
561 | ret = gpio_direction_output(phy->reset_gpio, 0); | 615 | ret = gpio_direction_output(phy->reset_gpio, 0); |
562 | if (ret < 0) { | 616 | if (ret < 0) { |
563 | dev_err(phy->dev, "gpio %d not set to 0\n", phy->reset_gpio); | 617 | dev_err(phy->u_phy.dev, "gpio %d not set to 0\n", |
618 | phy->reset_gpio); | ||
564 | return ret; | 619 | return ret; |
565 | } | 620 | } |
566 | msleep(5); | 621 | msleep(5); |
567 | ret = gpio_direction_output(phy->reset_gpio, 1); | 622 | ret = gpio_direction_output(phy->reset_gpio, 1); |
568 | if (ret < 0) { | 623 | if (ret < 0) { |
569 | dev_err(phy->dev, "gpio %d not set to 1\n", phy->reset_gpio); | 624 | dev_err(phy->u_phy.dev, "gpio %d not set to 1\n", |
625 | phy->reset_gpio); | ||
570 | return ret; | 626 | return ret; |
571 | } | 627 | } |
572 | 628 | ||
@@ -634,6 +690,9 @@ static void tegra_usb_phy_close(struct usb_phy *x) | |||
634 | { | 690 | { |
635 | struct tegra_usb_phy *phy = container_of(x, struct tegra_usb_phy, u_phy); | 691 | struct tegra_usb_phy *phy = container_of(x, struct tegra_usb_phy, u_phy); |
636 | 692 | ||
693 | if (!IS_ERR(phy->vbus)) | ||
694 | regulator_disable(phy->vbus); | ||
695 | |||
637 | clk_disable_unprepare(phy->pll_u); | 696 | clk_disable_unprepare(phy->pll_u); |
638 | } | 697 | } |
639 | 698 | ||
@@ -666,29 +725,30 @@ static int ulpi_open(struct tegra_usb_phy *phy) | |||
666 | { | 725 | { |
667 | int err; | 726 | int err; |
668 | 727 | ||
669 | phy->clk = devm_clk_get(phy->dev, "ulpi-link"); | 728 | phy->clk = devm_clk_get(phy->u_phy.dev, "ulpi-link"); |
670 | if (IS_ERR(phy->clk)) { | 729 | if (IS_ERR(phy->clk)) { |
671 | pr_err("%s: can't get ulpi clock\n", __func__); | 730 | pr_err("%s: can't get ulpi clock\n", __func__); |
672 | return PTR_ERR(phy->clk); | 731 | return PTR_ERR(phy->clk); |
673 | } | 732 | } |
674 | 733 | ||
675 | err = devm_gpio_request(phy->dev, phy->reset_gpio, "ulpi_phy_reset_b"); | 734 | err = devm_gpio_request(phy->u_phy.dev, phy->reset_gpio, |
735 | "ulpi_phy_reset_b"); | ||
676 | if (err < 0) { | 736 | if (err < 0) { |
677 | dev_err(phy->dev, "request failed for gpio: %d\n", | 737 | dev_err(phy->u_phy.dev, "request failed for gpio: %d\n", |
678 | phy->reset_gpio); | 738 | phy->reset_gpio); |
679 | return err; | 739 | return err; |
680 | } | 740 | } |
681 | 741 | ||
682 | err = gpio_direction_output(phy->reset_gpio, 0); | 742 | err = gpio_direction_output(phy->reset_gpio, 0); |
683 | if (err < 0) { | 743 | if (err < 0) { |
684 | dev_err(phy->dev, "gpio %d direction not set to output\n", | 744 | dev_err(phy->u_phy.dev, "gpio %d direction not set to output\n", |
685 | phy->reset_gpio); | 745 | phy->reset_gpio); |
686 | return err; | 746 | return err; |
687 | } | 747 | } |
688 | 748 | ||
689 | phy->ulpi = otg_ulpi_create(&ulpi_viewport_access_ops, 0); | 749 | phy->ulpi = otg_ulpi_create(&ulpi_viewport_access_ops, 0); |
690 | if (!phy->ulpi) { | 750 | if (!phy->ulpi) { |
691 | dev_err(phy->dev, "otg_ulpi_create returned NULL\n"); | 751 | dev_err(phy->u_phy.dev, "otg_ulpi_create returned NULL\n"); |
692 | err = -ENOMEM; | 752 | err = -ENOMEM; |
693 | return err; | 753 | return err; |
694 | } | 754 | } |
@@ -703,14 +763,7 @@ static int tegra_usb_phy_init(struct tegra_usb_phy *phy) | |||
703 | int i; | 763 | int i; |
704 | int err; | 764 | int err; |
705 | 765 | ||
706 | if (!phy->is_ulpi_phy) { | 766 | phy->pll_u = devm_clk_get(phy->u_phy.dev, "pll_u"); |
707 | if (phy->is_legacy_phy) | ||
708 | phy->config = &utmip_default[0]; | ||
709 | else | ||
710 | phy->config = &utmip_default[2]; | ||
711 | } | ||
712 | |||
713 | phy->pll_u = devm_clk_get(phy->dev, "pll_u"); | ||
714 | if (IS_ERR(phy->pll_u)) { | 767 | if (IS_ERR(phy->pll_u)) { |
715 | pr_err("Can't get pll_u clock\n"); | 768 | pr_err("Can't get pll_u clock\n"); |
716 | return PTR_ERR(phy->pll_u); | 769 | return PTR_ERR(phy->pll_u); |
@@ -733,6 +786,16 @@ static int tegra_usb_phy_init(struct tegra_usb_phy *phy) | |||
733 | goto fail; | 786 | goto fail; |
734 | } | 787 | } |
735 | 788 | ||
789 | if (!IS_ERR(phy->vbus)) { | ||
790 | err = regulator_enable(phy->vbus); | ||
791 | if (err) { | ||
792 | dev_err(phy->u_phy.dev, | ||
793 | "failed to enable usb vbus regulator: %d\n", | ||
794 | err); | ||
795 | goto fail; | ||
796 | } | ||
797 | } | ||
798 | |||
736 | if (phy->is_ulpi_phy) | 799 | if (phy->is_ulpi_phy) |
737 | err = ulpi_open(phy); | 800 | err = ulpi_open(phy); |
738 | else | 801 | else |
@@ -784,11 +847,138 @@ void tegra_ehci_phy_restore_end(struct usb_phy *x) | |||
784 | } | 847 | } |
785 | EXPORT_SYMBOL_GPL(tegra_ehci_phy_restore_end); | 848 | EXPORT_SYMBOL_GPL(tegra_ehci_phy_restore_end); |
786 | 849 | ||
850 | static int read_utmi_param(struct platform_device *pdev, const char *param, | ||
851 | u8 *dest) | ||
852 | { | ||
853 | u32 value; | ||
854 | int err = of_property_read_u32(pdev->dev.of_node, param, &value); | ||
855 | *dest = (u8)value; | ||
856 | if (err < 0) | ||
857 | dev_err(&pdev->dev, "Failed to read USB UTMI parameter %s: %d\n", | ||
858 | param, err); | ||
859 | return err; | ||
860 | } | ||
861 | |||
862 | static int utmi_phy_probe(struct tegra_usb_phy *tegra_phy, | ||
863 | struct platform_device *pdev) | ||
864 | { | ||
865 | struct resource *res; | ||
866 | int err; | ||
867 | struct tegra_utmip_config *config; | ||
868 | |||
869 | tegra_phy->is_ulpi_phy = false; | ||
870 | |||
871 | res = platform_get_resource(pdev, IORESOURCE_MEM, 1); | ||
872 | if (!res) { | ||
873 | dev_err(&pdev->dev, "Failed to get UTMI Pad regs\n"); | ||
874 | return -ENXIO; | ||
875 | } | ||
876 | |||
877 | tegra_phy->pad_regs = devm_ioremap(&pdev->dev, res->start, | ||
878 | resource_size(res)); | ||
879 | if (!tegra_phy->regs) { | ||
880 | dev_err(&pdev->dev, "Failed to remap UTMI Pad regs\n"); | ||
881 | return -ENOMEM; | ||
882 | } | ||
883 | |||
884 | tegra_phy->config = devm_kzalloc(&pdev->dev, | ||
885 | sizeof(*tegra_phy->config), GFP_KERNEL); | ||
886 | if (!tegra_phy->config) { | ||
887 | dev_err(&pdev->dev, | ||
888 | "unable to allocate memory for USB UTMIP config\n"); | ||
889 | return -ENOMEM; | ||
890 | } | ||
891 | |||
892 | config = tegra_phy->config; | ||
893 | |||
894 | err = read_utmi_param(pdev, "nvidia,hssync-start-delay", | ||
895 | &config->hssync_start_delay); | ||
896 | if (err < 0) | ||
897 | return err; | ||
898 | |||
899 | err = read_utmi_param(pdev, "nvidia,elastic-limit", | ||
900 | &config->elastic_limit); | ||
901 | if (err < 0) | ||
902 | return err; | ||
903 | |||
904 | err = read_utmi_param(pdev, "nvidia,idle-wait-delay", | ||
905 | &config->idle_wait_delay); | ||
906 | if (err < 0) | ||
907 | return err; | ||
908 | |||
909 | err = read_utmi_param(pdev, "nvidia,term-range-adj", | ||
910 | &config->term_range_adj); | ||
911 | if (err < 0) | ||
912 | return err; | ||
913 | |||
914 | err = read_utmi_param(pdev, "nvidia,xcvr-lsfslew", | ||
915 | &config->xcvr_lsfslew); | ||
916 | if (err < 0) | ||
917 | return err; | ||
918 | |||
919 | err = read_utmi_param(pdev, "nvidia,xcvr-lsrslew", | ||
920 | &config->xcvr_lsrslew); | ||
921 | if (err < 0) | ||
922 | return err; | ||
923 | |||
924 | if (tegra_phy->soc_config->requires_extra_tuning_parameters) { | ||
925 | err = read_utmi_param(pdev, "nvidia,xcvr-hsslew", | ||
926 | &config->xcvr_hsslew); | ||
927 | if (err < 0) | ||
928 | return err; | ||
929 | |||
930 | err = read_utmi_param(pdev, "nvidia,hssquelch-level", | ||
931 | &config->hssquelch_level); | ||
932 | if (err < 0) | ||
933 | return err; | ||
934 | |||
935 | err = read_utmi_param(pdev, "nvidia,hsdiscon-level", | ||
936 | &config->hsdiscon_level); | ||
937 | if (err < 0) | ||
938 | return err; | ||
939 | } | ||
940 | |||
941 | config->xcvr_setup_use_fuses = of_property_read_bool( | ||
942 | pdev->dev.of_node, "nvidia,xcvr-setup-use-fuses"); | ||
943 | |||
944 | if (!config->xcvr_setup_use_fuses) { | ||
945 | err = read_utmi_param(pdev, "nvidia,xcvr-setup", | ||
946 | &config->xcvr_setup); | ||
947 | if (err < 0) | ||
948 | return err; | ||
949 | } | ||
950 | |||
951 | return 0; | ||
952 | } | ||
953 | |||
954 | static const struct tegra_phy_soc_config tegra20_soc_config = { | ||
955 | .utmi_pll_config_in_car_module = false, | ||
956 | .has_hostpc = false, | ||
957 | .requires_usbmode_setup = false, | ||
958 | .requires_extra_tuning_parameters = false, | ||
959 | }; | ||
960 | |||
961 | static const struct tegra_phy_soc_config tegra30_soc_config = { | ||
962 | .utmi_pll_config_in_car_module = true, | ||
963 | .has_hostpc = true, | ||
964 | .requires_usbmode_setup = true, | ||
965 | .requires_extra_tuning_parameters = true, | ||
966 | }; | ||
967 | |||
968 | static struct of_device_id tegra_usb_phy_id_table[] = { | ||
969 | { .compatible = "nvidia,tegra30-usb-phy", .data = &tegra30_soc_config }, | ||
970 | { .compatible = "nvidia,tegra20-usb-phy", .data = &tegra20_soc_config }, | ||
971 | { }, | ||
972 | }; | ||
973 | MODULE_DEVICE_TABLE(of, tegra_usb_phy_id_table); | ||
974 | |||
787 | static int tegra_usb_phy_probe(struct platform_device *pdev) | 975 | static int tegra_usb_phy_probe(struct platform_device *pdev) |
788 | { | 976 | { |
977 | const struct of_device_id *match; | ||
789 | struct resource *res; | 978 | struct resource *res; |
790 | struct tegra_usb_phy *tegra_phy = NULL; | 979 | struct tegra_usb_phy *tegra_phy = NULL; |
791 | struct device_node *np = pdev->dev.of_node; | 980 | struct device_node *np = pdev->dev.of_node; |
981 | enum usb_phy_interface phy_type; | ||
792 | int err; | 982 | int err; |
793 | 983 | ||
794 | tegra_phy = devm_kzalloc(&pdev->dev, sizeof(*tegra_phy), GFP_KERNEL); | 984 | tegra_phy = devm_kzalloc(&pdev->dev, sizeof(*tegra_phy), GFP_KERNEL); |
@@ -797,6 +987,13 @@ static int tegra_usb_phy_probe(struct platform_device *pdev) | |||
797 | return -ENOMEM; | 987 | return -ENOMEM; |
798 | } | 988 | } |
799 | 989 | ||
990 | match = of_match_device(tegra_usb_phy_id_table, &pdev->dev); | ||
991 | if (!match) { | ||
992 | dev_err(&pdev->dev, "Error: No device match found\n"); | ||
993 | return -ENODEV; | ||
994 | } | ||
995 | tegra_phy->soc_config = match->data; | ||
996 | |||
800 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 997 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
801 | if (!res) { | 998 | if (!res) { |
802 | dev_err(&pdev->dev, "Failed to get I/O memory\n"); | 999 | dev_err(&pdev->dev, "Failed to get I/O memory\n"); |
@@ -813,23 +1010,15 @@ static int tegra_usb_phy_probe(struct platform_device *pdev) | |||
813 | tegra_phy->is_legacy_phy = | 1010 | tegra_phy->is_legacy_phy = |
814 | of_property_read_bool(np, "nvidia,has-legacy-mode"); | 1011 | of_property_read_bool(np, "nvidia,has-legacy-mode"); |
815 | 1012 | ||
816 | err = of_property_match_string(np, "phy_type", "ulpi"); | 1013 | phy_type = of_usb_get_phy_mode(np); |
817 | if (err < 0) { | 1014 | switch (phy_type) { |
818 | tegra_phy->is_ulpi_phy = false; | 1015 | case USBPHY_INTERFACE_MODE_UTMI: |
819 | 1016 | err = utmi_phy_probe(tegra_phy, pdev); | |
820 | res = platform_get_resource(pdev, IORESOURCE_MEM, 1); | 1017 | if (err < 0) |
821 | if (!res) { | 1018 | return err; |
822 | dev_err(&pdev->dev, "Failed to get UTMI Pad regs\n"); | 1019 | break; |
823 | return -ENXIO; | ||
824 | } | ||
825 | 1020 | ||
826 | tegra_phy->pad_regs = devm_ioremap(&pdev->dev, res->start, | 1021 | case USBPHY_INTERFACE_MODE_ULPI: |
827 | resource_size(res)); | ||
828 | if (!tegra_phy->regs) { | ||
829 | dev_err(&pdev->dev, "Failed to remap UTMI Pad regs\n"); | ||
830 | return -ENOMEM; | ||
831 | } | ||
832 | } else { | ||
833 | tegra_phy->is_ulpi_phy = true; | 1022 | tegra_phy->is_ulpi_phy = true; |
834 | 1023 | ||
835 | tegra_phy->reset_gpio = | 1024 | tegra_phy->reset_gpio = |
@@ -839,19 +1028,35 @@ static int tegra_usb_phy_probe(struct platform_device *pdev) | |||
839 | tegra_phy->reset_gpio); | 1028 | tegra_phy->reset_gpio); |
840 | return tegra_phy->reset_gpio; | 1029 | return tegra_phy->reset_gpio; |
841 | } | 1030 | } |
1031 | tegra_phy->config = NULL; | ||
1032 | break; | ||
1033 | |||
1034 | default: | ||
1035 | dev_err(&pdev->dev, "phy_type is invalid or unsupported\n"); | ||
1036 | return -EINVAL; | ||
842 | } | 1037 | } |
843 | 1038 | ||
844 | err = of_property_match_string(np, "dr_mode", "otg"); | 1039 | if (of_find_property(np, "dr_mode", NULL)) |
845 | if (err < 0) { | 1040 | tegra_phy->mode = of_usb_get_dr_mode(np); |
846 | err = of_property_match_string(np, "dr_mode", "peripheral"); | 1041 | else |
847 | if (err < 0) | 1042 | tegra_phy->mode = USB_DR_MODE_HOST; |
848 | tegra_phy->mode = TEGRA_USB_PHY_MODE_HOST; | ||
849 | else | ||
850 | tegra_phy->mode = TEGRA_USB_PHY_MODE_DEVICE; | ||
851 | } else | ||
852 | tegra_phy->mode = TEGRA_USB_PHY_MODE_OTG; | ||
853 | 1043 | ||
854 | tegra_phy->dev = &pdev->dev; | 1044 | if (tegra_phy->mode == USB_DR_MODE_UNKNOWN) { |
1045 | dev_err(&pdev->dev, "dr_mode is invalid\n"); | ||
1046 | return -EINVAL; | ||
1047 | } | ||
1048 | |||
1049 | /* On some boards, the VBUS regulator doesn't need to be controlled */ | ||
1050 | if (of_find_property(np, "vbus-supply", NULL)) { | ||
1051 | tegra_phy->vbus = devm_regulator_get(&pdev->dev, "vbus"); | ||
1052 | if (IS_ERR(tegra_phy->vbus)) | ||
1053 | return PTR_ERR(tegra_phy->vbus); | ||
1054 | } else { | ||
1055 | dev_notice(&pdev->dev, "no vbus regulator"); | ||
1056 | tegra_phy->vbus = ERR_PTR(-ENODEV); | ||
1057 | } | ||
1058 | |||
1059 | tegra_phy->u_phy.dev = &pdev->dev; | ||
855 | err = tegra_usb_phy_init(tegra_phy); | 1060 | err = tegra_usb_phy_init(tegra_phy); |
856 | if (err < 0) | 1061 | if (err < 0) |
857 | return err; | 1062 | return err; |
@@ -860,17 +1065,28 @@ static int tegra_usb_phy_probe(struct platform_device *pdev) | |||
860 | tegra_phy->u_phy.set_suspend = tegra_usb_phy_suspend; | 1065 | tegra_phy->u_phy.set_suspend = tegra_usb_phy_suspend; |
861 | 1066 | ||
862 | dev_set_drvdata(&pdev->dev, tegra_phy); | 1067 | dev_set_drvdata(&pdev->dev, tegra_phy); |
1068 | |||
1069 | err = usb_add_phy_dev(&tegra_phy->u_phy); | ||
1070 | if (err < 0) { | ||
1071 | tegra_usb_phy_close(&tegra_phy->u_phy); | ||
1072 | return err; | ||
1073 | } | ||
1074 | |||
863 | return 0; | 1075 | return 0; |
864 | } | 1076 | } |
865 | 1077 | ||
866 | static struct of_device_id tegra_usb_phy_id_table[] = { | 1078 | static int tegra_usb_phy_remove(struct platform_device *pdev) |
867 | { .compatible = "nvidia,tegra20-usb-phy", }, | 1079 | { |
868 | { }, | 1080 | struct tegra_usb_phy *tegra_phy = platform_get_drvdata(pdev); |
869 | }; | 1081 | |
870 | MODULE_DEVICE_TABLE(of, tegra_usb_phy_id_table); | 1082 | usb_remove_phy(&tegra_phy->u_phy); |
1083 | |||
1084 | return 0; | ||
1085 | } | ||
871 | 1086 | ||
872 | static struct platform_driver tegra_usb_phy_driver = { | 1087 | static struct platform_driver tegra_usb_phy_driver = { |
873 | .probe = tegra_usb_phy_probe, | 1088 | .probe = tegra_usb_phy_probe, |
1089 | .remove = tegra_usb_phy_remove, | ||
874 | .driver = { | 1090 | .driver = { |
875 | .name = "tegra-phy", | 1091 | .name = "tegra-phy", |
876 | .owner = THIS_MODULE, | 1092 | .owner = THIS_MODULE, |
@@ -879,29 +1095,5 @@ static struct platform_driver tegra_usb_phy_driver = { | |||
879 | }; | 1095 | }; |
880 | module_platform_driver(tegra_usb_phy_driver); | 1096 | module_platform_driver(tegra_usb_phy_driver); |
881 | 1097 | ||
882 | static int tegra_usb_phy_match(struct device *dev, void *data) | ||
883 | { | ||
884 | struct tegra_usb_phy *tegra_phy = dev_get_drvdata(dev); | ||
885 | struct device_node *dn = data; | ||
886 | |||
887 | return (tegra_phy->dev->of_node == dn) ? 1 : 0; | ||
888 | } | ||
889 | |||
890 | struct usb_phy *tegra_usb_get_phy(struct device_node *dn) | ||
891 | { | ||
892 | struct device *dev; | ||
893 | struct tegra_usb_phy *tegra_phy; | ||
894 | |||
895 | dev = driver_find_device(&tegra_usb_phy_driver.driver, NULL, dn, | ||
896 | tegra_usb_phy_match); | ||
897 | if (!dev) | ||
898 | return ERR_PTR(-EPROBE_DEFER); | ||
899 | |||
900 | tegra_phy = dev_get_drvdata(dev); | ||
901 | |||
902 | return &tegra_phy->u_phy; | ||
903 | } | ||
904 | EXPORT_SYMBOL_GPL(tegra_usb_get_phy); | ||
905 | |||
906 | MODULE_DESCRIPTION("Tegra USB PHY driver"); | 1098 | MODULE_DESCRIPTION("Tegra USB PHY driver"); |
907 | MODULE_LICENSE("GPL v2"); | 1099 | MODULE_LICENSE("GPL v2"); |
diff --git a/drivers/usb/phy/phy-twl4030-usb.c b/drivers/usb/phy/phy-twl4030-usb.c index 8f78d2d40722..90730c8762b8 100644 --- a/drivers/usb/phy/phy-twl4030-usb.c +++ b/drivers/usb/phy/phy-twl4030-usb.c | |||
@@ -648,7 +648,7 @@ static int twl4030_set_host(struct usb_otg *otg, struct usb_bus *host) | |||
648 | 648 | ||
649 | static int twl4030_usb_probe(struct platform_device *pdev) | 649 | static int twl4030_usb_probe(struct platform_device *pdev) |
650 | { | 650 | { |
651 | struct twl4030_usb_data *pdata = pdev->dev.platform_data; | 651 | struct twl4030_usb_data *pdata = dev_get_platdata(&pdev->dev); |
652 | struct twl4030_usb *twl; | 652 | struct twl4030_usb *twl; |
653 | int status, err; | 653 | int status, err; |
654 | struct usb_otg *otg; | 654 | struct usb_otg *otg; |
diff --git a/drivers/usb/phy/phy-twl6030-usb.c b/drivers/usb/phy/phy-twl6030-usb.c index 1753bd367e0a..16dbc9382678 100644 --- a/drivers/usb/phy/phy-twl6030-usb.c +++ b/drivers/usb/phy/phy-twl6030-usb.c | |||
@@ -324,7 +324,7 @@ static int twl6030_usb_probe(struct platform_device *pdev) | |||
324 | int status, err; | 324 | int status, err; |
325 | struct device_node *np = pdev->dev.of_node; | 325 | struct device_node *np = pdev->dev.of_node; |
326 | struct device *dev = &pdev->dev; | 326 | struct device *dev = &pdev->dev; |
327 | struct twl4030_usb_data *pdata = dev->platform_data; | 327 | struct twl4030_usb_data *pdata = dev_get_platdata(dev); |
328 | 328 | ||
329 | twl = devm_kzalloc(dev, sizeof *twl, GFP_KERNEL); | 329 | twl = devm_kzalloc(dev, sizeof *twl, GFP_KERNEL); |
330 | if (!twl) | 330 | if (!twl) |