/** @file\r
Processor specific parts of the GDB stub\r
\r
- Copyright (c) 2008-2009, Apple Inc. All rights reserved.\r
- \r
- All rights reserved. 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
+ Copyright (c) 2008 - 2009, Apple Inc. All rights reserved.<BR>\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
+ SPDX-License-Identifier: BSD-2-Clause-Patent\r
\r
**/\r
\r
// Array of exception types that need to be hooked by the debugger\r
//\r
EFI_EXCEPTION_TYPE_ENTRY gExceptionType[] = {\r
- { EXCEPT_X64_DIVIDE_ERROR, GDB_SIGFPE }, \r
+ { EXCEPT_X64_DIVIDE_ERROR, GDB_SIGFPE },\r
{ EXCEPT_X64_DEBUG, GDB_SIGTRAP },\r
{ EXCEPT_X64_NMI, GDB_SIGEMT },\r
{ EXCEPT_X64_BREAKPOINT, GDB_SIGTRAP },\r
\r
\r
// The offsets of registers SystemContextX64.\r
-// The fields in the array are in the gdb ordering. \r
+// The fields in the array are in the gdb ordering.\r
// HAVE TO DOUBLE-CHECK THE ORDER of the 24 regs\r
//\r
UINTN gRegisterOffsets[] = {\r
\r
/**\r
Return the number of entries in the gExceptionType[]\r
- \r
- @retval UINTN, the number of entries in the gExceptionType[] array. \r
+\r
+ @retval UINTN, the number of entries in the gExceptionType[] array.\r
**/\r
UINTN\r
MaxEfiException (\r
\r
/**\r
Return the number of entries in the gRegisters[]\r
- \r
- @retval UINTN, the number of entries (registers) in the gRegisters[] array. \r
+\r
+ @retval UINTN, the number of entries (registers) in the gRegisters[] array.\r
**/\r
UINTN\r
MaxRegisterCount (\r
return sizeof (gRegisterOffsets)/sizeof (UINTN);\r
}\r
\r
- \r
+\r
/**\r
- Check to see if the ISA is supported. \r
+ Check to see if the ISA is supported.\r
ISA = Instruction Set Architecture\r
\r
@retval TRUE if Isa is supported\r
/**\r
This takes in the register number and the System Context, and returns a pointer to the RegNumber-th register in gdb ordering\r
It is, by default, set to find the register pointer of the X64 member\r
- @param SystemContext Register content at time of the exception \r
+ @param SystemContext Register content at time of the exception\r
@param RegNumber The register to which we want to find a pointer\r
@retval the pointer to the RegNumber-th pointer\r
**/\r
UINTN *\r
FindPointerToRegister(\r
IN EFI_SYSTEM_CONTEXT SystemContext,\r
- IN UINTN RegNumber \r
+ IN UINTN RegNumber\r
)\r
{\r
UINT8 *TempPtr;\r
)\r
{\r
UINTN RegSize;\r
- \r
+\r
RegSize = 0;\r
while (RegSize < 64) {\r
*OutBufPtr++ = mHexToStr[((*FindPointerToRegister(SystemContext, RegNumber) >> (RegSize+4)) & 0xf)];\r
}\r
\r
\r
-/** ‘p n’ \r
- Reads the n-th register's value into an output buffer and sends it as a packet \r
+/** ‘p n’\r
+ Reads the n-th register's value into an output buffer and sends it as a packet\r
@param SystemContext Register content at time of the exception\r
@param InBuffer Pointer to the input buffer received from gdb server\r
**/\r
UINTN RegNumber;\r
CHAR8 OutBuffer[17]; // 1 reg=16 hex chars, and the end '\0' (escape seq)\r
CHAR8 *OutBufPtr; // pointer to the output buffer\r
- \r
+\r
RegNumber = AsciiStrHexToUintn (&InBuffer[1]);\r
- \r
+\r
if ((RegNumber < 0) || (RegNumber >= MaxRegisterCount())) {\r
- SendError (GDB_EINVALIDREGNUM); \r
+ SendError (GDB_EINVALIDREGNUM);\r
return;\r
}\r
- \r
+\r
OutBufPtr = OutBuffer;\r
OutBufPtr = BasicReadRegister(SystemContext, RegNumber, OutBufPtr);\r
- \r
+\r
*OutBufPtr = '\0'; // the end of the buffer\r
SendPacket (OutBuffer);\r
}\r
\r
\r
-/** ‘g’ \r
- Reads the general registers into an output buffer and sends it as a packet \r
+/** ‘g’\r
+ Reads the general registers into an output buffer and sends it as a packet\r
\r
@param SystemContext Register content at time of the exception\r
**/\r
VOID\r
EFIAPI\r
-ReadGeneralRegisters ( \r
+ReadGeneralRegisters (\r
IN EFI_SYSTEM_CONTEXT SystemContext\r
)\r
{\r
UINTN i;\r
CHAR8 OutBuffer[385]; // 24 regs, 16 hex chars each, and the end '\0' (escape seq)\r
CHAR8 *OutBufPtr; // pointer to the output buffer\r
- \r
+\r
OutBufPtr = OutBuffer;\r
- for(i = 0 ; i < MaxRegisterCount() ; i++) { // there are only 24 registers to read \r
+ for(i = 0 ; i < MaxRegisterCount() ; i++) { // there are only 24 registers to read\r
OutBufPtr = BasicReadRegister(SystemContext, i, OutBufPtr);\r
}\r
- \r
+\r
*OutBufPtr = '\0'; // the end of the buffer\r
SendPacket (OutBuffer);\r
}\r
UINTN RegSize;\r
UINTN TempValue; // the value transferred from a hex char\r
UINT64 NewValue; // the new value of the RegNumber-th Register\r
- \r
+\r
NewValue = 0;\r
RegSize = 0;\r
while (RegSize < 64) {\r
TempValue = HexCharToInt(*InBufPtr++);\r
- \r
+\r
if (TempValue < 0) {\r
- SendError (GDB_EBADMEMDATA); \r
+ SendError (GDB_EBADMEMDATA);\r
return NULL;\r
}\r
- \r
+\r
NewValue += (TempValue << (RegSize+4));\r
TempValue = HexCharToInt(*InBufPtr++);\r
- \r
+\r
if (TempValue < 0) {\r
- SendError (GDB_EBADMEMDATA); \r
+ SendError (GDB_EBADMEMDATA);\r
return NULL;\r
}\r
- \r
- NewValue += (TempValue << RegSize); \r
+\r
+ NewValue += (TempValue << RegSize);\r
RegSize = RegSize + 8;\r
}\r
*(FindPointerToRegister(SystemContext, RegNumber)) = NewValue;\r
Writes the new value of n-th register received into the input buffer to the n-th register\r
\r
@param SystemContext Register content at time of the exception\r
- @param InBuffer Ponter to the input buffer received from gdb server\r
+ @param InBuffer Pointer to the input buffer received from gdb server\r
**/\r
VOID\r
EFIAPI\r
CHAR8 RegNumBuffer[MAX_REG_NUM_BUF_SIZE]; // put the 'n..' part of the message into this array\r
CHAR8 *RegNumBufPtr;\r
CHAR8 *InBufPtr; // pointer to the input buffer\r
- \r
+\r
// find the register number to write\r
InBufPtr = &InBuffer[1];\r
RegNumBufPtr = RegNumBuffer;\r
while (*InBufPtr != '=') {\r
*RegNumBufPtr++ = *InBufPtr++;\r
- } \r
+ }\r
*RegNumBufPtr = '\0';\r
- RegNumber = AsciiStrHexToUintn (RegNumBuffer); \r
+ RegNumber = AsciiStrHexToUintn (RegNumBuffer);\r
\r
// check if this is a valid Register Number\r
if ((RegNumber < 0) || (RegNumber >= MaxRegisterCount())) {\r
- SendError (GDB_EINVALIDREGNUM); \r
+ SendError (GDB_EINVALIDREGNUM);\r
return;\r
}\r
InBufPtr++; // skips the '=' character\r
{\r
UINTN i;\r
CHAR8 *InBufPtr; /// pointer to the input buffer\r
- \r
- // check to see if the buffer is the right size which is \r
- // 1 (for 'G') + 16 (for 16 registers) * 8 ( for 8 hex chars each) = 385 \r
+\r
+ // check to see if the buffer is the right size which is\r
+ // 1 (for 'G') + 16 (for 16 registers) * 8 ( for 8 hex chars each) = 385\r
if (AsciiStrLen(InBuffer) != 385) { // 24 regs, 16 hex chars each, and the end '\0' (escape seq)\r
- //Bad message. Message is not the right length \r
- SendError (GDB_EBADBUFSIZE); \r
+ //Bad message. Message is not the right length\r
+ SendError (GDB_EBADBUFSIZE);\r
return;\r
}\r
- \r
+\r
InBufPtr = &InBuffer[1];\r
- \r
+\r
// Read the new values for the registers from the input buffer to an array, NewValueArray.\r
// The values in the array are in the gdb ordering\r
for(i=0; i < MaxRegisterCount(); i++) { // there are only 16 registers to write\r
InBufPtr = BasicWriteRegister(SystemContext, i, InBufPtr);\r
}\r
- \r
+\r
SendSuccess();\r
}\r
\r
\r
- /** \r
+ /**\r
Insert Single Step in the SystemContext\r
- \r
+\r
@param SystemContext Register content at time of the exception\r
**/\r
VOID\r
SystemContext.SystemContextX64->Rflags |= TF_BIT; //Setting the TF bit.\r
}\r
\r
- \r
- \r
-/** \r
+\r
+\r
+/**\r
Remove Single Step in the SystemContext\r
- \r
+\r
@param SystemContext Register content at time of the exception\r
**/\r
VOID\r
\r
\r
\r
-/** ‘c [addr ]’ \r
- Continue. addr is Address to resume. If addr is omitted, resume at current \r
+/** ‘c [addr ]’\r
+ Continue. addr is Address to resume. If addr is omitted, resume at current\r
Address.\r
- \r
- @param SystemContext Register content at time of the exception \r
+\r
+ @param SystemContext Register content at time of the exception\r
**/\r
VOID\r
EFIAPI\r
{\r
if (PacketData[1] != '\0') {\r
SystemContext.SystemContextX64->Rip = AsciiStrHexToUintn(&PacketData[1]);\r
- } \r
+ }\r
}\r
\r
\r
/** ‘s [addr ]’\r
- Single step. addr is the Address at which to resume. If addr is omitted, resume \r
+ Single step. addr is the Address at which to resume. If addr is omitted, resume\r
at same Address.\r
- \r
- @param SystemContext Register content at time of the exception \r
+\r
+ @param SystemContext Register content at time of the exception\r
**/\r
VOID\r
EFIAPI\r
if (PacketData[1] != '\0') {\r
SystemContext.SystemContextX64->Rip = AsciiStrHexToUintn (&PacketData[1]);\r
}\r
- \r
+\r
AddSingleStep (SystemContext);\r
}\r
\r
\r
/**\r
- Returns breakpoint data address from DR0-DR3 based on the input breakpoint \r
+ Returns breakpoint data address from DR0-DR3 based on the input breakpoint\r
number\r
\r
@param SystemContext Register content at time of the exception\r
@param BreakpointNumber Breakpoint number\r
\r
- @retval Address Data address from DR0-DR3 based on the \r
+ @retval Address Data address from DR0-DR3 based on the\r
breakpoint number.\r
\r
**/\r
}\r
\r
/**\r
- Returns currently detected breakpoint value based on the register \r
+ Returns currently detected breakpoint value based on the register\r
DR6 B0-B3 field.\r
If no breakpoint is detected then it returns 0.\r
\r
}\r
\r
/**\r
- Returns Breakpoint type (InstructionExecution, DataWrite, DataRead \r
+ Returns Breakpoint type (InstructionExecution, DataWrite, DataRead\r
or DataReadWrite) based on the Breakpoint number\r
\r
@param SystemContext Register content at time of the exception\r
@param BreakpointNumber Breakpoint number\r
\r
- @retval BREAK_TYPE Breakpoint type value read from register DR7 RWn \r
+ @retval BREAK_TYPE Breakpoint type value read from register DR7 RWn\r
field. For unknown value, it returns NotSupported.\r
\r
**/\r
}\r
\r
\r
-/** \r
+/**\r
Parses Length and returns the length which DR7 LENn field accepts.\r
- For example: If we receive 1-Byte length then we should return 0. \r
+ For example: If we receive 1-Byte length then we should return 0.\r
Zero gets written to DR7 LENn field.\r
\r
@param Length Breakpoint length in Bytes (1 byte, 2 byte, 4 byte)\r
IN UINTN Length\r
)\r
{\r
- if (Length == 1) { //1-Byte length \r
+ if (Length == 1) { //1-Byte length\r
return 0;\r
} else if (Length == 2) { //2-Byte length\r
return 1;\r
@param SystemContext Register content at time of the exception\r
@param Register Register value (0 - 3)\r
@param Address Breakpoint address value\r
- @param Type Breakpoint type (Instruction, Data write, \r
+ @param Type Breakpoint type (Instruction, Data write,\r
Data read or write etc.)\r
\r
@retval EFI_STATUS Appropriate status value.\r
//Convert length data\r
Length = ConvertLengthData (Length);\r
\r
- //For Instruction execution, length should be 0 \r
+ //For Instruction execution, length should be 0\r
//(Ref. Intel reference manual 18.2.4)\r
if ((Type == 0) && (Length != 0)) {\r
return EFI_INVALID_PARAMETER;\r
\r
//Hardware doesn't support ReadWatch (z3 packet) type. GDB can handle\r
//software breakpoint. We should send empty packet in both these cases.\r
- if ((Type == (BREAK_TYPE)DataRead) || \r
+ if ((Type == (BREAK_TYPE)DataRead) ||\r
(Type == (BREAK_TYPE)SoftwareBreakpoint)) {\r
return EFI_UNSUPPORTED;\r
}\r
}\r
\r
\r
-/** \r
- Returns register number 0 - 3 for the maching debug register. \r
- This function compares incoming Address, Type, Length and \r
+/**\r
+ Returns register number 0 - 3 for the matching debug register.\r
+ This function compares incoming Address, Type, Length and\r
if there is a match then it returns the appropriate register number.\r
In case of mismatch, function returns EFI_NOT_FOUND message.\r
\r
@param SystemContext Register content at time of the exception\r
- @param Address Breakpoint address value \r
+ @param Address Breakpoint address value\r
@param Length Breakpoint length value\r
@param Type Breakpoint type (Instruction, Data write, Data read\r
or write etc.)\r
\r
//Hardware doesn't support ReadWatch (z3 packet) type. GDB can handle\r
//software breakpoint. We should send empty packet in both these cases.\r
- if ((Type == (BREAK_TYPE)DataRead) || \r
+ if ((Type == (BREAK_TYPE)DataRead) ||\r
(Type == (BREAK_TYPE)SoftwareBreakpoint)) {\r
return EFI_UNSUPPORTED;\r
}\r
\r
Dr7.UintN = SystemContext.SystemContextIa32->Dr7;\r
\r
- if ((Dr7.Bits.G0 == 1) && \r
+ if ((Dr7.Bits.G0 == 1) &&\r
(Dr7.Bits.LEN0 == Length) &&\r
- (Dr7.Bits.RW0 == Type) && \r
+ (Dr7.Bits.RW0 == Type) &&\r
(Address == SystemContext.SystemContextIa32->Dr0)) {\r
*Register = 0;\r
- } else if ((Dr7.Bits.G1 == 1) && \r
+ } else if ((Dr7.Bits.G1 == 1) &&\r
(Dr7.Bits.LEN1 == Length) &&\r
- (Dr7.Bits.RW1 == Type) && \r
+ (Dr7.Bits.RW1 == Type) &&\r
(Address == SystemContext.SystemContextIa32->Dr1)) {\r
*Register = 1;\r
- } else if ((Dr7.Bits.G2 == 1) && \r
+ } else if ((Dr7.Bits.G2 == 1) &&\r
(Dr7.Bits.LEN2 == Length) &&\r
- (Dr7.Bits.RW2 == Type) && \r
+ (Dr7.Bits.RW2 == Type) &&\r
(Address == SystemContext.SystemContextIa32->Dr2)) {\r
*Register = 2;\r
- } else if ((Dr7.Bits.G3 == 1) && \r
+ } else if ((Dr7.Bits.G3 == 1) &&\r
(Dr7.Bits.LEN3 == Length) &&\r
- (Dr7.Bits.RW3 == Type) && \r
+ (Dr7.Bits.RW3 == Type) &&\r
(Address == SystemContext.SystemContextIa32->Dr3)) {\r
*Register = 3;\r
} else {\r
}\r
\r
switch (Type) {\r
- \r
+\r
case 0: //Software breakpoint\r
BreakType = SoftwareBreakpoint;\r
break;\r
- \r
+\r
case 1: //Hardware breakpoint\r
BreakType = InstructionExecution;\r
break;\r
- \r
+\r
case 2: //Write watchpoint\r
BreakType = DataWrite;\r
break;\r
\r
BOOLEAN\r
ValidateException (\r
- IN EFI_EXCEPTION_TYPE ExceptionType, \r
- IN OUT EFI_SYSTEM_CONTEXT SystemContext \r
+ IN EFI_EXCEPTION_TYPE ExceptionType,\r
+ IN OUT EFI_SYSTEM_CONTEXT SystemContext\r
)\r
{\r
return TRUE;\r