137e4dafaSPeter Tyser/* 237e4dafaSPeter Tyser * (C) Copyright 2004, Psyent Corporation <www.psyent.com> 337e4dafaSPeter Tyser * Scott McNutt <smcnutt@psyent.com> 437e4dafaSPeter Tyser * 51a459660SWolfgang Denk * SPDX-License-Identifier: GPL-2.0+ 637e4dafaSPeter Tyser */ 737e4dafaSPeter Tyser 825ddd1fbSWolfgang Denk#include <asm-offsets.h> 937e4dafaSPeter Tyser#include <config.h> 1037e4dafaSPeter Tyser#include <version.h> 1137e4dafaSPeter Tyser 1237e4dafaSPeter Tyser/************************************************************************* 1337e4dafaSPeter Tyser * RESTART 1437e4dafaSPeter Tyser ************************************************************************/ 1537e4dafaSPeter Tyser 1637e4dafaSPeter Tyser .text 1737e4dafaSPeter Tyser .global _start 1837e4dafaSPeter Tyser 1937e4dafaSPeter Tyser_start: 20fd2712d0SThomas Chou wrctl status, r0 /* Disable interrupts */ 2137e4dafaSPeter Tyser /* ICACHE INIT -- only the icache line at the reset address 2237e4dafaSPeter Tyser * is invalidated at reset. So the init must stay within 2337e4dafaSPeter Tyser * the cache line size (8 words). If GERMS is used, we'll 2437e4dafaSPeter Tyser * just be invalidating the cache a second time. If cache 2537e4dafaSPeter Tyser * is not implemented initi behaves as nop. 2637e4dafaSPeter Tyser */ 2737e4dafaSPeter Tyser ori r4, r0, %lo(CONFIG_SYS_ICACHELINE_SIZE) 2837e4dafaSPeter Tyser movhi r5, %hi(CONFIG_SYS_ICACHE_SIZE) 2937e4dafaSPeter Tyser ori r5, r5, %lo(CONFIG_SYS_ICACHE_SIZE) 30fd2712d0SThomas Chou0: initi r5 31fd2712d0SThomas Chou sub r5, r5, r4 32fd2712d0SThomas Chou bgt r5, r0, 0b 3337e4dafaSPeter Tyser br _except_end /* Skip the tramp */ 3437e4dafaSPeter Tyser 3537e4dafaSPeter Tyser /* EXCEPTION TRAMPOLINE -- the following gets copied 3637e4dafaSPeter Tyser * to the exception address (below), but is otherwise at the 3737e4dafaSPeter Tyser * default exception vector offset (0x0020). 3837e4dafaSPeter Tyser */ 3937e4dafaSPeter Tyser_except_start: 4037e4dafaSPeter Tyser movhi et, %hi(_exception) 4137e4dafaSPeter Tyser ori et, et, %lo(_exception) 4237e4dafaSPeter Tyser jmp et 4337e4dafaSPeter Tyser_except_end: 4437e4dafaSPeter Tyser 4537e4dafaSPeter Tyser /* INTERRUPTS -- for now, all interrupts masked and globally 4637e4dafaSPeter Tyser * disabled. 4737e4dafaSPeter Tyser */ 4837e4dafaSPeter Tyser wrctl ienable, r0 /* All disabled */ 4937e4dafaSPeter Tyser 5037e4dafaSPeter Tyser /* DCACHE INIT -- if dcache not implemented, initd behaves as 5137e4dafaSPeter Tyser * nop. 5237e4dafaSPeter Tyser */ 5337e4dafaSPeter Tyser movhi r4, %hi(CONFIG_SYS_DCACHELINE_SIZE) 5437e4dafaSPeter Tyser ori r4, r4, %lo(CONFIG_SYS_DCACHELINE_SIZE) 5537e4dafaSPeter Tyser movhi r5, %hi(CONFIG_SYS_DCACHE_SIZE) 5637e4dafaSPeter Tyser ori r5, r5, %lo(CONFIG_SYS_DCACHE_SIZE) 5737e4dafaSPeter Tyser mov r6, r0 5837e4dafaSPeter Tyser1: initd 0(r6) 5937e4dafaSPeter Tyser add r6, r6, r4 6037e4dafaSPeter Tyser bltu r6, r5, 1b 6137e4dafaSPeter Tyser 6237e4dafaSPeter Tyser /* RELOCATE CODE, DATA & COMMAND TABLE -- the following code 6337e4dafaSPeter Tyser * assumes code, data and the command table are all 6437e4dafaSPeter Tyser * contiguous. This lets us relocate everything as a single 6537e4dafaSPeter Tyser * block. Make sure the linker script matches this ;-) 6637e4dafaSPeter Tyser */ 6737e4dafaSPeter Tyser nextpc r4 6837e4dafaSPeter Tyser_cur: movhi r5, %hi(_cur - _start) 6937e4dafaSPeter Tyser ori r5, r5, %lo(_cur - _start) 7037e4dafaSPeter Tyser sub r4, r4, r5 /* r4 <- cur _start */ 7137e4dafaSPeter Tyser mov r8, r4 7237e4dafaSPeter Tyser movhi r5, %hi(_start) 7337e4dafaSPeter Tyser ori r5, r5, %lo(_start) /* r5 <- linked _start */ 7437e4dafaSPeter Tyser beq r4, r5, 3f 7537e4dafaSPeter Tyser 76e900298eSThomas Chou movhi r6, %hi(CONFIG_SYS_MONITOR_LEN) 77e900298eSThomas Chou ori r6, r6, %lo(CONFIG_SYS_MONITOR_LEN) 78e900298eSThomas Chou add r6, r6, r5 7937e4dafaSPeter Tyser2: ldwio r7, 0(r4) 8037e4dafaSPeter Tyser addi r4, r4, 4 8137e4dafaSPeter Tyser stwio r7, 0(r5) 8237e4dafaSPeter Tyser addi r5, r5, 4 8337e4dafaSPeter Tyser bne r5, r6, 2b 8437e4dafaSPeter Tyser3: 8537e4dafaSPeter Tyser 8637e4dafaSPeter Tyser /* JUMP TO RELOC ADDR */ 8737e4dafaSPeter Tyser movhi r4, %hi(_reloc) 8837e4dafaSPeter Tyser ori r4, r4, %lo(_reloc) 8937e4dafaSPeter Tyser jmp r4 9037e4dafaSPeter Tyser_reloc: 9137e4dafaSPeter Tyser 9237e4dafaSPeter Tyser /* COPY EXCEPTION TRAMPOLINE -- copy the tramp to the 9337e4dafaSPeter Tyser * exception address. Define CONFIG_ROM_STUBS to prevent 9437e4dafaSPeter Tyser * the copy (e.g. exception in flash or in other 9537e4dafaSPeter Tyser * softare/firmware component). 9637e4dafaSPeter Tyser */ 9737e4dafaSPeter Tyser#if !defined(CONFIG_ROM_STUBS) 9837e4dafaSPeter Tyser movhi r4, %hi(_except_start) 9937e4dafaSPeter Tyser ori r4, r4, %lo(_except_start) 10037e4dafaSPeter Tyser movhi r5, %hi(_except_end) 10137e4dafaSPeter Tyser ori r5, r5, %lo(_except_end) 10237e4dafaSPeter Tyser movhi r6, %hi(CONFIG_SYS_EXCEPTION_ADDR) 10337e4dafaSPeter Tyser ori r6, r6, %lo(CONFIG_SYS_EXCEPTION_ADDR) 10437e4dafaSPeter Tyser beq r4, r6, 7f /* Skip if at proper addr */ 10537e4dafaSPeter Tyser 10637e4dafaSPeter Tyser6: ldwio r7, 0(r4) 10737e4dafaSPeter Tyser stwio r7, 0(r6) 10837e4dafaSPeter Tyser addi r4, r4, 4 10937e4dafaSPeter Tyser addi r6, r6, 4 11037e4dafaSPeter Tyser bne r4, r5, 6b 11137e4dafaSPeter Tyser7: 11237e4dafaSPeter Tyser#endif 11337e4dafaSPeter Tyser 11437e4dafaSPeter Tyser /* STACK INIT -- zero top two words for call back chain. 11537e4dafaSPeter Tyser */ 11637e4dafaSPeter Tyser movhi sp, %hi(CONFIG_SYS_INIT_SP) 11737e4dafaSPeter Tyser ori sp, sp, %lo(CONFIG_SYS_INIT_SP) 11837e4dafaSPeter Tyser addi sp, sp, -8 11937e4dafaSPeter Tyser stw r0, 0(sp) 12037e4dafaSPeter Tyser stw r0, 4(sp) 12137e4dafaSPeter Tyser mov fp, sp 12237e4dafaSPeter Tyser 123*3e468e68SThomas Chou /* Allocate and zero GD, update SP */ 124*3e468e68SThomas Chou mov r4, sp 125*3e468e68SThomas Chou movhi r2, %hi(board_init_f_mem@h) 126*3e468e68SThomas Chou ori r2, r2, %lo(board_init_f_mem@h) 127*3e468e68SThomas Chou callr r2 128*3e468e68SThomas Chou 129*3e468e68SThomas Chou /* Update stack- and frame-pointers */ 130*3e468e68SThomas Chou mov sp, r2 131*3e468e68SThomas Chou mov fp, sp 132*3e468e68SThomas Chou 13337e4dafaSPeter Tyser /* 1345ff10aa7SThomas Chou * Call board_init_f -- never returns 13537e4dafaSPeter Tyser */ 1365ff10aa7SThomas Chou mov r4, r0 1375ff10aa7SThomas Chou movhi r2, %hi(board_init_f@h) 1385ff10aa7SThomas Chou ori r2, r2, %lo(board_init_f@h) 1395ff10aa7SThomas Chou callr r2 14037e4dafaSPeter Tyser 14137e4dafaSPeter Tyser /* NEVER RETURNS -- but branch to the _start just 14237e4dafaSPeter Tyser * in case ;-) 14337e4dafaSPeter Tyser */ 14437e4dafaSPeter Tyser br _start 14537e4dafaSPeter Tyser 14637e4dafaSPeter Tyser 1475ff10aa7SThomas Chou 1485ff10aa7SThomas Chou/* 1495ff10aa7SThomas Chou * relocate_code -- Nios2 handles the relocation above. But 1505ff10aa7SThomas Chou * the generic board code monkeys with the heap, stack, etc. 1515ff10aa7SThomas Chou * (it makes some assumptions that may not be appropriate 1525ff10aa7SThomas Chou * for Nios). Nevertheless, we capitulate here. 1535ff10aa7SThomas Chou * 1545ff10aa7SThomas Chou * We'll call the board_init_r from here since this isn't 1555ff10aa7SThomas Chou * supposed to return. 1565ff10aa7SThomas Chou * 1575ff10aa7SThomas Chou * void relocate_code (ulong sp, gd_t *global_data, 1585ff10aa7SThomas Chou * ulong reloc_addr) 1595ff10aa7SThomas Chou * __attribute__ ((noreturn)); 1605ff10aa7SThomas Chou */ 1615ff10aa7SThomas Chou .text 1625ff10aa7SThomas Chou .global relocate_code 1635ff10aa7SThomas Chou 1645ff10aa7SThomas Chourelocate_code: 1655ff10aa7SThomas Chou mov sp, r4 /* Set the new sp */ 1665ff10aa7SThomas Chou mov r4, r5 1674192b8c3SThomas Chou 1684192b8c3SThomas Chou /* 1694192b8c3SThomas Chou * ZERO BSS/SBSS -- bss and sbss are assumed to be adjacent 1704192b8c3SThomas Chou * and between __bss_start and __bss_end. 1714192b8c3SThomas Chou */ 1724192b8c3SThomas Chou movhi r5, %hi(__bss_start) 1734192b8c3SThomas Chou ori r5, r5, %lo(__bss_start) 1744192b8c3SThomas Chou movhi r6, %hi(__bss_end) 1754192b8c3SThomas Chou ori r6, r6, %lo(__bss_end) 1764192b8c3SThomas Chou beq r5, r6, 5f 1774192b8c3SThomas Chou 1784192b8c3SThomas Chou4: stwio r0, 0(r5) 1794192b8c3SThomas Chou addi r5, r5, 4 1804192b8c3SThomas Chou bne r5, r6, 4b 1814192b8c3SThomas Chou5: 1824192b8c3SThomas Chou 1835ff10aa7SThomas Chou movhi r8, %hi(board_init_r@h) 1845ff10aa7SThomas Chou ori r8, r8, %lo(board_init_r@h) 1855ff10aa7SThomas Chou callr r8 1865ff10aa7SThomas Chou ret 187