Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

MIPS: cavium-octeon: fix I/O space setup on non-PCI systems

Fix I/O space setup, so that on non-PCI systems using inb()/outb()
won't crash the system. Some drivers may try to probe I/O space and for
that purpose we can just allocate some normal memory initially. Drivers
trying to reserve a region will fail early as we set the size to 0. If
a real I/O space is present, the PCI/PCIe support code will re-adjust
the values accordingly.

Tested with EdgeRouter Lite by enabling CONFIG_SERIO_I8042 that caused
the originally reported crash.

Reported-by: Faidon Liambotis <paravoid@debian.org>
Signed-off-by: Aaro Koskinen <aaro.koskinen@iki.fi>
Acked-by: David Daney <david.daney@cavium.com>
Cc: linux-mips@linux-mips.org
Patchwork: https://patchwork.linux-mips.org/patch/5626/
Signed-off-by: Ralf Baechle <ralf@linux-mips.org>

authored by

Aaro Koskinen and committed by
Ralf Baechle
d8b74276 83eefabf

+33 -4
+28
arch/mips/cavium-octeon/setup.c
··· 8 8 * written by Ralf Baechle <ralf@linux-mips.org> 9 9 */ 10 10 #include <linux/compiler.h> 11 + #include <linux/vmalloc.h> 11 12 #include <linux/init.h> 12 13 #include <linux/kernel.h> 13 14 #include <linux/console.h> ··· 1140 1139 return err; 1141 1140 } 1142 1141 device_initcall(edac_devinit); 1142 + 1143 + static void __initdata *octeon_dummy_iospace; 1144 + 1145 + static int __init octeon_no_pci_init(void) 1146 + { 1147 + /* 1148 + * Initially assume there is no PCI. The PCI/PCIe platform code will 1149 + * later re-initialize these to correct values if they are present. 1150 + */ 1151 + octeon_dummy_iospace = vzalloc(IO_SPACE_LIMIT); 1152 + set_io_port_base((unsigned long)octeon_dummy_iospace); 1153 + ioport_resource.start = MAX_RESOURCE; 1154 + ioport_resource.end = 0; 1155 + return 0; 1156 + } 1157 + core_initcall(octeon_no_pci_init); 1158 + 1159 + static int __init octeon_no_pci_release(void) 1160 + { 1161 + /* 1162 + * Release the allocated memory if a real IO space is there. 1163 + */ 1164 + if ((unsigned long)octeon_dummy_iospace != mips_io_port_base) 1165 + vfree(octeon_dummy_iospace); 1166 + return 0; 1167 + } 1168 + late_initcall(octeon_no_pci_release);
+5 -4
arch/mips/pci/pci-octeon.c
··· 586 586 else 587 587 octeon_dma_bar_type = OCTEON_DMA_BAR_TYPE_BIG; 588 588 589 - /* PCI I/O and PCI MEM values */ 590 - set_io_port_base(OCTEON_PCI_IOSPACE_BASE); 591 - ioport_resource.start = 0; 592 - ioport_resource.end = OCTEON_PCI_IOSPACE_SIZE - 1; 593 589 if (!octeon_is_pci_host()) { 594 590 pr_notice("Not in host mode, PCI Controller not initialized\n"); 595 591 return 0; 596 592 } 593 + 594 + /* PCI I/O and PCI MEM values */ 595 + set_io_port_base(OCTEON_PCI_IOSPACE_BASE); 596 + ioport_resource.start = 0; 597 + ioport_resource.end = OCTEON_PCI_IOSPACE_SIZE - 1; 597 598 598 599 pr_notice("%s Octeon big bar support\n", 599 600 (octeon_dma_bar_type ==