MiMapMdlCommon

NTSTATUS __stdcall MiMapMdlCommon(
        _MDL *MemoryDescriptorList,
        _MMPTE *PointerPte,
        UINT64 EntryProtectionMask,
        _MEMORY_CACHING_TYPE CacheType){
  UINT64 v4; 
  INT64 v5; 
  __int64 ByteOffset; 
  __int64 ByteCount; 
  INT64 *v8; 
  __int16 v9; 
  unsigned __int64 v10; 
  int v11; 
  UINT64 v12; 
  char *v13; 
  UINT8 v14; 
  UINT64 v15; 
  int v16; 
  char *v17; 
  int ProtectionPfnCompatible; 
  UINT64 ValidPte; 
  __int64 v20; 
  unsigned __int64 v21; 
  unsigned __int64 v22; 
  BOOL v23; 
  int v24; 
  int v25; 
  INT64 v26; 
  _MDL *v27; 
  NTSTATUS v28; 
  __int16 v29; 
  unsigned __int64 v31; 
  int HasShadow; 
  __int64 v33; 
  __int64 *v34; 
  _MMPTE *PteBase; 
  unsigned __int64 v36; 
  unsigned __int64 v37; 
  __int64 v38; 
  UINT64 v39; 
  unsigned __int64 v40; 
  char v41; 
  unsigned __int64 v42; 
  unsigned __int64 v43; 
  unsigned __int64 v44; 
  __int64 v45; 
  __int64 *v46; 
  unsigned __int64 v47; 
  unsigned __int64 v48; 
  INT64 *v49; 
  unsigned __int64 v50; 
  UINT8 v51; 
  UINT8 v52; 
  UINT64 v53; 
  INT64 v54; 
  UINT64 ProtectionMask; 
  __int64 *v56; 
  UINT64 v57; 
  unsigned __int64 v58; 
  INT64 *v59; 
  _MDL *v60; 
  __int64 v61; 
  unsigned __int64 v62; 
  INT64 v63; 
  __int64 v64; 
  void *v65; 
  int result; 
  __int16 result_4; 
  __int64 v68; 
  __int64 v69; 
  __int64 v70; 
  int v71; 
  v60 = MemoryDescriptorList;
  v4 = (UINT64)PointerPte;
  v54 = EntryProtectionMask;
  v5 = EntryProtectionMask;
  LODWORD(ProtectionMask) = CacheType;
  ByteOffset = MemoryDescriptorList->ByteOffset;
  ByteCount = MemoryDescriptorList->ByteCount;
  v8 = (INT64 *)&MemoryDescriptorList[1];
  v9 = (__int16)MemoryDescriptorList->StartVa + ByteOffset;
  v59 = v8;
  v58 = v9 & 0xFFF;
  v10 = (ByteCount + 4095 + v58) >> 12;
  v57 = v10;
  v64 = (_QWORD)MmGetPteBase() << 25;
  v11 = 0;
  v65 = (void *)(ByteOffset + ((((_QWORD)PointerPte << 25) - v64) >> 16));
  if( ((unsigned __int16)PointerPte & 0xFFF) == 0 && !v5 && (v10 & 0x1FF) == 0 && (*(_DWORD *)v8 & 0x1FFi64) == 0 )
    v11 = 1;
LABEL_2:
  v53 = 0i64;
  v12 = 0i64;
  v13 = 0i64;
  if( v5 )
  {
    v14 = MiLockWorkingSetShared(v5);
    v51 = v14;
  }
  else
  {
    v14 = 17;
    v51 = 17;
  }
  while( 1 )
  {
    if( v14 != 17 )
    {
      if( !v13 )
        goto LABEL_35;
      if( (v4 & 0xFFF) == 0 )
      {
        MiUnlockPageTableInternal(v5, (UINT64)v13);
LABEL_35:
        v13 = (char *)MmGetPteBase() + ((v4 >> 9) & 0x7FFFFFFFF8i64);
        MiLockPageTableInternal(v5, (UINT64)v13, 0i64);
      }
    }
    v15 = *v8;
    v16 = ProtectionMask;
    if( (unsigned __int64)*v8 <= 0xFFFFFFFFFi64 && (*((_QWORD *)MmGetPfnDb() + 6 * v15 + 5) & 0x4000000000000i64) != 0 )
    {
      v17 = (char *)MmGetPfnDb() + 48 * v15;
      if( !*((_WORD *)v17 + 16) && !dword_140C4E40C )
        MiShowBadMapper(v15, 5ui64);
      if( (v17[34] & 0xC0) == 0xC0 )
        MiAssignInitialPageAttribute((INT64)v17, v71);
      ProtectionPfnCompatible = MiMakeProtectionPfnCompatible((unsigned int)ProtectionMask, (_MMPFN *)v17);
      v14 = v51;
      v16 = ProtectionPfnCompatible;
    }
    else if( v71 )
    {
      if( v71 == 2 )
        v16 = ProtectionMask | 0x18;
    }
    else
    {
      v16 = ProtectionMask | 8;
    }
    ValidPte = MiMakeValidPte(v4, *v8, v16 | 0xA0000000);
    v20 = 1i64;
    v21 = ValidPte;
    if( v11 != 1 )
      goto LABEL_12;
    if( v8 == v59 )
    {
      v12 = ValidPte;
      v53 = ValidPte;
      goto LABEL_18;
    }
    v31 = v12 ^ (v12 ^ ((v12 & 0xFFFFFFFFFFFFF000ui64) + 4096)) & 0xFFFFFFFFF000i64;
    v53 = v31;
    v12 = v31;
    if( v31 != v21 )
    {
      if( (((unsigned int)v21 | (unsigned int)v31) & 0x1FF000) != 0 )
      {
        v5 = v54;
        if( v14 != 17 )
        {
          if( v13 )
            MiUnlockPageTableInternal(v54, (UINT64)v13);
          MiUnlockWorkingSetShared(v54, v14);
        }
        v11 = 0;
        v57 = (v58 + 4095 + v60->ByteCount) >> 12;
        v4 -= 8 * (((char *)v8 - (char *)v60 - 48) >> 3);
        v8 = v59;
        goto LABEL_2;
      }
      v12 = v31 ^ (v21 ^ v31) & 0xFFFFFFFFF000i64;
      v53 = v12;
LABEL_12:
      if( v11 )
        goto LABEL_18;
      v22 = v21;
      v23 = MiPteInShadowRange(v4);
      v24 = 0;
      if( !v23 )
      {
        v20 = 1i64;
        goto LABEL_15;
      }
      HasShadow = MiPteHasShadow();
      v20 = 1i64;
      if( HasShadow )
      {
        v25 = 1;
        if( HIBYTE(word_140C4DD48) == (_BYTE)v24 && (v21 & 1) != 0 )
          v22 = v21 | 0x8000000000000000ui64;
      }
      else
      {
        if( (*(_DWORD *)(*((_QWORD *)KeGetCurrentThread() + 23) + 2172i64) & 0x1000) != 0 && (v21 & 1) != 0 )
          v22 = v21 | 0x8000000000000000ui64;
        v12 = v53;
LABEL_15:
        v25 = v24;
      }
      *(_QWORD *)v4 = v22;
      if( v25 )
        MiWritePteShadow();
    }
LABEL_18:
    ++v8;
    v4 += 8i64;
    v57 -= v20;
    if( !v57 )
      break;
    v14 = v51;
    v5 = v54;
  }
  if( v51 == 17 )
  {
    v26 = v54;
  }
  else
  {
    if( v13 )
      MiUnlockPageTableInternal(v54, (UINT64)v13);
    v26 = v54;
    MiUnlockWorkingSetShared(v54, v51);
    LODWORD(v20) = 1;
  }
  if( v11 == (_DWORD)v20 )
  {
    memset((INT64)&result, 0i64);
    v56 = 0i64;
    v33 = 0i64;
    ProtectionMask = 0i64;
    v34 = 0i64;
    PteBase = MmGetPteBase();
    v36 = (unsigned __int64)PteBase + (((v4 - 8 * ((v60->ByteCount + v58 + 4095) >> 12)) >> 9) & 0x7FFFFFFFF8i64);
    v37 = (v60->ByteCount + v58 + 4095) >> 21;
    v38 = v21 | 0x80;
    v57 = 0i64;
    v61 = v38;
    v39 = 0i64;
    v40 = v36 + 8 * v37;
    v62 = v40;
    if( v26 )
    {
      v41 = MiLockWorkingSetShared(v26);
      PteBase = MmGetPteBase();
    }
    else
    {
      v41 = 17;
    }
    v52 = v41;
    if( v36 < v40 )
    {
      v42 = v36;
      do
      {
        if( v41 != 17 )
        {
          v39 = (UINT64)PteBase + ((v42 >> 9) & 0x7FFFFFFFF8i64);
          v57 = v39;
          MiLockPageTableInternal(v26, v39, 0i64);
        }
        v43 = 512 - ((v36 >> 3) & 0x1FF);
        if( v43 > (__int64)(v62 - v42) >> 3 )
          v43 = (__int64)(v62 - v42) >> 3;
        v63 = v43;
        v58 = v42 + 8 * v43;
        if( v42 < v58 )
        {
          MiPteInShadowRange((UINT64)&v53);
          v44 = v58;
          v45 = (__int64)v56;
          do
          {
            ProtectionMask = (UINT64)v34;
            v53 = MI_READ_PTE_LOCK_FREE(v36);
            *(_QWORD *)v36 = ZeroPte;
            v34 = (__int64 *)((char *)MmGetPfnDb() + 48 * ((v53 >> 12) & 0xFFFFFFFFFi64));
            v46 = v34;
            if( ProtectionMask )
              v34 = (__int64 *)ProtectionMask;
            v36 += 8i64;
            v42 = v36;
            *v46 = v45;
            v45 = (__int64)v46;
          }
          while( v36 < v44 );
          v38 = v61;
          v39 = v57;
          v43 = v63;
          v56 = v46;
          ProtectionMask = (UINT64)v34;
        }
        result_4 = 0;
        v68 = 20i64;
        result = 0;
        v69 = 0i64;
        v70 = 0i64;
        MiInsertTbFlushEntry((INT64)&result, (__int64)((v42 << 25) - v64) >> 16, v43, 0i64);
        MiFlushTbList((__int64)&result);
        v47 = v43;
        v48 = v58;
        v36 = v42 - 8 * v47;
        v42 = v36;
        if( v36 < v58 )
        {
          v49 = v59;
          do
          {
            v38 ^= (v38 ^ (*v49 << 12)) & 0xFFFFFFFFF000i64;
            *(_QWORD *)v36 = v38;
            v36 += 8i64;
            v49 += 512;
            v42 = v36;
          }
          while( v36 < v48 );
          v34 = (__int64 *)ProtectionMask;
          v59 = v49;
          v39 = v57;
          v61 = v38;
        }
        v26 = v54;
        if( v39 )
          MiUnlockPageTableInternal(v54, v39);
        v41 = v52;
        PteBase = MmGetPteBase();
      }
      while( v36 < v62 );
      v33 = (__int64)v56;
    }
    if( v52 != 17 )
      MiUnlockWorkingSetShared(v26, v52);
    v50 = ExAcquireSpinLockExclusive(&dword_140C4E900);
    *v34 = qword_140C4E910;
    qword_140C4E910 = v33;
    ExReleaseSpinLockExclusiveFromDpcLevel((INT64 *)&dword_140C4E900);
    LOWORD(v20) = 1;
    __writecr8(v50);
  }
  v27 = v60;
  v28 = (int)v65;
  v29 = v20 | v60->MdlFlags;
  v60->MappedSystemVa = v65;
  v27->MdlFlags = v29;
  if( (v29 & 0x10) != 0 )
    v27->MdlFlags = v29 | 0x20;
  return v28;
}

Referenced by:

MmMapLockedPagesWithReservedMapping
MmMapLockedRestartPages