MiLargePageFault
VOID __fastcall MiLargePageFault(UINT64 FaultStatus, VOID *VirtualAddress, VOID *TrapInformation, CHAR PreviousMode){
unsigned __int64 PteBase;
unsigned int v7;
__int64 v8;
unsigned __int64 v9;
UINT64 v10;
_MMPTE v11;
__int64 v12;
int v13;
VOID *v14;
UINT64 v15;
INT64 v16;
__int64 v17;
_MMPTE *v18;
int v19;
unsigned __int64 v20;
_QWORD *v21;
_QWORD *v22;
__int64 v23;
unsigned __int64 v24;
__int64 i;
__int16 v26;
__int64 v27;
UINT64 Code;
UINT64 v29[2];
_MI_TB_FLUSH_LIST TbFlushList[48];
memset(TbFlushList, 0i64, 0xB8u);
PteBase = (unsigned __int64)MmGetPteBase();
v7 = 1;
v8 = 0x200000i64;
v9 = (__int64)(((__int64)(((_QWORD)VirtualAddress << 25) - (PteBase << 25)) >> 16 << 25) - (PteBase << 25)) >> 16;
while( v9 >= PteBase && v9 <= (unsigned __int64)MmGetPteLimit() )
{
++v7;
v9 = (__int64)((v9 << 25) - (PteBase << 25)) >> 16;
v8 <<= 9;
}
LODWORD(v10) = MI_READ_PTE_LOCK_FREE((INT64)VirtualAddress);
v11.u.Long = *(_QWORD *)(FaultStatus + 16);
v12 = v10;
v29[0] = v10;
if( ((v11.u.Long & 1) == 0 || *(_BYTE *)(v11.u.Long & 0xFFFFFFFFFFFFFFFEui64) != 1)
&& (*(_DWORD *)(FaultStatus + 80) & 0x20) == 0 )
{
if( (*(_BYTE *)(FaultStatus + 8) & 2) != 0 )
{
if( (v10 & 0x800) == 0 )
return;
LODWORD(Code) = 0;
MiNoFaultFound();
if( v13 )
{
TbFlushList[0] = 1;
v14 = (VOID *)(*(_QWORD *)FaultStatus & -v8);
LOWORD(TbFlushList[1]) = 0;
*(_QWORD *)&TbFlushList[4] = 0i64;
TbFlushList[2] = 20;
*(_QWORD *)&TbFlushList[6] = 0i64;
MiInsertTbFlushEntry(TbFlushList, v14, 1ui64, v7);
MiFlushTbList(TbFlushList);
}
}
v15 = v12;
if( (*(_BYTE *)(FaultStatus + 8) & 0x10) != 0 )
{
if( v12 >= 0 )
{
if( (*(_DWORD *)(FaultStatus + 80) & 0x40) == 0 )
MiCheckSystemNxFault(FaultStatus, (VOID *)v12, (VOID *)7, v11, Code);
}
else
{
if( !MiCanGrantExecute(KeGetCurrentThread()->ApcState.Process, *(VOID **)FaultStatus) )
return;
MiPteInShadowRange((UINT64)v29);
if( (((unsigned __int64)MmGetPfnDb()[((unsigned __int64)v12 >> 12) & 0xFFFFFFFFFi64].u4._bf_0 >> 50) & 1) == 0 )
return;
v15 = v29[0] & 0x7FFFFFFFFFFFFFFFi64;
v16 = v29[0] & 0x7FFFFFFFFFFFFFFFi64;
v29[0] &= ~0x8000000000000000ui64;
if( (MiFlags & 0x100) != 0 || (MiFlags & 0x200) != 0 )
{
v15 |= 0x20ui64;
v16 = v15;
v29[0] = v15;
}
MiWriteValidPteNewProtection((INT64 *)VirtualAddress, v16);
if( (MiFlags & 0x100) == 0 && (MiFlags & 0x200) == 0 )
KeFlushSingleTb(*(_QWORD *)FaultStatus, FlushUser, 0i64);
}
}
v17 = *(_QWORD *)(FaultStatus + 16);
if( (v17 & 1) != 0 )
{
v18 = (_MMPTE *)(v17 & 0xFFFFFFFFFFFFFFFEui64);
if( LOBYTE(v18->u.Long) == 5 )
{
MiValidVirtualizationFault((_MI_FAULT_VA_LIST *)FaultStatus, v18, (UINT8)VirtualAddress);
if( v19 )
{
v20 = *(_QWORD *)FaultStatus;
LODWORD(v21) = MiGetVirtualFaultPageInfo((INT64)v18, *(_QWORD *)FaultStatus);
v22 = v21;
MiPteInShadowRange((UINT64)v29);
v23 = (v15 >> 12) & 0xFFFFFFFFFi64;
v24 = v20 >> 12;
for( i = 1i64; v7; --v7 )
{
v26 = v24;
v24 >>= 9;
v27 = i * (v26 & 0x1FF);
i <<= 9;
v23 += v27;
}
*v22 ^= (v23 ^ *v22) & 0xFFFFFFFFFFFFFi64;
}
}
}
}
}Referenced by:
MiInPagePageTable
MiUserFault