ReactOS  0.4.15-dev-3440-g915569a
workque.c File Reference
#include "fatprocs.h"
Include dependency graph for workque.c:

Go to the source code of this file.

Macros

#define FSP_PER_DEVICE_THRESHOLD   (2)
 

Functions

VOID NTAPI FatOplockComplete (IN PVOID Context, IN PIRP Irp)
 
VOID NTAPI FatPrePostIrp (IN PVOID Context, IN PIRP Irp)
 
NTSTATUS FatFsdPostRequest (IN PIRP_CONTEXT IrpContext, IN PIRP Irp)
 
VOID FatAddToWorkque (IN PIRP_CONTEXT IrpContext, IN PIRP Irp)
 

Macro Definition Documentation

◆ FSP_PER_DEVICE_THRESHOLD

#define FSP_PER_DEVICE_THRESHOLD   (2)

Definition at line 24 of file workque.c.

Function Documentation

◆ FatAddToWorkque()

VOID FatAddToWorkque ( IN PIRP_CONTEXT  IrpContext,
IN PIRP  Irp 
)

Definition at line 280 of file workque.c.

304 {
305  KIRQL SavedIrql;
307 
309 
310  //
311  // Check if this request has an associated file object, and thus volume
312  // device object.
313  //
314 
315  if ( IrpSp->FileObject != NULL ) {
316 
318 
321  DeviceObject );
322 
323  //
324  // Check to see if this request should be sent to the overflow
325  // queue. If not, then send it off to an exworker thread.
326  //
327 
328  KeAcquireSpinLock( &Vdo->OverflowQueueSpinLock, &SavedIrql );
329 
331 
332  //
333  // We cannot currently respond to this IRP so we'll just enqueue it
334  // to the overflow queue on the volume.
335  //
336 
338  &IrpContext->WorkQueueItem.List );
339 
340  Vdo->OverflowQueueCount += 1;
341 
342  KeReleaseSpinLock( &Vdo->OverflowQueueSpinLock, SavedIrql );
343 
344  return;
345 
346  } else {
347 
348  //
349  // We are going to send this Irp to an ex worker thread so up
350  // the count.
351  //
352 
353  Vdo->PostedRequestCount += 1;
354 
355  KeReleaseSpinLock( &Vdo->OverflowQueueSpinLock, SavedIrql );
356  }
357  }
358 
359  //
360  // Send it off.....
361  //
362 
363  ExInitializeWorkItem( &IrpContext->WorkQueueItem,
365  IrpContext );
366 
367 #ifdef _MSC_VER
368 #pragma prefast( suppress:28159, "prefast indicates this is an obsolete API but it is ok for fastfat to keep using it." )
369 #endif
370  ExQueueWorkItem( &IrpContext->WorkQueueItem, CriticalWorkQueue );
371 
372  return;
373 }
VOID NTAPI ExQueueWorkItem(IN PWORK_QUEUE_ITEM WorkItem, IN WORK_QUEUE_TYPE QueueType)
Definition: work.c:723
VOID NTAPI KeAcquireSpinLock(PKSPIN_LOCK SpinLock, PKIRQL OldIrql)
Definition: spinlock.c:50
#define InsertTailList(ListHead, Entry)
#define FSP_PER_DEVICE_THRESHOLD
Definition: workque.c:24
ULONG OverflowQueueCount
Definition: cdstruc.h:746
UCHAR KIRQL
Definition: env_spec_w32.h:591
_In_ PDEVICE_OBJECT DeviceObject
Definition: wdfdevice.h:2055
_In_ PIRP Irp
Definition: csq.h:116
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
#define ExInitializeWorkItem(Item, Routine, Context)
Definition: exfuncs.h:265
PDEVICE_OBJECT DeviceObject
Definition: iotypes.h:3223
__drv_aliasesMem FORCEINLINE PIO_STACK_LOCATION IoGetCurrentIrpStackLocation(_In_ PIRP Irp)
Definition: iofuncs.h:2793
PFILE_OBJECT FileObject
Definition: iotypes.h:3169
_In_ PIO_STACK_LOCATION IrpSp
Definition: create.c:4137
__volatile LONG PostedRequestCount
Definition: cdstruc.h:739
WORKER_THREAD_ROUTINE FatFspDispatch
Definition: fatprocs.h:2380
#define NULL
Definition: types.h:112
#define KeReleaseSpinLock(sl, irql)
Definition: env_spec_w32.h:627
KSPIN_LOCK OverflowQueueSpinLock
Definition: cdstruc.h:760
LIST_ENTRY OverflowQueue
Definition: cdstruc.h:754

Referenced by _Requires_lock_held_(), FatFsdPostRequest(), and FatOplockComplete().

◆ FatFsdPostRequest()

NTSTATUS FatFsdPostRequest ( IN PIRP_CONTEXT  IrpContext,
IN PIRP  Irp 
)

Definition at line 229 of file workque.c.

254 {
255  PAGED_CODE();
256 
258  NT_ASSERT( IrpContext->OriginatingIrp == Irp );
259 
260  FatPrePostIrp( IrpContext, Irp );
261 
262  FatAddToWorkque( IrpContext, Irp );
263 
264  //
265  // And return to our caller
266  //
267 
268  return STATUS_PENDING;
269 }
_In_ PIRP Irp
Definition: csq.h:116
#define STATUS_PENDING
Definition: ntstatus.h:82
#define ARGUMENT_PRESENT(ArgumentPointer)
VOID FatAddToWorkque(IN PIRP_CONTEXT IrpContext, IN PIRP Irp)
Definition: workque.c:280
VOID NTAPI FatPrePostIrp(IN PVOID Context, IN PIRP Irp)
Definition: workque.c:91
#define PAGED_CODE()
#define NT_ASSERT
Definition: rtlfuncs.h:3310

Referenced by _Requires_lock_held_(), FatCommonQueryEa(), FatCommonSetEa(), FatMultiAsyncCompletionRoutine(), and FatSingleAsyncCompletionRoutine().

◆ FatOplockComplete()

VOID NTAPI FatOplockComplete ( IN PVOID  Context,
IN PIRP  Irp 
)

Definition at line 35 of file workque.c.

61 {
62  PAGED_CODE();
63 
64  //
65  // Check on the return value in the Irp.
66  //
67 
68  if (Irp->IoStatus.Status == STATUS_SUCCESS) {
69 
70  //
71  // Insert the Irp context in the workqueue.
72  //
73 
75 
76  //
77  // Otherwise complete the request.
78  //
79 
80  } else {
81 
82  FatCompleteRequest( (PIRP_CONTEXT) Context, Irp, Irp->IoStatus.Status );
83  }
84 
85  return;
86 }
#define FatCompleteRequest(IRPCONTEXT, IRP, STATUS)
Definition: fatprocs.h:2633
_In_ PIRP Irp
Definition: csq.h:116
VOID FatAddToWorkque(IN PIRP_CONTEXT IrpContext, IN PIRP Irp)
Definition: workque.c:280
#define STATUS_SUCCESS
Definition: shellext.h:65
#define PAGED_CODE()

Referenced by _Requires_lock_held_(), and FatSetRenameInfo().

◆ FatPrePostIrp()

VOID NTAPI FatPrePostIrp ( IN PVOID  Context,
IN PIRP  Irp 
)

Definition at line 91 of file workque.c.

116 {
118  PIRP_CONTEXT IrpContext;
119 
120  PAGED_CODE();
121 
122  //
123  // If there is no Irp, we are done.
124  //
125 
126  if (Irp == NULL) {
127 
128  return;
129  }
130 
132 
133  IrpContext = (PIRP_CONTEXT) Context;
134 
135  //
136  // If there is a STACK FatIoContext pointer, clean and NULL it.
137  //
138 
139  if ((IrpContext->FatIoContext != NULL) &&
140  FlagOn(IrpContext->Flags, IRP_CONTEXT_STACK_IO_CONTEXT)) {
141 
142  ClearFlag(IrpContext->Flags, IRP_CONTEXT_STACK_IO_CONTEXT);
143  IrpContext->FatIoContext = NULL;
144  }
145 
146  //
147  // We need to lock the user's buffer, unless this is an MDL-read,
148  // in which case there is no user buffer.
149  //
150  // **** we need a better test than non-MDL (read or write)!
151 
152  if (IrpContext->MajorFunction == IRP_MJ_READ ||
153  IrpContext->MajorFunction == IRP_MJ_WRITE) {
154 
155  //
156  // If not an Mdl request, lock the user's buffer.
157  //
158 
159  if (!FlagOn( IrpContext->MinorFunction, IRP_MN_MDL )) {
160 
161  FatLockUserBuffer( IrpContext,
162  Irp,
163  (IrpContext->MajorFunction == IRP_MJ_READ) ?
165  (IrpContext->MajorFunction == IRP_MJ_READ) ?
166  IrpSp->Parameters.Read.Length : IrpSp->Parameters.Write.Length );
167  }
168 
169  //
170  // We also need to check whether this is a query file operation.
171  //
172 
173  } else if (IrpContext->MajorFunction == IRP_MJ_DIRECTORY_CONTROL
174  && IrpContext->MinorFunction == IRP_MN_QUERY_DIRECTORY) {
175 
176  FatLockUserBuffer( IrpContext,
177  Irp,
179  IrpSp->Parameters.QueryDirectory.Length );
180 
181  //
182  // We also need to check whether this is a query ea operation.
183  //
184 
185  } else if (IrpContext->MajorFunction == IRP_MJ_QUERY_EA) {
186 
187  FatLockUserBuffer( IrpContext,
188  Irp,
190  IrpSp->Parameters.QueryEa.Length );
191 
192  //
193  // We also need to check whether this is a set ea operation.
194  //
195 
196  } else if (IrpContext->MajorFunction == IRP_MJ_SET_EA) {
197 
198  FatLockUserBuffer( IrpContext,
199  Irp,
200  IoReadAccess,
201  IrpSp->Parameters.SetEa.Length );
202 
203  //
204  // These two FSCTLs use neither I/O, so check for them.
205  //
206 
207  } else if ((IrpContext->MajorFunction == IRP_MJ_FILE_SYSTEM_CONTROL) &&
208  (IrpContext->MinorFunction == IRP_MN_USER_FS_REQUEST) &&
209  ((IrpSp->Parameters.FileSystemControl.FsControlCode == FSCTL_GET_VOLUME_BITMAP) ||
210  (IrpSp->Parameters.FileSystemControl.FsControlCode == FSCTL_GET_RETRIEVAL_POINTERS))) {
211 
212  FatLockUserBuffer( IrpContext,
213  Irp,
215  IrpSp->Parameters.FileSystemControl.OutputBufferLength );
216  }
217 
218  //
219  // Mark that we've already returned pending to the user
220  //
221 
223 
224  return;
225 }
IRP_CONTEXT * PIRP_CONTEXT
Definition: cdstruc.h:1211
#define IRP_CONTEXT_STACK_IO_CONTEXT
Definition: ext2fs.h:1084
VOID FatLockUserBuffer(IN PIRP_CONTEXT IrpContext, IN OUT PIRP Irp, IN LOCK_OPERATION Operation, IN ULONG BufferLength)
Definition: deviosup.c:3276
#define IRP_MN_QUERY_DIRECTORY
Definition: rdpdr.c:55
_In_ PIRP Irp
Definition: csq.h:116
#define IRP_MJ_SET_EA
#define IRP_MJ_DIRECTORY_CONTROL
Definition: rdpdr.c:51
#define IRP_MJ_QUERY_EA
#define IRP_MN_USER_FS_REQUEST
Definition: iotypes.h:4403
#define IRP_MJ_FILE_SYSTEM_CONTROL
#define FSCTL_GET_RETRIEVAL_POINTERS
Definition: winioctl.h:95
#define IRP_MN_MDL
Definition: iotypes.h:4419
#define FlagOn(_F, _SF)
Definition: ext2fs.h:179
ClearFlag(Dirent->Flags, DIRENT_FLAG_NOT_PERSISTENT)
__drv_aliasesMem FORCEINLINE PIO_STACK_LOCATION IoGetCurrentIrpStackLocation(_In_ PIRP Irp)
Definition: iofuncs.h:2793
#define FSCTL_GET_VOLUME_BITMAP
Definition: winioctl.h:94
_In_ PIO_STACK_LOCATION IrpSp
Definition: create.c:4137
#define NULL
Definition: types.h:112
#define IRP_MJ_READ
Definition: rdpdr.c:46
#define IRP_MJ_WRITE
Definition: rdpdr.c:47
struct _NAMED_PIPE_CREATE_PARAMETERS * Parameters
Definition: iotypes.h:3128
IoMarkIrpPending(Irp)
#define PAGED_CODE()

Referenced by _Requires_lock_held_(), and FatFsdPostRequest().