windows-nt/Source/XPSP1/NT/base/boot/bootcode/ntfs/ia64/simsal.s
2020-09-26 16:20:57 +08:00

260 lines
6.9 KiB
ArmAsm

/**
*** Copyright (C) 1996-97 Intel Corporation. All rights reserved.
***
*** The information and source code contained herein is the exclusive
*** property of Intel Corporation and may not be disclosed, examined
*** or reproduced in whole or in part without explicit written authorization
*** from the company.
**/
//++
//
// Module name
// SIMSAL.S
// Author
// Allen Kay (akay) May-6-97
// Description
// Initializes the CPU and loads the first sector from the boot partition.
// SIMSAL does the following:
// 1. Initialize PSR with interrupt disabled.
// 2. Invalidate ALAT.
// 3. Invalidate RS.
// 4. Setup GP.
// 5. Set region registers rr[r0] - rr[r7] to RID=0, PS=8K, E=0.
// 6. Initialize SP to 0x00902000.
// 7. Initialize BSP to 0x00202000.
// 8. Enable register stack engine.
// 9. Setup IVA to 0x001F8000.
// 10. Setup virtual->physical address translation
// 0x80000000->0x00000000 in dtr0/itr0 for NT kernel.
// 11. Setup virtual->physical address translation
// 0x80400000->0x00400000 in dtr1/itr1 for HAL.dll.
// 12. Setup virtual->physical address translation
// 0x00800000->0x00800000 in dtr1/itr1 for NTLDR.
//---
#include "ksia64.h"
#include "susetup.h"
#include "ntfsdefs.h"
.file "start.s"
.global SscExit
.type SscExit, @function
.global ReadSectors
.type ReadSectors, @function
#define Buffer 0x0
//
// Interrupt Vector Table
//
#define VECTOR(Offset, Name) \
.##org Offset; \
Name:: \
mov a0 = cr##.##iip; \
br##.##call##.##sptk##.##clr brp = SscExit
.section ivt = "ax", "progbits"
BlIvtBase::
VECTOR(0x0000, BlVhptTransVector)
VECTOR(0x0400, BlInstTlbVector)
VECTOR(0x0800, BlDataTlbVector)
VECTOR(0x0C00, BlAltInstTlbVector)
VECTOR(0x1000, BlAltDataTlbVector)
VECTOR(0x1400, BlNestedTlbVector)
VECTOR(0x1800, BlInstKeyMissVector)
VECTOR(0x1C00, BlDataKeyMissVector)
VECTOR(0x2000, BlDirtyBitVector)
VECTOR(0x2400, BlInstAccessBitVector)
VECTOR(0x2800, BlDataAccessBitVector)
VECTOR(0x2C00, BlBreakVector)
VECTOR(0x3000, BlExternalInterruptVector)
VECTOR(0x5000, BlPageNotPresentVector)
VECTOR(0x5100, BlKeyPermVector)
VECTOR(0x5200, BlInstAccessRightsVector)
VECTOR(0x5300, BlDataAccessRightsVector)
VECTOR(0x5400, BlGeneralExceptionVector)
VECTOR(0x5500, BlDisabledFpRegisterVector)
VECTOR(0x5600, BlNatConsumptionVector)
VECTOR(0x5700, BlSpeculationVector)
VECTOR(0x6900, BlIA32ExceptionVector)
VECTOR(0x6A00, BlIA32InterceptionVector)
VECTOR(0x6B00, BlIA32InterruptionVector)
// ***************************************************************************
// Initialize the processor
// ***************************************************************************
NESTED_ENTRY(SimSal)
NESTED_SETUP(3,3,8,0)
PROLOGUE_END
rpT0 = t22
rpT1 = t21
rpT2 = t20
rpT3 = t19
mov psr.l = zero // initialize psr.l
movl t0 = FPSR_FOR_KERNEL
mov ar.fpsr = t0 // initialize fpsr
invala // invalidate ALAT
mov ar.rsc = zero // invalidate register stack
loadrs
//
// Initialize Region Registers
//
mov t0 = RR_PAGE_SIZE
mov t1 = zero
Bl_RRLoop:
dep t2 = t2, t1, RR_SHIFT, RR_BITS
mov rr[t2] = t0
add t1 = 1, t1
cmp4.geu pt0, pt1 = RR_SIZE, t1
(pt0) br.cond.sptk.clr Bl_RRLoop
//
// Initialize the protection key registers with only pkr[0] = valid.
//
mov t0 = PKR_VALID
mov t1 = zero
mov pkr[t1] = t0
mov t0 = zero
Bl_PKRLoop:
add t1 = t1, zero, 1 // increment PKR
cmp.gtu pt0, pt1 = PKRNUM, t1
(pt0) mov pkr[t1] = t0
(pt0) br.cond.sptk.clr Bl_PKRLoop
//
// Setup SP
//
movl sp = BL_SP_BASE
//
// Set up tbe scratch area
//
add sp = -STACK_SCRATCH_AREA, sp
//
// Setup register stack backing store.
//
mov t0 = RSC_KERNEL_DISABLED
mov ar.rsc = t0
movl t1 = BL_SP_BASE
mov ar.bspstore = t1
//
// Setup the base address of interrupt vector table
//
movl t0 = BlIvtBase
mov cr.iva = t0
//
// Setup system address translation for NT kernel
//
//
movl t0 = BOOT_SYSTEM_PAGE << PAGE_SHIFT
ADDS4 (t0, 0, t0)
mov cr.ifa = t0
movl t1 = IDTR_IIP_VALUE(0,0,BL_PAGE_SIZE)
mov cr.itir = t1
movl t2 = TR_VALUE(1,BOOT_PHYSICAL_PAGE,3,0,1,1,1,1)
mov t3 = zero
itr.d dtr[t3] = t2
itr.i itr[t3] = t2
//
// Setup the aliased kernel space
//
zxt4 t0 = t0 // zero extend kernel address
mov t4 = 6 // create alias in region 6
mov t5 = 2 // index
dep t0 = t4, t0, 61, 3
mov cr.ifa = t0
itr.i itr[t5] = t2
//
// Setup 1-1 address translation for NT kernel
//
movl t0 = BOOT_USER_PAGE << PAGE_SHIFT
ADDS4 (t0, 0, t0)
mov cr.ifa = t0
movl t2 = TR_VALUE(1,BOOT_USER_PAGE,3,0,1,1,1,1)
add t3 = 1, t3
itr.d dtr[t3] = t2
itr.i itr[t3] = t2
//
// Turn on address translation, interrupt, psr.ed, protection key.
//
movl t1 = MASK(PSR_BN,1) | MASK(PSR_IT,1) | MASK(PSR_DA,1) | MASK(PSR_RT,1) | MASK(PSR_DT,1) | MASK(PSR_PK,1) | MASK(PSR_I,1)| MASK(PSR_IC,1)
mov cr.ipsr = t1
//
// Initialize DCR to defer all speculation faults
//
movl t0 = DCR_DEFER_ALL
mov cr.dcr = t0
//
// Read the first sector of the boot partition
//
mov out0 = zero
movl out1 = 1
movl out2 = Buffer
mov ap = sp
br.call.sptk.many brp = ReadSectors
//
// Read the first sector of the boot partition
//
mov out0 = zero
#ifdef BSDT
movl t0 = Buffer // get the sector count
add rpT0 = 6, t0
ld2 out1 = [rpT0]
#else
movl out1 = 64 // read 64 sectors, 32KB
#endif
movl out2 = Buffer
mov ap = sp
br.call.sptk.many brp = ReadSectors
//
// Now pass control to the first sector code
//
#ifdef BSDT
movl t0 = Buffer // (the second sector).
add rpT0 = 8, t0
ld4 t1 = [rpT0]
#else
movl t1 = 0xd0 // since no bsdt, hardcode it for now.
#endif
mov cr.iip = t1
rfi;;
NESTED_EXIT(SimSal)