Skip to content

Commit

Permalink
Allow breakpoint callbacks to modify guest ip
Browse files Browse the repository at this point in the history
- Update the breakpoint callback prototype to allow callbacks to modify
the guest instruction pointer

- Fix unwind logic BpmVmxProcessDebugExceptionEvent

- Minor style changes
  • Loading branch information
changeofpace committed Mar 17, 2019
1 parent dd131e2 commit 2700fb1
Show file tree
Hide file tree
Showing 17 changed files with 611 additions and 237 deletions.
2 changes: 0 additions & 2 deletions Tests/test_breakpoint_stress.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -199,10 +199,8 @@ InitializeStressTestContext(
case 1: pContext->Exerciser = StressTest2; break;
case 2: pContext->Exerciser = StressTest3; break;
default:
{
status = FALSE;
goto exit;
}
}

exit:
Expand Down
20 changes: 10 additions & 10 deletions Tests/test_facade_stress.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -72,12 +72,16 @@ GenerateRandomThreadLocalBreakpointParameters(
*pType = {};
*pSize = {};

//
// Address must be a valid userspace address.
//
*pAddress = (ULONG_PTR)GenerateBoundedRandomValue(
MIN_VALID_USER_ADDRESS,
MAX_VALID_USER_ADDRESS);

//
// Type.
//
switch ((HWBP_TYPE)(RANDOM_ULONG % 3))
{
case HWBP_TYPE::Execute: Type = HWBP_TYPE::Execute; break;
Expand All @@ -86,38 +90,34 @@ GenerateRandomThreadLocalBreakpointParameters(
default: Type = HWBP_TYPE::Access; break;
}

//
// Size.
//
// NOTE Data breakpoints must be aligned based on the size-condition.
//
switch ((HWBP_SIZE)(RANDOM_ULONG % 4))
{
case HWBP_SIZE::Byte:
{
Size = HWBP_SIZE::Byte;
break;
}

case HWBP_SIZE::Word:
{
Size = HWBP_SIZE::Word;
ALIGN_DOWN_POINTER_BY(pAddress, sizeof(WORD));
break;
}

case HWBP_SIZE::Qword:
{
Size = HWBP_SIZE::Qword;
ALIGN_DOWN_POINTER_BY(pAddress, sizeof(DWORD64));
break;
}

case HWBP_SIZE::Dword:
{
__fallthrough;
}

default:
{
Size = HWBP_SIZE::Dword;
ALIGN_DOWN_POINTER_BY(pAddress, sizeof(DWORD));
break;
}
}

// Set out parameters.
Expand Down
66 changes: 38 additions & 28 deletions Tests/test_util.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -191,48 +191,53 @@ iSetThreadLocalHardwareBreakpoint(

switch (Index)
{
//
// Dr0
//
case 0:
{
// Dr0.
Context.Dr0 = Address;
NewDr7.L0 = Enable;
NewDr7.RW0 = (UCHAR)Type;
NewDr7.Len0 = (UCHAR)Size;
break;
}

//
// Dr1
//
case 1:
{
// Dr1.
Context.Dr1 = Address;
NewDr7.L1 = Enable;
NewDr7.RW1 = (UCHAR)Type;
NewDr7.Len1 = (UCHAR)Size;
break;
}

//
// Dr2
//
case 2:
{
// Dr2.
Context.Dr2 = Address;
NewDr7.L2 = Enable;
NewDr7.RW2 = (UCHAR)Type;
NewDr7.Len2 = (UCHAR)Size;
break;
}

//
// Dr3
//
case 3:
{
// Dr3.
Context.Dr3 = Address;
NewDr7.L3 = Enable;
NewDr7.RW3 = (UCHAR)Type;
NewDr7.Len3 = (UCHAR)Size;
break;
}

//
// Invalid debug address register index.
//
default:
{
printf("Invalid debug address register index.\n");
status = FALSE;
goto exit;
}
}

Context.Dr7 = NewDr7.All;
Expand Down Expand Up @@ -340,9 +345,10 @@ VerifyThreadLocalBreakpointByIndex(

switch (Index)
{
//
// Dr0
//
case 0:
{
// Dr0.
if (Address != Context.Dr0 ||
Type != (HWBP_TYPE)ActualDr7.RW0 ||
Size != (HWBP_SIZE)ActualDr7.Len0)
Expand All @@ -352,10 +358,11 @@ VerifyThreadLocalBreakpointByIndex(
}

break;
}

//
// Dr1
//
case 1:
{
// Dr1.
if (Address != Context.Dr1 ||
Type != (HWBP_TYPE)ActualDr7.RW1 ||
Size != (HWBP_SIZE)ActualDr7.Len1)
Expand All @@ -365,10 +372,11 @@ VerifyThreadLocalBreakpointByIndex(
}

break;
}

//
// Dr2
//
case 2:
{
// Dr2.
if (Address != Context.Dr2 ||
Type != (HWBP_TYPE)ActualDr7.RW2 ||
Size != (HWBP_SIZE)ActualDr7.Len2)
Expand All @@ -378,10 +386,11 @@ VerifyThreadLocalBreakpointByIndex(
}

break;
}

//
// Dr3
//
case 3:
{
// Dr3.
if (Address != Context.Dr3 ||
Type != (HWBP_TYPE)ActualDr7.RW3 ||
Size != (HWBP_SIZE)ActualDr7.Len3)
Expand All @@ -391,13 +400,14 @@ VerifyThreadLocalBreakpointByIndex(
}

break;
}

//
// Invalid debug address register index.
//
default:
{
printf("Invalid index: %u\n", Index);
status = FALSE;
goto exit;
}
}

exit:
Expand Down
4 changes: 4 additions & 0 deletions Tests/tests.h
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,10 @@

#include "..\VivienneVMM\config.h"

//
// TODO Add a test which executes an 'int 1' instruction.
//

//=============================================================================
// Parser
//=============================================================================
Expand Down
4 changes: 2 additions & 2 deletions VivienneVMM/HyperPlatform/HyperPlatform/ia32_type.h
Original file line number Diff line number Diff line change
Expand Up @@ -1360,7 +1360,7 @@ union PendingDebugExceptions
ULONG_PTR all;
struct
{
ULONG_PTR dar_bitmap : 4; //!< [0:3]
ULONG_PTR condition_bitmap : 4; //!< [0:3]
ULONG_PTR reserved1 : 8; //!< [4:11]
ULONG_PTR enabled_breakpoint : 1; //!< [12]
ULONG_PTR reserved2 : 1; //!< [13]
Expand All @@ -1377,7 +1377,7 @@ union DebugExceptionQualification
ULONG_PTR all;
struct
{
ULONG_PTR dar_bitmap : 4; //!< [0:3]
ULONG_PTR condition_bitmap : 4; //!< [0:3]
ULONG_PTR reserved1 : 9; //!< [4:12]
ULONG_PTR debug_register_access : 1;//!< [13]
ULONG_PTR single_step_or_branch : 1;//!< [14]
Expand Down
4 changes: 4 additions & 0 deletions VivienneVMM/HyperPlatform/HyperPlatform/vm.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -684,6 +684,10 @@ _Use_decl_annotations_ static bool VmpSetupVmcs(
vm_procctl_requested.fields.mwait_exiting = false;
vm_procctl_requested.fields.rdpmc_exiting = false;
vm_procctl_requested.fields.rdtsc_exiting = false;
//
// TODO Determine if we can disable this setting without impacting
// HyperPlatform because we do not support x86.
//
vm_procctl_requested.fields.cr3_load_exiting = true;
vm_procctl_requested.fields.cr3_store_exiting = false;
vm_procctl_requested.fields.cr8_load_exiting = false;
Expand Down
4 changes: 1 addition & 3 deletions VivienneVMM/HyperPlatform/HyperPlatform/vmm.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -400,7 +400,7 @@ _Use_decl_annotations_ static void VmmpHandleException(
NTSTATUS ntstatus = BpmVmxProcessDebugExceptionEvent(
guest_context->gp_regs,
&guest_context->flag_reg,
guest_context->ip);
&guest_context->ip);
if (!NT_SUCCESS(ntstatus))
{
// If the breakpoint manager did not handle the exception then
Expand Down Expand Up @@ -929,9 +929,7 @@ _Use_decl_annotations_ static void VmmpHandleDrAccess(
}
}

//
// TODO Use the Dr6 and Dr7 reserved-bits enforcement below in BPM and FCD.
//
#ifdef CFG_ENABLE_DEBUGREGISTERFACADE
NTSTATUS ntstatus = STATUS_SUCCESS;

Expand Down
8 changes: 4 additions & 4 deletions VivienneVMM/VivienneVMM.vcxproj
Original file line number Diff line number Diff line change
Expand Up @@ -56,14 +56,14 @@
<WarningLevel>Level4</WarningLevel>
<AdditionalIncludeDirectories>$(SolutionDir)VivienneVMM\HyperPlatform\;$(IntDir);%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<LanguageStandard>stdcpp17</LanguageStandard>
<DisableSpecificWarnings>30030;5040;4603;4627;4986;4987;4996;%(DisableSpecificWarnings)</DisableSpecificWarnings>
<DisableSpecificWarnings>4201;6066;30030;5040;4603;4627;4986;4987;4996;%(DisableSpecificWarnings)</DisableSpecificWarnings>
</ClCompile>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<ClCompile>
<AdditionalIncludeDirectories>$(SolutionDir)VivienneVMM\HyperPlatform\;$(IntDir);%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<LanguageStandard>stdcpp17</LanguageStandard>
<DisableSpecificWarnings>30030;5040;4748;%(DisableSpecificWarnings)</DisableSpecificWarnings>
<DisableSpecificWarnings>4201;6066;30030;5040;4748;%(DisableSpecificWarnings)</DisableSpecificWarnings>
</ClCompile>
</ItemDefinitionGroup>
<ItemGroup>
Expand All @@ -74,7 +74,7 @@
<ClInclude Include="..\common\driver_io_types.h" />
<ClInclude Include="..\common\kdebug.h" />
<ClInclude Include="..\common\time_util.h" />
<ClInclude Include="breakpoint_callbacks.h" />
<ClInclude Include="breakpoint_callback.h" />
<ClInclude Include="breakpoint_manager.h" />
<ClInclude Include="capture_execution_context.h" />
<ClInclude Include="config.h" />
Expand Down Expand Up @@ -102,7 +102,7 @@
</ItemGroup>
<ItemGroup>
<ClCompile Include="..\common\time_util.cpp" />
<ClCompile Include="breakpoint_callbacks.cpp" />
<ClCompile Include="breakpoint_callback.cpp" />
<ClCompile Include="breakpoint_manager.cpp" />
<ClCompile Include="capture_execution_context.cpp" />
<ClCompile Include="debug_register_facade.cpp" />
Expand Down
12 changes: 6 additions & 6 deletions VivienneVMM/VivienneVMM.vcxproj.filters
Original file line number Diff line number Diff line change
Expand Up @@ -44,9 +44,6 @@
<ClInclude Include="dispatch.h">
<Filter>VivienneVMM\Header Files</Filter>
</ClInclude>
<ClInclude Include="breakpoint_callbacks.h">
<Filter>VivienneVMM\Header Files</Filter>
</ClInclude>
<ClInclude Include="register_util.h">
<Filter>VivienneVMM\Header Files</Filter>
</ClInclude>
Expand Down Expand Up @@ -110,6 +107,9 @@
<ClInclude Include="ioctl_validation.h">
<Filter>VivienneVMM\Header Files</Filter>
</ClInclude>
<ClInclude Include="breakpoint_callback.h">
<Filter>VivienneVMM\Header Files</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<ClCompile Include="..\common\time_util.cpp">
Expand All @@ -121,9 +121,6 @@
<ClCompile Include="register_util.cpp">
<Filter>VivienneVMM\Source Files</Filter>
</ClCompile>
<ClCompile Include="breakpoint_callbacks.cpp">
<Filter>VivienneVMM\Source Files</Filter>
</ClCompile>
<ClCompile Include="breakpoint_manager.cpp">
<Filter>VivienneVMM\Source Files</Filter>
</ClCompile>
Expand Down Expand Up @@ -172,6 +169,9 @@
<ClCompile Include="ioctl_validation.cpp">
<Filter>VivienneVMM\Source Files</Filter>
</ClCompile>
<ClCompile Include="breakpoint_callback.cpp">
<Filter>VivienneVMM\Source Files</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<MASM Include="HyperPlatform\HyperPlatform\Arch\x64\x64.asm">
Expand Down
Loading

0 comments on commit 2700fb1

Please sign in to comment.