MiAllocatePerSessionProtos

NTSTATUS __stdcall MiAllocatePerSessionProtos(
        _SUBSECTION *Subsection,
        VOID *MappingBase,
        UINT64 ImagePteIndex,
        UINT64 PrivateDiff,
        _RTL_BALANCED_NODE **AllocatedProtos){
  UINT64 *v6; 
  _RTL_BALANCED_NODE *v7; 
  _MI_PARTITION *ControlAreaPartition; 
  _RTL_BALANCED_NODE *Pool; 
  INT64 v10; 
  INT64 v11; 
  _RTL_BALANCED_NODE *v12; 
  _RTL_BALANCED_NODE *v13; 
  unsigned __int64 *v14; 
  _KSCHEDULING_GROUP_POLICY v15; 
  _KSCHEDULING_GROUP *v16; 
  unsigned __int64 v17; 
  unsigned __int64 v18; 
  _RTL_BALANCED_NODE *v19; 
  _MMPTE *SubsectionBase; 
  unsigned int v21; 
  unsigned int v22; 
  unsigned __int64 v23; 
  unsigned __int64 v24; 
  int v25; 
  int v26; 
  unsigned __int64 v27; 
  UINT64 v28; 
  _MMPTE *v29; 
  NTSTATUS v30; 
  UINT64 v32; 
  UINT64 v33; 
  _MDL *v34; 
  int v35; 
  _CONTROL_AREA *v36; 
  int v37; 
  _RTL_BALANCED_NODE *v38; 
  unsigned int NumberOfPtes; 
  ULONG_PTR *Partition; 
  _RTL_BALANCED_NODE *Node; 
  _MMPTE *v42; 
  _CONTROL_AREA *ControlArea; 
  _RTL_BALANCED_NODE *v44; 

  *AllocatedProtos = 0i64;
  v6 = 0i64;
  v7 = 0i64;
  ControlArea = Subsection->ControlArea;
  ControlAreaPartition = MiGetControlAreaPartition(Subsection->ControlArea, (_EPROCESS *)MappingBase);
  Partition = (ULONG_PTR *)&ControlAreaPartition->Core.PartitionId;
  if( !MiChargeCommit(ControlAreaPartition, Subsection->PtesInSubsection, 0i64) )
    return -1073741523;
  Pool = (_RTL_BALANCED_NODE *)MiAllocatePool(64i64, 0x58ui64, 0x73536D4Dui64);
  v12 = Pool;
  v44 = Pool;
  if( !Pool )
  {
    v30 = -1073741670;
    goto LABEL_17;
  }
  LODWORD(Pool[3].Right) = 1;
  v13 = (_RTL_BALANCED_NODE *)MiAllocatePool(274i64, 8i64 * Subsection->PtesInSubsection, 0x74536D4Dui64);
  v14 = (unsigned __int64 *)v13;
  if( !v13 )
  {
    v30 = -1073741670;
    goto LABEL_16;
  }
  v12[3].Children[0] = v13;
  memset(v13, 0i64, 8 * Subsection->PtesInSubsection);
  MiMakeSubsectionPte((_KSCHEDULING_GROUP *)Subsection, v15, v16);
  v18 = v17;
  v19 = v12 + 1;
  Node = v12 + 1;
  v12[2].Children[0] = (_RTL_BALANCED_NODE *)((unsigned __int64)v12[2].Children[0] & 0xFFFFFFFFFFFFFFF8ui64 | 3);
  SubsectionBase = Subsection->SubsectionBase;
  v42 = SubsectionBase;
  v21 = 0;
  NumberOfPtes = 0;
  if( Subsection->PtesInSubsection )
  {
    v22 = 0;
    do
    {
      LODWORD(v23) = MI_READ_PTE_LOCK_FREE((INT64)SubsectionBase);
      v24 = v23;
      if( !v23 )
        break;
      if( !MappingBase )
      {
        MiPteInShadowRange((UINT64)v14);
        IS_PTE_NOT_DEMAND_ZERO();
        if( v26 )
        {
          v27 = v18;
          if( v25 && (KeGetCurrentThread()->ApcState.Process->Flags3 & 0x1000) != 0 && (v18 & 1) != 0 )
            v27 = v18 | 0x8000000000000000ui64;
          *v14 = v27;
        }
        else
        {
          if( v25 && (KeGetCurrentThread()->ApcState.Process->Flags3 & 0x1000) != 0 && (v24 & 1) != 0 )
            v24 |= 0x8000000000000000ui64;
          *v14 = v24;
        }
      }
      ++v14;
      SubsectionBase = ++v42;
      ++v22;
    }
    while( v22 < Subsection->PtesInSubsection );
    NumberOfPtes = v22;
    v12 = v44;
    v6 = 0i64;
    v19 = Node;
    v21 = NumberOfPtes;
  }
  v28 = v21;
  v12[2].Children[1] = (_RTL_BALANCED_NODE *)v21;
  MiUpdateSystemProtoPtesTree(v19, 1i64);
  v29 = (_MMPTE *)v12[3].Children[0];
  if( MappingBase )
  {
    v32 = v28 << 12;
    LODWORD(v33) = MmSizeOfMdl(MappingBase, (_DWORD)v28 << 12);
    v34 = (_MDL *)MiAllocatePool(64i64, v33, 0x206C644Dui64);
    v6 = (UINT64 *)v34;
    if( !v34 )
      goto LABEL_40;
    v34->Next = 0i64;
    v34->Size = 8 * (((v32 + ((unsigned __int16)MappingBase & 0xFFF) + 4095i64) >> 12) + 6);
    v34->MdlFlags = 0;
    v34->StartVa = (void *)((unsigned __int64)MappingBase & 0xFFFFFFFFFFFFF000ui64);
    v34->ByteOffset = (unsigned __int16)MappingBase & 0xFFF;
    v34->ByteCount = v32;
    MmProbeAndLockPages(v34, 0, IoReadAccess);
    v35 = ((unsigned __int16)Subsection->u.SubsectionFlags._bf_0 >> 1) & 0x1F;
    if( MiChargeResident(Partition, v28, 0i64) == MiChargeFailed )
    {
LABEL_40:
      v30 = -1073741670;
      goto LABEL_15;
    }
    if( (MiFlags & 0x10000) != 0 && (MiFlags & 0x8000) != 0 && (v35 & 2) != 0 )
      v36 = ControlArea;
    else
      v36 = ControlArea;
    MiFillPerSessionProtos(v36, v29, v6 + 6, NumberOfPtes);
    v30 = v37;
    if( v37 < 0 )
      goto LABEL_15;
  }
  *AllocatedProtos = v12;
  v12 = 0i64;
  v30 = 0;
LABEL_15:
  v7 = Node;
LABEL_16:
  ControlAreaPartition = (_MI_PARTITION *)Partition;
LABEL_17:
  if( v6 )
  {
    MmUnlockPages((INT64)v6, v10, v11);
    ExFreePoolWithTag(v6, 0);
  }
  if( v12 )
  {
    if( v7 )
      MiUpdateSystemProtoPtesTree(v7, 0i64);
    v38 = v12[3].Children[0];
    if( v38 )
      ExFreePoolWithTag(v38, 0);
    ExFreePoolWithTag(v12, 0);
  }
  if( v30 < 0 )
    MiReturnCommit(ControlAreaPartition, Subsection->PtesInSubsection);
  return v30;
}

Referenced by:

MiCreatePerSessionProtos
MiCreateSessionDriverProtos