MmCopyToCachedPage
NTSTATUS __stdcall MmCopyToCachedPage(
PVOID SystemCacheAddress,
PVOID UserBuffer,
UINT64 Offset,
UINT64 CountInBytes,
UINT64 Flags){
UINT64 v5;
unsigned __int64 BugCheckParameter4;
unsigned __int64 v7;
UINT64 v8;
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;} v9;
INT64 *v10;
INT64 *v11;
POHANDLE *v12;
INT64 *v13;
char v14;
_XSTATE_CONFIGURATION *v15;
__int64 v16;
__int64 v17;
_MMPFN *v18;
UINT8 v19;
__int64 v20;
int v21;
int PageAvoidRead;
_MMPFN *v24;
__int64 v25;
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;} v26;
unsigned __int64 v27;
NTSTATUS v28;
__int64 v29;
int v30;
_SLIST_ENTRY *v31;
_XSTATE_CONFIGURATION *v32;
int v33;
__int64 v34;
int v35;
VOID *v36;
_MMPFN *PfnDb;
_MMPTE *v38;
__int64 v39;
__int64 v40;
INT64 v41;
int v42;
int v43;
unsigned __int64 v44;
__int64 v45;
UINT64 v46;
UINT64 v47;
_KTBFLUSH_TYPE v48;
_MMPFN *v49;
char PageIrql[4];
NTSTATUS v51;
INT64 v52;
INT8 a4[8];
__int64 v54;
INT64 v55;
UINT64 v56;
UINT64 v57;
POHANDLE *ptr32;
INT64 v59;
unsigned int v62;
v62 = Offset;
v5 = CountInBytes;
BugCheckParameter4 = (unsigned int)Offset;
v7 = (unsigned __int64)SystemCacheAddress;
*(_QWORD *)a4 = 0i64;
v51 = 0;
v54 = 0i64;
v55 = 0i64;
v8 = *(unsigned __int64 *)((char *)&MmGetPdeBase()->u.Long
+ (((unsigned __int64)SystemCacheAddress >> 18) & 0x3FFFFFF8));
v57 = v8;
MiPteInShadowRange((UINT64)&v57);
v9.Long = (unsigned __int64)MmGetPfnDb()[(v8 >> 12) & 0xFFFFFFFFFi64].OriginalPte.u;
if( v9.Long )
v9.Long += 40 * ((v7 >> 18) & 7);
v10 = *(INT64 **)(v9.Long + 24);
v11 = (INT64 *)((unsigned __int64)v10 & 0xFFFFFFFFFFFFFFFEui64);
if( ((unsigned __int8)v10 & 1) == 0 )
v11 = v10;
v59 = *v11;
v12 = (POHANDLE *)(*(_QWORD *)(*(&stru_140C4DB30 + 267) + 8i64 * (*(_WORD *)(v59 + 60) & 0x3FF)) + 7232i64);
ptr32 = v12;
if( BugCheckParameter4 + v5 > 0x1000 || BugCheckParameter4 + v5 < v5 )
KeBugCheckEx(0x1Au, (PVOID)0x776, (PVOID)v7, (PVOID)v5, (PVOID)BugCheckParameter4);
v13 = (INT64 *)((char *)MmGetPteBase() + ((v7 >> 9) & 0x7FFFFFFFF8i64));
v14 = Flags;
if( (Flags & 4) != 0 && ((v62 & 0x3F) != 0 || (v5 & 0x3F) != 0) )
return -1073740684;
if( (Flags & 8) != 0 )
{
v15 = (_XSTATE_CONFIGURATION *)MiReservePtes((_MI_SYSTEM_PTE_TYPE *)((char *)&stru_140C4DB30 + 4432), 1ui64);
v52 = (INT64)v15;
if( !v15 )
return -1073741670;
v12 = ptr32;
}
else
{
v15 = 0i64;
v52 = 0i64;
}
if( (*v13 & 1) == 0 )
{
LABEL_11:
v16 = *v13;
if( (*v13 & 1) != 0 )
{
if( !v15 )
{
v34 = v54;
goto LABEL_53;
}
LODWORD(v40) = MiMapSystemCachePage(v15, (INT64)v13, Flags);
v34 = v40;
v54 = v40;
if( v40 )
goto LABEL_53;
}
if( *(&stru_140C4DB30 + 42) )
{
if( (v16 & 0x10) != 0 )
v16 &= ~0x10ui64;
else
v16 &= ~*(&stru_140C4DB30 + 42);
}
v17 = v16 >> 16;
while( 1 )
{
while( 1 )
{
v18 = 0i64;
v19 = 17;
PageIrql[0] = 17;
LODWORD(v20) = MI_READ_PTE_LOCK_FREE(v17);
*(_QWORD *)a4 = v20;
if( (v20 & 1) == 0 && (v20 & 0x400) != 0 )
goto LABEL_18;
while( 1 )
{
v18 = MiLockProtoPoolPage((_MMPTE *)v17, (UINT8 *)PageIrql);
if( v18 )
break;
MmAccessFault(2ui64, (PVOID)v17, 0, 0i64);
}
v24 = MiLockLeafPage((_MMPTE *)v17, 0i64);
LODWORD(v25) = MI_READ_PTE_LOCK_FREE(v17);
*(_QWORD *)a4 = v25;
if( v24 )
break;
v19 = PageIrql[0];
v7 = (unsigned __int64)SystemCacheAddress;
LABEL_18:
if( v18 )
MiUnlockProtoPoolPage((ULONG_PTR)v18, v19);
LOBYTE(v21) = MiControlAreaUsingExtents(v59);
if( v21 )
{
v35 = MmAccessFault(0i64, (PVOID)v7, 0, 0i64);
v51 = v35;
if( v35 < 0 )
goto LABEL_48;
}
else
{
LODWORD(v5) = CountInBytes;
PageAvoidRead = MiMakePageAvoidRead(v17, UserBuffer, v62, CountInBytes, v14, (_MMPTE *)a4, &v51);
if( !PageAvoidRead )
return v51;
v42 = PageAvoidRead - 1;
if( v42 )
{
v43 = v42 - 2;
if( !v43 )
{
v33 = 0;
goto LABEL_41;
}
if( v43 != 1 )
{
v33 = 1;
LABEL_41:
MiMakeSystemCachePteValid(ptr32, (_HANDLE)v13, a4[0]);
v34 = v54;
goto LABEL_42;
}
LABEL_52:
v34 = v54;
goto LABEL_53;
}
}
}
if( (v25 & 1) != 0 )
break;
v26.Long = (unsigned __int64)v24->OriginalPte.u;
if( (v26.Long & 0x400) != 0 )
v27 = v26.Long >> 11;
else
v27 = v26.Long >> 3;
if( (v27 & 1) != 0 && (LODWORD(v41) = MiMakeTransitionHeatBatch((INT64)v24), v55 = v41, v41 == -1) )
{
_InterlockedAnd64(&v24->u2.Lock, 0x7FFFFFFFFFFFFFFFui64);
MiUnlockProtoPoolPage((ULONG_PTR)v18, PageIrql[0]);
MiReplenishTransitionPageHeatList();
v55 = 0i64;
v7 = (unsigned __int64)SystemCacheAddress;
}
else
{
v28 = MiUnlinkStandbyPfn((UINT64 *)v17, v14);
if( !v28 )
{
LODWORD(v29) = MI_READ_PTE_LOCK_FREE(v17);
*(_QWORD *)a4 = v29;
}
LABEL_32:
v51 = 0;
v30 = 0;
if( v52 && !v28 && MiAddLockedPageCharge(v24, 0i64) == MiChargeFailed )
{
v51 = -1073741670;
v30 = -1073741670;
}
_InterlockedAnd64(&v24->u2.Lock, 0x7FFFFFFFFFFFFFFFui64);
MiUnlockProtoPoolPage((ULONG_PTR)v18, PageIrql[0]);
v31 = (_SLIST_ENTRY *)v55;
if( v55 )
{
MiProcessTransitionHeatBatch(v55);
MiFreeTransitionPageHeatList(v31);
v55 = 0i64;
}
if( v30 < 0 )
{
v35 = v51;
goto LABEL_48;
}
v14 = Flags;
v7 = (unsigned __int64)SystemCacheAddress;
if( v28 != 1 )
{
if( v28 != 2 )
{
v32 = (_XSTATE_CONFIGURATION *)v52;
if( v52 )
{
v44 = *(_QWORD *)a4;
MiPteInShadowRange((UINT64)a4);
LODWORD(v45) = MiMapFrame(v32, (v44 >> 12) & 0xFFFFFFFFFi64);
v54 = v45;
}
v7 = (unsigned __int64)SystemCacheAddress;
LODWORD(v5) = CountInBytes;
v33 = 1;
goto LABEL_41;
}
v7 = (unsigned __int64)SystemCacheAddress;
v35 = MmAccessFault(0i64, SystemCacheAddress, 0, 0i64);
v51 = v35;
if( v35 < 0 )
goto LABEL_48;
}
}
}
v24->u2._bf_0 ^= (((v24->u2._bf_0 & 0x3FFFFFFFFFFFFFFFi64) + 1) ^ v24->u2._bf_0) & 0x3FFFFFFFFFFFFFFFi64;
v28 = 0;
goto LABEL_32;
}
if( !v15 )
{
MiDirtySystemCachePte((INT64)v12, v13, *v13);
goto LABEL_52;
}
LODWORD(v39) = MiMapSystemCachePage(v15, (INT64)v13, Flags);
v34 = v39;
v54 = v39;
if( !v39 )
{
v15 = (_XSTATE_CONFIGURATION *)v52;
goto LABEL_11;
}
LABEL_53:
v33 = 1;
LABEL_42:
v35 = 0;
v51 = 0;
if( v33 )
{
if( !v34 )
v34 = v7;
v36 = (VOID *)(v62 + v34);
if( (v14 & 4) != 0 )
RtlCopyMemoryNonTemporal(v36, UserBuffer, v5);
else
memmove(v36, UserBuffer, v5);
}
LABEL_48:
PfnDb = MmGetPfnDb();
v38 = (_MMPTE *)v52;
if( v52 )
{
LODWORD(v46) = MI_READ_PTE_LOCK_FREE(v52);
v47 = v46;
v56 = v46;
MiReleasePtes((_MI_SYSTEM_PTE_TYPE *)((char *)&stru_140C4DB30 + 4432), v38, 1ui64, v48);
if( (v47 & 1) != 0 )
{
MiPteInShadowRange((UINT64)&v56);
v49 = &PfnDb[(v47 >> 12) & 0xFFFFFFFFFi64];
PageIrql[0] = MiLockPageInline(v49);
MiRemoveLockedPageChargeAndDecRef(v49);
_InterlockedAnd64(&v49->u2.Lock, 0x7FFFFFFFFFFFFFFFui64);
__writecr8((unsigned __int8)PageIrql[0]);
return v51;
}
}
return v35;
}Referenced by:
CcMapAndCopyInToCache