HvWriteExternal

NTSTATUS __stdcall HvWriteExternal(_HHIVE *Hive){
  NTSTATUS v1; 
  unsigned int Length; 
  NTSTATUS v4; 
  unsigned int v5; 
  _HMAP_ENTRY *CellMap; 
  unsigned int v7; 
  int v8; 
  int v9; 
  VOID **PoolWithTag; 
  _HBASE_BLOCK *v11; 
  int(__fastcall *FileWrite)(_HHIVE *, unsigned int, CMP_OFFSET_ARRAY *, unsigned int, unsigned int); 
  int v13; 
  unsigned int v14; 
  _HMAP_ENTRY *v15; 
  unsigned __int64 v16; 
  int v17; 
  int(__fastcall *v18)(_HHIVE *, unsigned int, CMP_OFFSET_ARRAY *, unsigned int, unsigned int); 
  __int128 v21; 
  __int64 v22; 

  v1 = 0;
  v21 = 0i64;
  v22 = 0i64;
  if( !Hive[1].ReleaseCellRoutine )
    return -1073741811;
  Length = Hive->Storage[0].Length;
  v4 = CmpDoFileSetSizeEx((INT64)Hive, 2ui64, Length + 4096, 0);
  if( v4 < 0 )
    return v4;
  v5 = 0;
  while( v5 < Length )
  {
    CellMap = HvpGetCellMap(Hive, v5);
    if( !CellMap )
      KeBugCheckEx(0x51u, (PVOID)1, Hive, (PVOID)v7, (PVOID)0xCE4);
    v8 = *(_DWORD *)((CellMap->PermanentBinAddress & 0xFFFFFFFFFFFFFFF0ui64) + 8);
    v5 = v8 + v7;
    if( v5 > Hive->Storage[0].Length || (v8 & 0xFFF) != 0 )
      return -1073741492;
  }
  if( v5 < Hive->Storage[0].Length )
    return v4;
  v9 = 4096;
  PoolWithTag = ExAllocatePoolWithTag(5ui64, 0x1000ui64, 538987843i64);
  v11 = (_HBASE_BLOCK *)PoolWithTag;
  if( !PoolWithTag )
    return -1073741670;
  memmove(PoolWithTag, Hive->BaseBlock, 0x1000u);
  v11->Length = Length;
  v11->Cluster = 1;
  v11->CheckSum = HvpHeaderCheckSum(v11);
  FileWrite = Hive->FileWrite;
  *((_QWORD *)&v21 + 1) = v11;
  LODWORD(v22) = 4096;
  v13 = FileWrite(Hive, 2u, (CMP_OFFSET_ARRAY *)&v21, 1u, 0);
  ExFreePoolWithTag(v11, 0);
  if( v13 >= 0 )
  {
    v14 = 0;
    if( Length )
    {
      while( 1 )
      {
        v15 = HvpGetCellMap(Hive, v14);
        if( !v15 )
          KeBugCheckEx(0x51u, (PVOID)1, Hive, (PVOID)v14, (PVOID)0xD39);
        v16 = v15->PermanentBinAddress & 0xFFFFFFFFFFFFFFF0ui64;
        v17 = *(_DWORD *)(v16 + 8);
        *((_QWORD *)&v21 + 1) = v16;
        v18 = Hive->FileWrite;
        LODWORD(v21) = v9;
        LODWORD(v22) = v17;
        if( ((int(__fastcall *)(_HHIVE *, __int64, __int128 *))v18)(Hive, 2i64, &v21) < 0 )
          return -1073741491;
        v9 += v17;
        v14 += v17;
        if( v14 >= Length )
          goto LABEL_15;
      }
    }
    else
    {
LABEL_15:
      if( (int)CmpFileFlush(Hive, 2ui64) < 0 )
        return -1073741491;
      return v1;
    }
  }
  return -1073741491;
}

Referenced by:

CmSaveKey
CmSaveMergedKeys