MiResolveSharedZeroFault
CHAR __fastcall MiResolveSharedZeroFault(INT64 a1){
unsigned __int64 *v1;
unsigned __int64 v3;
_MMPTE *PteBase;
__int64 v5;
int v6;
__int64 *v7;
__int64 v8;
__int64 v9;
unsigned int v10;
unsigned __int64 v11;
_MMPTE *Pml4eBase;
_MMPTE *PxeUserLimit;
char *v14;
signed __int64 v15;
_MMPTE *v16;
__int64 v17;
_QWORD *v18;
__int64 v19;
__int128 *CurrentThread;
__int64 v21;
unsigned int v22;
unsigned __int64 v23;
unsigned __int64 v24;
unsigned __int64 v25;
unsigned __int64 v26;
unsigned __int64 v27;
__int128 v28;
__int128 v29;
__int128 v30;
unsigned __int64 v31;
unsigned __int64 v32;
unsigned __int64 i;
_QWORD *v34;
unsigned __int64 v35;
unsigned __int64 v36;
unsigned __int64 v37;
__int128 *v38;
_QWORD *v39;
unsigned __int64 v40;
unsigned int v41;
_MMPTE *v42;
INT64 v43;
char *v44;
signed __int64 v45;
_MMPTE *v46;
__int64 v47;
__int64 v48;
__int64 v49;
unsigned __int64 v50;
__int128 v52;
__int128 v53;
__int128 v54;
__int128 v55;
__int128 v56;
__int128 v57;
__int128 v58;
_SUBSECTION *ContainingSubsection;
unsigned __int64 v60;
__int64 v61;
__int128 v62;
__int128 v63;
__int128 v64;
__int128 v65;
int v66;
UINT64 SpinCount;
UINT64 v68;
unsigned __int64 v69;
v1 = *(unsigned __int64 **)(a1 + 8);
v52 = 0i64;
ContainingSubsection = 0i64;
v3 = *v1;
PteBase = MmGetPteBase();
v5 = (*v1 >> 9) & 0x7FFFFFFFF8i64;
v53 = 0i64;
v54 = 0i64;
v55 = 0i64;
v56 = 0i64;
v57 = 0i64;
v58 = 0i64;
v6 = *(_DWORD *)(a1 + 32);
v7 = (__int64 *)((char *)PteBase + v5);
v8 = *(_QWORD *)(a1 + 24);
v66 = v6;
v9 = (_QWORD)PteBase << 25;
v10 = 0;
v61 = v9;
v11 = (((_QWORD)v7 << 25) - v9) >> 16;
while( 1 )
{
Pml4eBase = MmGetPml4eBase();
PxeUserLimit = MmGetPxeUserLimit();
if( v11 <= 0x7FFFFFFEFFFFi64 )
break;
++v10;
v11 = (__int64)((v11 << 25) - v9) >> 16;
if( v10 >= 3 )
goto LABEL_16;
}
v14 = (char *)MmGetPfnDb()
+ 48
* ((*(_QWORD *)((char *)MmGetPdeBase() + (((unsigned __int64)((((_QWORD)v7 << 25) - v9) >> 16) >> 18) & 0x3FFFFFF8)) >> 12) & 0xFFFFFFFFFi64);
LODWORD(SpinCount) = 0;
if( _interlockedbittestandset64((volatile signed __int32 *)v14 + 6, 0x3Fui64) )
{
do
{
do
KeYieldProcessorEx(&SpinCount);
while( *((__int64 *)v14 + 3) < 0 );
}
while( _interlockedbittestandset64((volatile signed __int32 *)v14 + 6, 0x3Fui64) );
v6 = v66;
PxeUserLimit = MmGetPxeUserLimit();
}
*((_QWORD *)v14 + 2) ^= ((unsigned int)*((_QWORD *)v14 + 2) ^ ((unsigned int)*((_QWORD *)v14 + 2) + 0x10000)) & 0x3FF0000;
_InterlockedAnd64((volatile signed __int64 *)v14 + 3, 0x7FFFFFFFFFFFFFFFui64);
v15 = *((_QWORD *)v14 + 1) | 0x8000000000000000ui64;
v62 = 0i64;
v63 = 0i64;
if( (unsigned __int64)((v15 >> 47) + 1) > 1 )
{
Pml4eBase = MmGetPml4eBase();
}
else
{
v16 = MmGetPteBase();
*(_QWORD *)&v62 = (char *)v16 + (((unsigned __int64)v15 >> 9) & 0x7FFFFFFFF8i64);
*((_QWORD *)&v62 + 1) = (char *)v16 + (((unsigned __int64)v62 >> 9) & 0x7FFFFFFFF8i64);
*(_QWORD *)&v63 = (char *)v16 + ((*((_QWORD *)&v62 + 1) >> 9) & 0x7FFFFFFFF8i64);
Pml4eBase = MmGetPml4eBase();
*((_QWORD *)&v63 + 1) = (char *)v16 + (((unsigned __int64)v63 >> 9) & 0x7FFFFFFFF8i64);
v17 = 4i64;
do
v18 = (_QWORD *)*(&v61 + v17--);
while( (*v18 & 1) != 0 && (*v18 & 0x80u) == 0i64 && v17 );
}
LABEL_16:
if( v6 == 256 )
{
v19 = (v8 << 16) | 0x400;
if( qword_140C4DC80 )
{
if( (v19 & qword_140C4DC80) != 0 )
v19 |= 0x10ui64;
else
v19 |= qword_140C4DC80;
}
}
else
{
v19 = MiSwizzleInvalidPte(32 * (v6 & 0x1F | 0xFFFFFFFFF8000020ui64));
}
LOBYTE(CurrentThread) = (_BYTE)Pml4eBase;
if( v7 >= (__int64 *)Pml4eBase )
{
LOBYTE(CurrentThread) = (_BYTE)PxeUserLimit;
if( v7 <= (__int64 *)PxeUserLimit )
{
CurrentThread = (__int128 *)KeGetCurrentThread();
if( (*(_DWORD *)(*((_QWORD *)CurrentThread + 23) + 2172i64) & 0x1000) != 0 && (v19 & 1) != 0 )
v19 |= 0x8000000000000000ui64;
}
}
*v7 = v19;
v21 = *(_QWORD *)(a1 + 64);
if( v21 )
{
v22 = *(_DWORD *)(v21 + 48);
v23 = *(unsigned int *)(v21 + 24) | ((unsigned __int64)*(unsigned __int8 *)(v21 + 32) << 32);
v24 = *(unsigned int *)(v21 + 28) | ((unsigned __int64)*(unsigned __int8 *)(v21 + 33) << 32);
v60 = v23;
if( MiVadPageSizes[(v22 >> 18) & 3] == 16 )
{
v25 = v3 & 0xFFFFFFFFFFFF0000ui64;
*((_QWORD *)&v52 + 1) = 0x10000i64;
*(_QWORD *)&v52 = v25;
CurrentThread = (__int128 *)(v25 >> 12);
if( v25 >> 12 < v23 )
return(char)CurrentThread;
CurrentThread = (__int128 *)((v25 + 0xFFFF) >> 12);
if( (unsigned __int64)CurrentThread > v24 )
return(char)CurrentThread;
v26 = 16i64;
}
else
{
LODWORD(CurrentThread) = *(_DWORD *)a1;
if( (*(_DWORD *)a1 & 2) != 0 )
{
CurrentThread = *(__int128 **)(a1 + 56);
v26 = 256i64;
v69 = 256i64;
v27 = v24 - (v3 >> 12) + 1;
v28 = CurrentThread[1];
v53 = *CurrentThread;
v54 = v28;
v29 = CurrentThread[3];
v55 = CurrentThread[2];
v56 = v29;
v30 = CurrentThread[5];
v57 = CurrentThread[4];
v58 = v30;
if( v27 < 0x100 )
{
v26 = v27;
v69 = v27;
}
LABEL_40:
v32 = 0i64;
for( i = 0i64; i < v26; v32 = v35 )
{
v34 = (_QWORD *)(*((_QWORD *)&v53 + 1) + 16i64 * *((_QWORD *)&v54 + 1));
v35 = (*v34 + ((_QWORD)v55 << 12)) & 0xFFFFFFFFFFFFF000ui64;
v36 = (unsigned __int64)MmGetPteBase() + ((v35 >> 9) & 0x7FFFFFFFF8i64);
if( i )
{
LOBYTE(CurrentThread) = v32;
if( v35 != v32 + 4096 || (v36 & 0xFFF) == 0 )
break;
}
if( !*(_QWORD *)v36 )
{
CurrentThread = (__int128 *)MiGetProtoPteAddress((_MMVAD *)v21, v35 >> 12, 4ui64, &ContainingSubsection);
v38 = CurrentThread;
if( !CurrentThread )
return(char)CurrentThread;
v39 = *(_QWORD **)(v21 + 120);
if( (__int64)v39 < 0 )
{
CurrentThread = (__int128 *)((unsigned __int64)(*v39 - 1i64) >> 12);
if( (v35 >> 12) - v60 > (unsigned __int64)CurrentThread )
return(char)CurrentThread;
}
v40 = (__int64)((v36 << 25) - v61) >> 16;
v41 = 0;
while( v40 > 0x7FFFFFFEFFFFi64 )
{
++v41;
v40 = (__int64)((v40 << 25) - v61) >> 16;
if( v41 >= 3 )
goto LABEL_51;
}
v37 = (unsigned __int64)MmGetPdeBase()
+ (((unsigned __int64)((__int64)((v36 << 25) - v61) >> 16) >> 18) & 0x3FFFFFF8);
v44 = (char *)MmGetPfnDb() + 48 * ((*(_QWORD *)v37 >> 12) & 0xFFFFFFFFFi64);
LODWORD(v68) = 0;
while( _interlockedbittestandset64((volatile signed __int32 *)v44 + 6, 0x3Fui64) )
{
do
KeYieldProcessorEx(&v68);
while( *((__int64 *)v44 + 3) < 0 );
}
*((_QWORD *)v44 + 2) ^= ((unsigned int)*((_QWORD *)v44 + 2) ^ ((unsigned int)*((_QWORD *)v44 + 2) + 0x10000)) & 0x3FF0000;
_InterlockedAnd64((volatile signed __int64 *)v44 + 3, 0x7FFFFFFFFFFFFFFFui64);
v45 = *((_QWORD *)v44 + 1) | 0x8000000000000000ui64;
v64 = 0i64;
v65 = 0i64;
if( (unsigned __int64)((v45 >> 47) + 1) > 1 )
{
LABEL_51:
v42 = MmGetPxeUserLimit();
goto LABEL_52;
}
v46 = MmGetPteBase();
v47 = 4i64;
*(_QWORD *)&v64 = (char *)v46 + (((unsigned __int64)v45 >> 9) & 0x7FFFFFFFF8i64);
*((_QWORD *)&v64 + 1) = (char *)v46 + (((unsigned __int64)v64 >> 9) & 0x7FFFFFFFF8i64);
*(_QWORD *)&v65 = (char *)v46 + ((*((_QWORD *)&v64 + 1) >> 9) & 0x7FFFFFFFF8i64);
v42 = MmGetPxeUserLimit();
*((_QWORD *)&v65 + 1) = (char *)v46 + (((unsigned __int64)v65 >> 9) & 0x7FFFFFFFF8i64);
do
v37 = *((_QWORD *)&v63 + v47-- + 1);
while( (*(_QWORD *)v37 & 1) != 0 && (*(_QWORD *)v37 & 0x80u) == 0i64 && v47 );
LABEL_52:
if( v66 == 256 )
{
v43 = MiSwizzleInvalidPte(((_QWORD)v38 << 16) | 0x400i64);
}
else
{
v43 = 32 * (v66 & 0x1F | 0xFFFFFFFFF8000020ui64);
if( qword_140C4DC80 )
{
if( (qword_140C4DC80 & v43) != 0 )
v43 |= 0x10ui64;
else
v43 |= qword_140C4DC80;
}
}
if( v36 >= (unsigned __int64)MmGetPml4eBase()
&& v36 <= (unsigned __int64)v42
&& (*(_DWORD *)(*((_QWORD *)KeGetCurrentThread() + 23) + 2172i64) & 0x1000) != 0
&& (v43 & 1) != 0 )
{
v43 |= v37;
}
*(_QWORD *)v36 = v43;
v26 = v69;
}
v48 = *(_DWORD *)v34 & 0xFFF;
v49 = v34[1] + 4095i64;
*(_QWORD *)&v55 = v55 + 1;
if( (_QWORD)v55 == (unsigned __int64)(v49 + v48) >> 12 )
{
v50 = *((_QWORD *)&v54 + 1) + 1i64;
*(_QWORD *)&v55 = 0i64;
*((_QWORD *)&v54 + 1) = v50;
if( v50 < (unsigned __int64)v54 )
{
LOBYTE(CurrentThread) = BYTE8(v53);
if( !*(_QWORD *)(*((_QWORD *)&v53 + 1) + 16 * v50 + 8) )
break;
}
}
LOBYTE(CurrentThread) = v54;
if( *((_QWORD *)&v54 + 1) == (_QWORD)v54 )
break;
++i;
}
return(char)CurrentThread;
}
if( (v22 & 0x70) == 32 )
return(char)CurrentThread;
v26 = 8i64;
v31 = v24 - (v3 >> 12);
*(_QWORD *)&v52 = v3 & 0xFFFFFFFFFFFFF000ui64;
if( v31 + 1 < 8 )
v26 = v31 + 1;
*((_QWORD *)&v52 + 1) = v26 << 12;
}
CurrentThread = &v52;
*(_QWORD *)&v55 = 0i64;
*((_QWORD *)&v53 + 1) = &v52;
v54 = 1ui64;
LOWORD(v53) = 2;
v69 = v26;
goto LABEL_40;
}
return(char)CurrentThread;
}Referenced by:
MiZeroFault