MiCopyDataPageToImagePage
INT64 __fastcall MiCopyDataPageToImagePage(
_MMINPAGE_SUPPORT *InPageSupport,
_SUBSECTION *Subsection,
_MMPTE *ImageProtoPte,
VOID *TrapInformation,
UINT64 PageFrameIndex,
_MMPFN *LockedProtoPfn){
_MMINPAGE_SUPPORT *v8;
void *v9;
unsigned int v10;
_CONTROL_AREA *v11;
unsigned int SessionIdForVa;
unsigned __int64 v13;
INT64 *v14;
unsigned __int64 v15;
unsigned __int64 v16;
__int64 v17;
UINT64 v18;
UINT64 v19;
ULONG_PTR v20;
unsigned int v22;
unsigned __int64 v23;
__int64 v24;
unsigned int v25;
ULONG_PTR *p_BugCheckParameter2;
__int64 v27;
unsigned __int64 v28;
__int64 v29;
unsigned __int64 v30;
_MMPFN *v31;
_ETHREAD *CurrentThread;
ULONG_PTR *v33;
UINT64 v34;
char v35;
int locked;
_MMPFN *v37;
ULONG_PTR *v38;
UINT64 v39;
char *v40;
MMPTE *v41;
char v42;
_MMPFN *v43;
UINT64 v44;
INT64 v45;
INT64 v46;
__int64 v47;
int v48;
_MMPFN *DecayPfn;
INT64 v50;
_MMPFN *PfnDb;
UINT8 v52;
UINT8 *v53;
UINT64 v54;
UINT64 v55;
unsigned int v56;
INT64 *SpinLock;
unsigned int v58;
_CONTROL_AREA *Src;
_ETHREAD *v60;
unsigned __int64 v61;
_MMPFN *LockedPfns;
UINT64 SpinCount;
_MMPFN *a3;
ULONG_PTR BugCheckParameter2;
_MMPFN *ProtoPagePfn;
char v67;
char v68;
__int64 v69;
_MMPFN *v70;
char v71;
UINT64 v72;
UINT8 v74;
MMPTE *PointerPte;
unsigned __int64 v76;
v76 = (unsigned __int64)TrapInformation;
PointerPte = ImageProtoPte;
v74 = 0;
v8 = InPageSupport;
memset((INT64)&BugCheckParameter2, 0i64);
v9 = (void *)*((_QWORD *)v8 + 28);
LOBYTE(v10) = 0;
a3 = 0i64;
v11 = *(_CONTROL_AREA **)Subsection;
Src = *(_CONTROL_AREA **)Subsection;
SessionIdForVa = MiGetSessionIdForVa(v9);
v13 = MiStartingOffset((__int64)Subsection, (unsigned __int64)ImageProtoPte, SessionIdForVa);
v14 = (INT64 *)((char *)v11 + 72);
v61 = v13;
SpinLock = (INT64 *)((char *)v11 + 72);
v15 = v13;
ExAcquireSpinLockExclusiveAtDpcLevel((INT64 *)v11 + 9);
v16 = *((_QWORD *)v11 + 8) & 0xFFFFFFFFFFFFFFF0ui64;
ExAcquireSpinLockExclusiveAtDpcLevel((INT64 *)&dword_140C4C6C0);
v17 = **(_QWORD **)(v16 + 40);
if( !v17 || !(unsigned int)ExTryAcquireSpinLockExclusiveAtDpcLevel((INT64 *)(v17 + 72)) )
{
ExReleaseSpinLockExclusiveFromDpcLevel((INT64 *)&dword_140C4C6C0);
LABEL_3:
if( (v10 & 1) != 0 )
ExReleaseSpinLockExclusiveFromDpcLevel((INT64 *)(v17 + 72));
if( (v10 & 2) == 0 )
ExReleaseSpinLockExclusiveFromDpcLevel(v14);
if( v69 )
_InterlockedAnd64((volatile signed __int64 *)(v69 + 24), 0x7FFFFFFFFFFFFFFFui64);
if( v70 )
MiUnlockNestedProtoPoolPage(v70);
v20 = BugCheckParameter2;
if( v68 == 1 )
MiRemoveLockedPageChargeAndDecRef((_MMPFN *)BugCheckParameter2);
if( v20 )
_InterlockedAnd64((volatile signed __int64 *)(v20 + 24), 0x7FFFFFFFFFFFFFFFui64);
if( ProtoPagePfn )
{
LOBYTE(v18) = 2;
MiUnlockProtoPoolPage(ProtoPagePfn, v18);
}
if( (v10 & 4) != 0 )
MiDereferenceControlAreaPfnList(Src, 0i64, v19, 3ui64);
return 0i64;
}
ExReleaseSpinLockExclusiveFromDpcLevel((INT64 *)&dword_140C4C6C0);
v19 = 0i64;
LOBYTE(v10) = 1;
if( !*(_QWORD *)(v17 + 32) || (*(_DWORD *)(v17 + 56) & 3) != 0 )
goto LABEL_3;
v72 = MiEndingOffset(Subsection);
v23 = v15 >> 12;
v10 = v22 + 8;
v24 = v17 + 128;
if( (unsigned int)(v15 >> 12) != (unsigned int)((v72 - 1) >> 12) )
v10 = v22;
while( 1 )
{
v25 = *(_DWORD *)(v24 + 44);
if( (unsigned int)v23 < v25 )
break;
v24 = *(_QWORD *)(v24 + 16);
LODWORD(v23) = v23 - v25;
if( !v24 )
goto LABEL_3;
}
p_BugCheckParameter2 = &BugCheckParameter2;
v58 = 2;
while( 1 )
{
if( *(_DWORD *)(v24 + 104) == (_DWORD)v19 )
goto LABEL_87;
v27 = *(_QWORD *)(v24 + 8);
v18 = 0x7FFFFFFFF8i64;
if( !v27 )
goto LABEL_87;
v28 = v27 + 8i64 * (unsigned int)v23;
if( !v28 )
goto LABEL_87;
v29 = (v28 >> 9) & 0x7FFFFFFFF8i64;
v30 = ((unsigned __int64)PointerPte >> 9) & 0x7FFFFFFFF8i64;
p_BugCheckParameter2[2] = v28;
if( v29 == v30
|| p_BugCheckParameter2 != &BugCheckParameter2 && v29 == ((*(p_BugCheckParameter2 - 3) >> 9) & 0x7FFFFFFFF8i64) )
{
MiTryLockLeafPage((_MMPTE *)v28, 0x7FFFFFFFF8ui64);
}
else
{
if( (int)MiTryLockProtoPoolPageAtDpc((INT64 *)v28, 0x7FFFFFFFF8i64, &a3, (_MMPFN **)p_BugCheckParameter2) < 0 )
goto LABEL_87;
p_BugCheckParameter2[1] = (ULONG_PTR)a3;
}
v31 = (_MMPFN *)*p_BugCheckParameter2;
if( !*p_BugCheckParameter2
|| (*((_BYTE *)v31 + 34) & 0x20) != 0
|| (*((_BYTE *)v31 + 35) & 0x40) != 0
|| *((_WORD *)v31 + 16) >= 0x7FFFu )
{
goto LABEL_87;
}
p_BugCheckParameter2[3] = MI_READ_PTE_LOCK_FREE(v28);
if( p_BugCheckParameter2 != &BugCheckParameter2 || (v61 & 0xFFF) == 0 || v10 >= 8 )
break;
p_BugCheckParameter2 += 5;
++v58;
LODWORD(v23) = v23 + 1;
v19 = 0i64;
if( (unsigned int)v23 >= *(_DWORD *)(v24 + 44) )
{
v24 = *(_QWORD *)(v24 + 16);
LODWORD(v23) = 0;
if( !v24 )
goto LABEL_87;
}
}
ExReleaseSpinLockExclusiveFromDpcLevel((INT64 *)(v17 + 72));
++*((_QWORD *)Src + 4);
ExReleaseSpinLockExclusiveFromDpcLevel(SpinLock);
CurrentThread = (_ETHREAD *)KeGetCurrentThread();
v33 = &BugCheckParameter2;
v34 = BugCheckParameter2;
LOBYTE(v10) = v10 & 0xF8 | 6;
v60 = CurrentThread;
LockedPfns = (_MMPFN *)BugCheckParameter2;
if( !BugCheckParameter2 )
goto LABEL_55;
while( 1 )
{
v35 = 0;
if( (v33[3] & 1) == 0 && !*(_WORD *)(v34 + 32) )
{
*((_BYTE *)v33 + 32) = (*(_BYTE *)(v34 + 35) & 8) != 0;
if( !(unsigned int)MiUnlinkPageFromList((_MMPFN *)v34, 0i64) )
{
MiDiscardTransitionPteEx(v34, 0i64);
LABEL_87:
v14 = SpinLock;
goto LABEL_3;
}
v35 = 1;
*(_QWORD *)(v34 + 24) &= 0xC000000000000000ui64;
}
locked = MiAddLockedPageCharge(v34, 0);
v19 = 0i64;
if( !locked )
{
if( v35 )
MiPfnReferenceCountIsZero((_MMPFN *)v34, (__int64)(v34 - (_QWORD)MmGetPfnDb()) / 48, 0i64);
goto LABEL_87;
}
*((_BYTE *)v33 + 33) = 1;
if( v33 != &BugCheckParameter2 )
break;
v33 += 5;
v34 = *v33;
LockedPfns = (_MMPFN *)v34;
if( !v34 )
goto LABEL_54;
}
_InterlockedAnd64((volatile signed __int64 *)(v34 + 24), 0x7FFFFFFFFFFFFFFFui64);
v37 = (_MMPFN *)v33[1];
if( v37 )
{
MiUnlockNestedProtoPoolPage(v37);
v33[1] = 0i64;
}
LABEL_54:
CurrentThread = v60;
LABEL_55:
*((_DWORD *)v8 + 48) |= 0x20u;
v38 = &BugCheckParameter2;
_InterlockedAnd64((volatile signed __int64 *)(BugCheckParameter2 + 24), 0x7FFFFFFFFFFFFFFFui64);
if( ProtoPagePfn )
{
LOBYTE(v18) = 2;
MiUnlockProtoPoolPage(ProtoPagePfn, v18);
}
v39 = PageFrameIndex;
v40 = (char *)MmGetPfnDb() + 48 * PageFrameIndex;
LODWORD(SpinCount) = 0;
if( _interlockedbittestandset64((volatile signed __int32 *)v40 + 6, 0x3Fui64) )
{
do
{
do
KeYieldProcessorEx(&SpinCount);
while( *((__int64 *)v40 + 3) < 0 );
}
while( _interlockedbittestandset64((volatile signed __int32 *)v40 + 6, 0x3Fui64) );
CurrentThread = v60;
}
v41 = PointerPte;
MiInitializeTransitionPfn(v39, PointerPte);
v42 = v40[34] & 0xF8 | 2;
v40[34] = v42;
*((_WORD *)v40 + 16) = 1;
v40[34] = v42 | 0x20;
*(_QWORD *)v40 = (char *)v8 + 32;
if( (v76 & 1) != 0 && *(_BYTE *)(v76 & 0xFFFFFFFFFFFFFFFEui64) == 1 )
{
MiAdvanceFaultList((_QWORD *)(v76 & 0xFFFFFFFFFFFFFFFEui64));
*((_DWORD *)v8 + 48) |= 8u;
}
v40[35] ^= (v40[35] ^ (*((_DWORD *)v8 + 48) >> 9)) & 7;
_InterlockedAnd64((volatile signed __int64 *)v40 + 3, 0x7FFFFFFFFFFFFFFFui64);
*((_QWORD *)v8 + 21) = MI_READ_PTE_LOCK_FREE((INT64)v41);
*((_QWORD *)v8 + 29) = v41;
if( (int)PsGetIoPriorityThread((__int64)CurrentThread) < 2 )
*((_DWORD *)v8 + 48) |= 0x80u;
v43 = LockedProtoPfn;
*((_QWORD *)v8 + 34) = 0i64;
*((_QWORD *)v8 + 38) = 0i64;
*((_DWORD *)v8 + 70) = 56;
*((_QWORD *)v8 + 39) = 4096i64;
*((_QWORD *)v8 + 40) = v39;
MiObtainProtoReference((INT64)v43, 0);
LOBYTE(v44) = 2;
MiUnlockProtoPoolPage(v43, v44);
*((_WORD *)v8 + 141) |= 0x42u;
*((_QWORD *)v8 + 31) = v40;
*((_QWORD *)v8 + 26) = Src;
*((_QWORD *)v8 + 12) = v61;
*((_QWORD *)v8 + 30) = v41;
*((_QWORD *)v8 + 25) = 0i64;
*((_QWORD *)v8 + 20) = v43;
v45 = MiReservePtes((INT64)&qword_140C4EC80, v58);
v46 = v45;
if( v45 )
{
v47 = ((v45 << 25) - ((_QWORD)MmGetPteBase() << 25)) >> 16;
*(_QWORD *)v45 = MiMakeValidPte(v45, v39, 2684354564i64);
*(_QWORD *)(v46 + 8) = MiMakeValidPte(
v46 + 8,
(__int64)(BugCheckParameter2 - (_QWORD)MmGetPfnDb()) / 48,
536870913i64);
if( v69 )
*(_QWORD *)(v46 + 16) = MiMakeValidPte(v46 + 16, (v69 - (__int64)MmGetPfnDb()) / 48, 536870913i64);
if( v61 + 4096 > v72 )
{
v56 = ((_WORD)v72 - (_WORD)v61) & 0xFFF;
memmove((UINT8 *)v47, (UINT8 *)(v47 + (v61 & 0xFFF) + 4096), ((_WORD)v72 - (_WORD)v61) & 0xFFF);
memset(v56 + v47, 0i64);
}
else
{
KeCopyPage((PVOID)v47);
}
MiReleasePtes((INT64)&qword_140C4EC80, v46, v58);
__incgsdword(0x2E98u);
v43 = LockedProtoPfn;
v48 = 0;
}
else
{
v48 = -1073741670;
}
*((_DWORD *)v8 + 20) = v48;
DecayPfn = 0i64;
if( v67 || v71 )
DecayPfn = (_MMPFN *)MiCreateDecayPfn();
v50 = BugCheckParameter2;
LockedPfns = (_MMPFN *)BugCheckParameter2;
if( BugCheckParameter2 )
{
PfnDb = MmGetPfnDb();
while( 1 )
{
v74 = MiLockPageInline(v50);
v52 = v74;
if( !(unsigned int)MiRemoveLockedPageCharge(v50) )
goto LABEL_74;
if( !DecayPfn || !*((_BYTE *)v38 + 32) || (*(_QWORD *)(v50 + 24) & 0x4000000000000000i64) != 0 )
break;
LOBYTE(v54) = v52;
MiInsertAndUnlockStandbyPages(DecayPfn, &LockedPfns, (UINT8 *)1, v54);
v74 = 17;
LABEL_76:
if( v38 == &BugCheckParameter2 )
{
v38 += 5;
v50 = *v38;
LockedPfns = (_MMPFN *)v50;
if( v50 )
continue;
}
v8 = InPageSupport;
v43 = LockedProtoPfn;
goto LABEL_79;
}
MiPfnReferenceCountIsZero((_MMPFN *)v50, (v50 - (__int64)PfnDb) / 48, v53);
LABEL_74:
if( v52 != 17 )
{
_InterlockedAnd64((volatile signed __int64 *)(v50 + 24), 0x7FFFFFFFFFFFFFFFui64);
__writecr8(v74);
}
goto LABEL_76;
}
LABEL_79:
if( DecayPfn )
MiDecayPfnFullyInitialized((CHAR *)DecayPfn);
MiRelockProtoPoolPage((INT64)v43, &v74);
LOBYTE(v55) = v74;
*((_DWORD *)v8 + 48) &= ~0x20u;
MiUnlockProtoPoolPage(v43, v55);
*((_QWORD *)v8 + 11) = 4096i64;
KeSetEvent((PRKEVENT)((char *)v8 + 32), 0);
return 1i64;
}Referenced by:
MiResolveMappedFileFault