/** @file\r
Contains code that implements the virtual machine.\r
\r
-Copyright (c) 2006 - 2014, Intel Corporation. All rights reserved.<BR>\r
-This program and the accompanying materials\r
-are licensed and made available under the terms and conditions of the BSD License\r
-which accompanies this distribution. The full text of the license may be found at\r
-http://opensource.org/licenses/bsd-license.php\r
-\r
-THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
-WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
+Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>\r
+SPDX-License-Identifier: BSD-2-Clause-Patent\r
\r
**/\r
\r
#include "EbcInt.h"\r
#include "EbcExecute.h"\r
+#include "EbcDebuggerHook.h"\r
\r
\r
//\r
{ ExecuteMOVIn }, // opcode 0x38 - mov immediate natural\r
{ ExecuteMOVREL }, // opcode 0x39 - move data relative to PC\r
{ NULL }, // opcode 0x3a\r
- { NULL }, // opcode 0x3b \r
- { NULL }, // opcode 0x3c \r
- { NULL }, // opcode 0x3d \r
- { NULL }, // opcode 0x3e \r
- { NULL } // opcode 0x3f \r
+ { NULL }, // opcode 0x3b\r
+ { NULL }, // opcode 0x3c\r
+ { NULL }, // opcode 0x3d\r
+ { NULL }, // opcode 0x3e\r
+ { NULL } // opcode 0x3f\r
};\r
\r
//\r
Status = EFI_UNSUPPORTED;\r
goto Done;\r
}\r
+\r
+ EbcDebuggerHookExecuteStart (VmPtr);\r
+\r
//\r
// The EBC VM is a strongly ordered processor, so perform a fence operation before\r
// and after each instruction is executed.\r
\r
MemoryFence ();\r
\r
+ EbcDebuggerHookExecuteEnd (VmPtr);\r
+\r
//\r
// If the step flag is set, signal an exception and continue. We don't\r
// clear it here. Assuming the debugger is responsible for clearing it.\r
ConditionFlag = (UINT8) VMFLAG_ISSET (VmPtr, VMFLAGS_CC);\r
if ((Operand & CONDITION_M_CONDITIONAL) != 0) {\r
if (CompareSet != ConditionFlag) {\r
+ EbcDebuggerHookJMPStart (VmPtr);\r
VmPtr->Ip += Size;\r
+ EbcDebuggerHookJMPEnd (VmPtr);\r
return EFI_SUCCESS;\r
}\r
}\r
//\r
// Take jump -- relative or absolute\r
//\r
+ EbcDebuggerHookJMPStart (VmPtr);\r
if ((Operand & JMP_M_RELATIVE) != 0) {\r
VmPtr->Ip += (UINTN) Data64 + Size;\r
} else {\r
VmPtr->Ip = (VMIP) (UINTN) Data64;\r
}\r
+ EbcDebuggerHookJMPEnd (VmPtr);\r
\r
return EFI_SUCCESS;\r
}\r
return EFI_UNSUPPORTED;\r
}\r
\r
+ EbcDebuggerHookJMPStart (VmPtr);\r
if ((Operand & JMP_M_RELATIVE) != 0) {\r
VmPtr->Ip += (UINTN) Addr + Size;\r
} else {\r
VmPtr->Ip = (VMIP) Addr;\r
}\r
+ EbcDebuggerHookJMPEnd (VmPtr);\r
+\r
} else {\r
//\r
// Form: JMP32 Rx {Immed32}\r
return EFI_UNSUPPORTED;\r
}\r
\r
+ EbcDebuggerHookJMPStart (VmPtr);\r
if ((Operand & JMP_M_RELATIVE) != 0) {\r
VmPtr->Ip += (UINTN) Addr + Size;\r
} else {\r
VmPtr->Ip = (VMIP) Addr;\r
}\r
+ EbcDebuggerHookJMPEnd (VmPtr);\r
+\r
}\r
\r
return EFI_SUCCESS;\r
//\r
if ((Opcode & CONDITION_M_CONDITIONAL) != 0) {\r
if (CompareSet != ConditionFlag) {\r
+ EbcDebuggerHookJMP8Start (VmPtr);\r
VmPtr->Ip += 2;\r
+ EbcDebuggerHookJMP8End (VmPtr);\r
return EFI_SUCCESS;\r
}\r
}\r
//\r
// Want to check for offset == -2 and then raise an exception?\r
//\r
+ EbcDebuggerHookJMP8Start (VmPtr);\r
VmPtr->Ip += (Offset * 2) + 2;\r
+ EbcDebuggerHookJMP8End (VmPtr);\r
return EFI_SUCCESS;\r
}\r
\r
if (OPERAND1_INDIRECT (Operands)) {\r
VmWriteMemN (VmPtr, (UINTN) (VmPtr->Gpr[OPERAND1_REGNUM (Operands)] + Index16), DataN);\r
} else {\r
- VmPtr->Gpr[OPERAND1_REGNUM (Operands)] = (INT64) (UINT64) ((UINTN) DataN + Index16);\r
+ VmPtr->Gpr[OPERAND1_REGNUM (Operands)] = (INT64) (UINT64) (UINTN) (DataN + Index16);\r
}\r
\r
return EFI_SUCCESS;\r
//\r
Opcode = GETOPCODE (VmPtr);\r
Operands = GETOPERANDS (VmPtr);\r
+\r
+ if ((Operands & OPERAND_M_NATIVE_CALL) != 0) {\r
+ EbcDebuggerHookCALLEXStart (VmPtr);\r
+ } else {\r
+ EbcDebuggerHookCALLStart (VmPtr);\r
+ }\r
+\r
//\r
// Assign these as well to avoid compiler warnings\r
//\r
}\r
}\r
\r
+ if ((Operands & OPERAND_M_NATIVE_CALL) != 0) {\r
+ EbcDebuggerHookCALLEXEnd (VmPtr);\r
+ } else {\r
+ EbcDebuggerHookCALLEnd (VmPtr);\r
+ }\r
+\r
return EFI_SUCCESS;\r
}\r
\r
IN VM_CONTEXT *VmPtr\r
)\r
{\r
+\r
+ EbcDebuggerHookRETStart (VmPtr);\r
+\r
//\r
// If we're at the top of the stack, then simply set the done\r
// flag and return\r
VmPtr->Gpr[0] += 8;\r
}\r
\r
+\r
+ EbcDebuggerHookRETEnd (VmPtr);\r
+\r
return EFI_SUCCESS;\r
}\r
\r
if (Flag != 0) {\r
VMFLAG_SET (VmPtr, VMFLAGS_CC);\r
} else {\r
- VMFLAG_CLEAR (VmPtr, VMFLAGS_CC);\r
+ VMFLAG_CLEAR (VmPtr, (UINT64)VMFLAGS_CC);\r
}\r
//\r
// Advance the IP\r
if (Flag != 0) {\r
VMFLAG_SET (VmPtr, VMFLAGS_CC);\r
} else {\r
- VMFLAG_CLEAR (VmPtr, VMFLAGS_CC);\r
+ VMFLAG_CLEAR (VmPtr, (UINT64)VMFLAGS_CC);\r
}\r
//\r
// Advance the IP\r
if ((*VmPtr->Ip & DATAMANIP_M_64) != 0) {\r
return (UINT64) ((INT64) ((INT64) Op1 - (INT64) Op2));\r
} else {\r
- return (UINT64) ((INT64) ((INT32) Op1 - (INT32) Op2));\r
+ return (UINT64) ((INT64) ((INT32) ((INT32) Op1 - (INT32) Op2)));\r
}\r
}\r
\r
if ((*VmPtr->Ip & DATAMANIP_M_64) != 0) {\r
return MultS64x64 ((INT64)Op1, (INT64)Op2);\r
} else {\r
- return (UINT64) ((INT64) ((INT32) Op1 * (INT32) Op2));\r
+ return (UINT64) ((INT64) ((INT32) ((INT32) Op1 * (INT32) Op2)));\r
}\r
}\r
\r
if ((*VmPtr->Ip & DATAMANIP_M_64) != 0) {\r
return MultU64x64 (Op1, Op2);\r
} else {\r
- return (UINT64) ((UINT32) Op1 * (UINT32) Op2);\r
+ return (UINT64) ((UINT32) ((UINT32) Op1 * (UINT32) Op2));\r
}\r
}\r
\r
//\r
DataManipDispatchTableIndex = (Opcode & OPCODE_M_OPCODE) - OPCODE_NOT;\r
if ((DataManipDispatchTableIndex < 0) ||\r
- (DataManipDispatchTableIndex >= sizeof (mDataManipDispatchTable) / sizeof (mDataManipDispatchTable[0]))) {\r
+ (DataManipDispatchTableIndex >= ARRAY_SIZE (mDataManipDispatchTable))) {\r
EbcDebugSignalException (\r
EXCEPT_EBC_INVALID_OPCODE,\r
EXCEPTION_FLAG_ERROR,\r