1 /* $NetBSD: omap3_platform.c,v 1.3 2020/07/10 12:25:10 skrll Exp $ */ 2 3 /*- 4 * Copyright (c) 2019 Jared McNeill <jmcneill@invisible.ca> 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 17 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 18 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 19 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 21 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 23 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 24 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26 * SUCH DAMAGE. 27 */ 28 29 #include "opt_soc.h" 30 #include "opt_console.h" 31 32 #include <sys/cdefs.h> 33 __KERNEL_RCSID(0, "$NetBSD: omap3_platform.c,v 1.3 2020/07/10 12:25:10 skrll Exp $"); 34 35 #include <sys/param.h> 36 #include <sys/bus.h> 37 #include <sys/cpu.h> 38 #include <sys/device.h> 39 #include <sys/termios.h> 40 41 #include <dev/fdt/fdtvar.h> 42 #include <arm/fdt/arm_fdtvar.h> 43 44 #include <uvm/uvm_extern.h> 45 46 #include <machine/bootconfig.h> 47 #include <arm/cpufunc.h> 48 49 #include <dev/ic/ns16550reg.h> 50 #include <dev/ic/comreg.h> 51 52 #include <evbarm/fdt/platform.h> 53 #include <evbarm/fdt/machdep.h> 54 55 #include <net/if_ether.h> 56 57 #include <libfdt.h> 58 59 #define OMAP3_L4_CORE_VBASE KERNEL_IO_VBASE 60 #define OMAP3_L4_CORE_PBASE 0x48000000 61 #define OMAP3_L4_CORE_SIZE 0x00100000 62 63 #define OMAP3_L4_WKUP_VBASE (OMAP3_L4_CORE_VBASE + OMAP3_L4_CORE_SIZE) 64 #define OMAP3_L4_WKUP_PBASE 0x48300000 65 #define OMAP3_L4_WKUP_SIZE 0x00100000 66 67 #define OMAP3_L4_PER_VBASE (OMAP3_L4_WKUP_VBASE + OMAP3_L4_WKUP_SIZE) 68 #define OMAP3_L4_PER_PBASE 0x49000000 69 #define OMAP3_L4_PER_SIZE 0x00100000 70 71 #define OMAP3_PRCM_BASE 0x48306000 72 #define OMAP3_PRCM_GR_BASE (OMAP3_PRCM_BASE + 0x1200) 73 #define PRM_RSTCTRL (OMAP3_PRCM_GR_BASE + 0x50) 74 #define PRM_RSTCTRL_RST_DPLL3 __BIT(2) 75 76 #define OMAP3_32KTIMER_BASE 0x48320000 77 #define REG_32KSYNCNT_CR (OMAP3_32KTIMER_BASE + 0x10) 78 79 static inline vaddr_t 80 omap3_phystovirt(paddr_t pa) 81 { 82 if (pa >= OMAP3_L4_CORE_PBASE && 83 pa < OMAP3_L4_CORE_PBASE + OMAP3_L4_CORE_SIZE) 84 return (pa - OMAP3_L4_CORE_PBASE) + OMAP3_L4_CORE_VBASE; 85 86 if (pa >= OMAP3_L4_WKUP_PBASE && 87 pa < OMAP3_L4_WKUP_PBASE + OMAP3_L4_WKUP_SIZE) 88 return (pa - OMAP3_L4_WKUP_PBASE) + OMAP3_L4_WKUP_VBASE; 89 90 if (pa >= OMAP3_L4_PER_PBASE && 91 pa < OMAP3_L4_PER_PBASE + OMAP3_L4_PER_SIZE) 92 return (pa - OMAP3_L4_PER_PBASE) + OMAP3_L4_PER_VBASE; 93 94 panic("%s: pa %#x not in devmap", __func__, (uint32_t)pa); 95 } 96 97 #define OMAP3_PHYSTOVIRT(pa) \ 98 (((pa) - OMAP3_L4_CORE_VBASE) + OMAP3_L4_CORE_PBASE) 99 100 extern struct arm32_bus_dma_tag arm_generic_dma_tag; 101 extern struct bus_space arm_generic_bs_tag; 102 extern struct bus_space arm_generic_a4x_bs_tag; 103 104 static const struct pmap_devmap * 105 omap3_platform_devmap(void) 106 { 107 static const struct pmap_devmap devmap[] = { 108 DEVMAP_ENTRY(OMAP3_L4_CORE_VBASE, 109 OMAP3_L4_CORE_PBASE, 110 OMAP3_L4_CORE_SIZE), 111 DEVMAP_ENTRY(OMAP3_L4_WKUP_VBASE, 112 OMAP3_L4_WKUP_PBASE, 113 OMAP3_L4_WKUP_SIZE), 114 DEVMAP_ENTRY(OMAP3_L4_PER_VBASE, 115 OMAP3_L4_PER_PBASE, 116 OMAP3_L4_PER_SIZE), 117 DEVMAP_ENTRY_END 118 }; 119 120 return devmap; 121 } 122 123 static void 124 omap3_platform_init_attach_args(struct fdt_attach_args *faa) 125 { 126 faa->faa_bst = &arm_generic_bs_tag; 127 faa->faa_a4x_bst = &arm_generic_a4x_bs_tag; 128 faa->faa_dmat = &arm_generic_dma_tag; 129 } 130 131 void omap3_platform_early_putchar(char); 132 133 void __noasan 134 omap3_platform_early_putchar(char c) 135 { 136 #ifdef CONSADDR 137 volatile uint32_t *uartaddr = cpu_earlydevice_va_p() ? 138 (volatile uint32_t *)omap3_phystovirt(CONSADDR): 139 (volatile uint32_t *)CONSADDR; 140 141 while ((le32toh(uartaddr[com_lsr]) & LSR_TXRDY) == 0) 142 ; 143 144 uartaddr[com_data] = htole32(c); 145 #endif 146 } 147 148 static void 149 omap3_platform_device_register(device_t self, void *aux) 150 { 151 } 152 153 static u_int 154 omap3_platform_uart_freq(void) 155 { 156 return 48000000U; 157 } 158 159 static void 160 omap3_platform_reset(void) 161 { 162 volatile uint32_t *rstctrl = 163 (volatile uint32_t *)omap3_phystovirt(PRM_RSTCTRL); 164 165 *rstctrl |= PRM_RSTCTRL_RST_DPLL3; 166 167 for (;;) 168 __asm("wfi"); 169 } 170 171 static void 172 omap3_platform_delay(u_int n) 173 { 174 volatile uint32_t *cr = 175 (volatile uint32_t *)omap3_phystovirt(REG_32KSYNCNT_CR); 176 uint32_t cur, prev; 177 178 long ticks = howmany(n * 32768, 1000000); 179 prev = *cr; 180 while (ticks > 0) { 181 cur = *cr; 182 if (cur >= prev) 183 ticks -= (cur - prev); 184 else 185 ticks -= (UINT32_MAX - cur + prev); 186 prev = cur; 187 } 188 } 189 190 static const struct arm_platform omap3_platform = { 191 .ap_devmap = omap3_platform_devmap, 192 .ap_bootstrap = arm_fdt_cpu_bootstrap, 193 .ap_init_attach_args = omap3_platform_init_attach_args, 194 .ap_device_register = omap3_platform_device_register, 195 .ap_reset = omap3_platform_reset, 196 .ap_delay = omap3_platform_delay, 197 .ap_uart_freq = omap3_platform_uart_freq, 198 }; 199 200 ARM_PLATFORM(omap3, "ti,omap3", &omap3_platform); 201