Source code of Windows XP (NT5)
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.
 
 
 
 
 
 

269 lines
6.1 KiB

//++
//
// Module Name:
//
// jmpuwind.s
//
// Abstract:
//
// This module implements the IA64 specific routine to jump to the runtime
// time library unwind routine.
//
// Author:
//
// William K. Cheung (wcheung) 4-Jan-1996
//
//
// based on the version by David N. Cutler (davec) 12-Sep-1990
//
// Environment:
//
// Any mode.
//
// Revision History:
//
//--
#include "ksia64.h"
//++
//
// LONG
// __C_ExecuteExceptionFilter (
// ULONGLONG MemoryStack,
// ULONGLONG BackingStore,
// NTSTATUS ExceptionCode,
// PEXCEPTION_POINTERS ExceptionPointers,
// ULONGLONG ExceptionFilter,
// ULONGLONG GlobalPointer
// )
//
// Routine Description:
//
// This function sets the gp register and transfers control to the specified
// exception filter routine.
//
// Arguments:
//
// MemoryStack (a0) - memory stack pointer of establisher frame
//
// BackingStore (a1) - backing store pointer of establisher frame
//
// ExceptionCode (a2) - Exception Code.
//
// ExceptionPointers (a3) - Supplies a pointer to the exception pointers
// structure.
//
// ExceptionFilter (a4) - Entry point of exception filter
//
// GlobalPointer (a5) - GP of exception filter
//
// Return Value:
//
// The value returned by the exception filter routine.
//
//--
LEAF_ENTRY(__C_ExecuteExceptionFilter)
mov gp = a5
mov bt0 = a4
br bt0 // branch to exception filter
;;
LEAF_EXIT(__C_ExecuteExceptionFilter)
//++
//
// VOID
// __C_ExecuteTerminationHandler (
// ULONGLONG MemoryStack,
// ULONGLONG BackingStore,
// BOOLEAN AbnormalTermination,
// ULONGLONG TerminationHandler,
// ULONGLONG GlobalPointer
// )
//
// Routine Description:
//
// This function sets the gp register and transfers control to the specified
// termination handler routine.
//
// Arguments:
//
// MemoryStack (a0) - memory stack pointer of establisher frame
//
// BackingStore (a1) - backing store pointer of establisher frame
//
// AbnormalTermination (a2) - Supplies a boolean value that determines
// whether the termination is abnormal.
//
// TerminationHandler (a3) - Entry point of termination handler
//
// GlobalPointer (a4) - GP of termination handler
//
// Return Value:
//
// None.
//
//--
LEAF_ENTRY(__C_ExecuteTerminationHandler)
mov gp = a4
mov bt0 = a3
br bt0 // branch to termination handler
;;
LEAF_EXIT(__C_ExecuteTerminationHandler)
//++
//
// VOID
// __jump_unwind (
// IN PVOID TargetMsFrame,
// IN PVOID TargetBsFrame,
// IN PVOID TargetPc,
// )
//
// Routine Description:
//
// This function transfer control to unwind. It is used by the MIPS
// compiler when a goto out of the body or a try statement occurs.
//
// Arguments:
//
// TargetMsFrame (a0) - Supplies the memory stack frame pointer of the
// target of the unwind.
//
// TargetBsFrame (a1) - Supplies the backing store frame pointer of the
// target of the unwind.
//
// TargetPc (a2) - Supplies the target instruction address where control
// is to be transfered to after the unwind operation is complete.
//
// Return Value:
//
// None.
//
// N.B. The first 2 input registers are reused for local while the third
// input register is reused as output register.
//
//--
.global RtlUnwind2
.type RtlUnwind2, @function
.global RtlPcToFileHeader
.type RtlPcToFileHeader, @function
NESTED_ENTRY(__jump_unwind)
.regstk 3, 2, 6, 0
.prologue 0xC, loc0
.fframe ContextFrameLength, Jn10
alloc loc0 = ar.pfs, 3, 3, 6, 0
mov loc1 = brp
[Jn10:] add sp = -ContextFrameLength, sp
;;
mov loc2 = gp
PROLOGUE_END
//
// Call RtlPcToFileHeader to get the image base of caller
// The image base is returned in memory location STACK_SCRATCH_AREA, sp
// and also in register v0
//
mov out0 = brp
add out1 = STACK_SCRATCH_AREA, sp
br.call.sptk brp = RtlPcToFileHeader
;;
mov gp = loc2
//
// Add image base to image relative offset passed in a2
//
add out2 = v0, a2
//
// Setup rest of arguments to RtlUnwind2
//
add out5 = STACK_SCRATCH_AREA, sp
mov out4 = zero
mov out3 = zero
mov out1 = a1
mov out0 = a0
br.call.sptk brp = RtlUnwind2
;;
.restore Jn20
[Jn20:] add sp = ContextFrameLength, sp
nop.f 0
mov ar.pfs = loc0
nop.m 0
mov brp = loc1
br.ret.sptk brp
NESTED_EXIT(__jump_unwind)
//++
// VOID
// _NLG_Notify(
// IN PVOID Funclet
// IN FRAME_POINTERS EstablisherFrame,
// IN ULONG NLGCode
// )
//
// Routine Description:
//
// Provides the handler/longjmp addresses to the debugger
//
// Arguments:
//
// Funclet (a0) - Supplies the target address of non-local goto
// EstablisherFrame (a1,a2) - Supplies a pointer to frame of the establisher
// function
// NLGCode (a3) - Supplies NLG identifying value
//
// Return Value:
//
// None.
//
//--
.global __NLG_Dispatch
.global __NLG_Destination
.sdata
__NLG_Destination::
data8 0x19930520 // signature
data8 0 // handler address
data8 0 // code
data8 0 // memory stack frame pointer
data8 0 // register stack frame pointer
LEAF_ENTRY(_NLG_Notify)
add t0 = @gprel(__NLG_Destination+0x8), gp
add t1 = @gprel(__NLG_Destination+0x10), gp
nop.i 0
;;
st8 [t0] = a0, 16
st8 [t1] = a3, 16
nop.i 0
;;
st8 [t0] = a1
st8 [t1] = a2
nop.i 0
__NLG_Dispatch::
nop.m 0
nop.i 0
br.ret.sptk b0
LEAF_EXIT(_NLG_Notify)