MmFreeVirtualMemory

INT64 __fastcall MmFreeVirtualMemory(INT64 rcx0, UINT64 *a2, INT64 *a3, INT64 a4, CHAR a5, INT64 a6){
  int v6; 
  UINT64 v7; 
  unsigned __int64 v8; 
  __int64 v9; 
  int v10; 
  unsigned __int64 v12; 
  int v13; 
  unsigned __int64 v14; 
  __int64 v15; 
  int v16; 
  INT64 v17; 
  int v18; 
  unsigned __int64 v19; 
  unsigned __int64 v20; 
  UINT64 v21; 
  UINT64 v22; 
  int v23; 
  int v24; 
  bool v25; 
  __int64 v26; 
  __int64 v27; 
  int v28; 
  unsigned __int64 v29; 
  unsigned __int64 v30; 
  int v31; 
  UINT64 v32; 
  UINT64 v33; 
  int v34; 
  int v35; 
  int v36; 
  __int64 v37; 
  int v38; 
  INT64 Tag; 
  char AddressSpaceHeldExclusve[4]; 
  int v41; 
  int v42; 
  char v43[12]; 
  UINT64 a1; 
  int v45; 
  INT64 v46; 
  UINT64 StartingVpn; 
  unsigned __int64 v48; 
  INT64 v49; 
  unsigned __int64 v50; 
  __int64 v51; 
  INT64 *v52; 
  UINT64 *v53; 
  volatile signed __int32 *v54[2]; 
  _ETHREAD *CurrentThread; 
  _KAPC_STATE ApcState; 
  v46 = rcx0;
  v42 = a4;
  v52 = a3;
  v53 = a2;
  v51 = 0i64;
  v6 = a4;
  memset(&ApcState, 0, 32);
  *(_QWORD *)&ApcState.InProgressFlags = 0i64;
  memset(v43, 0, sizeof(v43));
  v54[1] = 0i64;
  v54[0] = 0i64;
  if( (a4 & 0xC000) == 0 || (a4 & 0xC000) == 49152 )
    return 3221225714i64;
  v7 = *a2;
  v8 = *a3;
  CurrentThread = (_ETHREAD *)KeGetCurrentThread();
  v9 = *((_QWORD *)CurrentThread + 23);
  v50 = v7;
  v49 = v8;
  if( v7 > 0x7FFFFFFEFFFFi64 )
    return 3221225712i64;
  if( 0x7FFFFFFF0000i64 - v7 < v8 )
    return 3221225713i64;
  if( (v6 & 2) != 0 )
  {
    if( (v6 & 1) != 0 )
      return 3221225485i64;
    v10 = a6 | 0x4000000;
    v6 &= ~2u;
    v42 = v6;
  }
  else
  {
    v10 = a6;
  }
  v41 = v10;
  if( (v6 & 1) != 0 )
  {
    if( (v6 & 2) != 0 )
      return 3221225485i64;
    v10 |= 0xC000000u;
    v6 &= ~1u;
    v41 = v10;
    v42 = v6;
  }
  v45 = v10 & 0x4000000;
  if( (v10 & 0x4000000) == 0 )
    goto LABEL_18;
  if( v6 != 0x8000 )
    return 3221225714i64;
  if( !v8 || v8 != (v8 & 0xFFFFFFFFFFFFF000ui64) )
    return 3221225713i64;
  if( v7 != (v7 & 0xFFFFFFFFFFFFF000ui64) )
    return 3221225712i64;
LABEL_18:
  v12 = v7 & 0x7FFFFFFFF000i64;
  v13 = 0;
  StartingVpn = (v7 & 0xFFFFFFFFFFFFF000ui64) >> 12;
  a1 = v7 & 0xFFFFFFFFFFFFF000ui64;
  v14 = (v7 + v8 - 1) | 0xFFF;
  ApcState.Process = 0i64;
  v48 = v14 >> 12;
  if( rcx0 == -1 )
  {
    v15 = v9;
  }
  else
  {
    *(_DWORD *)v43 = ObpReferenceObjectByHandleWithTag(
                       rcx0,
                       8,
                       (__int64)PsProcessType,
                       a5,
                       0x6D566D4Du,
                       (__int64)&v43[4],
                       0i64,
                       0i64);
    v16 = *(_DWORD *)v43;
    if( *(int *)v43 < 0 )
      return(unsigned int)v16;
    v15 = *(_QWORD *)&v43[4];
    if( v9 != *(_QWORD *)&v43[4] )
    {
      v13 = 1;
      KiStackAttachProcess(*(_KPROCESS **)&v43[4], 0i64, &ApcState);
    }
    v10 = v41;
    v12 = a1;
  }
  AddressSpaceHeldExclusve[0] = 0;
  if( (v6 & 0xFFFF3FFF) != 0 && (!*(_QWORD *)(v15 + 2240) || (v6 & 0x10000) == 0 || (v6 & 0x4000) != 0) )
  {
    v16 = -1073741582;
    goto LABEL_120;
  }
  if( (v10 & 0xC000000) == 201326592 )
  {
    v16 = MiCoalescePlaceholderAllocations(v15, v12, v14, a5);
    goto LABEL_120;
  }
  *(_DWORD *)&v43[4] = v6 & 0x8000;
  v17 = MiObtainReferencedVadEx(v12, *(_DWORD *)&v43[4] != 0, (INT64 *)v43);
  if( !v17 )
  {
    v16 = *(_DWORD *)v43;
    goto LABEL_120;
  }
  while( 1 )
  {
    v18 = *(_DWORD *)&v43[4];
    v19 = *(unsigned int *)(v17 + 24) | ((unsigned __int64)*(unsigned __int8 *)(v17 + 32) << 32);
    v20 = *(unsigned int *)(v17 + 28) | ((unsigned __int64)*(unsigned __int8 *)(v17 + 33) << 32);
    if( v49 )
    {
      v21 = v48;
    }
    else
    {
      v48 = *(unsigned int *)(v17 + 28) | ((unsigned __int64)*(unsigned __int8 *)(v17 + 33) << 32);
      v21 = v20;
      v14 = (v20 << 12) | 0xFFF;
      if( *(_DWORD *)&v43[4] )
      {
        if( StartingVpn != v19 )
          goto LABEL_104;
        a1 = v19 << 12;
      }
    }
    v22 = StartingVpn;
    if( StartingVpn < v19 || StartingVpn > v20 || v21 < v19 || v21 > v20 )
    {
      v16 = -1073741798;
      goto LABEL_117;
    }
    v23 = *(_DWORD *)(v17 + 48);
    v24 = v23 & 0x100000;
    if( (v42 & 0x10000) == 0 )
    {
      if( !v24 )
        goto LABEL_115;
      v25 = (v23 & 0x70) == 16;
LABEL_48:
      if( v25 )
        goto LABEL_115;
      goto LABEL_49;
    }
    if( v24 || (v23 & 0x70) != 0 )
    {
LABEL_115:
      v16 = -1073741797;
      goto LABEL_117;
    }
    if( StartingVpn == v19 )
    {
      v25 = v21 == v20;
      goto LABEL_48;
    }
LABEL_49:
    if( v45 )
    {
      if( !MiLocateVadEvent(v17, 128i64) )
      {
        v26 = *(unsigned int *)(v17 + 52);
        LODWORD(v26) = v26 & 0x7FFFFFFF;
        if( (v26 | ((unsigned __int64)*(unsigned __int8 *)(v17 + 34) << 31)) != 0x7FFFFFFFDi64 )
          break;
      }
      v27 = *(unsigned int *)(v17 + 52);
      LODWORD(v27) = v27 & 0x7FFFFFFF;
      if( (v27 | ((unsigned __int64)*(unsigned __int8 *)(v17 + 34) << 31)) == 0x7FFFFFFFDi64
        && v22 == v19
        && v21 == v20 )
      {
        break;
      }
    }
    v28 = v41;
    if( (v41 & 0x40000000) != 0 && (!v24 || (v23 & 0x1000000) != 0 || (v23 & 0x4000000) == 0) )
      break;
    if( (v23 & 8) == 0 || (v41 & 0x40000000) != 0 )
      goto LABEL_69;
    if( !v18 )
    {
      v30 = v50;
      v29 = v21 - v22;
      goto LABEL_66;
    }
    if( (*(_DWORD *)(v15 + 1124) & 0x20) == 0 )
    {
      v29 = v20 - v19;
      v30 = v19 << 12;
LABEL_66:
      v16 = MiCheckSecuredVad(v17, v30, (v29 + 1) << 12, 0x55u, a5);
      goto LABEL_67;
    }
    v16 = 0;
LABEL_67:
    if( v16 < 0 )
      goto LABEL_117;
    v22 = StartingVpn;
    v21 = v48;
    v28 = v41;
LABEL_69:
    if( !*(_DWORD *)&v43[4] )
    {
      v33 = v49;
      v32 = a1;
      if( v49 )
        v33 = v14 - a1 + 1;
      v34 = *(_DWORD *)(v17 + 48);
      if( (v34 & 0x100000) == 0
        || (v34 & 0x1000000) != 0
        || (v34 & 0x2000000) == 0
        || (LODWORD(Tag) = v28, v35 = MiDecommitEnclavePages(v15, v17, a1, v33, Tag), v16 = v35, v35 == -1073741802) )
      {
        v36 = *(_DWORD *)(v17 + 48);
        if( (*(_BYTE *)(v17 + 48) & 0x70) == 48
          || (v36 & 0x100000) != 0
          && ((v36 & 0x400000) != 0 || (v36 & 0xC0000u) >= 0x80000)
          && ((v36 & 0x500000) != 5242880 || v33 && (((MiGetVadPageSize(v17) << 12) - 1) & (v32 | (v14 + 1))) != 0)
          || (v37 = *(unsigned int *)(v17 + 52),
              LODWORD(v37) = v37 & 0x7FFFFFFF,
              (v37 | ((unsigned __int64)*(unsigned __int8 *)(v17 + 34) << 31)) == 0x7FFFFFFFDi64) )
        {
          v16 = -1073741664;
          goto LABEL_117;
        }
        if( !v33 )
        {
          if( v50 >> 12 != (*(unsigned int *)(v17 + 24) | ((unsigned __int64)*(unsigned __int8 *)(v17 + 32) << 32)) )
          {
LABEL_104:
            v16 = -1073741665;
            goto LABEL_117;
          }
          v14 = ((*(unsigned int *)(v17 + 28) | ((unsigned __int64)*(unsigned __int8 *)(v17 + 33) << 32)) << 12) | 0xFFF;
        }
        MiDecommitRegion((_MMVAD_SHORT *)v17, (PVOID)v32, (PVOID)v14);
        LODWORD(v51) = v38;
      }
      else if( v35 < 0 )
      {
        goto LABEL_117;
      }
      MiUnlockAndDereferenceVad((PVOID)v17);
      if( (_DWORD)v51 )
        MiDeleteEmptyPageTables(v32, v14, 0);
      if( v13 )
        KiUnstackDetachProcess(&ApcState, 0i64);
      if( v46 != -1 )
        ObfDereferenceObjectWithTag((PVOID)v15, 0x6D566D4Dui64);
      *v52 = v33;
LABEL_85:
      *v53 = v32;
      return 0i64;
    }
    if( (*(_DWORD *)(v15 + 2172) & 0x100) != 0 && (v22 != v19 || v21 != v20) )
    {
      v16 = -1073741558;
      goto LABEL_117;
    }
    v31 = MiFreeVadRange((_MMVAD *)v17, (UINT8 *)AddressSpaceHeldExclusve, v22, v21, (_EPROCESS *)v15);
    v16 = v31;
    if( v31 >= 0 )
    {
      if( v13 )
        KiUnstackDetachProcess(&ApcState, 0i64);
      if( v54[0] )
        MiFreeEnclaveModules(v54, (void *)v15);
      if( v46 != -1 )
        ObfDereferenceObjectWithTag((PVOID)v15, 0x6D566D4Dui64);
      v32 = a1;
      *v52 = v14 - a1 + 1;
      goto LABEL_85;
    }
    if( v31 != -1073741267 )
      goto LABEL_117;
  }
  v16 = -1073741800;
LABEL_117:
  MiUnlockAndDereferenceVad((PVOID)v17);
  if( AddressSpaceHeldExclusve[0] == 1 )
    UNLOCK_ADDRESS_SPACE((__int64)CurrentThread, v15);
LABEL_120:
  if( v13 )
    KiUnstackDetachProcess(&ApcState, 0i64);
  if( v46 != -1 )
    ObfDereferenceObjectWithTag((PVOID)v15, 0x6D566D4Dui64);
  return(unsigned int)v16;
}

Referenced by:

NtFreeVirtualMemory
PsDispatchIumService
PspDeleteUserStack
PspFreeCurrentThreadUserShadowStack
PspFreeUserFiberShadowStack
PspReserveAndCommitUserShadowStack
PspSetupUserFiberShadowStack
PspSetupUserShadowStack