// SPDX-License-Identifier: GPL-2.0 /* * Glue code for the ISP1760 driver and bus * Currently there is support for * - OpenFirmware * - PCI * - PDEV (generic platform device centralized driver model) * * (c) 2007 Sebastian Siewior <bigeasy@linutronix.de> * Copyright 2021 Linaro, Rui Miguel Silva <rui.silva@linaro.org> *
*/
/* Grab the PLX PCI shared memory of the ISP 1761 we need */
mem_start = pci_resource_start(dev, 3);
mem_length = pci_resource_len(dev, 3); if (mem_length < 0xffff) {
printk(KERN_ERR "memory length for this resource is wrong\n"); return -ENOMEM;
}
if (!request_mem_region(mem_start, mem_length, "ISP-PCI")) {
printk(KERN_ERR "host controller already in use\n"); return -EBUSY;
}
/* bad pci latencies can contribute to overruns */
pci_read_config_byte(dev, PCI_LATENCY_TIMER, &latency); if (latency) {
pci_read_config_byte(dev, PCI_MAX_LAT, &limit); if (limit && limit < latency)
pci_write_config_byte(dev, PCI_LATENCY_TIMER, limit);
}
/* Try to check whether we can access Scratch Register of * Host Controller or not. The initial PCI access is retried until * local init for the PCI bridge is completed
*/
retry_count = 20;
reg_data = 0; while ((reg_data != 0xFACE) && retry_count) { /*by default host is in 16bit mode, so * io operations at this stage must be 16 bit
* */
writel(0xface, iobase + ISP176x_HC_SCRATCH);
udelay(100);
reg_data = readl(iobase + ISP176x_HC_SCRATCH) & 0x0000ffff;
retry_count--;
}
/* Host Controller presence is detected by writing to scratch register * and reading back and checking the contents are same or not
*/ if (reg_data != 0xFACE) {
dev_err(&dev->dev, "scratch register mismatch %x\n", reg_data); return -ENOMEM;
}
/* Grab the PLX PCI mem maped port start address we need */
mem_start = pci_resource_start(dev, 0);
mem_length = pci_resource_len(dev, 0);
if (!request_mem_region(mem_start, mem_length, "ISP1761 IO MEM")) {
printk(KERN_ERR "request region #1\n"); return -EBUSY;
}
if (of_device_is_compatible(dp, "nxp,usb-isp1761"))
devflags |= ISP1760_FLAG_ISP1761;
if (of_device_is_compatible(dp, "nxp,usb-isp1763"))
devflags |= ISP1760_FLAG_ISP1763;
/* * Some systems wire up only 8 of 16 data lines or * 16 of the 32 data lines
*/
of_property_read_u32(dp, "bus-width", &bus_width); if (bus_width == 16)
devflags |= ISP1760_FLAG_BUS_WIDTH_16; elseif (bus_width == 8)
devflags |= ISP1760_FLAG_BUS_WIDTH_8;
if (usb_get_dr_mode(&pdev->dev) == USB_DR_MODE_PERIPHERAL)
devflags |= ISP1760_FLAG_PERIPHERAL_EN;
if (of_property_read_bool(dp, "analog-oc"))
devflags |= ISP1760_FLAG_ANALOG_OC;
if (of_property_read_bool(dp, "dack-polarity"))
devflags |= ISP1760_FLAG_DACK_POL_HIGH;
if (of_property_read_bool(dp, "dreq-polarity"))
devflags |= ISP1760_FLAG_DREQ_POL_HIGH;
} else {
pr_err("isp1760: no platform data\n"); return -ENXIO;
}
ret = isp1760_register(mem_res, irq, irqflags, &pdev->dev, devflags); if (ret < 0) return ret;
pr_info("ISP1760 USB device initialised\n"); return 0;
}
staticint __init isp1760_init(void)
{ int ret, any_ret = -ENODEV;
isp1760_init_kmem_once();
ret = platform_driver_register(&isp1760_plat_driver); if (!ret)
any_ret = 0; #ifdef CONFIG_USB_PCI
ret = pci_register_driver(&isp1761_pci_driver); if (!ret)
any_ret = 0; #endif
if (any_ret)
isp1760_deinit_kmem_cache(); return any_ret;
}
module_init(isp1760_init);
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.