MiWriteAwePtes
NTSTATUS __stdcall MiWriteAwePtes(INT64 a1, INT64 rdx0, UINT64 a3, INT64 a4, UINT64 a5, CHAR a6){
UINT64 v6;
__int64 v8;
__int64 v9;
_DWORD *v10;
__int64 v11;
__int64 v12;
UINT64 v13;
_MMPTE *PteBase;
union {unsigned __int64 Long;volatile unsigned __int64 VolatileLong;_MMPTE_HARDWARE Hard;_MMPTE_PROTOTYPE Proto;_MMPTE_SOFTWARE Soft;_MMPTE_TIMESTAMP TimeStamp;_MMPTE_TRANSITION Trans;_MMPTE_SUBSECTION Subsect;_MMPTE_LIST List;} v15;
unsigned int v16;
unsigned int v17;
int v18;
union {unsigned __int64 Long;volatile unsigned __int64 VolatileLong;_MMPTE_HARDWARE Hard;_MMPTE_PROTOTYPE Proto;_MMPTE_SOFTWARE Soft;_MMPTE_TIMESTAMP TimeStamp;_MMPTE_TRANSITION Trans;_MMPTE_SUBSECTION Subsect;_MMPTE_LIST List;} v19;
unsigned int v20;
union {unsigned __int64 Long;volatile unsigned __int64 VolatileLong;_MMPTE_HARDWARE Hard;_MMPTE_PROTOTYPE Proto;_MMPTE_SOFTWARE Soft;_MMPTE_TIMESTAMP TimeStamp;_MMPTE_TRANSITION Trans;_MMPTE_SUBSECTION Subsect;_MMPTE_LIST List;} v21;
UINT64 v22;
UINT8 v23;
_BOOL4 v24;
VOID *v25;
UINT64 v26;
INT64 v27;
INT64 v28;
_QWORD *v29;
__int64 v30;
unsigned __int64 v31;
_MMPTE *v32;
unsigned int v33;
unsigned int v34;
unsigned int v35;
unsigned __int8 v36;
int v37;
union {unsigned __int64 Long;volatile unsigned __int64 VolatileLong;_MMPTE_HARDWARE Hard;_MMPTE_PROTOTYPE Proto;_MMPTE_SOFTWARE Soft;_MMPTE_TIMESTAMP TimeStamp;_MMPTE_TRANSITION Trans;_MMPTE_SUBSECTION Subsect;_MMPTE_LIST List;} v38;
union {unsigned __int64 Long;volatile unsigned __int64 VolatileLong;_MMPTE_HARDWARE Hard;_MMPTE_PROTOTYPE Proto;_MMPTE_SOFTWARE Soft;_MMPTE_TIMESTAMP TimeStamp;_MMPTE_TRANSITION Trans;_MMPTE_SUBSECTION Subsect;_MMPTE_LIST List;} v39;
_MMPTE *v40;
__int64 v41;
char *v42;
NTSTATUS updated;
UINT64 v44;
VOID *v45;
UINT64 v46;
CHAR v47;
UINT8 v48;
__int64 v49;
INT64 v50;
INT64 v51;
INT64 v52;
__int64 v53;
INT64 v54;
UINT64 v55;
unsigned __int64 v56;
unsigned __int64 v57;
unsigned __int64 v58;
__int64 v59;
_MMPFN *v60;
unsigned __int64 v61;
__int64 v62;
__int64 v63;
unsigned __int64 v64;
unsigned __int64 v65;
_MMSUPPORT_INSTANCE *p_Instance;
int v67;
int IsContended;
__int64 v69;
int ShouldYieldProcessor;
union {unsigned __int64 Long;volatile unsigned __int64 VolatileLong;_MMPTE_HARDWARE Hard;_MMPTE_PROTOTYPE Proto;_MMPTE_SOFTWARE Soft;_MMPTE_TIMESTAMP TimeStamp;_MMPTE_TRANSITION Trans;_MMPTE_SUBSECTION Subsect;_MMPTE_LIST List;} v71;
bool v72;
NTSTATUS v73;
__int64 v74;
UINT64 v75;
VOID *v76;
UINT64 v77;
CHAR v78;
NTSTATUS v79;
VOID *v80;
UINT64 v81;
CHAR v82;
UINT64 Flags;
UINT8 WsIrql;
unsigned int WsIrql_4;
UINT64 NumberOfEntries;
union {unsigned __int64 Long;volatile unsigned __int64 VolatileLong;_MMPTE_HARDWARE Hard;_MMPTE_PROTOTYPE Proto;_MMPTE_SOFTWARE Soft;_MMPTE_TIMESTAMP TimeStamp;_MMPTE_TRANSITION Trans;_MMPTE_SUBSECTION Subsect;_MMPTE_LIST List;} v88;
unsigned int v89;
__int64 v90;
INT64 v91;
_BOOL4 v92;
__int64 v93;
_MMSUPPORT_FULL *p_Vm;
unsigned int a2;
INT64 v96;
union {unsigned __int64 Long;volatile unsigned __int64 VolatileLong;_MMPTE_HARDWARE Hard;_MMPTE_PROTOTYPE Proto;_MMPTE_SOFTWARE Soft;_MMPTE_TIMESTAMP TimeStamp;_MMPTE_TRANSITION Trans;_MMPTE_SUBSECTION Subsect;_MMPTE_LIST List;} v97;
__int64 v98;
UINT64 SpinCount;
__int64 v100;
unsigned __int64 v101;
UINT64 v102;
__int64 v103;
INT64 v104;
INT64 v105;
UINT64 ReserveSize;
__int64 v107;
INT64 v108;
UINT64 v109;
__int64 v110;
_MI_TB_FLUSH_LIST TbFlushList[48];
v6 = a5;
v102 = a3;
v104 = rdx0;
v105 = a4;
memset(TbFlushList, 0i64, 0xB8u);
v107 = *(_QWORD *)(a1 + 32);
p_Vm = &KeGetCurrentThread()->ApcState.Process->Vm;
v98 = *(_QWORD *)(v107 + 8);
LODWORD(v8) = MiGetAweViewPageSize(a1);
TbFlushList[2] = 20;
v93 = 0i64;
v91 = 0i64;
v11 = v9;
WsIrql_4 = 0;
if( v8 )
v11 = v8;
ReserveSize = 0i64;
v90 = v11;
LOWORD(TbFlushList[1]) = 0;
*(_QWORD *)&TbFlushList[4] = 0i64;
a2 = v11 == 512;
TbFlushList[0] = 1;
v12 = v9;
*(_QWORD *)&TbFlushList[6] = 0i64;
v13 = 0i64;
PteBase = MmGetPteBase();
if( v11 == 512 )
v12 = 1i64;
NumberOfEntries = v12;
if( (a6 & 1) != 0 )
{
v15.Long = *(unsigned __int64 *)(a1 + 24);
v88.Long = v15.Long;
v16 = (a2 << 26) | 0x80000000;
v17 = *(_DWORD *)(v15.Long + 48);
if( (v17 & 0x300000) == 3145728 )
v16 = a2 << 26;
if( (*v10 & 1) != 0 )
v18 = 4;
else
v18 = (v17 >> 7) & 0x1F;
LODWORD(v19.Long) = MiMakeValidPte((_XSTATE_CONFIGURATION *)&PteBase[0x7FFFFFFEFi64], 0i64, v18 | v16);
v97.Long = v19.Long;
v20 = (v17 >> 12) & 0x3F;
v21.Long = v19.Long;
v89 = v20;
MiLockWorkingSetShared();
v22 = NumberOfEntries;
WsIrql = v23;
v24 = (v17 & 0x1100000) == 17825792;
}
else
{
v15.Long = 0i64;
v88.Long = 0i64;
v21.Long = 0i64;
v97.Long = 0i64;
v20 = 0;
v89 = 0;
WsIrql = 17;
LODWORD(v25) = MiGetLeafVa(a5);
v24 = (MiLocateAddress(v25)->Core.u.LongFlags & 0x1100000) == 17825792;
}
v26 = 0i64;
v92 = v24;
v101 = 0i64;
if( !v102 )
{
v71.Long = v88.Long;
goto LABEL_116;
}
v27 = v104;
v28 = v105;
v29 = (_QWORD *)v104;
v109 = 8 * v22;
v30 = v105 - v104;
v103 = 0i64;
v110 = v105 - v104;
v96 = v104;
while( 1 )
{
if( v28 )
{
v31 = *(_QWORD *)((char *)v29 + v30);
v32 = MmGetPteBase();
v33 = a2;
v6 = (UINT64)v32 + ((v31 >> 9) & 0x7FFFFFFFF8i64);
if( v90 == 512 )
{
do
{
v6 = (UINT64)v32 + ((v6 >> 9) & 0x7FFFFFFFF8i64);
--v33;
}
while( v33 );
}
if( v31 < (*(unsigned int *)(v15.Long + 24) | ((unsigned __int64)*(unsigned __int8 *)(v15.Long + 32) << 32)) << 12
|| v31 > (((*(unsigned int *)(v15.Long + 28) | ((unsigned __int64)*(unsigned __int8 *)(v15.Long + 33) << 32)) << 12) | 0xFFF) )
{
v15.Long = (unsigned __int64)MiGetAweNode(v31)[3].u;
v88.Long = v15.Long;
v35 = *(_DWORD *)(v15.Long + 48);
if( ((unsigned __int8)*(_DWORD *)v107 & v36) != 0 )
v37 = 4;
else
v37 = (v35 >> 7) & 0x1F;
LODWORD(v38.Long) = MiMakeValidPte((_XSTATE_CONFIGURATION *)&v32[0x7FFFFFFEFi64], 0i64, v37 | v34);
v29 = (_QWORD *)v96;
v21.Long = v38.Long;
v20 = (v35 >> 12) & 0x3F;
v97.Long = v38.Long;
v89 = v20;
}
if( !v27 || (v39.Long = v21.Long, !*v29) )
v39.Long = ZeroPte.u.Long;
}
else
{
v39.Long = ZeroPte.u.Long;
if( v27 )
v39.Long = v21.Long;
}
if( (v39.Long & 1) != 0 )
v39.Long ^= (v39.Long ^ (*v29 << 12)) & 0xFFFFFFFFF000i64;
v40 = MmGetPteBase();
v41 = (v6 >> 9) & 0x7FFFFFFFF8i64;
if( v15.Long )
{
v42 = (char *)v40 + v41;
if( (_MMPTE *)v13 != (_MMPTE *)((char *)v40 + v41) )
{
if( v13 )
{
updated = MiUpdateAwePageTable(v13, v91, WsIrql_4);
MiFlushTbList(TbFlushList);
if( v92 )
v93 = 0i64;
MiUnlockPageTableInternal((INT64)p_Vm, v13);
v44 = 0i64;
if( updated )
{
LOBYTE(v44) = WsIrql;
MiUnlockWorkingSetShared(&p_Vm->Instance, v44);
MiGetLeafVa(v13 + 8);
LODWORD(v45) = MiGetLeafVa(v13);
MiDeleteEmptyPageTables(v45, v46, v47);
MiLockWorkingSetShared();
WsIrql = v48;
}
v91 = 0i64;
WsIrql_4 = 0;
}
LODWORD(Flags) = 0;
MiMakeSystemAddressValid((VOID *)v6, 0i64, v20, WsIrql, Flags);
v13 = (UINT64)v42;
}
v15.Long = v88.Long;
}
else
{
v13 = (UINT64)v40 + v41;
}
v49 = v6;
v50 = *(_QWORD *)v6;
v51 = 0i64;
v108 = *(_QWORD *)v6;
if( v93 )
v49 = v93;
v93 = v49;
v100 = v49;
if( (v39.Long & 1) == 0 )
{
if( v50 )
{
WsIrql_4 -= NumberOfEntries;
v91 -= NumberOfEntries;
if( (v50 & 1) == 0 || (v51 = 3i64, v90 != 512) )
v51 = 4i64;
}
goto LABEL_57;
}
if( (v50 & 1) != 0 )
{
if( v39.Long != v50 )
{
LOBYTE(v51) = v90 == 512;
v51 = (unsigned int)(v51 + 1);
}
LABEL_57:
v52 = NumberOfEntries;
goto LABEL_58;
}
v52 = NumberOfEntries;
v51 = 5i64;
if( (v50 & 0x800) == 0 )
{
v91 += NumberOfEntries;
if( !v50 )
WsIrql_4 += NumberOfEntries;
}
LABEL_58:
MiWriteAweClusterPte((INT64)p_Vm, (INT64 *)v6, v39.Hard._bf_0, v51, v52);
if( v50 )
{
if( (v50 & 1) != 0 )
{
if( v15.Long )
{
if( v90 == 512 )
{
if( NumberOfEntries )
{
v54 = v6;
v55 = NumberOfEntries;
do
{
MiInsertLargeTbFlushEntry(TbFlushList, a2, v54);
v54 += 8i64;
--v55;
}
while( v55 );
v20 = v89;
v21.Long = v97.Long;
}
}
else
{
MiInsertTbFlushEntry(
TbFlushList,
(VOID *)((__int64)((v6 << 25) - ((_QWORD)MmGetPteBase() << 25)) >> 16),
NumberOfEntries,
0i64);
}
}
LODWORD(v56) = MI_READ_PTE_LOCK_FREE((INT64)&v108);
v57 = v56 >> 12;
}
else
{
v58 = v50;
if( *(&stru_140C4DB30 + 42) && (v50 & 0x10) == 0 )
v58 = v50 & ~*(&stru_140C4DB30 + 42);
v57 = v58 >> 12;
}
v53 = 0xFFFFFFFFFi64;
v59 = v57 & 0xFFFFFFFFFi64;
}
else
{
v59 = -1i64;
}
if( !v50 )
{
v63 = v98;
LABEL_90:
v62 = v90;
goto LABEL_91;
}
v60 = &MmGetPfnDb()[v59];
v61 = 0i64;
v62 = v90;
v63 = v98;
if( v90 )
{
v64 = v90;
do
{
if( (v60->u2._bf_0 & 0x3FFFFFFFFFFFFFFFi64) == 1 )
goto LABEL_86;
LODWORD(SpinCount) = 0;
if( _interlockedbittestandset64((volatile signed __int32 *)&v60->u2, 0x3Fui64) )
{
do
{
do
KeYieldProcessorEx(&SpinCount);
while( v60->u2._bf_0 < 0 );
}
while( _interlockedbittestandset64((volatile signed __int32 *)&v60->u2, 0x3Fui64) );
v64 = v90;
}
v53 = v60->u2._bf_0 & 0x3FFFFFFFFFFFFFFFi64;
if( v53 == 1 )
v53 = 1i64;
else
v60->u2._bf_0 ^= (v60->u2._bf_0 ^ (v53 - 1)) & 0x3FFFFFFFFFFFFFFFi64;
_InterlockedAnd64(&v60->u2.Lock, 0x7FFFFFFFFFFFFFFFui64);
if( v53 == 1 )
LABEL_86:
MiDecrementAweMapCount((VOID *)v53, (UINT64)v60, (UINT64)&ReserveSize);
v63 = v98;
v60 += v98;
v61 += v98;
}
while( v61 < v64 );
v20 = v89;
v21.Long = v97.Long;
goto LABEL_90;
}
LABEL_91:
v65 = v101 + 1;
v29 = (_QWORD *)(v96 + 8);
v6 += v109;
++v101;
v96 += 8i64;
v103 += NumberOfEntries;
if( (v103 & 0x3F) == 0 || v62 != v63 )
break;
v71.Long = v88.Long;
v26 = 0i64;
p_Instance = &p_Vm->Instance;
LABEL_98:
v72 = v65 < v102;
v27 = v104;
v30 = v110;
v28 = v105;
if( !v72 )
goto LABEL_112;
v15.Long = v88.Long;
}
p_Instance = &p_Vm->Instance;
LOBYTE(v67) = MiWorkingSetIsContended((INT64)p_Vm);
v26 = 0i64;
if( v67 )
{
v69 = v100;
}
else
{
IsContended = MiPageTableLockIsContended((__int64)p_Vm, v13);
v69 = v100;
v26 = 0i64;
if( !IsContended )
{
v93 = v100;
ShouldYieldProcessor = KeShouldYieldProcessor();
v26 = 0i64;
if( !ShouldYieldProcessor )
{
v71.Long = v88.Long;
LABEL_97:
v29 = (_QWORD *)v96;
goto LABEL_98;
}
}
}
if( v65 != v102 )
{
v73 = MiUpdateAwePageTable(v13, v91, WsIrql_4);
MiFlushTbList(TbFlushList);
v93 = v69;
if( v92 )
{
v74 = v69;
if( v69 )
v74 = 0i64;
v93 = v74;
}
MiUnlockPageTableInternal((INT64)p_Vm, v13);
LOBYTE(v75) = WsIrql;
MiUnlockWorkingSetShared(&p_Vm->Instance, v75);
v71.Long = v88.Long;
if( v73 && v88.Long )
{
MiGetLeafVa(v13 + 8);
LODWORD(v76) = MiGetLeafVa(v13);
MiDeleteEmptyPageTables(v76, v77, v78);
}
v91 = 0i64;
v13 = 0i64;
WsIrql_4 = 0;
MiLockWorkingSetShared();
v65 = v101;
v26 = 0i64;
goto LABEL_97;
}
v71.Long = v88.Long;
LABEL_112:
if( v13 )
{
v79 = MiUpdateAwePageTable(v13, v91, WsIrql_4);
if( v71.Long )
{
MiFlushTbList(TbFlushList);
MiUnlockPageTableInternal((INT64)p_Instance, v13);
goto LABEL_117;
}
return ReserveSize;
}
LABEL_116:
p_Instance = &p_Vm->Instance;
v79 = 0;
LABEL_117:
LOBYTE(v26) = WsIrql;
MiUnlockWorkingSetShared(p_Instance, v26);
if( v79 && v71.Long )
{
MiGetLeafVa(v13 + 8);
LODWORD(v80) = MiGetLeafVa(v13);
MiDeleteEmptyPageTables(v80, v81, v82);
}
return ReserveSize;
}Referenced by:
MiDeleteVadAwePtes
NtMapUserPhysicalPages
NtMapUserPhysicalPagesScatter