1 /* 2 * CPU-specific routines originally from U-Boot. 3 * See: uboot-xburst/files/arch/mips/cpu/xburst/cpu.c 4 * See: u-boot/arch/mips/include/asm/cacheops.h 5 * 6 * Copyright (C) 2000-2009 Wolfgang Denk, DENX Software Engineering, <wd@denx.de> 7 * Copyright (C) 2015, 2016 Paul Boddie <paul@boddie.org.uk> 8 * 9 * This program is free software; you can redistribute it and/or 10 * modify it under the terms of the GNU General Public License as 11 * published by the Free Software Foundation; either version 2 of 12 * the License, or (at your option) any later version. 13 * 14 * This program is distributed in the hope that it will be useful, 15 * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 * GNU General Public License for more details. 18 * 19 * You should have received a copy of the GNU General Public License 20 * along with this program; if not, write to the Free Software 21 * Foundation, Inc., 51 Franklin Street, Fifth Floor, 22 * Boston, MA 02110-1301, USA 23 */ 24 25 #include "mips.h" 26 #include "paging.h" 27 #include "sdram.h" 28 29 .text 30 .globl flush_icache_tag 31 .globl flush_icache_region 32 .globl flush_icache_config 33 .globl flush_dcache_region 34 .globl handle_error_level 35 .globl enable_interrupts 36 .globl init_interrupts 37 .globl invoke_task 38 .globl configure_tlb 39 .globl map_page_set_index 40 .globl map_page_index_op 41 .globl map_page_op 42 .set noreorder 43 44 45 46 flush_icache_tag: 47 mtc0 $zero, CP0_TAGLO 48 mtc0 $zero, CP0_TAGHI 49 jr $ra 50 nop 51 52 53 54 flush_icache_region: 55 cache Index_Store_Tag_I, 0($a0) 56 jr $ra 57 nop 58 59 60 61 flush_icache_config: 62 move $t3, $zero 63 mfc0 $t3, CP0_CONFIG, 7 64 nop 65 ori $t3, 2 66 mtc0 $t3, CP0_CONFIG, 7 67 jr $ra 68 nop 69 70 71 72 flush_dcache_region: 73 cache Index_Writeback_Inv_D, 0($a0) 74 jr $ra 75 nop 76 77 78 79 handle_error_level: 80 mfc0 $t3, CP0_STATUS 81 li $t4, 0xfffffffb /* ERL = 0 */ 82 and $t3, $t3, $t4 83 mtc0 $t3, CP0_STATUS 84 jr $ra 85 nop 86 87 88 89 enable_interrupts: 90 mfc0 $t3, CP0_STATUS 91 li $t4, 0x0000fc01 /* IE = enable interrupts */ 92 or $t3, $t3, $t4 93 mtc0 $t3, CP0_STATUS 94 jr $ra 95 nop 96 97 98 99 init_interrupts: 100 101 /* Set exception registers. */ 102 103 mtc0 $zero, CP0_WATCHLO 104 li $t3, 0x00800000 /* IV = 1 (use 0x80000200 for interrupts) */ 105 mtc0 $t3, CP0_CAUSE 106 mfc0 $t4, CP0_STATUS 107 li $t3, 0xffbfffff /* BEV=0 */ 108 and $t3, $t3, $t4 109 mtc0 $t3, CP0_STATUS 110 jr $ra 111 nop 112 113 114 115 /* (u8 asid, u32 *base, u32 *stack_pointer) */ 116 117 invoke_task: 118 mtc0 $a0, CP0_ENTRYHI 119 nop 120 move $t4, $a2 /* use arguments before they are overwritten */ 121 lw $sp, 0($t4) /* set the stack pointer */ 122 move $t3, $a1 /* load parameters from the stored registers */ 123 lw $a0, 16($t3) 124 lw $a1, 20($t3) 125 lw $a2, 24($t3) 126 lw $a3, 28($t3) 127 lw $t9, 100($t3) 128 lw $gp, 104($t3) 129 mtc0 $t9, CP0_EPC 130 mfc0 $t3, CP0_STATUS 131 ori $t3, $t3, 0x2 /* EXL = 1 */ 132 mtc0 $t3, CP0_STATUS 133 eret 134 nop 135 136 137 138 configure_tlb: 139 mtc0 $zero, CP0_CONTEXT 140 mtc0 $zero, CP0_WIRED /* first random entry is zero */ 141 mfc0 $v0, CP0_CONFIG /* return the limit */ 142 jr $ra 143 nop 144 145 146 147 /* (u32 index) */ 148 149 map_page_set_index: 150 mtc0 $a0, CP0_INDEX 151 jr $ra 152 nop 153 154 155 156 /* (u32 lower, u32 upper, u32 start, u32 pagemask) */ 157 158 map_page_index_op: 159 jal map_page_op_setup 160 nop 161 162 tlbwi 163 jr $ra 164 nop 165 166 167 168 /* (u32 lower, u32 upper, u32 start, u32 pagemask) */ 169 170 map_page_op: 171 jal map_page_op_setup 172 nop 173 174 tlbwr 175 jr $ra 176 nop 177 178 179 180 /* (u32 lower, u32 upper, u32 start, u32 pagemask) */ 181 182 map_page_op_setup: 183 mtc0 $a3, CP0_PAGEMASK 184 185 /* Set physical address. */ 186 187 mtc0 $a0, CP0_ENTRYLO0 188 mtc0 $a1, CP0_ENTRYLO1 189 190 /* Set virtual address. */ 191 192 mtc0 $a2, CP0_ENTRYHI 193 jr $ra 194 nop 195 196 197 198 .set reorder