1. Advance IP in case of Break(3) in breakpoint exception

2. Add stack management algorithm to avoid pool allocation during EBC instruction interpretation. 
3. Add multi EBC image support.

git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@2519 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
qhuang8
2007-03-30 08:44:55 +00:00
parent 784220c3f7
commit 73ebf379a4
13 changed files with 420 additions and 121 deletions

View File

@@ -32,6 +32,8 @@ Abstract:
#define VM_STACK_SIZE (1024 * 8)
#define EBC_THUNK_SIZE 64
#define STACK_REMAIN_SIZE (1024 * 4)
STATIC
VOID
PushU64 (
@@ -71,7 +73,18 @@ EbcInterpret (
UINTN Arg2,
UINTN Arg3,
UINTN Arg4,
UINTN Arg5
UINTN Arg5,
UINTN Arg6,
UINTN Arg7,
UINTN Arg8,
UINTN Arg9,
UINTN Arg10,
UINTN Arg11,
UINTN Arg12,
UINTN Arg13,
UINTN Arg14,
UINTN Arg15,
UINTN Arg16
)
/*++
@@ -98,6 +111,8 @@ Returns:
//
VM_CONTEXT VmContext;
UINTN Addr;
EFI_STATUS Status;
UINTN StackIndex;
//
// Get the EBC entry point from the processor register.
@@ -125,8 +140,15 @@ Returns:
//
// Adjust the VM's stack pointer down.
//
VmContext.R[0] = (UINT64) Addr;
VmContext.R[0] -= VM_STACK_SIZE;
Status = GetEBCStack((EFI_HANDLE)(UINTN)-1, &VmContext.StackPool, &StackIndex);
if (EFI_ERROR(Status)) {
return Status;
}
VmContext.StackTop = (UINT8*)VmContext.StackPool + (STACK_REMAIN_SIZE);
VmContext.R[0] = (UINT64) ((UINT8*)VmContext.StackPool + STACK_POOL_SIZE);
VmContext.HighStackBottom = (UINTN) VmContext.R[0];
VmContext.R[0] -= sizeof (UINTN);
//
// Align the stack on a natural boundary.
@@ -148,6 +170,18 @@ Returns:
// For the worst case, assume there are 4 arguments passed in registers, store
// them to VM's stack.
//
PushU64 (&VmContext, (UINT64) Arg16);
PushU64 (&VmContext, (UINT64) Arg15);
PushU64 (&VmContext, (UINT64) Arg14);
PushU64 (&VmContext, (UINT64) Arg13);
PushU64 (&VmContext, (UINT64) Arg12);
PushU64 (&VmContext, (UINT64) Arg11);
PushU64 (&VmContext, (UINT64) Arg10);
PushU64 (&VmContext, (UINT64) Arg9);
PushU64 (&VmContext, (UINT64) Arg8);
PushU64 (&VmContext, (UINT64) Arg7);
PushU64 (&VmContext, (UINT64) Arg6);
PushU64 (&VmContext, (UINT64) Arg5);
PushU64 (&VmContext, (UINT64) Arg4);
PushU64 (&VmContext, (UINT64) Arg3);
PushU64 (&VmContext, (UINT64) Arg2);
@@ -178,7 +212,6 @@ Returns:
// the stack too, so adjust accordingly.
// VmContext.HighStackBottom = (UINTN)(Addr + sizeof (VmContext) + sizeof (Addr));
//
VmContext.HighStackBottom = (UINTN) &Arg5;
//
// Begin executing the EBC code
@@ -188,6 +221,7 @@ Returns:
//
// Return the value in R[7] unless there was an error
//
ReturnEBCStack(StackIndex);
return (UINT64) VmContext.R[7];
}
@@ -221,6 +255,8 @@ Returns:
//
VM_CONTEXT VmContext;
UINTN Addr;
EFI_STATUS Status;
UINTN StackIndex;
//
// Get the EBC entry point from the processor register. Make sure you don't
@@ -250,8 +286,16 @@ Returns:
// pointer and adjust it down by the max needed for the interpreter.
//
Addr = EbcLLGetStackPointer ();
VmContext.R[0] = (UINT64) Addr;
VmContext.R[0] -= VM_STACK_SIZE;
Status = GetEBCStack(ImageHandle, &VmContext.StackPool, &StackIndex);
if (EFI_ERROR(Status)) {
return Status;
}
VmContext.StackTop = (UINT8*)VmContext.StackPool + (STACK_REMAIN_SIZE);
VmContext.R[0] = (UINT64) ((UINT8*)VmContext.StackPool + STACK_POOL_SIZE);
VmContext.HighStackBottom = (UINTN) VmContext.R[0];
VmContext.R[0] -= sizeof (UINTN);
//
// Put a magic value in the stack gap, then adjust down again
@@ -287,7 +331,6 @@ Returns:
// Entry function needn't access high stack context, simply
// put the stack pointer here.
//
VmContext.HighStackBottom = (UINTN) Addr;
//
// Begin executing the EBC code
@@ -297,6 +340,7 @@ Returns:
//
// Return the value in R[7] unless there was an error
//
ReturnEBCStack(StackIndex);
return (UINT64) VmContext.R[7];
}