forked from ~ljy/RK356X_SDK_RELEASE

hc
2024-05-13 9d77db3c730780c8ef5ccd4b66403ff5675cfe4e
kernel/drivers/usb/host/ohci-omap.c
....@@ -18,7 +18,7 @@
1818 #include <linux/clk.h>
1919 #include <linux/dma-mapping.h>
2020 #include <linux/err.h>
21
-#include <linux/gpio.h>
21
+#include <linux/gpio/consumer.h>
2222 #include <linux/io.h>
2323 #include <linux/jiffies.h>
2424 #include <linux/kernel.h>
....@@ -53,38 +53,29 @@
5353
5454 #define DRIVER_DESC "OHCI OMAP driver"
5555
56
-#ifdef CONFIG_TPS65010
57
-#include <linux/mfd/tps65010.h>
58
-#else
59
-
60
-#define LOW 0
61
-#define HIGH 1
62
-
63
-#define GPIO1 1
64
-
65
-static inline int tps65010_set_gpio_out_value(unsigned gpio, unsigned value)
66
-{
67
- return 0;
68
-}
69
-
70
-#endif
71
-
72
-static struct clk *usb_host_ck;
73
-static struct clk *usb_dc_ck;
56
+struct ohci_omap_priv {
57
+ struct clk *usb_host_ck;
58
+ struct clk *usb_dc_ck;
59
+ struct gpio_desc *power;
60
+ struct gpio_desc *overcurrent;
61
+};
7462
7563 static const char hcd_name[] = "ohci-omap";
7664 static struct hc_driver __read_mostly ohci_omap_hc_driver;
7765
78
-static void omap_ohci_clock_power(int on)
66
+#define hcd_to_ohci_omap_priv(h) \
67
+ ((struct ohci_omap_priv *)hcd_to_ohci(h)->priv)
68
+
69
+static void omap_ohci_clock_power(struct ohci_omap_priv *priv, int on)
7970 {
8071 if (on) {
81
- clk_enable(usb_dc_ck);
82
- clk_enable(usb_host_ck);
72
+ clk_enable(priv->usb_dc_ck);
73
+ clk_enable(priv->usb_host_ck);
8374 /* guesstimate for T5 == 1x 32K clock + APLL lock time */
8475 udelay(100);
8576 } else {
86
- clk_disable(usb_host_ck);
87
- clk_disable(usb_dc_ck);
77
+ clk_disable(priv->usb_host_ck);
78
+ clk_disable(priv->usb_dc_ck);
8879 }
8980 }
9081
....@@ -92,22 +83,22 @@
9283 * Board specific gang-switched transceiver power on/off.
9384 * NOTE: OSK supplies power from DC, not battery.
9485 */
95
-static int omap_ohci_transceiver_power(int on)
86
+static int omap_ohci_transceiver_power(struct ohci_omap_priv *priv, int on)
9687 {
9788 if (on) {
9889 if (machine_is_omap_innovator() && cpu_is_omap1510())
9990 __raw_writeb(__raw_readb(INNOVATOR_FPGA_CAM_USB_CONTROL)
10091 | ((1 << 5/*usb1*/) | (1 << 3/*usb2*/)),
10192 INNOVATOR_FPGA_CAM_USB_CONTROL);
102
- else if (machine_is_omap_osk())
103
- tps65010_set_gpio_out_value(GPIO1, LOW);
93
+ else if (priv->power)
94
+ gpiod_set_value_cansleep(priv->power, 0);
10495 } else {
10596 if (machine_is_omap_innovator() && cpu_is_omap1510())
10697 __raw_writeb(__raw_readb(INNOVATOR_FPGA_CAM_USB_CONTROL)
10798 & ~((1 << 5/*usb1*/) | (1 << 3/*usb2*/)),
10899 INNOVATOR_FPGA_CAM_USB_CONTROL);
109
- else if (machine_is_omap_osk())
110
- tps65010_set_gpio_out_value(GPIO1, HIGH);
100
+ else if (priv->power)
101
+ gpiod_set_value_cansleep(priv->power, 1);
111102 }
112103
113104 return 0;
....@@ -196,6 +187,7 @@
196187 {
197188 struct ohci_hcd *ohci = hcd_to_ohci(hcd);
198189 struct omap_usb_config *config = dev_get_platdata(hcd->self.controller);
190
+ struct ohci_omap_priv *priv = hcd_to_ohci_omap_priv(hcd);
199191 int need_transceiver = (config->otg != 0);
200192 int ret;
201193
....@@ -235,7 +227,7 @@
235227 }
236228 #endif
237229
238
- omap_ohci_clock_power(1);
230
+ omap_ohci_clock_power(priv, 1);
239231
240232 if (cpu_is_omap15xx()) {
241233 omap_1510_local_bus_power(1);
....@@ -266,8 +258,6 @@
266258
267259 /* gpio9 for overcurrent detction */
268260 omap_cfg_reg(W8_1610_GPIO9);
269
- gpio_request(9, "OHCI overcurrent");
270
- gpio_direction_input(9);
271261
272262 /* for paranoia's sake: disable USB.PUEN */
273263 omap_cfg_reg(W4_USB_HIGHZ);
....@@ -281,7 +271,7 @@
281271 }
282272
283273 /* FIXME hub_wq hub requests should manage power switching */
284
- omap_ohci_transceiver_power(1);
274
+ omap_ohci_transceiver_power(priv, 1);
285275
286276 /* board init will have already handled HMC and mux setup.
287277 * any external transceiver should already be initialized
....@@ -305,6 +295,7 @@
305295 {
306296 int retval, irq;
307297 struct usb_hcd *hcd = 0;
298
+ struct ohci_omap_priv *priv;
308299
309300 if (pdev->num_resources != 2) {
310301 dev_err(&pdev->dev, "invalid num_resources: %i\n",
....@@ -318,34 +309,58 @@
318309 return -ENODEV;
319310 }
320311
321
- usb_host_ck = clk_get(&pdev->dev, "usb_hhc_ck");
322
- if (IS_ERR(usb_host_ck))
323
- return PTR_ERR(usb_host_ck);
324
-
325
- if (!cpu_is_omap15xx())
326
- usb_dc_ck = clk_get(&pdev->dev, "usb_dc_ck");
327
- else
328
- usb_dc_ck = clk_get(&pdev->dev, "lb_ck");
329
-
330
- if (IS_ERR(usb_dc_ck)) {
331
- clk_put(usb_host_ck);
332
- return PTR_ERR(usb_dc_ck);
333
- }
334
-
335
-
336312 hcd = usb_create_hcd(&ohci_omap_hc_driver, &pdev->dev,
337313 dev_name(&pdev->dev));
338
- if (!hcd) {
339
- retval = -ENOMEM;
340
- goto err0;
341
- }
314
+ if (!hcd)
315
+ return -ENOMEM;
316
+
342317 hcd->rsrc_start = pdev->resource[0].start;
343318 hcd->rsrc_len = pdev->resource[0].end - pdev->resource[0].start + 1;
319
+ priv = hcd_to_ohci_omap_priv(hcd);
320
+
321
+ /* Obtain two optional GPIO lines */
322
+ priv->power = devm_gpiod_get_optional(&pdev->dev, "power", GPIOD_ASIS);
323
+ if (IS_ERR(priv->power)) {
324
+ retval = PTR_ERR(priv->power);
325
+ goto err_put_hcd;
326
+ }
327
+ if (priv->power)
328
+ gpiod_set_consumer_name(priv->power, "OHCI power");
329
+
330
+ /*
331
+ * This "overcurrent" GPIO line isn't really used in the code,
332
+ * but has a designated hardware function.
333
+ * TODO: implement proper overcurrent handling.
334
+ */
335
+ priv->overcurrent = devm_gpiod_get_optional(&pdev->dev, "overcurrent",
336
+ GPIOD_IN);
337
+ if (IS_ERR(priv->overcurrent)) {
338
+ retval = PTR_ERR(priv->overcurrent);
339
+ goto err_put_hcd;
340
+ }
341
+ if (priv->overcurrent)
342
+ gpiod_set_consumer_name(priv->overcurrent, "OHCI overcurrent");
343
+
344
+ priv->usb_host_ck = clk_get(&pdev->dev, "usb_hhc_ck");
345
+ if (IS_ERR(priv->usb_host_ck)) {
346
+ retval = PTR_ERR(priv->usb_host_ck);
347
+ goto err_put_hcd;
348
+ }
349
+
350
+ if (!cpu_is_omap15xx())
351
+ priv->usb_dc_ck = clk_get(&pdev->dev, "usb_dc_ck");
352
+ else
353
+ priv->usb_dc_ck = clk_get(&pdev->dev, "lb_ck");
354
+
355
+ if (IS_ERR(priv->usb_dc_ck)) {
356
+ retval = PTR_ERR(priv->usb_dc_ck);
357
+ goto err_put_host_ck;
358
+ }
344359
345360 if (!request_mem_region(hcd->rsrc_start, hcd->rsrc_len, hcd_name)) {
346361 dev_dbg(&pdev->dev, "request_mem_region failed\n");
347362 retval = -EBUSY;
348
- goto err1;
363
+ goto err_put_dc_ck;
349364 }
350365
351366 hcd->regs = ioremap(hcd->rsrc_start, hcd->rsrc_len);
....@@ -370,11 +385,12 @@
370385 iounmap(hcd->regs);
371386 err2:
372387 release_mem_region(hcd->rsrc_start, hcd->rsrc_len);
373
-err1:
388
+err_put_dc_ck:
389
+ clk_put(priv->usb_dc_ck);
390
+err_put_host_ck:
391
+ clk_put(priv->usb_host_ck);
392
+err_put_hcd:
374393 usb_put_hcd(hcd);
375
-err0:
376
- clk_put(usb_dc_ck);
377
- clk_put(usb_host_ck);
378394 return retval;
379395 }
380396
....@@ -393,21 +409,20 @@
393409 static int ohci_hcd_omap_remove(struct platform_device *pdev)
394410 {
395411 struct usb_hcd *hcd = platform_get_drvdata(pdev);
412
+ struct ohci_omap_priv *priv = hcd_to_ohci_omap_priv(hcd);
396413
397414 dev_dbg(hcd->self.controller, "stopping USB Controller\n");
398415 usb_remove_hcd(hcd);
399
- omap_ohci_clock_power(0);
416
+ omap_ohci_clock_power(priv, 0);
400417 if (!IS_ERR_OR_NULL(hcd->usb_phy)) {
401418 (void) otg_set_host(hcd->usb_phy->otg, 0);
402419 usb_put_phy(hcd->usb_phy);
403420 }
404
- if (machine_is_omap_osk())
405
- gpio_free(9);
406421 iounmap(hcd->regs);
407422 release_mem_region(hcd->rsrc_start, hcd->rsrc_len);
423
+ clk_put(priv->usb_dc_ck);
424
+ clk_put(priv->usb_host_ck);
408425 usb_put_hcd(hcd);
409
- clk_put(usb_dc_ck);
410
- clk_put(usb_host_ck);
411426 return 0;
412427 }
413428
....@@ -419,6 +434,7 @@
419434 {
420435 struct usb_hcd *hcd = platform_get_drvdata(pdev);
421436 struct ohci_hcd *ohci = hcd_to_ohci(hcd);
437
+ struct ohci_omap_priv *priv = hcd_to_ohci_omap_priv(hcd);
422438 bool do_wakeup = device_may_wakeup(&pdev->dev);
423439 int ret;
424440
....@@ -430,7 +446,7 @@
430446 if (ret)
431447 return ret;
432448
433
- omap_ohci_clock_power(0);
449
+ omap_ohci_clock_power(priv, 0);
434450 return ret;
435451 }
436452
....@@ -438,12 +454,13 @@
438454 {
439455 struct usb_hcd *hcd = platform_get_drvdata(dev);
440456 struct ohci_hcd *ohci = hcd_to_ohci(hcd);
457
+ struct ohci_omap_priv *priv = hcd_to_ohci_omap_priv(hcd);
441458
442459 if (time_before(jiffies, ohci->next_statechange))
443460 msleep(5);
444461 ohci->next_statechange = jiffies;
445462
446
- omap_ohci_clock_power(1);
463
+ omap_ohci_clock_power(priv, 1);
447464 ohci_resume(hcd, false);
448465 return 0;
449466 }
....@@ -470,7 +487,8 @@
470487
471488 static const struct ohci_driver_overrides omap_overrides __initconst = {
472489 .product_desc = "OMAP OHCI",
473
- .reset = ohci_omap_reset
490
+ .reset = ohci_omap_reset,
491
+ .extra_priv_size = sizeof(struct ohci_omap_priv),
474492 };
475493
476494 static int __init ohci_omap_init(void)