The forthcoming octeon-hcd USB driver (currently in staging) needs to be converted into a proper platform device. Before we can do that we need to register the device in OCTEON platform setup, so that e.g. EdgeRouter Lite users continue to have a working USB. Signed-off-by: Aaro Koskinen <aaro.koskinen@xxxxxx> --- arch/mips/cavium-octeon/octeon-platform.c | 58 +++++++++++++++++++++++++++++++ 1 file changed, 58 insertions(+) diff --git a/arch/mips/cavium-octeon/octeon-platform.c b/arch/mips/cavium-octeon/octeon-platform.c index 1830874..6d01582 100644 --- a/arch/mips/cavium-octeon/octeon-platform.c +++ b/arch/mips/cavium-octeon/octeon-platform.c @@ -166,6 +166,64 @@ out: } device_initcall(octeon_ohci_device_init); +static int __init octeon_hcd_device_init(void) +{ + struct resource usb_res; + struct platform_device *pdev; + + if (!(OCTEON_IS_MODEL(OCTEON_CN56XX) || + OCTEON_IS_MODEL(OCTEON_CN52XX) || + OCTEON_IS_MODEL(OCTEON_CN50XX) || + OCTEON_IS_MODEL(OCTEON_CN31XX) || + OCTEON_IS_MODEL(OCTEON_CN30XX))) + return 0; + + if (octeon_is_simulation() || usb_disabled()) + return 0; + + /* + * Only CN52XX and CN56XX have DWC_OTG USB hardware and the IOB priority + * registers. Under heavy network load USB hardware can be starved by + * the IOB causing a crash. Give it a priority boost if it has been + * waiting more than 400 cycles to avoid this situation. + * + * Testing indicates that a cnt_val of 8192 is not sufficient, but no + * failures are seen with 4096. We choose a value of 400 to give a + * safety factor of 10. + */ + if (OCTEON_IS_MODEL(OCTEON_CN52XX) || OCTEON_IS_MODEL(OCTEON_CN56XX)) { + union cvmx_iob_n2c_l2c_pri_cnt pri_cnt; + + pri_cnt.u64 = 0; + pri_cnt.s.cnt_enb = 1; + pri_cnt.s.cnt_val = 400; + cvmx_write_csr(CVMX_IOB_N2C_L2C_PRI_CNT, pri_cnt.u64); + } + + memset(&usb_res, 0, sizeof(usb_res)); + usb_res.start = OCTEON_IRQ_USB0; + usb_res.end = OCTEON_IRQ_USB0; + usb_res.flags = IORESOURCE_IRQ; + pdev = platform_device_register_simple("octeon-hcd", 0, &usb_res, 1); + if (IS_ERR(pdev)) + return PTR_ERR(pdev); + + /* For all chips except CN52XX there is only one port. */ + if (!OCTEON_IS_MODEL(OCTEON_CN52XX)) + return 0; + + memset(&usb_res, 0, sizeof(usb_res)); + usb_res.start = OCTEON_IRQ_USB1; + usb_res.end = OCTEON_IRQ_USB1; + usb_res.flags = IORESOURCE_IRQ; + pdev = platform_device_register_simple("octeon-hcd", 1, &usb_res, 1); + if (IS_ERR(pdev)) + return PTR_ERR(pdev); + + return 0; +} +device_initcall(octeon_hcd_device_init); + #endif /* CONFIG_USB */ static struct of_device_id __initdata octeon_ids[] = { -- 1.8.4.rc3