SimpleVisor is a simple, portable, Intel VT-x hypervisor with two specific goals: using the least amount of assembly code (10 lines), and having the smallest amount of VMX-related code to support dynamic hyperjacking and unhyperjacking (that is, virtualizing the host state from within the host). It works on Windows and UEFI.
There is a miscalculation in the range of a singular 2MB frame which causes an extraneous frame to be marked as the wrong cache type at the beginning of the range. This is because the code incorrectly checks a range of a given frame to be 0 to 2MB instead of 0 to 2MB-1 inclusive.
Consider the following case:
An MTRR Variable Range Register marks the following range as UC:
Begin=0xC0000000
End=0xFFFFFFFF
Frame number 0x5FF is preparing to be marked, which has only addresses that fall outside the range above.
There is a miscalculation in the range of a singular 2MB frame which causes an extraneous frame to be marked as the wrong cache type at the beginning of the range. This is because the code incorrectly checks a range of a given frame to be 0 to 2MB instead of 0 to 2MB-1 inclusive.
Consider the following case:
0xC0000000
0xFFFFFFFF
LargePageAddress
=(0x5FF * 2MB)
=0xBFE00000
LargePageAddress + _2MB
=(0x5FF + 1) * 2MB
=0xC0000000
<-- IncorrectVpData->MtrrData[i].PhysicalAddressMin
=0xC0000000
((LargePageAddress + _2MB) >= VpData->MtrrData[i].PhysicalAddressMin)
LargePageAddress + _2MB >= 0xC0000000
evaluates toTRUE
(Incorrect)The fix is simple, just only check the range of 0 to 2MB-1 for every frame.