IopSynchronousServiceTail

NTSTATUS __stdcall IopSynchronousServiceTail(
        PDEVICE_OBJECT DeviceObject,
        PIRP Irp,
        _FILE_OBJECT *FileObject,
        UINT8 DeferredIoCompletion,
        INT8 RequestorMode,
        UINT8 SynchronousIo,
        _TRANSFER_TYPE TransferType){
  unsigned __int64 UserApcRoutine; 
  _QWORD *p_Type; 
  _IO_COMPLETION_CONTEXT *CompletionContext; 
  PVOID *v13; 
  void *v14; 
  _QWORD *FileObjectExtension; 
  _DWORD *v16; 
  _ETHREAD *v17; 
  unsigned int v18; 
  char *v19; 
  __int64 v20; 
  _ETHREAD *v21; 
  unsigned int v22; 
  unsigned int v23; 
  unsigned int v24; 
  NTSTATUS IoPriorityHint; 
  _BYTE *IrpExtension; 
  NTSTATUS v28; 
  _BYTE *v30; 
  int v31; 
  INT8 v32; 
  NTSTATUS v33; 
  char v34; 
  unsigned __int8 CurrentIrql; 
  unsigned int DeviceType; 
  _ETHREAD *CurrentThread; 
  _ETHREAD *Thread; 
  unsigned int Flags; 
  _IO_STATUS_BLOCK *UserIosb; 
  char v41; 
  INT64 v42; 
  INT64 v43; 
  UINT8 Timeout; 
  INT8 v45; 
  PVOID Object; 
  __int64 v47; 
  __int64 v48; 
  _GUID ActivityId; 

  UserApcRoutine = (unsigned __int64)Irp->Overlay.UserApcRoutine;
  p_Type = &FileObject->Type;
  Object = FileObject;
  if( (UserApcRoutine & 1) != 0 )
  {
    Irp->AllocationFlags |= 0x10u;
    UserApcRoutine &= ~1ui64;
    Irp->Overlay.UserApcRoutine = (void(__fastcall *)(void *, _IO_STATUS_BLOCK *, unsigned int))UserApcRoutine;
  }
  CompletionContext = FileObject->CompletionContext;
  if( SynchronousIo || UserApcRoutine )
  {
    if( (FileObject->Flags & 2) != 0 )
      Irp->AllocationFlags |= 2u;
    goto LABEL_13;
  }
  if( Irp->Overlay.UserApcContext && !Irp->UserEvent && CompletionContext )
  {
    IopQueueIrpToFileObject(Irp, FileObject, (PVOID *)FileObject, (PVOID)DeferredIoCompletion, Timeout, v45);
    if( v34 )
      goto LABEL_14;
    goto LABEL_13;
  }
  if( (Irp->Flags & 0x10) != 0
    || CompletionContext
    || !FileObject->FileObjectExtension
    || (FileObjectExtension = IopGetFileObjectExtension(FileObject, FoExtTypeIosbRange, 0i64)) == 0i64 )
  {
LABEL_13:
    IopQueueThreadIrp(Irp);
    goto LABEL_14;
  }
  while( 1 )
  {
    UserIosb = Irp->UserIosb;
    if( (unsigned __int64)UserIosb >= *FileObjectExtension && (unsigned __int64)&UserIosb[1] <= FileObjectExtension[1] )
    {
      p_Type = Object;
      if( (_EPROCESS *)FileObjectExtension[4] == KeGetCurrentThread()->ApcState.Process )
      {
        IopQueueIrpToFileObject(Irp, (_FILE_OBJECT *)Object, v13, v14, Timeout, v45);
        if( v41 )
          break;
      }
    }
    FileObjectExtension = (_QWORD *)FileObjectExtension[5];
    if( !FileObjectExtension )
      goto LABEL_13;
  }
  Irp->UserIosb = (_IO_STATUS_BLOCK *)((char *)Irp->UserIosb + FileObjectExtension[3] - *FileObjectExtension);
LABEL_14:
  v16 = (_DWORD *)p_Type[26];
  if( v16 && (*v16 & 4) != 0 && PsIsProcessAppContainer(KeGetCurrentThread()->ApcState.Process) )
  {
    v28 = -1073739504;
    Irp->IoStatus.Status = -1073739504;
    IofCompleteRequest(Irp, 0);
    v19 = (char *)Object;
    goto LABEL_33;
  }
  if( (unsigned int)TransferType <= WriteTransfer )
  {
    DeviceType = DeviceObject->DeviceType;
    if( DeviceType == 8 || DeviceType == 7 || DeviceType == 9 || DeviceType == 36 )
      IoSetDiskIoAttributionFromThread(Irp, (_ETHREAD *)KeGetCurrentThread());
    CurrentThread = (_ETHREAD *)KeGetCurrentThread();
    if( TransferType )
    {
      ++CurrentThread->Tcb.WriteOperationCount;
      v18 = 12000;
    }
    else
    {
      ++CurrentThread->Tcb.ReadOperationCount;
      v18 = 11996;
    }
  }
  else
  {
    v17 = (_ETHREAD *)KeGetCurrentThread();
    ++v17->Tcb.OtherOperationCount;
    v18 = 12004;
  }
  __incgsdword(v18);
  v19 = (char *)Object;
  if( !SynchronousIo )
    ObfReferenceObject(Object);
  v20 = p_Type[26];
  if( v20 && *(_DWORD *)(v20 + 80) )
  {
    v24 = Irp->Flags & 0xFFF1FFFF;
    Irp->Flags = v24;
    v23 = *(_DWORD *)(v20 + 80);
  }
  else
  {
    v21 = (_ETHREAD *)KeGetCurrentThread();
    v22 = (v21->CrossThreadFlags >> 9) & 7;
    if( (v21->Tcb.Process->Flags & 0x100000) != 0 )
      v22 = 0;
    if( v22 < 2 && v21 == (_ETHREAD *)KeGetCurrentThread() && v21->IoBoostCount )
      v22 = 2;
    v23 = v22 + 1;
    v19 = (char *)Object;
    v24 = Irp->Flags & 0xFFF1FFFF;
    Irp->Flags = v24;
  }
  Irp->Flags = v24 | (v23 << 17);
  IoPriorityHint = IoGetIoPriorityHint((INT64)Irp);
  if( Irp->RequestorMode )
    goto LABEL_25;
  if( IoPriorityHint < 2 )
  {
    Thread = Irp->Tail.Thread;
    if( Thread && ((Thread->Tcb._bf_0 & 0x400) != 0 || (Thread->SameThreadPassiveFlags & 0x80u) != 0) )
    {
LABEL_25:
      if( IoPriorityHint < 2 )
      {
        if( TransferType )
        {
          if( TransferType == WriteTransfer )
            ++*(&stru_140C452E0 + 284);
        }
        else
        {
          ++*(&stru_140C452E0 + 283);
        }
      }
      goto LABEL_26;
    }
    Flags = Irp->Flags;
    ++*(&stru_140C452E0 + 285);
    Irp->Flags = Flags & 0xFFF1FFFF | 0x60000;
  }
LABEL_26:
  if( (Irp->AllocationFlags & 0x80u) == 0
    && (IrpExtension = Irp->Tail.IrpExtension) != 0i64
    && (*IrpExtension & 2) != 0 )
  {
    ActivityId = *(_GUID *)((char *)Irp->Tail.IrpExtension + 24);
    LODWORD(v42) = IoSetActivityIdThread((INT64)&ActivityId);
    v43 = v42;
    v28 = IofCallDriver((UINT64)DeviceObject, (UINT64)Irp);
    IoSetActivityIdThread(v43);
  }
  else
  {
    v28 = IofCallDriver((UINT64)DeviceObject, (UINT64)Irp);
  }
  if( !SynchronousIo )
    ObDereferenceObjectDeferDelete((UINT64)v19);
LABEL_33:
  if( DeferredIoCompletion && v28 != 259 )
  {
    v48 = 0i64;
    v47 = 0i64;
    CurrentIrql = KeGetCurrentIrql();
    __writecr8(1ui64);
    IopCompleteRequest((__int64)&Irp->Tail, (__int64)&v48, &v47, (_KAPC **)&Object, &v47);
    __writecr8(CurrentIrql);
  }
  if( SynchronousIo )
  {
    if( v28 == 259 )
    {
      v30 = v19 + 152;
      v31 = *((_DWORD *)v19 + 20) & 4;
      while( (*v30 & 0x7F) != 0 || !*((_DWORD *)v19 + 39) )
      {
        v32 = v31 ? RequestorMode : 0;
        v33 = KeWaitForSingleObject((UINT64)v30, 0, v32, 1, 0i64);
        if( v33 != 257 && v33 != 192 )
          break;
        if( v31 )
          goto LABEL_98;
        if( (*(_DWORD *)&KeGetCurrentThread()[1].gapD8[8] & 1) != 0 || IopCheckIrpCancelled((INT64)v30, (INT64)Irp) )
        {
          v19 = (char *)Object;
LABEL_98:
          IopCancelAlertedRequest(v30, Irp);
          break;
        }
        v19 = (char *)Object;
      }
      v28 = *((_DWORD *)v19 + 14);
    }
    IopReleaseFileObjectLock((PADAPTER_OBJECT)v19);
  }
  else if( CompletionContext && (v28 & 0xC0000000) == 0x80000000 )
  {
    return 259;
  }
  return v28;
}

Referenced by:

IopSetEaOrQuotaInformationFile
IopXxxControlFile
NtFlushBuffersFileEx
NtLockFile
NtNotifyChangeDirectoryFileEx
NtQueryDirectoryFileEx
NtQueryEaFile
NtQueryQuotaInformationFile
NtQueryVolumeInformationFile
NtReadFile
NtReadFileScatter
NtSetEaFile
NtSetVolumeInformationFile
NtUnlockFile
NtWriteFile
NtWriteFileGather