locore.S revision 1.8
11.8Sthorpej/* $NetBSD: locore.S,v 1.8 2002/08/17 16:36:34 thorpej Exp $ */ 21.1Schris 31.1Schris/* 41.1Schris * Copyright (C) 1994-1997 Mark Brinicombe 51.1Schris * Copyright (C) 1994 Brini 61.1Schris * All rights reserved. 71.1Schris * 81.1Schris * Redistribution and use in source and binary forms, with or without 91.1Schris * modification, are permitted provided that the following conditions 101.1Schris * are met: 111.1Schris * 1. Redistributions of source code must retain the above copyright 121.1Schris * notice, this list of conditions and the following disclaimer. 131.1Schris * 2. Redistributions in binary form must reproduce the above copyright 141.1Schris * notice, this list of conditions and the following disclaimer in the 151.1Schris * documentation and/or other materials provided with the distribution. 161.1Schris * 3. All advertising materials mentioning features or use of this software 171.1Schris * must display the following acknowledgement: 181.1Schris * This product includes software developed by Brini. 191.1Schris * 4. The name of Brini may not be used to endorse or promote products 201.1Schris * derived from this software without specific prior written permission. 211.1Schris * 221.1Schris * THIS SOFTWARE IS PROVIDED BY BRINI ``AS IS'' AND ANY EXPRESS OR 231.1Schris * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 241.1Schris * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 251.1Schris * IN NO EVENT SHALL BRINI BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 261.1Schris * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 271.1Schris * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 281.1Schris * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 291.1Schris * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 301.1Schris * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 311.1Schris * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 321.1Schris */ 331.1Schris 341.1Schris#include "opt_ipkdb.h" 351.1Schris#include "assym.h" 361.1Schris#include <sys/syscall.h> 371.1Schris#include <sys/errno.h> 381.1Schris#include <machine/asm.h> 391.1Schris#include <machine/cpu.h> 401.1Schris#include <machine/frame.h> 411.1Schris#include <machine/param.h> 421.1Schris 431.1Schris/* What size should this really be ? It is only used by init_arm() */ 441.1Schris#define INIT_ARM_STACK_SIZE 2048 451.1Schris 461.1Schris/* 471.1Schris * This is for kvm_mkdb, and should be the address of the beginning 481.1Schris * of the kernel text segment (not necessarily the same as kernbase). 491.1Schris */ 501.1Schris 511.2Sthorpej .text 521.2Sthorpej .align 0 531.5Sthorpej 541.5SthorpejENTRY_NP(kernel_text) 551.2Sthorpej 561.1SchrisASENTRY_NP(start) 571.7Sbriggs add r1, pc, #(.Lstart - . - 8) 581.4Sthorpej ldmia r1, {r1, r2, sp} /* Set initial stack and */ 591.4Sthorpej sub r2, r2, r1 /* get zero init data */ 601.1Schris mov r3, #0 611.1Schris 621.7Sbriggs.L1: 631.4Sthorpej str r3, [r1], #0x0004 /* Zero the bss */ 641.1Schris subs r2, r2, #4 651.7Sbriggs bgt .L1 661.1Schris 671.4Sthorpej mov fp, #0x00000000 /* trace back starts here */ 681.4Sthorpej bl _C_LABEL(initarm) /* Off we go */ 691.1Schris 701.1Schris /* init arm will return the new stack pointer. */ 711.1Schris mov sp, r0 721.1Schris 731.1Schris mov fp, #0x00000000 /* trace back starts here */ 741.1Schris mov ip, sp 751.1Schris stmfd sp!, {fp, ip, lr, pc} 761.1Schris sub fp, ip, #4 771.1Schris 781.4Sthorpej bl _C_LABEL(main) /* call main()! */ 791.1Schris 801.8Sthorpej add r0, pc, #.Lmainreturned - . - 8 811.4Sthorpej b _C_LABEL(panic) 821.4Sthorpej /* NOTEACHED */ 831.1Schris 841.7Sbriggs.Lstart: 851.1Schris .word _edata 861.1Schris .word _end 871.1Schris .word svcstk + INIT_ARM_STACK_SIZE 881.4Sthorpej 891.8Sthorpej.Lmainreturned: 901.4Sthorpej .asciz "main() returned" 911.4Sthorpej .align 0 921.1Schris 931.1Schris .bss 941.1Schrissvcstk: 951.1Schris .space INIT_ARM_STACK_SIZE 961.1Schris 971.1Schris .text 981.1Schris .align 0 991.1Schris 1001.1Schris#ifndef OFW 1011.1Schris /* OFW based systems will used OF_boot() */ 1021.1Schris 1031.8Sthorpej.Lcpufuncs: 1041.1Schris .word _C_LABEL(cpufuncs) 1051.1Schris 1061.1SchrisENTRY_NP(cpu_reset) 1071.7Sbriggs mrs r2, cpsr 1081.1Schris bic r2, r2, #(PSR_MODE) 1091.1Schris orr r2, r2, #(PSR_SVC32_MODE) 1101.1Schris orr r2, r2, #(I32_bit | F32_bit) 1111.1Schris msr cpsr_all, r2 1121.1Schris 1131.8Sthorpej ldr r4, .Lcpu_reset_address 1141.1Schris ldr r4, [r4] 1151.1Schris 1161.8Sthorpej ldr r0, .Lcpufuncs 1171.7Sbriggs add lr, pc, #.Lboot_cache_purged - . - 8 1181.3Sthorpej ldr pc, [r0, #CF_IDCACHE_WBINV_ALL] 1191.1Schris 1201.7Sbriggs.Lboot_cache_purged: 1211.1Schris 1221.1Schris /* 1231.1Schris * Load the cpu_reset_needs_v4_MMU_disable flag to determine if it's 1241.1Schris * necessary. 1251.1Schris */ 1261.1Schris 1271.8Sthorpej ldr r1, .Lcpu_reset_needs_v4_MMU_disable 1281.1Schris ldr r1, [r1] 1291.1Schris cmp r1, #0 1301.1Schris 1311.1Schris /* 1321.1Schris * MMU & IDC off, 32 bit program & data space 1331.1Schris * Hurl ourselves into the ROM 1341.1Schris */ 1351.1Schris mov r0, #(CPU_CONTROL_32BP_ENABLE | CPU_CONTROL_32BD_ENABLE) 1361.1Schris mcr 15, 0, r0, c1, c0, 0 1371.6Sthorpej mcrne 15, 0, r0, c8, c7, 0 /* nail I+D TLB on ARMv4 and greater */ 1381.1Schris mov pc, r4 1391.1Schris 1401.1Schris /* 1411.1Schris * _cpu_reset_address contains the address to branch to, to complete 1421.1Schris * the cpu reset after turning the MMU off 1431.1Schris * This variable is provided by the hardware specific code 1441.1Schris */ 1451.8Sthorpej.Lcpu_reset_address: 1461.1Schris .word _C_LABEL(cpu_reset_address) 1471.1Schris 1481.1Schris /* 1491.1Schris * cpu_reset_needs_v4_MMU_disable contains a flag that signals if the 1501.1Schris * v4 MMU disable instruction needs executing... it is an illegal instruction 1511.1Schris * on f.e. ARM6/7 that locks up the computer in an endless illegal 1521.1Schris * instruction / data-abort / reset loop. 1531.1Schris */ 1541.8Sthorpej.Lcpu_reset_needs_v4_MMU_disable: 1551.1Schris .word _C_LABEL(cpu_reset_needs_v4_MMU_disable) 1561.1Schris 1571.1Schris#endif /* OFW */ 1581.1Schris 1591.1Schris#ifdef IPKDB 1601.1Schris/* 1611.1Schris * Execute(inst, psr, args, sp) 1621.1Schris * 1631.1Schris * Execute INSTruction with PSR and ARGS[0] - ARGS[3] making 1641.1Schris * available stack at SP for next undefined instruction trap. 1651.1Schris * 1661.1Schris * Move the instruction onto the stack and jump to it. 1671.1Schris */ 1681.1SchrisENTRY_NP(Execute) 1691.1Schris mov ip, sp 1701.1Schris stmfd sp!, {r2, r4-r7, fp, ip, lr, pc} 1711.1Schris sub fp, ip, #4 1721.1Schris mov ip, r3 1731.7Sbriggs ldr r7, .Lreturn 1741.1Schris stmfd sp!, {r0, r7} 1751.7Sbriggs add r7, pc, #.LExec - . - 8 1761.1Schris mov r5, r1 1771.7Sbriggs mrs r4, cpsr 1781.1Schris ldmia r2, {r0-r3} 1791.1Schris mov r6, sp 1801.1Schris mov sp, ip 1811.1Schris msr cpsr_all, r5 1821.1Schris mov pc, r6 1831.7Sbriggs.LExec: 1841.7Sbriggs mrs r5, cpsr 1851.1Schris/* XXX Cannot switch thus easily back from user mode */ 1861.1Schris msr cpsr_all, r4 1871.1Schris add sp, r6, #8 1881.1Schris ldmfd sp!, {r6} 1891.1Schris stmia r6, {r0-r3} 1901.1Schris mov r0, r5 1911.1Schris ldmdb fp, {r4-r7, fp, sp, pc} 1921.7Sbriggs.Lreturn: 1931.1Schris mov pc, r7 1941.1Schris#endif 1951.1Schris 1961.1Schris/* 1971.1Schris * setjump + longjmp 1981.1Schris */ 1991.1SchrisENTRY(setjmp) 2001.1Schris stmia r0, {r4-r14} 2011.1Schris mov r0, #0x00000000 2021.1Schris mov pc, lr 2031.1Schris 2041.1SchrisENTRY(longjmp) 2051.1Schris ldmia r0, {r4-r14} 2061.1Schris mov r0, #0x00000001 2071.1Schris mov pc, lr 2081.1Schris 2091.1Schris .data 2101.1Schris .global _C_LABEL(esym) 2111.1Schris_C_LABEL(esym): .word _C_LABEL(end) 2121.1Schris 2131.1SchrisENTRY_NP(abort) 2141.1Schris b _C_LABEL(abort) 2151.1Schris 2161.1Schris 2171.1Schris/* 2181.1Schris * Atomic bit set and clear functions 2191.1Schris */ 2201.1Schris 2211.1SchrisENTRY(atomic_set_bit) 2221.7Sbriggs mrs r2, cpsr 2231.1Schris orr r3, r2, #(I32_bit) 2241.1Schris msr cpsr_all, r3 2251.1Schris 2261.1Schris ldr r3, [r0] 2271.1Schris orr r3, r3, r1 2281.1Schris str r3, [r0] 2291.1Schris 2301.1Schris msr cpsr_all, r2 2311.1Schris mov pc, lr 2321.1Schris 2331.1Schris 2341.1SchrisENTRY(atomic_clear_bit) 2351.7Sbriggs mrs r2, cpsr 2361.1Schris orr r3, r2, #(I32_bit) 2371.1Schris msr cpsr_all, r3 2381.1Schris 2391.1Schris ldr r3, [r0] 2401.1Schris bic r3, r3, r1 2411.1Schris str r3, [r0] 2421.1Schris 2431.1Schris msr cpsr_all, r2 2441.1Schris mov pc, lr 2451.1Schris 2461.1Schris/* End of locore.S */ 247