Index: head/sys/arm/allwinner/a10_common.c =================================================================== --- head/sys/arm/allwinner/a10_common.c (revision 306266) +++ head/sys/arm/allwinner/a10_common.c (revision 306267) @@ -1,72 +1,68 @@ /*- * Copyright (c) 2012 Ganbold Tsagaankhuu * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_aintc_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { int offset; if (fdt_is_compatible(node, "allwinner,sun4i-a10-ic")) offset = 0; else if (fdt_is_compatible(node, "arm,gic")) offset = 32; else return (ENXIO); *interrupt = fdt32_to_cpu(intr[0]) + offset; *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_aintc_decode_ic, NULL }; #endif /* INTRNG */ Index: head/sys/arm/altera/socfpga/socfpga_common.c =================================================================== --- head/sys/arm/altera/socfpga/socfpga_common.c (revision 306266) +++ head/sys/arm/altera/socfpga/socfpga_common.c (revision 306267) @@ -1,96 +1,92 @@ /*- * Copyright (c) 2014 Ruslan Bukin * All rights reserved. * * This software was developed by SRI International and the University of * Cambridge Computer Laboratory under DARPA/AFRL contract (FA8750-10-C-0237) * ("CTSRD"), as part of the DARPA CRASH research programme. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include void cpu_reset(void) { uint32_t addr, paddr; bus_addr_t vaddr; phandle_t node; if (rstmgr_warmreset() == 0) goto end; node = OF_finddevice("rstmgr"); if (node == -1) goto end; if ((OF_getprop(node, "reg", &paddr, sizeof(paddr))) > 0) { addr = fdt32_to_cpu(paddr); if (bus_space_map(fdtbus_bs_tag, addr, 0x8, 0, &vaddr) == 0) { bus_space_write_4(fdtbus_bs_tag, vaddr, RSTMGR_CTRL, CTRL_SWWARMRSTREQ); } } end: while (1); } -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_pic_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { if (!fdt_is_compatible(node, "arm,gic")) return (ENXIO); *interrupt = fdt32_to_cpu(intr[0]); *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_pic_decode_ic, NULL }; #endif Index: head/sys/arm/amlogic/aml8726/aml8726_machdep.c =================================================================== --- head/sys/arm/amlogic/aml8726/aml8726_machdep.c (revision 306266) +++ head/sys/arm/amlogic/aml8726/aml8726_machdep.c (revision 306267) @@ -1,201 +1,197 @@ /*- * Copyright 2013-2015 John Wehle * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include "opt_global.h" #include __FBSDID("$FreeBSD$"); #include "opt_platform.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #if defined(SOCDEV_PA) && defined(SOCDEV_VA) vm_offset_t aml8726_aobus_kva_base = SOCDEV_VA; #else vm_offset_t aml8726_aobus_kva_base; #endif static void aml8726_fixup_busfreq() { phandle_t node; pcell_t freq, prop; ssize_t len; /* * Set the bus-frequency for the SoC simple-bus if it * needs updating (meaning the current frequency is zero). */ if ((freq = aml8726_clkmsr_bus_frequency()) == 0 || (node = OF_finddevice("/soc")) == 0 || fdt_is_compatible_strict(node, "simple-bus") == 0) while (1); freq = cpu_to_fdt32(freq); len = OF_getencprop(node, "bus-frequency", &prop, sizeof(prop)); if ((len / sizeof(prop)) == 1 && prop == 0) OF_setprop(node, "bus-frequency", (void *)&freq, sizeof(freq)); } vm_offset_t platform_lastaddr(void) { return (devmap_lastaddr()); } void platform_probe_and_attach(void) { } void platform_gpio_init(void) { /* * The UART console driver used for debugging early boot code * needs to know the virtual base address of the aobus. It's * expected to equal SOCDEV_VA prior to initarm calling setttb * ... afterwards it needs to be updated due to the new page * tables. * * This means there's a deadzone in initarm between setttb * and platform_gpio_init during which printf can't be used. */ aml8726_aobus_kva_base = (vm_offset_t)devmap_ptov(0xc8100000, 0x100000); /* * The hardware mux used by clkmsr is unique to the SoC (though * currently clk81 is at a fixed location, however that might * change in the future). */ aml8726_identify_soc(); /* * My aml8726-m3 development box which identifies the CPU as * a Cortex A9-r2 rev 4 randomly locks up during boot when WFI * is used. */ switch (aml8726_soc_hw_rev) { case AML_SOC_HW_REV_M3: cpufuncs.cf_sleep = (void *)cpufunc_nullop; break; default: break; } /* * This FDT fixup should arguably be called through fdt_fixup_table, * however currently there's no mechanism to specify a fixup which * should always be invoked. * * It needs to be called prior to the console being initialized which * is why it's called here, rather than from platform_late_init. */ aml8726_fixup_busfreq(); } void platform_late_init(void) { } /* * Construct static devmap entries to map out the core * peripherals using 1mb section mappings. */ int platform_devmap_init(void) { devmap_add_entry(0xc1100000, 0x200000); /* cbus */ devmap_add_entry(0xc4200000, 0x100000); /* pl310 */ devmap_add_entry(0xc4300000, 0x100000); /* periph */ devmap_add_entry(0xc8000000, 0x100000); /* apbbus */ devmap_add_entry(0xc8100000, 0x100000); /* aobus */ devmap_add_entry(0xc9000000, 0x800000); /* ahbbus */ devmap_add_entry(0xd9000000, 0x100000); /* ahb */ devmap_add_entry(0xda000000, 0x100000); /* secbus */ return (0); } -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG #ifndef DEV_GIC static int fdt_pic_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { /* * The single core chips have just an Amlogic PIC. */ if (!fdt_is_compatible_strict(node, "amlogic,aml8726-pic")) return (ENXIO); *interrupt = fdt32_to_cpu(intr[1]); *trig = INTR_TRIGGER_EDGE; *pol = INTR_POLARITY_HIGH; return (0); } #endif fdt_pic_decode_t fdt_pic_table[] = { #ifdef DEV_GIC &gic_decode_fdt, #else &fdt_pic_decode_ic, #endif NULL }; #endif /* INTRNG */ Index: head/sys/arm/annapurna/alpine/common.c =================================================================== --- head/sys/arm/annapurna/alpine/common.c (revision 306266) +++ head/sys/arm/annapurna/alpine/common.c (revision 306267) @@ -1,162 +1,159 @@ /*- * Copyright (c) 2013 Ruslan Bukin * Copyright (c) 2015 Semihalf. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * */ #include __FBSDID("$FreeBSD$"); #include "opt_platform.h" #include #include #include #include #include #include #include #include #include #define WDTLOAD 0x000 #define LOAD_MIN 0x00000001 #define LOAD_MAX 0xFFFFFFFF #define WDTVALUE 0x004 #define WDTCONTROL 0x008 /* control register masks */ #define INT_ENABLE (1 << 0) #define RESET_ENABLE (1 << 1) #define WDTLOCK 0xC00 #define UNLOCK 0x1ACCE551 #define LOCK 0x00000001 extern bus_addr_t al_devmap_pa; -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; static int alpine_get_wdt_base(uint32_t *pbase, uint32_t *psize); static int alpine_pic_decode_fdt(uint32_t iparent, uint32_t *intr, int *interrupt, int *trig, int *pol); int alpine_get_devmap_base(bus_addr_t *pa, bus_addr_t *size); int alpine_get_devmap_base(bus_addr_t *pa, bus_addr_t *size) { phandle_t node; if ((node = OF_finddevice("/")) == 0) return (ENXIO); if ((node = fdt_find_compatible(node, "simple-bus", 1)) == 0) return (ENXIO); return fdt_get_range(node, 0, pa, size); } static int alpine_get_wdt_base(uint32_t *pbase, uint32_t *psize) { phandle_t node; u_long base = 0; u_long size = 0; if (pbase == NULL || psize == NULL) return (EINVAL); if ((node = OF_finddevice("/")) == -1) return (EFAULT); if ((node = fdt_find_compatible(node, "simple-bus", 1)) == 0) return (EFAULT); if ((node = fdt_find_compatible(node, "arm,sp805", 1)) == 0) return (EFAULT); if (fdt_regsize(node, &base, &size)) return (EFAULT); *pbase = base; *psize = size; return (0); } void cpu_reset(void) { uint32_t wdbase, wdsize; bus_addr_t wdbaddr; int ret; ret = alpine_get_wdt_base(&wdbase, &wdsize); if (ret) { printf("Unable to get WDT base, do power down manually..."); goto infinite; } ret = bus_space_map(fdtbus_bs_tag, al_devmap_pa + wdbase, wdsize, 0, &wdbaddr); if (ret) { printf("Unable to map WDT base, do power down manually..."); goto infinite; } bus_space_write_4(fdtbus_bs_tag, wdbaddr, WDTLOCK, UNLOCK); bus_space_write_4(fdtbus_bs_tag, wdbaddr, WDTLOAD, LOAD_MIN); bus_space_write_4(fdtbus_bs_tag, wdbaddr, WDTCONTROL, INT_ENABLE | RESET_ENABLE); infinite: while (1) {} } #ifndef INTRNG static int alpine_pic_decode_fdt(uint32_t iparent, uint32_t *intr, int *interrupt, int *trig, int *pol) { int rv = 0; rv = gic_decode_fdt(iparent, intr, interrupt, trig, pol); if (rv == 0) { /* This was recognized as our PIC and decoded. */ interrupt = FDT_MAP_IRQ(iparent, interrupt); /* Configure the interrupt if callback provided */ if (arm_config_irq) (*arm_config_irq)(*interrupt, *trig, *pol); } return (rv); } fdt_pic_decode_t fdt_pic_table[] = { &alpine_pic_decode_fdt, NULL }; #endif Index: head/sys/arm/at91/at91_common.c =================================================================== --- head/sys/arm/at91/at91_common.c (revision 306266) +++ head/sys/arm/at91/at91_common.c (revision 306267) @@ -1,124 +1,120 @@ /*- * Copyright (c) 2014 M. Warner Losh. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include __FBSDID("$FreeBSD$"); #define _ARM32_BUS_DMA_PRIVATE #include #include #include #include #include #include #include #include #include #include #include #include #include #include extern const struct devmap_entry at91_devmap[]; -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_aic_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { int offset; if (fdt_is_compatible(node, "atmel,at91rm9200-aic")) offset = 0; else return (ENXIO); *interrupt = fdt32_to_cpu(intr[0]) + offset; *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_aic_decode_ic, NULL }; #endif static void at91_eoi(void *unused) { uint32_t *eoicr = (uint32_t *)(0xdffff000 + IC_EOICR); *eoicr = 0; } vm_offset_t platform_lastaddr(void) { return (devmap_lastaddr()); } void platform_probe_and_attach(void) { arm_post_filter = at91_eoi; at91_soc_id(); } int platform_devmap_init(void) { // devmap_add_entry(0xfff00000, 0x00100000); /* 1MB - uart, aic and timers*/ devmap_register_table(at91_devmap); return (0); } void platform_gpio_init(void) { } void platform_late_init(void) { } Index: head/sys/arm/broadcom/bcm2835/bcm2835_common.c =================================================================== --- head/sys/arm/broadcom/bcm2835/bcm2835_common.c (revision 306266) +++ head/sys/arm/broadcom/bcm2835/bcm2835_common.c (revision 306267) @@ -1,81 +1,77 @@ /*- * Copyright (C) 2008-2011 MARVELL INTERNATIONAL LTD. * All rights reserved. * * Developed by Semihalf. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * 3. Neither the name of MARVELL nor the names of contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include #include #include -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_intc_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { if (fdt_is_compatible(node, "broadcom,bcm2835-armctrl-ic")) { *interrupt = fdt32_to_cpu(intr[0]); *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } #ifdef SOC_BCM2836 if (fdt_is_compatible(node, "brcm,bcm2836-l1-intc")) { *interrupt = fdt32_to_cpu(intr[0]) + 72; *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } #endif return (ENXIO); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_intc_decode_ic, NULL }; #endif /* INTRNG */ Index: head/sys/arm/freescale/imx/imx6_machdep.c =================================================================== --- head/sys/arm/freescale/imx/imx6_machdep.c (revision 306266) +++ head/sys/arm/freescale/imx/imx6_machdep.c (revision 306267) @@ -1,360 +1,356 @@ /*- * Copyright (c) 2013 Ian Lepore * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include "opt_platform.h" #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include "platform_if.h" -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - static uint32_t gpio1_node; #ifndef INTRNG /* * Work around the linux workaround for imx6 erratum 006687, in which some * ethernet interrupts don't go to the GPC and thus won't wake the system from * Wait mode. We don't use Wait mode (which halts the GIC, leaving only GPC * interrupts able to wake the system), so we don't experience the bug at all. * The linux workaround is to reconfigure GPIO1_6 as the ENET interrupt by * writing magic values to an undocumented IOMUX register, then letting the gpio * interrupt driver notify the ethernet driver. We'll be able to do all that * (even though we don't need to) once the INTRNG project is committed and the * imx_gpio driver becomes an interrupt driver. Until then, this crazy little * workaround watches for requests to map an interrupt 6 with the interrupt * controller node referring to gpio1, and it substitutes the proper ffec * interrupt number. */ static int imx6_decode_fdt(uint32_t iparent, uint32_t *intr, int *interrupt, int *trig, int *pol) { if (fdt32_to_cpu(intr[0]) == 6 && OF_node_from_xref(iparent) == gpio1_node) { *interrupt = 150; *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } return (gic_decode_fdt(iparent, intr, interrupt, trig, pol)); } fdt_pic_decode_t fdt_pic_table[] = { &imx6_decode_fdt, NULL }; #endif /* * Fix FDT data related to interrupts. * * Driven by the needs of linux and its drivers (as always), the published FDT * data for imx6 now sets the interrupt parent for most devices to the GPC * interrupt controller, which is for use when the chip is in deep-sleep mode. * We don't support deep sleep or have a GPC-PIC driver; we need all interrupts * to be handled by the GIC. * * Luckily, the change to the FDT data was to assign the GPC as the interrupt * parent for the soc node and letting that get inherited by all other devices * (except a few that directly name GIC as their interrupt parent). So we can * set the world right by just changing the interrupt-parent property of the soc * node to refer to GIC instead of GPC. This will get us by until we write our * own GPC driver (or until linux changes its mind and the FDT data again). * * We validate that we have data that looks like we expect before changing it: * - SOC node exists and has GPC as its interrupt parent. * - GPC node exists and has GIC as its interrupt parent. * - GIC node exists and is its own interrupt parent. * * This applies to all models of imx6. Luckily all of them have the devices * involved at the same addresses on the same busses, so we don't need any * per-soc logic. We handle this at platform attach time rather than via the * fdt_fixup_table, because the latter requires matching on the FDT "model" * property, and this applies to all boards including those not yet invented. */ static void fix_fdt_interrupt_data(void) { phandle_t gicipar, gicnode, gicxref; phandle_t gpcipar, gpcnode, gpcxref; phandle_t socipar, socnode; int result; socnode = OF_finddevice("/soc"); if (socnode == -1) return; result = OF_getencprop(socnode, "interrupt-parent", &socipar, sizeof(socipar)); if (result <= 0) return; gicnode = OF_finddevice("/soc/interrupt-controller@00a01000"); if (gicnode == -1) return; result = OF_getencprop(gicnode, "interrupt-parent", &gicipar, sizeof(gicipar)); if (result <= 0) return; gicxref = OF_xref_from_node(gicnode); gpcnode = OF_finddevice("/soc/aips-bus@02000000/gpc@020dc000"); if (gpcnode == -1) return; result = OF_getencprop(gpcnode, "interrupt-parent", &gpcipar, sizeof(gpcipar)); if (result <= 0) return; gpcxref = OF_xref_from_node(gpcnode); if (socipar != gpcxref || gpcipar != gicxref || gicipar != gicxref) return; gicxref = cpu_to_fdt32(gicxref); OF_setprop(socnode, "interrupt-parent", &gicxref, sizeof(gicxref)); } static vm_offset_t imx6_lastaddr(platform_t plat) { return (devmap_lastaddr()); } static int imx6_attach(platform_t plat) { /* Fix soc interrupt-parent property. */ fix_fdt_interrupt_data(); /* Inform the MPCore timer driver that its clock is variable. */ arm_tmr_change_frequency(ARM_TMR_FREQUENCY_VARIES); return (0); } static void imx6_late_init(platform_t plat) { const uint32_t IMX6_WDOG_SR_PHYS = 0x020bc004; imx_wdog_init_last_reset(IMX6_WDOG_SR_PHYS); /* Cache the gpio1 node handle for imx6_decode_fdt() workaround code. */ gpio1_node = OF_node_from_xref( OF_finddevice("/soc/aips-bus@02000000/gpio@0209c000")); } /* * Set up static device mappings. * * This attempts to cover the most-used devices with 1MB section mappings, which * is good for performance (uses fewer TLB entries for device access). * * ARMMP covers the interrupt controller, MPCore timers, global timer, and the * L2 cache controller. Most of the 1MB range is unused reserved space. * * AIPS1/AIPS2 cover most of the on-chip devices such as uart, spi, i2c, etc. * * Notably not mapped right now are HDMI, GPU, and other devices below ARMMP in * the memory map. When we get support for graphics it might make sense to * static map some of that area. Be careful with other things in that area such * as OCRAM that probably shouldn't be mapped as VM_MEMATTR_DEVICE memory. */ static int imx6_devmap_init(platform_t plat) { const uint32_t IMX6_ARMMP_PHYS = 0x00a00000; const uint32_t IMX6_ARMMP_SIZE = 0x00100000; const uint32_t IMX6_AIPS1_PHYS = 0x02000000; const uint32_t IMX6_AIPS1_SIZE = 0x00100000; const uint32_t IMX6_AIPS2_PHYS = 0x02100000; const uint32_t IMX6_AIPS2_SIZE = 0x00100000; devmap_add_entry(IMX6_ARMMP_PHYS, IMX6_ARMMP_SIZE); devmap_add_entry(IMX6_AIPS1_PHYS, IMX6_AIPS1_SIZE); devmap_add_entry(IMX6_AIPS2_PHYS, IMX6_AIPS2_SIZE); return (0); } static void imx6_cpu_reset(platform_t plat) { const uint32_t IMX6_WDOG_CR_PHYS = 0x020bc000; imx_wdog_cpu_reset(IMX6_WDOG_CR_PHYS); } /* * Determine what flavor of imx6 we're running on. * * This code is based on the way u-boot does it. Information found on the web * indicates that Freescale themselves were the original source of this logic, * including the strange check for number of CPUs in the SCU configuration * register, which is apparently needed on some revisions of the SOLO. * * According to the documentation, there is such a thing as an i.MX6 Dual * (non-lite flavor). However, Freescale doesn't seem to have assigned it a * number or provided any logic to handle it in their detection code. * * Note that the ANALOG_DIGPROG and SCU configuration registers are not * documented in the chip reference manual. (SCU configuration is mentioned, * but not mapped out in detail.) I think the bottom two bits of the scu config * register may be ncpu-1. * * This hasn't been tested yet on a dual[-lite]. * * On a solo: * digprog = 0x00610001 * hwsoc = 0x00000062 * scu config = 0x00000500 * On a quad: * digprog = 0x00630002 * hwsoc = 0x00000063 * scu config = 0x00005503 */ u_int imx_soc_type() { uint32_t digprog, hwsoc; uint32_t *pcr; static u_int soctype; const vm_offset_t SCU_CONFIG_PHYSADDR = 0x00a00004; #define HWSOC_MX6SL 0x60 #define HWSOC_MX6DL 0x61 #define HWSOC_MX6SOLO 0x62 #define HWSOC_MX6Q 0x63 if (soctype != 0) return (soctype); digprog = imx6_anatop_read_4(IMX6_ANALOG_DIGPROG_SL); hwsoc = (digprog >> IMX6_ANALOG_DIGPROG_SOCTYPE_SHIFT) & IMX6_ANALOG_DIGPROG_SOCTYPE_MASK; if (hwsoc != HWSOC_MX6SL) { digprog = imx6_anatop_read_4(IMX6_ANALOG_DIGPROG); hwsoc = (digprog & IMX6_ANALOG_DIGPROG_SOCTYPE_MASK) >> IMX6_ANALOG_DIGPROG_SOCTYPE_SHIFT; /*printf("digprog = 0x%08x\n", digprog);*/ if (hwsoc == HWSOC_MX6DL) { pcr = devmap_ptov(SCU_CONFIG_PHYSADDR, 4); if (pcr != NULL) { /*printf("scu config = 0x%08x\n", *pcr);*/ if ((*pcr & 0x03) == 0) { hwsoc = HWSOC_MX6SOLO; } } } } /* printf("hwsoc 0x%08x\n", hwsoc); */ switch (hwsoc) { case HWSOC_MX6SL: soctype = IMXSOC_6SL; break; case HWSOC_MX6SOLO: soctype = IMXSOC_6S; break; case HWSOC_MX6DL: soctype = IMXSOC_6DL; break; case HWSOC_MX6Q : soctype = IMXSOC_6Q; break; default: printf("imx_soc_type: Don't understand hwsoc 0x%02x, " "digprog 0x%08x; assuming IMXSOC_6Q\n", hwsoc, digprog); soctype = IMXSOC_6Q; break; } return (soctype); } /* * Early putc routine for EARLY_PRINTF support. To use, add to kernel config: * option SOCDEV_PA=0x02000000 * option SOCDEV_VA=0x02000000 * option EARLY_PRINTF * Resist the temptation to change the #if 0 to #ifdef EARLY_PRINTF here. It * makes sense now, but if multiple SOCs do that it will make early_putc another * duplicate symbol to be eliminated on the path to a generic kernel. */ #if 0 static void imx6_early_putc(int c) { volatile uint32_t * UART_STAT_REG = (uint32_t *)0x02020098; volatile uint32_t * UART_TX_REG = (uint32_t *)0x02020040; const uint32_t UART_TXRDY = (1 << 3); while ((*UART_STAT_REG & UART_TXRDY) == 0) continue; *UART_TX_REG = c; } early_putc_t *early_putc = imx6_early_putc; #endif static platform_method_t imx6_methods[] = { PLATFORMMETHOD(platform_attach, imx6_attach), PLATFORMMETHOD(platform_lastaddr, imx6_lastaddr), PLATFORMMETHOD(platform_devmap_init, imx6_devmap_init), PLATFORMMETHOD(platform_late_init, imx6_late_init), PLATFORMMETHOD(platform_cpu_reset, imx6_cpu_reset), PLATFORMMETHOD_END, }; FDT_PLATFORM_DEF2(imx6, imx6s, "i.MX6 Solo", 0, "fsl,imx6s", 0); FDT_PLATFORM_DEF2(imx6, imx6d, "i.MX6 Dual", 0, "fsl,imx6d", 0); FDT_PLATFORM_DEF2(imx6, imx6q, "i.MX6 Quad", 0, "fsl,imx6q", 0); Index: head/sys/arm/freescale/imx/imx_common.c =================================================================== --- head/sys/arm/freescale/imx/imx_common.c (revision 306266) +++ head/sys/arm/freescale/imx/imx_common.c (revision 306267) @@ -1,74 +1,70 @@ /*- * Copyright (C) 2008-2011 MARVELL INTERNATIONAL LTD. * Copyright (c) 2012, 2013 The FreeBSD Foundation * All rights reserved. * * Developed by Semihalf. * * Portions of this software were developed by Oleksandr Rybalko * under sponsorship from the FreeBSD Foundation. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * 3. Neither the name of MARVELL nor the names of contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include #include #include -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_intc_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { *interrupt = fdt32_to_cpu(intr[0]); *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_intc_decode_ic, NULL }; #endif /* INTRNG */ Index: head/sys/arm/freescale/vybrid/vf_common.c =================================================================== --- head/sys/arm/freescale/vybrid/vf_common.c (revision 306266) +++ head/sys/arm/freescale/vybrid/vf_common.c (revision 306267) @@ -1,88 +1,84 @@ /*- * Copyright (c) 2013 Ruslan Bukin * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include void cpu_reset(void) { phandle_t src; uint32_t addr, paddr; bus_addr_t vaddr; if (src_swreset() == 0) goto end; src = OF_finddevice("src"); if ((src != 0) && (OF_getprop(src, "reg", &paddr, sizeof(paddr))) > 0) { addr = fdt32_to_cpu(paddr); if (bus_space_map(fdtbus_bs_tag, addr, 0x10, 0, &vaddr) == 0) { bus_space_write_4(fdtbus_bs_tag, vaddr, 0x00, SW_RST); } } end: while (1); } -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_pic_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { if (!fdt_is_compatible(node, "arm,gic")) return (ENXIO); *interrupt = fdt32_to_cpu(intr[0]); *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_pic_decode_ic, NULL }; #endif Index: head/sys/arm/lpc/lpc_intc.c =================================================================== --- head/sys/arm/lpc/lpc_intc.c (revision 306266) +++ head/sys/arm/lpc/lpc_intc.c (revision 306267) @@ -1,252 +1,248 @@ /*- * Copyright (c) 2010 Jakub Wojciech Klama * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include struct lpc_intc_softc { struct resource * li_res; bus_space_tag_t li_bst; bus_space_handle_t li_bsh; }; static int lpc_intc_probe(device_t); static int lpc_intc_attach(device_t); static void lpc_intc_eoi(void *); static struct lpc_intc_softc *intc_softc = NULL; #define intc_read_4(_sc, _reg) \ bus_space_read_4((_sc)->li_bst, (_sc)->li_bsh, (_reg)) #define intc_write_4(_sc, _reg, _val) \ bus_space_write_4((_sc)->li_bst, (_sc)->li_bsh, (_reg), (_val)) static int lpc_intc_probe(device_t dev) { if (!ofw_bus_status_okay(dev)) return (ENXIO); if (!ofw_bus_is_compatible(dev, "lpc,pic")) return (ENXIO); device_set_desc(dev, "LPC32x0 Interrupt Controller"); return (BUS_PROBE_DEFAULT); } static int lpc_intc_attach(device_t dev) { struct lpc_intc_softc *sc = device_get_softc(dev); int rid = 0; if (intc_softc) return (ENXIO); sc->li_res = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid, RF_ACTIVE); if (!sc->li_res) { device_printf(dev, "could not alloc resources\n"); return (ENXIO); } sc->li_bst = rman_get_bustag(sc->li_res); sc->li_bsh = rman_get_bushandle(sc->li_res); intc_softc = sc; arm_post_filter = lpc_intc_eoi; /* Clear interrupt status registers and disable all interrupts */ intc_write_4(sc, LPC_INTC_MIC_ER, 0); intc_write_4(sc, LPC_INTC_SIC1_ER, 0); intc_write_4(sc, LPC_INTC_SIC2_ER, 0); intc_write_4(sc, LPC_INTC_MIC_RSR, ~0); intc_write_4(sc, LPC_INTC_SIC1_RSR, ~0); intc_write_4(sc, LPC_INTC_SIC2_RSR, ~0); return (0); } static device_method_t lpc_intc_methods[] = { DEVMETHOD(device_probe, lpc_intc_probe), DEVMETHOD(device_attach, lpc_intc_attach), { 0, 0 } }; static driver_t lpc_intc_driver = { "pic", lpc_intc_methods, sizeof(struct lpc_intc_softc), }; static devclass_t lpc_intc_devclass; DRIVER_MODULE(pic, simplebus, lpc_intc_driver, lpc_intc_devclass, 0, 0); int arm_get_next_irq(int last) { struct lpc_intc_softc *sc = intc_softc; uint32_t value; int i; /* IRQs 0-31 are mapped to LPC_INTC_MIC_SR */ value = intc_read_4(sc, LPC_INTC_MIC_SR); for (i = 0; i < 32; i++) { if (value & (1 << i)) return (i); } /* IRQs 32-63 are mapped to LPC_INTC_SIC1_SR */ value = intc_read_4(sc, LPC_INTC_SIC1_SR); for (i = 0; i < 32; i++) { if (value & (1 << i)) return (i + 32); } /* IRQs 64-95 are mapped to LPC_INTC_SIC2_SR */ value = intc_read_4(sc, LPC_INTC_SIC2_SR); for (i = 0; i < 32; i++) { if (value & (1 << i)) return (i + 64); } return (-1); } void arm_mask_irq(uintptr_t nb) { struct lpc_intc_softc *sc = intc_softc; int reg; uint32_t value; /* Make sure that interrupt isn't active already */ lpc_intc_eoi((void *)nb); if (nb > 63) { nb -= 64; reg = LPC_INTC_SIC2_ER; } else if (nb > 31) { nb -= 32; reg = LPC_INTC_SIC1_ER; } else reg = LPC_INTC_MIC_ER; /* Clear bit in ER register */ value = intc_read_4(sc, reg); value &= ~(1 << nb); intc_write_4(sc, reg, value); } void arm_unmask_irq(uintptr_t nb) { struct lpc_intc_softc *sc = intc_softc; int reg; uint32_t value; if (nb > 63) { nb -= 64; reg = LPC_INTC_SIC2_ER; } else if (nb > 31) { nb -= 32; reg = LPC_INTC_SIC1_ER; } else reg = LPC_INTC_MIC_ER; /* Set bit in ER register */ value = intc_read_4(sc, reg); value |= (1 << nb); intc_write_4(sc, reg, value); } static void lpc_intc_eoi(void *data) { struct lpc_intc_softc *sc = intc_softc; int reg; int nb = (int)data; uint32_t value; if (nb > 63) { nb -= 64; reg = LPC_INTC_SIC2_RSR; } else if (nb > 31) { nb -= 32; reg = LPC_INTC_SIC1_RSR; } else reg = LPC_INTC_MIC_RSR; /* Set bit in RSR register */ value = intc_read_4(sc, reg); value |= (1 << nb); intc_write_4(sc, reg, value); } -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_pic_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { if (!fdt_is_compatible(node, "lpc,pic")) return (ENXIO); *interrupt = fdt32_to_cpu(intr[0]); *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_pic_decode_ic, NULL }; #endif Index: head/sys/arm/nvidia/tegra124/tegra124_machdep.c =================================================================== --- head/sys/arm/nvidia/tegra124/tegra124_machdep.c (revision 306266) +++ head/sys/arm/nvidia/tegra124/tegra124_machdep.c (revision 306267) @@ -1,160 +1,156 @@ /*- * Copyright (c) 2016 Michal Meloun * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include "opt_platform.h" #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include "platform_if.h" #define PMC_PHYSBASE 0x7000e400 #define PMC_SIZE 0x400 #define PMC_CONTROL_REG 0x0 #define PMC_SCRATCH0 0x50 #define PMC_SCRATCH0_MODE_RECOVERY (1 << 31) #define PMC_SCRATCH0_MODE_BOOTLOADER (1 << 30) #define PMC_SCRATCH0_MODE_RCM (1 << 1) #define PMC_SCRATCH0_MODE_MASK (PMC_SCRATCH0_MODE_RECOVERY | \ PMC_SCRATCH0_MODE_BOOTLOADER | \ PMC_SCRATCH0_MODE_RCM) -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - static vm_offset_t tegra124_lastaddr(platform_t plat) { return (devmap_lastaddr()); } static int tegra124_attach(platform_t plat) { return (0); } static void tegra124_late_init(platform_t plat) { } /* * Set up static device mappings. * */ static int tegra124_devmap_init(platform_t plat) { devmap_add_entry(0x70000000, 0x01000000); return (0); } static void tegra124_cpu_reset(platform_t plat) { bus_space_handle_t pmc; uint32_t reg; printf("Resetting...\n"); bus_space_map(fdtbus_bs_tag, PMC_PHYSBASE, PMC_SIZE, 0, &pmc); reg = bus_space_read_4(fdtbus_bs_tag, pmc, PMC_SCRATCH0); reg &= PMC_SCRATCH0_MODE_MASK; bus_space_write_4(fdtbus_bs_tag, pmc, PMC_SCRATCH0, reg | PMC_SCRATCH0_MODE_BOOTLOADER); /* boot to bootloader */ bus_space_read_4(fdtbus_bs_tag, pmc, PMC_SCRATCH0); reg = bus_space_read_4(fdtbus_bs_tag, pmc, PMC_CONTROL_REG); spinlock_enter(); dsb(); bus_space_write_4(fdtbus_bs_tag, pmc, PMC_CONTROL_REG, reg | 0x10); bus_space_read_4(fdtbus_bs_tag, pmc, PMC_CONTROL_REG); while(1) ; } /* * Early putc routine for EARLY_PRINTF support. To use, add to kernel config: * option SOCDEV_PA=0x02000000 * option SOCDEV_VA=0x02000000 * option EARLY_PRINTF */ #if 0 static void tegra124_early_putc(int c) { volatile uint32_t * UART_STAT_REG = (uint32_t *)0x02020098; volatile uint32_t * UART_TX_REG = (uint32_t *)0x02020040; const uint32_t UART_TXRDY = (1 << 3); while ((*UART_STAT_REG & UART_TXRDY) == 0) continue; *UART_TX_REG = c; } early_putc_t *early_putc = tegra124_early_putc; #endif static platform_method_t tegra124_methods[] = { PLATFORMMETHOD(platform_attach, tegra124_attach), PLATFORMMETHOD(platform_lastaddr, tegra124_lastaddr), PLATFORMMETHOD(platform_devmap_init, tegra124_devmap_init), PLATFORMMETHOD(platform_late_init, tegra124_late_init), PLATFORMMETHOD(platform_cpu_reset, tegra124_cpu_reset), #ifdef SMP PLATFORMMETHOD(platform_mp_start_ap, tegra124_mp_start_ap), PLATFORMMETHOD(platform_mp_setmaxid, tegra124_mp_setmaxid), #endif PLATFORMMETHOD_END, }; FDT_PLATFORM_DEF(tegra124, "Nvidia Jetson-TK1", 0, "nvidia,jetson-tk1", 0); Index: head/sys/arm/qemu/virt_common.c =================================================================== --- head/sys/arm/qemu/virt_common.c (revision 306266) +++ head/sys/arm/qemu/virt_common.c (revision 306267) @@ -1,49 +1,45 @@ /*- * Copyright (c) 2015 Andrew Turner * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * */ #include __FBSDID("$FreeBSD$"); #include "opt_platform.h" #include #include #include #include -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG fdt_pic_decode_t fdt_pic_table[] = { &gic_decode_fdt, NULL }; #endif Index: head/sys/arm/rockchip/rk30xx_common.c =================================================================== --- head/sys/arm/rockchip/rk30xx_common.c (revision 306266) +++ head/sys/arm/rockchip/rk30xx_common.c (revision 306267) @@ -1,65 +1,61 @@ /*- * Copyright (c) 2013 Ganbold Tsagaankhuu * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_aintc_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { if (!fdt_is_compatible(node, "arm,gic")) return (ENXIO); *interrupt = fdt32_to_cpu(intr[0]); *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_aintc_decode_ic, NULL }; #endif Index: head/sys/arm/samsung/exynos/exynos5_common.c =================================================================== --- head/sys/arm/samsung/exynos/exynos5_common.c (revision 306266) +++ head/sys/arm/samsung/exynos/exynos5_common.c (revision 306267) @@ -1,75 +1,71 @@ /*- * Copyright (c) 2013 Ruslan Bukin * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include void cpu_reset(void) { bus_space_handle_t bsh; bus_space_map(fdtbus_bs_tag, 0x10040400, 0x1000, 0, &bsh); bus_space_write_4(fdtbus_bs_tag, bsh, 0, 1); while (1); } -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_pic_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { if (!fdt_is_compatible(node, "arm,gic")) return (ENXIO); *interrupt = fdt32_to_cpu(intr[0]); *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_pic_decode_ic, NULL }; #endif Index: head/sys/arm/ti/ti_common.c =================================================================== --- head/sys/arm/ti/ti_common.c (revision 306266) +++ head/sys/arm/ti/ti_common.c (revision 306267) @@ -1,84 +1,80 @@ /*- * Copyright (C) 2008-2011 MARVELL INTERNATIONAL LTD. * All rights reserved. * * Developed by Semihalf. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * 3. Neither the name of MARVELL nor the names of contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include "opt_platform.h" #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include #include #include #include -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG #ifdef SOC_TI_AM335X static int fdt_aintc_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { if (!fdt_is_compatible(node, "ti,aintc") && !fdt_is_compatible(node, "ti,am33xx-intc")) return (ENXIO); *interrupt = fdt32_to_cpu(intr[0]); *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } #endif fdt_pic_decode_t fdt_pic_table[] = { #if defined(SOC_OMAP4) &gic_decode_fdt, #endif #ifdef SOC_TI_AM335X &fdt_aintc_decode_ic, #endif NULL }; #endif /* !INTRNG */ Index: head/sys/arm/versatile/versatile_common.c =================================================================== --- head/sys/arm/versatile/versatile_common.c (revision 306266) +++ head/sys/arm/versatile/versatile_common.c (revision 306267) @@ -1,74 +1,70 @@ /*- * Copyright (C) 2008-2011 MARVELL INTERNATIONAL LTD. * All rights reserved. * * Developed by Semihalf. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * 3. Neither the name of MARVELL nor the names of contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include #include #include -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_intc_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { if (!fdt_is_compatible(node, "arm,versatile-vic")) return (ENXIO); *interrupt = fdt32_to_cpu(intr[0]); *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_intc_decode_ic, NULL }; #endif Index: head/sys/arm/xilinx/zy7_machdep.c =================================================================== --- head/sys/arm/xilinx/zy7_machdep.c (revision 306266) +++ head/sys/arm/xilinx/zy7_machdep.c (revision 306267) @@ -1,131 +1,127 @@ /*- * Copyright (c) 2013 Thomas Skibo * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * $FreeBSD$ */ /* * Machine dependent code for Xilinx Zynq-7000 Soc. * * Reference: Zynq-7000 All Programmable SoC Technical Reference Manual. * (v1.4) November 16, 2012. Xilinx doc UG585. */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include #include #include void (*zynq7_cpu_reset)(void); vm_offset_t platform_lastaddr(void) { return (devmap_lastaddr()); } void platform_probe_and_attach(void) { } void platform_gpio_init(void) { } void platform_late_init(void) { } /* * Set up static device mappings. Not strictly necessary -- simplebus will * dynamically establish mappings as needed -- but doing it this way gets us * nice efficient 1MB section mappings. */ int platform_devmap_init(void) { devmap_add_entry(ZYNQ7_PSIO_HWBASE, ZYNQ7_PSIO_SIZE); devmap_add_entry(ZYNQ7_PSCTL_HWBASE, ZYNQ7_PSCTL_SIZE); return (0); } -struct fdt_fixup_entry fdt_fixup_table[] = { - { NULL, NULL } -}; - #ifndef INTRNG static int fdt_gic_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig, int *pol) { if (!fdt_is_compatible(node, "arm,gic")) return (ENXIO); *interrupt = fdt32_to_cpu(intr[0]); *trig = INTR_TRIGGER_CONFORM; *pol = INTR_POLARITY_CONFORM; return (0); } fdt_pic_decode_t fdt_pic_table[] = { &fdt_gic_decode_ic, NULL }; #endif void cpu_reset() { if (zynq7_cpu_reset != NULL) (*zynq7_cpu_reset)(); printf("cpu_reset: no platform cpu_reset. hanging.\n"); for (;;) ; } Index: head/sys/dev/ofw/ofw_fdt.c =================================================================== --- head/sys/dev/ofw/ofw_fdt.c (revision 306266) +++ head/sys/dev/ofw/ofw_fdt.c (revision 306267) @@ -1,479 +1,488 @@ /*- * Copyright (c) 2009-2010 The FreeBSD Foundation * All rights reserved. * * This software was developed by Semihalf under sponsorship from * the FreeBSD Foundation. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #include __FBSDID("$FreeBSD$"); #include #include #include #include #include #include #include #include #include #include "ofw_if.h" #ifdef DEBUG #define debugf(fmt, args...) do { printf("%s(): ", __func__); \ printf(fmt,##args); } while (0) #else #define debugf(fmt, args...) #endif +#if defined(__arm__) +#if defined(SOC_MV_ARMADAXP) || defined(SOC_MV_ARMADA38X) || \ + defined(SOC_MV_DISCOVERY) || defined(SOC_MV_DOVE) || \ + defined(SOC_MV_FREY) || defined(SOC_MV_KIRKWOOD) || \ + defined(SOC_MV_LOKIPLUS) || defined(SOC_MV_ORION) +#define FDT_MARVELL +#endif +#endif + static int ofw_fdt_init(ofw_t, void *); static phandle_t ofw_fdt_peer(ofw_t, phandle_t); static phandle_t ofw_fdt_child(ofw_t, phandle_t); static phandle_t ofw_fdt_parent(ofw_t, phandle_t); static phandle_t ofw_fdt_instance_to_package(ofw_t, ihandle_t); static ssize_t ofw_fdt_getproplen(ofw_t, phandle_t, const char *); static ssize_t ofw_fdt_getprop(ofw_t, phandle_t, const char *, void *, size_t); static int ofw_fdt_nextprop(ofw_t, phandle_t, const char *, char *, size_t); static int ofw_fdt_setprop(ofw_t, phandle_t, const char *, const void *, size_t); static ssize_t ofw_fdt_canon(ofw_t, const char *, char *, size_t); static phandle_t ofw_fdt_finddevice(ofw_t, const char *); static ssize_t ofw_fdt_instance_to_path(ofw_t, ihandle_t, char *, size_t); static ssize_t ofw_fdt_package_to_path(ofw_t, phandle_t, char *, size_t); static int ofw_fdt_interpret(ofw_t, const char *, int, cell_t *); static ofw_method_t ofw_fdt_methods[] = { OFWMETHOD(ofw_init, ofw_fdt_init), OFWMETHOD(ofw_peer, ofw_fdt_peer), OFWMETHOD(ofw_child, ofw_fdt_child), OFWMETHOD(ofw_parent, ofw_fdt_parent), OFWMETHOD(ofw_instance_to_package, ofw_fdt_instance_to_package), OFWMETHOD(ofw_getproplen, ofw_fdt_getproplen), OFWMETHOD(ofw_getprop, ofw_fdt_getprop), OFWMETHOD(ofw_nextprop, ofw_fdt_nextprop), OFWMETHOD(ofw_setprop, ofw_fdt_setprop), OFWMETHOD(ofw_canon, ofw_fdt_canon), OFWMETHOD(ofw_finddevice, ofw_fdt_finddevice), OFWMETHOD(ofw_instance_to_path, ofw_fdt_instance_to_path), OFWMETHOD(ofw_package_to_path, ofw_fdt_package_to_path), OFWMETHOD(ofw_interpret, ofw_fdt_interpret), { 0, 0 } }; static ofw_def_t ofw_fdt = { OFW_FDT, ofw_fdt_methods, 0 }; OFW_DEF(ofw_fdt); static void *fdtp = NULL; static int sysctl_handle_dtb(SYSCTL_HANDLER_ARGS) { return (sysctl_handle_opaque(oidp, fdtp, fdt_totalsize(fdtp), req)); } static void sysctl_register_fdt_oid(void *arg) { /* If there is no FDT registered, skip adding the sysctl */ if (fdtp == NULL) return; SYSCTL_ADD_PROC(NULL, SYSCTL_STATIC_CHILDREN(_hw_fdt), OID_AUTO, "dtb", CTLTYPE_OPAQUE | CTLFLAG_RD, NULL, 0, sysctl_handle_dtb, "", "Device Tree Blob"); } SYSINIT(dtb_oid, SI_SUB_KMEM, SI_ORDER_ANY, sysctl_register_fdt_oid, 0); static int ofw_fdt_init(ofw_t ofw, void *data) { int err; /* Check FDT blob integrity */ if ((err = fdt_check_header(data)) != 0) return (err); fdtp = data; return (0); } /* * Device tree functions. * * We use the offset from fdtp to the node as the 'phandle' in OF interface. * * phandle is a u32 value, therefore we cannot use the pointer to node as * phandle in 64 bit. We also do not use the usual fdt offset as phandle, * as it can be 0, and the OF interface has special meaning for phandle 0. */ static phandle_t fdt_offset_phandle(int offset) { if (offset < 0) return (0); return ((phandle_t)offset + fdt_off_dt_struct(fdtp)); } static int fdt_phandle_offset(phandle_t p) { int pint = (int)p; int dtoff = fdt_off_dt_struct(fdtp); if (pint < dtoff) return (-1); return (pint - dtoff); } /* Return the next sibling of this node or 0. */ static phandle_t ofw_fdt_peer(ofw_t ofw, phandle_t node) { int depth, offset; if (node == 0) { /* Find root node */ offset = fdt_path_offset(fdtp, "/"); return (fdt_offset_phandle(offset)); } offset = fdt_phandle_offset(node); if (offset < 0) return (0); for (depth = 1, offset = fdt_next_node(fdtp, offset, &depth); offset >= 0; offset = fdt_next_node(fdtp, offset, &depth)) { if (depth < 0) return (0); if (depth == 1) return (fdt_offset_phandle(offset)); } return (0); } /* Return the first child of this node or 0. */ static phandle_t ofw_fdt_child(ofw_t ofw, phandle_t node) { int depth, offset; offset = fdt_phandle_offset(node); if (offset < 0) return (0); for (depth = 0, offset = fdt_next_node(fdtp, offset, &depth); (offset >= 0) && (depth > 0); offset = fdt_next_node(fdtp, offset, &depth)) { if (depth < 0) return (0); if (depth == 1) return (fdt_offset_phandle(offset)); } return (0); } /* Return the parent of this node or 0. */ static phandle_t ofw_fdt_parent(ofw_t ofw, phandle_t node) { int offset, paroffset; offset = fdt_phandle_offset(node); if (offset < 0) return (0); paroffset = fdt_parent_offset(fdtp, offset); return (fdt_offset_phandle(paroffset)); } /* Return the package handle that corresponds to an instance handle. */ static phandle_t ofw_fdt_instance_to_package(ofw_t ofw, ihandle_t instance) { /* Where real OF uses ihandles in the tree, FDT uses xref phandles */ return (OF_node_from_xref(instance)); } /* Get the length of a property of a package. */ static ssize_t ofw_fdt_getproplen(ofw_t ofw, phandle_t package, const char *propname) { const struct fdt_property *prop; int offset, len; offset = fdt_phandle_offset(package); if (offset < 0) return (-1); len = -1; prop = fdt_get_property(fdtp, offset, propname, &len); if (prop == NULL && strcmp(propname, "name") == 0) { /* Emulate the 'name' property */ fdt_get_name(fdtp, offset, &len); return (len + 1); } if (prop == NULL && offset == fdt_path_offset(fdtp, "/chosen")) { if (strcmp(propname, "fdtbootcpu") == 0) return (sizeof(cell_t)); if (strcmp(propname, "fdtmemreserv") == 0) return (sizeof(uint64_t)*2*fdt_num_mem_rsv(fdtp)); } if (prop == NULL) return (-1); return (len); } /* Get the value of a property of a package. */ static ssize_t ofw_fdt_getprop(ofw_t ofw, phandle_t package, const char *propname, void *buf, size_t buflen) { const void *prop; const char *name; int len, offset; uint32_t cpuid; offset = fdt_phandle_offset(package); if (offset < 0) return (-1); prop = fdt_getprop(fdtp, offset, propname, &len); if (prop == NULL && strcmp(propname, "name") == 0) { /* Emulate the 'name' property */ name = fdt_get_name(fdtp, offset, &len); strncpy(buf, name, buflen); if (len + 1 > buflen) len = buflen; return (len + 1); } if (prop == NULL && offset == fdt_path_offset(fdtp, "/chosen")) { if (strcmp(propname, "fdtbootcpu") == 0) { cpuid = cpu_to_fdt32(fdt_boot_cpuid_phys(fdtp)); len = sizeof(cpuid); prop = &cpuid; } if (strcmp(propname, "fdtmemreserv") == 0) { prop = (char *)fdtp + fdt_off_mem_rsvmap(fdtp); len = sizeof(uint64_t)*2*fdt_num_mem_rsv(fdtp); } } if (prop == NULL) return (-1); if (len > buflen) len = buflen; bcopy(prop, buf, len); return (len); } /* * Get the next property of a package. Return values: * -1: package or previous property does not exist * 0: no more properties * 1: success */ static int ofw_fdt_nextprop(ofw_t ofw, phandle_t package, const char *previous, char *buf, size_t size) { const struct fdt_property *prop; const char *name; int offset; offset = fdt_phandle_offset(package); if (offset < 0) return (-1); /* Find the first prop in the node */ offset = fdt_first_property_offset(fdtp, offset); if (offset < 0) return (0); /* No properties */ if (previous != NULL) { while (offset >= 0) { prop = fdt_get_property_by_offset(fdtp, offset, NULL); if (prop == NULL) return (-1); /* Internal error */ offset = fdt_next_property_offset(fdtp, offset); if (offset < 0) return (0); /* No more properties */ /* Check if the last one was the one we wanted */ name = fdt_string(fdtp, fdt32_to_cpu(prop->nameoff)); if (strcmp(name, previous) == 0) break; } } prop = fdt_get_property_by_offset(fdtp, offset, &offset); if (prop == NULL) return (-1); /* Internal error */ strncpy(buf, fdt_string(fdtp, fdt32_to_cpu(prop->nameoff)), size); return (1); } /* Set the value of a property of a package. */ static int ofw_fdt_setprop(ofw_t ofw, phandle_t package, const char *propname, const void *buf, size_t len) { int offset; offset = fdt_phandle_offset(package); if (offset < 0) return (-1); return (fdt_setprop_inplace(fdtp, offset, propname, buf, len)); } /* Convert a device specifier to a fully qualified pathname. */ static ssize_t ofw_fdt_canon(ofw_t ofw, const char *device, char *buf, size_t len) { return (-1); } /* Return a package handle for the specified device. */ static phandle_t ofw_fdt_finddevice(ofw_t ofw, const char *device) { int offset; offset = fdt_path_offset(fdtp, device); if (offset < 0) return (-1); return (fdt_offset_phandle(offset)); } /* Return the fully qualified pathname corresponding to an instance. */ static ssize_t ofw_fdt_instance_to_path(ofw_t ofw, ihandle_t instance, char *buf, size_t len) { phandle_t phandle; phandle = OF_instance_to_package(instance); if (phandle == -1) return (-1); return (OF_package_to_path(phandle, buf, len)); } /* Return the fully qualified pathname corresponding to a package. */ static ssize_t ofw_fdt_package_to_path(ofw_t ofw, phandle_t package, char *buf, size_t len) { return (-1); } -#if defined(__arm__) || defined(__powerpc__) +#if defined(FDT_MARVELL) || defined(__powerpc__) static int ofw_fdt_fixup(ofw_t ofw) { #define FDT_MODEL_LEN 80 char model[FDT_MODEL_LEN]; phandle_t root; ssize_t len; int i; if ((root = ofw_fdt_finddevice(ofw, "/")) == -1) return (ENODEV); if ((len = ofw_fdt_getproplen(ofw, root, "model")) <= 0) return (0); bzero(model, FDT_MODEL_LEN); if (ofw_fdt_getprop(ofw, root, "model", model, FDT_MODEL_LEN) <= 0) return (0); /* * Search fixup table and call handler if appropriate. */ for (i = 0; fdt_fixup_table[i].model != NULL; i++) { if (strncmp(model, fdt_fixup_table[i].model, FDT_MODEL_LEN) != 0) continue; if (fdt_fixup_table[i].handler != NULL) (*fdt_fixup_table[i].handler)(root); } return (0); } #endif static int ofw_fdt_interpret(ofw_t ofw, const char *cmd, int nret, cell_t *retvals) { -#if defined(__arm__) || defined(__powerpc__) +#if defined(FDT_MARVELL) || defined(__powerpc__) int rv; /* * Note: FDT does not have the possibility to 'interpret' commands, * but we abuse the interface a bit to use it for doing non-standard * operations on the device tree blob. * * Currently the only supported 'command' is to trigger performing * fixups. */ if (strncmp("perform-fixup", cmd, 13) != 0) return (0); rv = ofw_fdt_fixup(ofw); if (nret > 0) retvals[0] = rv; return (rv); #else return (0); #endif }