Windows NT 4.0 source code leak
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

621 lines
15 KiB

/* #pragma comment(exestr, "@(#) NEC(MIPS) r94anmi.s 1.2 95/10/17 01:19:11" ) */
//
// TITLE("R94A NMI routine")
//++
//
// Copyright (c) 1995 NEC Corporation
//
// Module Name:
//
// r94anmi.s
//
// Abstract:
//
// This routine support for dump switch.
//
// Author:
//
// Akitoshi Kuriyama (NEC Software Kobe,Inc)
//
// Environment:
//
// Kernel mode only.
//
// R4400 based only.
//
// Revision History:
//
// [email protected] Sun Oct 15 20:11:38 JST 1995
// - new code for J94D (!_MRCDUMP_ _MRCPOWER_ compile option need)
//
//--
#include "halmips.h"
SBTTL("NMI dispatch routine")
//++
//
// VOID
// HalpNMIDispatch (
// VOID
// )
//
// Routine Description:
//
// This function was called by firmware when NMI occuerd.
//
// Arguments:
//
// none.
//
// Return Value:
//
// none.
//
//--
LEAF_ENTRY(HalpNMIDispatch)
.set noreorder
.set noat
//
// Save temporary Registers for use.
// save area shoud have for every processros.
//
li k0,0xffffc070 // get processor number.
lw k0,(k0) //
bne k0,zero,10f //
nop // fill
la k1,HalpNMISave0 // set save address.
j 20f //
nop // fill
10:
la k1,HalpNMISave1 // set save address.
nop // 1 cycle hazzerd
20:
sw AT,0x0(k1) // register save.
sw v0,0x4(k1) //
sw v1,0x8(k1) //
sw a0,0xc(k1) //
sw a1,0x10(k1) //
sw a2,0x14(k1) //
sw a3,0x18(k1) //
sw t0,0x1c(k1) //
sw t1,0x20(k1) //
sw t2,0x24(k1) //
sw t3,0x28(k1) //
sw t4,0x2c(k1) //
sw t5,0x30(k1) //
sw t6,0x34(k1) //
sw t7,0x38(k1) //
sw t8,0x3c(k1) //
sw t9,0x40(k1) //
sw gp,0x44(k1) //
sw sp,0x48(k1) //
sw s8,0x4c(k1) //
sw ra,0x50(k1) //
mfc0 k0,psr //
nop //
nop //
sw k0,0x54(k1) //
nop //
mfc0 k0,cause //
nop //
nop //
sw k0,0x58(k1) //
nop //
mfc0 k0,epc //
nop //
nop //
sw k0,0x5c(k1) //
nop //
mfc0 k0,errorepc //
nop //
nop //
sw k0,0x60(k1) //
nop //
mfc0 k0,cacheerr //
nop //
nop //
sw k0,0x64(k1) //
sdc1 f0,0x68(k1) //
//
// Set Dump Switch Status register to tlb fixed entry
//
li t0,4 // set index 4(hurricane register)
li t1,0x80012 << 6 // set MRC register
li t2,0x8000e << 6 // set Self-Test address
mfc0 t3,index // save tlb registers
mfc0 t4,entryhi //
mfc0 t5,entrylo0 //
mfc0 t6,entrylo1 //
mfc0 t7,pagemask //
mtc0 t0,index //
nop
nop
nop
tlbr // read index 4 tlb
nop
nop
nop
nop
mfc0 t8,entrylo0 // Get entrylo0
mfc0 t9,entrylo1 // Get entrylo1
nop
nop
nop
or t1,t8,t1 // set MRC address
or t2,t8,t2 // set Self-test address
nop
mtc0 t1,entrylo0 // set MRC to tlb 4 0
mtc0 t2,entrylo1 // set Self-test to tlb 4 1
nop //
nop //
nop //
nop //
tlbwi // write to tlb entry
nop //
nop //
nop //
nop //
//
// read dump status
//
#if defined(_MRCDUMP_)
li t1,0xffffc108 // load MRC Mode value
#else // SELFTEST DUMP
li t1,0xffffd000 // load Self-Test value
li k0,0x1b // set dash
sb k0,(t1) // display led
sync
#endif // _MRCDUMP_
lb k0,(t1) // load Dump switch status.
nop //
lb k0,(t1) // wait
nop //
//
// Check dump status
//
li t1,2 // check for dump switch
and k0,k0,t1 //
#if defined(_MRCDUMP_)
beq k0,zero,30f // if 0 dump swith was not pressed
#else // _MRCDUMP_
bne k0,zero,30f // if 0 dump swith was pressed
#endif // _MRCDUMP_
nop //
#if !defined(_MRCDUMP_)
li t1,0xffffd000 // set dump switch status address
li t2,0x1b // display LED dash
sb t2,(t1) //
sync //
#endif // not _MRCDUMP_
//
// enable powoff NMI
//
#if defined(_MRCPOWER_)
li t1,0xffffc108 //
li t0,0x82 //
nop //
sb t0,(t1) //
nop //
li t0,0x80 //
nop //
sb t0,(t1) //
nop //
li t0,0x02 //
nop //
sb t0,(t1) //
nop //
#endif // _MRCPOWER_
//
// restore tlb 4 entry
//
mtc0 t8,entrylo0 // restore tlb 4 0
mtc0 t9,entrylo1 // restore tlb 4 1
nop //
nop //
nop //
nop //
tlbwi // write to tlb entry
nop //
nop //
nop //
nop //
//
// restore tlb registers
//
mtc0 t3,index //
mtc0 t4,entryhi //
mtc0 t5,entrylo0 //
mtc0 t6,entrylo1 //
mtc0 t7,pagemask //
#if !defined(_MRCDUMP_)
la k0,0xffffc5b8 // get NEC I/O port value
lb t0,(k0) //
nop // 1 cycle hazzerd
li t1,0xfd // clear dump enable bit
and t0,t0,t1
sb t0,(k0) // set NEC I/O port value
#endif // not _MRCDUMP_
//
// set NMI flag 1
//
la t2,HalpNMIFlag // set NMI flag address
li t3,0xa0000000 // set KSEG1_BASE
or t2,t2,t3 //
li t3,1 //
sw t3,(t2) // set NMI flag 1
//
// set dump flag 1
//
la t2,HalpDumpNMIFlag // set Dump NMI flag address
li t3,0xa0000000 // set KSEG1_BASE
or t2,t2,t3 //
li t3,1 //
sw t3,(t2) // set NMI flag 1
//
// clear psr BEV bit
//
mfc0 t0,psr // get psr
li t2,0xffbfffff // clear BEV bit
nop // fill
nop // fill
and t0,t0,t2 //
nop //
mtc0 t0,psr // set psr
lw t0,0x1c(k1) // restore temporary registers
lw t1,0x20(k1) //
lw t2,0x24(k1) //
lw t3,0x28(k1) //
lw t4,0x2c(k1) //
lw t5,0x30(k1) //
lw t6,0x34(k1) //
lw t7,0x38(k1) //
lw t8,0x3c(k1) //
lw t9,0x40(k1) //
lw AT,0x0(k1) //
eret // return to error epc
nop // errata
nop //
nop //
eret //
nop //
30:
//
// No Dump Switch.
//
// Check Power Switch
#if defined(_MRCPOWER_)
li t1,0xffffc108
nop
li t0,0x02
nop
sb t0,(t1)
nop
#endif // _MRCPOWER_
mtc0 t8,entrylo0 // restore tlb 4
mtc0 t9,entrylo1 // restore tlb 4
nop //
nop //
nop //
nop //
tlbwi // write to tlb entry
nop //
nop //
nop //
nop //
mtc0 t3,index // restore tlb registers
mtc0 t4,entryhi //
mtc0 t5,entrylo0 //
mtc0 t6,entrylo1 //
mtc0 t7,pagemask //
//
// set NMI flag 1
//
la t2,HalpNMIFlag // set NMI flag address
li t3,0xa0000000 // set KSEG1_BASE
or t2,t2,t3 //
li t3,1 //
sw t3,(t2) // set NMI flag 1
// S003 +++
li t1,0xffffc078 // check NMI source
lw t0,(t1) // check NMI source
nop //
beq t0,zero,40f //
nop //
li t1,0xffffc020
nop
ldc1 f0,(t1) // clear processor invalid
nop
sdc1 f0,0x70(k1) // save processor invalid
40:
// S003 ---
mfc0 t0,psr // get psr
li t2,0xffbfffff // clear BEV bit
nop // fill
nop // fill
and t0,t0,t2 //
nop //
mtc0 t0,psr // set psr
lw t0,0x1c(k1) // restore temporary registers
lw t1,0x20(k1) //
lw t2,0x24(k1) //
lw t3,0x28(k1) //
lw t4,0x2c(k1) //
lw t5,0x30(k1) //
lw t6,0x34(k1) //
lw t7,0x38(k1) //
lw t8,0x3c(k1) //
lw t9,0x40(k1) //
lw AT,0x0(k1) //
ldc1 f0,0x68(k1) //
nop
eret // return to errorepc
nop // errata
nop //
nop //
eret //
nop //
// L001 ---
.set at
.set reorder
.end HalpNMIDispatch
// Start M008
SBTTL("Software Power Off")
//++
//
// VOID
// HalpPowOffNMIDispatch (
// VOID
// )
//
// Routine Description:
//
// This function was called by firmware when NMI occuerd.
//
// Arguments:
//
// none.
//
// Return Value:
//
// none.
//
//--
LEAF_ENTRY(HalpPowOffNMIDispatch)
.set noat
.set noreorder
//
// Save temporary Registers for use.
// save area shoud have for every processros.
//
li k0,0xffffc070 // get processor number.
lw k0,(k0) //
bne k0,zero,60f //
nop // fill
la k1,HalpNMISave0 // set save address.
j 70f //
nop // fill
60:
la k1,HalpNMISave1 // set save address.
nop // 1 cycle hazzerd
70:
sw t0,0(k1) // save temporary registers
sw t1,4(k1) //
sw t2,8(k1) //
sw t3,12(k1) //
sw t4,16(k1) //
sw t5,20(k1) //
sw t6,24(k1) //
sw t7,28(k1) //
sw AT,32(k1) //
//
// Set Power Switch Status register to tlb fixed entry
//
li t0,4 // set index 4(hurricane register)
li t1,0x80012 << 6 // set MRC register
mfc0 t3,index // save tlb registers
mfc0 t4,entryhi //
mfc0 t5,entrylo0 //
mfc0 t6,entrylo1 //
mfc0 t7,pagemask //
mtc0 t0,index //
nop
nop
nop
tlbr // read index 4 tlb
nop
nop
nop
nop
mfc0 t2,entrylo0 // set Self-test address to tlb
nop
nop
nop
or t1,t2,t1
nop
mtc0 t1,entrylo0 // set Self-Test to tlb 4
nop //
nop //
nop //
nop //
tlbwi // write to tlb entry
nop //
nop //
nop //
nop //
li t1,0xffffc100 // load MRC Int value
nop
lb k0,(t1) // load Interrupt status.
nop
lb k0,(t1) // wait
nop
li t0,0x01 // set clear value
sb t0,(t1) // clear OffSw bit
li t1,0x4 // check for OffSw switch
nop //
and k0,k0,t1 //
beq k0,zero,80f // 0 means Power switch was not pressed
nop //
li t1,0xffffc130 // load MRC Software PowerOff Register
nop
lb t0,0x1 // set PowerOff Value
90:
sb t0,(t1) // write PowerOff bit
beq zero,zero,90b
nop
eret
nop
nop
nop
eret
nop
80:
//
// No Power Switch.
//
mtc0 t2,entrylo0 // restore tlb 4
nop //
nop //
nop //
nop //
tlbwi // write to tlb entry
nop //
nop //
nop //
nop //
mtc0 t3,index // restore tlb registers
mtc0 t4,entryhi //
mtc0 t5,entrylo0 //
mtc0 t6,entrylo1 //
mtc0 t7,pagemask //
la t2,HalpNMIFlag // set NMI flag address
li t3,0xa0000000 // set KSEG1_BASE
or t2,t2,t3 //
li t3,1 //
sw t3,(t2) // set NMI flag 1
lw t0,0xffffc078 // check NMI source
nop //
beq t0,zero,45f //
nop //
lw t0,0xffffc020 // clear processor invalid
45:
mfc0 t0,psr // get psr
li t2,0xffbfffff // clear BEV bit
nop // fill
nop // fill
and t0,t0,t2 //
nop //
mtc0 t0,psr // set psr
lw t0,0(k1) // restore temporary registers
lw t1,4(k1) //
lw t2,8(k1) //
lw t3,12(k1) //
lw t4,16(k1) //
lw t5,20(k1) //
lw t6,24(k1) //
lw t7,28(k1) //
lw AT,32(k1) //
eret // return to errorepc
nop // errata
nop //
nop //
eret //
nop //
.set reorder
.set at
.end HalpPowOffNMIDispatch
// End M008