1 // SPDX-License-Identifier: GPL-2.0-or-later 2 /* 3 * Corenet based SoC DS Setup 4 * 5 * Maintained by Kumar Gala (see MAINTAINERS for contact information) 6 * 7 * Copyright 2009-2011 Freescale Semiconductor Inc. 8 */ 9 10 #include <linux/kernel.h> 11 #include <linux/pci.h> 12 #include <linux/kdev_t.h> 13 #include <linux/delay.h> 14 #include <linux/interrupt.h> 15 16 #include <asm/time.h> 17 #include <asm/machdep.h> 18 #include <asm/pci-bridge.h> 19 #include <asm/pgtable.h> 20 #include <asm/ppc-pci.h> 21 #include <mm/mmu_decl.h> 22 #include <asm/prom.h> 23 #include <asm/udbg.h> 24 #include <asm/mpic.h> 25 #include <asm/ehv_pic.h> 26 #include <asm/swiotlb.h> 27 #include <soc/fsl/qe/qe_ic.h> 28 29 #include <linux/of_platform.h> 30 #include <sysdev/fsl_soc.h> 31 #include <sysdev/fsl_pci.h> 32 #include "smp.h" 33 #include "mpc85xx.h" 34 35 void __init corenet_gen_pic_init(void) 36 { 37 struct mpic *mpic; 38 unsigned int flags = MPIC_BIG_ENDIAN | MPIC_SINGLE_DEST_CPU | 39 MPIC_NO_RESET; 40 41 struct device_node *np; 42 43 if (ppc_md.get_irq == mpic_get_coreint_irq) 44 flags |= MPIC_ENABLE_COREINT; 45 46 mpic = mpic_alloc(NULL, 0, flags, 0, 512, " OpenPIC "); 47 BUG_ON(mpic == NULL); 48 49 mpic_init(mpic); 50 51 np = of_find_compatible_node(NULL, NULL, "fsl,qe-ic"); 52 if (np) { 53 qe_ic_init(np, 0, qe_ic_cascade_low_mpic, 54 qe_ic_cascade_high_mpic); 55 of_node_put(np); 56 } 57 } 58 59 /* 60 * Setup the architecture 61 */ 62 void __init corenet_gen_setup_arch(void) 63 { 64 mpc85xx_smp_init(); 65 66 swiotlb_detect_4g(); 67 68 pr_info("%s board\n", ppc_md.name); 69 70 mpc85xx_qe_init(); 71 } 72 73 static const struct of_device_id of_device_ids[] = { 74 { 75 .compatible = "simple-bus" 76 }, 77 { 78 .compatible = "mdio-mux-gpio" 79 }, 80 { 81 .compatible = "fsl,fpga-ngpixis" 82 }, 83 { 84 .compatible = "fsl,fpga-qixis" 85 }, 86 { 87 .compatible = "fsl,srio", 88 }, 89 { 90 .compatible = "fsl,p4080-pcie", 91 }, 92 { 93 .compatible = "fsl,qoriq-pcie-v2.2", 94 }, 95 { 96 .compatible = "fsl,qoriq-pcie-v2.3", 97 }, 98 { 99 .compatible = "fsl,qoriq-pcie-v2.4", 100 }, 101 { 102 .compatible = "fsl,qoriq-pcie-v3.0", 103 }, 104 { 105 .compatible = "fsl,qe", 106 }, 107 /* The following two are for the Freescale hypervisor */ 108 { 109 .name = "hypervisor", 110 }, 111 { 112 .name = "handles", 113 }, 114 {} 115 }; 116 117 int __init corenet_gen_publish_devices(void) 118 { 119 return of_platform_bus_probe(NULL, of_device_ids, NULL); 120 } 121 122 static const char * const boards[] __initconst = { 123 "fsl,P2041RDB", 124 "fsl,P3041DS", 125 "fsl,OCA4080", 126 "fsl,P4080DS", 127 "fsl,P5020DS", 128 "fsl,P5040DS", 129 "fsl,T2080QDS", 130 "fsl,T2080RDB", 131 "fsl,T2081QDS", 132 "fsl,T4240QDS", 133 "fsl,T4240RDB", 134 "fsl,B4860QDS", 135 "fsl,B4420QDS", 136 "fsl,B4220QDS", 137 "fsl,T1023RDB", 138 "fsl,T1024QDS", 139 "fsl,T1024RDB", 140 "fsl,T1040D4RDB", 141 "fsl,T1042D4RDB", 142 "fsl,T1040QDS", 143 "fsl,T1042QDS", 144 "fsl,T1040RDB", 145 "fsl,T1042RDB", 146 "fsl,T1042RDB_PI", 147 "keymile,kmcent2", 148 "keymile,kmcoge4", 149 "varisys,CYRUS", 150 NULL 151 }; 152 153 /* 154 * Called very early, device-tree isn't unflattened 155 */ 156 static int __init corenet_generic_probe(void) 157 { 158 char hv_compat[24]; 159 int i; 160 #ifdef CONFIG_SMP 161 extern struct smp_ops_t smp_85xx_ops; 162 #endif 163 164 if (of_device_compatible_match(of_root, boards)) 165 return 1; 166 167 /* Check if we're running under the Freescale hypervisor */ 168 for (i = 0; boards[i]; i++) { 169 snprintf(hv_compat, sizeof(hv_compat), "%s-hv", boards[i]); 170 if (of_machine_is_compatible(hv_compat)) { 171 ppc_md.init_IRQ = ehv_pic_init; 172 173 ppc_md.get_irq = ehv_pic_get_irq; 174 ppc_md.restart = fsl_hv_restart; 175 pm_power_off = fsl_hv_halt; 176 ppc_md.halt = fsl_hv_halt; 177 #ifdef CONFIG_SMP 178 /* 179 * Disable the timebase sync operations because we 180 * can't write to the timebase registers under the 181 * hypervisor. 182 */ 183 smp_85xx_ops.give_timebase = NULL; 184 smp_85xx_ops.take_timebase = NULL; 185 #endif 186 return 1; 187 } 188 } 189 190 return 0; 191 } 192 193 define_machine(corenet_generic) { 194 .name = "CoreNet Generic", 195 .probe = corenet_generic_probe, 196 .setup_arch = corenet_gen_setup_arch, 197 .init_IRQ = corenet_gen_pic_init, 198 #ifdef CONFIG_PCI 199 .pcibios_fixup_bus = fsl_pcibios_fixup_bus, 200 .pcibios_fixup_phb = fsl_pcibios_fixup_phb, 201 #endif 202 /* 203 * Core reset may cause issues if using the proxy mode of MPIC. 204 * So, use the mixed mode of MPIC if enabling CPU hotplug. 205 * 206 * Likewise, problems have been seen with kexec when coreint is enabled. 207 */ 208 #if defined(CONFIG_HOTPLUG_CPU) || defined(CONFIG_KEXEC_CORE) 209 .get_irq = mpic_get_irq, 210 #else 211 .get_irq = mpic_get_coreint_irq, 212 #endif 213 .calibrate_decr = generic_calibrate_decr, 214 .progress = udbg_progress, 215 #ifdef CONFIG_PPC64 216 .power_save = book3e_idle, 217 #else 218 .power_save = e500_idle, 219 #endif 220 }; 221 222 machine_arch_initcall(corenet_generic, corenet_gen_publish_devices); 223