ReactOS  0.4.13-dev-563-g0561610
except.c
Go to the documentation of this file.
1 /*
2  * COPYRIGHT: See COPYRIGHT.TXT
3  * PROJECT: Ext2 File System Driver for WinNT/2K/XP
4  * FILE: except.c
5  * PROGRAMMER: Matt Wu <mattwu@163.com>
6  * HOMEPAGE: http://www.ext2fsd.com
7  * UPDATE HISTORY:
8  */
9 
10 /* INCLUDES *****************************************************************/
11 
12 #include "ext2fs.h"
13 
14 /* GLOBALS ***************************************************************/
15 
17 
18 /* DEFINITIONS *************************************************************/
19 
22  IN PEXT2_IRP_CONTEXT IrpContext,
23  IN PEXCEPTION_POINTERS ExceptionPointer
24 )
25 {
28  PEXCEPTION_RECORD ExceptRecord;
29 
30  ExceptRecord = ExceptionPointer->ExceptionRecord;
31  ExceptionCode = ExceptRecord->ExceptionCode;
32 
33  DbgPrint("-------------------------------------------------------------\n");
34  DbgPrint("Exception happends in Ext2Fsd (code %xh):\n", ExceptionCode);
35  DbgPrint(".exr %p;.cxr %p;\n", ExceptionPointer->ExceptionRecord,
36  ExceptionPointer->ContextRecord);
37  DbgPrint("-------------------------------------------------------------\n");
38 
39  DbgBreak();
40 
41  //
42  // Check IrpContext is valid or not
43  //
44 
45  if (IrpContext) {
46  if ((IrpContext->Identifier.Type != EXT2ICX) ||
47  (IrpContext->Identifier.Size != sizeof(EXT2_IRP_CONTEXT))) {
48  DbgBreak();
49  IrpContext = NULL;
50  } else if (IrpContext->DeviceObject) {
51  PEXT2_VCB Vcb = NULL;
52  Vcb = (PEXT2_VCB) IrpContext->DeviceObject->DeviceExtension;
53  if (NULL == Vcb) {
55  } else {
56  if (Vcb->Identifier.Type == EXT2VCB && !IsMounted(Vcb)) {
58  }
59  }
60  }
61  } else {
64  } else {
66  (ULONG_PTR)ExceptionPointer->ContextRecord,
67  (ULONG_PTR)ExceptRecord->ExceptionAddress );
68  }
69  }
70 
71  if (IrpContext) {
72  SetFlag(IrpContext->Flags, IRP_CONTEXT_FLAG_WAIT);
73  }
74 
77  //
78  // If the exception is expected execute our handler
79  //
80 
81  DEBUG(DL_ERR, ( "Ext2ExceptionFilter: Catching exception %xh\n",
82  ExceptionCode));
83 
85 
86  if (IrpContext) {
87  IrpContext->ExceptionInProgress = TRUE;
88  IrpContext->ExceptionCode = ExceptionCode;
89  }
90 
91  } else {
92 
93  //
94  // Continue search for an higher level exception handler
95  //
96 
97  DEBUG(DL_ERR, ( "Ext2ExceptionFilter: Passing on exception %#x\n",
98  ExceptionCode));
99 
101 
102  if (IrpContext) {
103  Ext2FreeIrpContext(IrpContext);
104  }
105  }
106 
107  return Status;
108 }
109 
110 
111 NTSTATUS
113 {
115 
116  if (IrpContext) {
117 
118  if ( (IrpContext->Identifier.Type != EXT2ICX) ||
119  (IrpContext->Identifier.Size != sizeof(EXT2_IRP_CONTEXT))) {
120  DbgBreak();
121  return STATUS_UNSUCCESSFUL;
122  }
123 
124  Status = IrpContext->ExceptionCode;
125 
126  if (IrpContext->Irp) {
127 
128  //
129  // Check if this error is a result of user actions
130  //
131 
132  PEXT2_VCB Vcb = NULL;
133  PIRP Irp = IrpContext->Irp;
135 
137  Vcb = (PEXT2_VCB) IrpContext->DeviceObject->DeviceExtension;
138 
139  if (NULL == Vcb) {
141  } else if (Vcb->Identifier.Type != EXT2VCB) {
143  } else if (!IsMounted(Vcb)) {
144  if (IsFlagOn(Vcb->Flags, VCB_DEVICE_REMOVED)) {
146  } else {
148  }
149  } else {
150 
151  /* queue it again if our request is at top level */
152  if (IrpContext->IsTopLevel &&
153  ((Status == STATUS_CANT_WAIT) ||
155  (KeGetCurrentIrql() >= APC_LEVEL)))) {
156 
157  Status = Ext2QueueRequest(IrpContext);
158  }
159  }
160 
161  if (Status == STATUS_PENDING) {
162  goto errorout;
163  }
164 
165  Irp->IoStatus.Status = Status;
166 
168 
169  //
170  // Now we will generate a pop-up to user
171  //
172 
173  PDEVICE_OBJECT RealDevice;
174  PVPB Vpb = NULL;
176 
177  if (IrpSp->FileObject != NULL) {
178  Vpb = IrpSp->FileObject->Vpb;
179  }
180 
181  //
182  // Get the initial thread
183  //
184 
185  Thread = Irp->Tail.Overlay.Thread;
186  RealDevice = IoGetDeviceToVerify( Thread );
187 
188  if (RealDevice == NULL) {
189  //
190  // Get current thread
191  //
192 
194  RealDevice = IoGetDeviceToVerify( Thread );
195 
196  ASSERT( RealDevice != NULL );
197  }
198 
199  Status = IrpContext->ExceptionCode;
200 
201  if (RealDevice != NULL) {
202 
203  if (IrpContext->ExceptionCode == STATUS_VERIFY_REQUIRED) {
204 
205  Status = IoVerifyVolume (RealDevice, FALSE);
206 
207  ExAcquireResourceSharedLite(&Vcb->MainResource, TRUE);
208  if (NT_SUCCESS(Status) && (!IsMounted(Vcb) ||
209  IsFlagOn(Vcb->Flags, VCB_DISMOUNT_PENDING))) {
211  }
212  ExReleaseResourceLite(&Vcb->MainResource);
213 
214  if (Ext2CheckDismount(IrpContext, Vcb, FALSE)) {
217  Irp = NULL;
218  goto errorout;
219  }
220 
221  if ( (IrpContext->MajorFunction == IRP_MJ_CREATE) &&
222  (IrpContext->FileObject->RelatedFileObject == NULL) &&
224 
225  Irp->IoStatus.Information = IO_REMOUNT;
226 
229  Irp = NULL;
230  }
231 
232  if (Irp) {
233 
234  if (!NT_SUCCESS(Status)) {
235  IoSetHardErrorOrVerifyDevice(Irp, RealDevice);
237  Ext2NormalizeAndRaiseStatus(IrpContext, Status);
238  }
239 
240  Status = Ext2QueueRequest(IrpContext);
241  }
242 
243  goto errorout;
244 
245  } else {
246 
248 
250  IoRaiseHardError( Irp, Vpb, RealDevice );
252  goto release_context;
253  }
254  }
255  }
256 
258  }
259 
260 release_context:
261 
262  Ext2FreeIrpContext(IrpContext);
263 
264  } else {
265 
267  }
268 
269 errorout:
270 
271  return Status;
272 }
273 
#define KeGetCurrentIrql()
Definition: env_spec_w32.h:706
_Inout_ PIRP _In_ NTSTATUS ExceptionCode
Definition: cdprocs.h:1782
#define IN
Definition: typedefs.h:38
BOOLEAN NTAPI FsRtlIsNtstatusExpected(IN NTSTATUS NtStatus)
Definition: filter.c:61
#define IsMounted(Vcb)
Definition: ext2fs.h:803
#define TRUE
Definition: types.h:120
#define IRP_CONTEXT_FLAG_WAIT
Definition: cdstruc.h:1221
#define IRP_MJ_CREATE
Definition: rdpdr.c:44
#define PsGetCurrentThread()
Definition: env_spec_w32.h:81
#define DbgPrint
Definition: loader.c:25
_In_ PIRP Irp
Definition: csq.h:116
#define STATUS_INVALID_PARAMETER
Definition: udferr_usr.h:135
#define VCB_DEVICE_REMOVED
Definition: ext2fs.h:791
#define IoIsErrorUserInduced(Status)
Definition: iofuncs.h:2769
LONG NTSTATUS
Definition: precomp.h:26
#define EXT2_BUGCHK_EXCEPT
Definition: ext2fs.h:318
PDEVICE_OBJECT NTAPI IoGetDeviceToVerify(IN PETHREAD Thread)
Definition: util.c:336
#define STATUS_WRONG_VOLUME
Definition: udferr_usr.h:140
#define STATUS_VERIFY_REQUIRED
Definition: udferr_usr.h:130
PEXT2_GLOBAL Ext2Global
Definition: init.c:16
PVOID ExceptionAddress
Definition: compat.h:199
uint32_t ULONG_PTR
Definition: typedefs.h:63
DWORD ExceptionCode
Definition: compat.h:196
BOOLEAN Ext2CheckDismount(IN PEXT2_IRP_CONTEXT IrpContext, IN PEXT2_VCB Vcb, IN BOOLEAN bForce)
Definition: fsctl.c:2592
#define EXCEPTION_CONTINUE_SEARCH
Definition: excpt.h:86
NTSTATUS Ext2QueueRequest(IN PEXT2_IRP_CONTEXT IrpContext)
Definition: dispatch.c:150
VOID Ext2FreeIrpContext(IN PEXT2_IRP_CONTEXT IrpContext)
Definition: memory.c:114
#define Ext2BugCheck(A, B, C, D)
Definition: ext2fs.h:335
#define IsFlagOn(a, b)
Definition: ext2fs.h:177
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:85
smooth NULL
Definition: ftsmooth.c:416
if(!(yy_init))
Definition: macro.lex.yy.c:714
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define STATUS_PENDING
Definition: ntstatus.h:82
#define STATUS_NO_SUCH_DEVICE
Definition: udferr_usr.h:136
#define Vcb
Definition: cdprocs.h:1425
_In_opt_ PFILE_OBJECT _In_opt_ PETHREAD Thread
Definition: fltkernel.h:2653
#define Ext2CompleteRequest(Irp, bPrint, PriorityBoost)
Definition: ext2fs.h:1438
VOID FASTCALL ExReleaseResourceLite(IN PERESOURCE Resource)
Definition: resource.c:1817
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
NTSTATUS Ext2ExceptionFilter(IN PEXT2_IRP_CONTEXT IrpContext, IN PEXCEPTION_POINTERS ExceptionPointer)
Definition: except.c:21
#define VCB_DISMOUNT_PENDING
Definition: ext2fs.h:782
NTSTATUS Ext2CompleteIrpContext(IN PEXT2_IRP_CONTEXT IrpContext, IN NTSTATUS Status)
Definition: read.c:32
Status
Definition: gdiplustypes.h:24
#define DL_ERR
Definition: ext2fs.h:1397
struct _EXCEPTION_RECORD * ExceptionRecord
Definition: compat.h:198
__drv_aliasesMem FORCEINLINE PIO_STACK_LOCATION IoGetCurrentIrpStackLocation(_In_ PIRP Irp)
Definition: iofuncs.h:2745
#define Ext2NormalizeAndRaiseStatus(IRPCONTEXT, STATUS)
Definition: ext2fs.h:263
#define SetFlag(_F, _SF)
Definition: ext2fs.h:187
PFILE_OBJECT FileObject
Definition: iotypes.h:2812
_In_ PIO_STACK_LOCATION IrpSp
Definition: create.c:4157
#define STATUS_REPARSE
Definition: ntstatus.h:83
BOOLEAN NTAPI ExAcquireResourceSharedLite(IN PERESOURCE Resource, IN BOOLEAN Wait)
Definition: resource.c:885
Definition: iotypes.h:166
#define STATUS_VOLUME_DISMOUNTED
Definition: ntstatus.h:733
#define IO_NO_INCREMENT
Definition: iotypes.h:565
#define DbgBreak()
Definition: ext2fs.h:46
VOID NTAPI IoSetHardErrorOrVerifyDevice(IN PIRP Irp, IN PDEVICE_OBJECT DeviceObject)
Definition: util.c:316
struct _EXT2_VCB * PEXT2_VCB
#define DEBUG(args)
Definition: rdesktop.h:129
VOID NTAPI IoRaiseHardError(IN PIRP Irp, IN PVPB Vpb, IN PDEVICE_OBJECT RealDeviceObject)
Definition: error.c:656
NTSTATUS Ext2ExceptionHandler(IN PEXT2_IRP_CONTEXT IrpContext)
Definition: except.c:112
#define IO_REMOUNT
Definition: iotypes.h:511
return STATUS_SUCCESS
Definition: btrfs.c:2777
IoMarkIrpPending(Irp)
NTSTATUS NTAPI IoVerifyVolume(IN PDEVICE_OBJECT DeviceObject, IN BOOLEAN AllowRawMount)
Definition: volume.c:882
#define APC_LEVEL
Definition: env_spec_w32.h:695
IN OUT PVCB IN PDEVICE_OBJECT IN PVPB Vpb
Definition: fatprocs.h:1664
VOID NTAPI IoSetDeviceToVerify(IN PETHREAD Thread, IN PDEVICE_OBJECT DeviceObject)
Definition: util.c:304
#define STATUS_CANT_WAIT
Definition: ntstatus.h:438