1 /* $Id: iomgr.c,v 1.49 2004/07/22 18:36:35 ekohl Exp $
3 * COPYRIGHT: See COPYING in the top level directory
4 * PROJECT: ReactOS kernel
5 * FILE: ntoskrnl/io/iomgr.c
6 * PURPOSE: Initializes the io manager
7 * PROGRAMMER: David Welch (welch@mcmail.com)
12 /* INCLUDES ****************************************************************/
15 #include <ddk/ntddk.h>
16 #include <internal/ob.h>
17 #include <internal/io.h>
18 #include <internal/pool.h>
19 #include <internal/module.h>
20 #include <rosrtl/string.h>
23 #include <internal/debug.h>
25 /* GLOBALS *******************************************************************/
27 #define TAG_DEVICE_TYPE TAG('D', 'E', 'V', 'T')
28 #define TAG_FILE_TYPE TAG('F', 'I', 'L', 'E')
30 /* DATA ********************************************************************/
33 POBJECT_TYPE EXPORTED IoDeviceObjectType
= NULL
;
34 POBJECT_TYPE EXPORTED IoFileObjectType
= NULL
;
35 ULONG EXPORTED IoReadOperationCount
= 0;
36 ULONGLONG EXPORTED IoReadTransferCount
= 0;
37 ULONG EXPORTED IoWriteOperationCount
= 0;
38 ULONGLONG EXPORTED IoWriteTransferCount
= 0;
39 ULONG IoOtherOperationCount
= 0;
40 ULONGLONG IoOtherTransferCount
= 0;
41 KSPIN_LOCK EXPORTED IoStatisticsLock
= 0;
43 static GENERIC_MAPPING IopFileMapping
= {FILE_GENERIC_READ
,
48 /* FUNCTIONS ****************************************************************/
51 IopCloseFile(PVOID ObjectBody
,
54 PFILE_OBJECT FileObject
= (PFILE_OBJECT
)ObjectBody
;
56 PIO_STACK_LOCATION StackPtr
;
59 DPRINT("IopCloseFile()\n");
61 if (HandleCount
> 0 || FileObject
->DeviceObject
== NULL
)
67 //NOTE: Allmost certain that the latest changes to I/O Mgr makes this redundant (OriginalFileObject case)
68 ObReferenceObjectByPointer(FileObject
,
69 STANDARD_RIGHTS_REQUIRED
,
74 KeResetEvent( &FileObject
->Event
);
76 Irp
= IoBuildSynchronousFsdRequest(IRP_MJ_CLEANUP
,
77 FileObject
->DeviceObject
,
83 StackPtr
= IoGetNextIrpStackLocation(Irp
);
84 StackPtr
->FileObject
= FileObject
;
86 Status
= IoCallDriver(FileObject
->DeviceObject
, Irp
);
87 if (Status
== STATUS_PENDING
)
89 KeWaitForSingleObject(&FileObject
->Event
, Executive
, KernelMode
, FALSE
, NULL
);
95 IopDeleteFile(PVOID ObjectBody
)
97 PFILE_OBJECT FileObject
= (PFILE_OBJECT
)ObjectBody
;
99 PIO_STACK_LOCATION StackPtr
;
102 DPRINT("IopDeleteFile()\n");
104 if (FileObject
->DeviceObject
)
107 //NOTE: Allmost certain that the latest changes to I/O Mgr makes this redundant (OriginalFileObject case)
109 ObReferenceObjectByPointer(ObjectBody
,
110 STANDARD_RIGHTS_REQUIRED
,
114 KeResetEvent( &FileObject
->Event
);
115 Irp
= IoBuildSynchronousFsdRequest(IRP_MJ_CLOSE
,
116 FileObject
->DeviceObject
,
122 Irp
->Flags
|= IRP_CLOSE_OPERATION
;
123 StackPtr
= IoGetNextIrpStackLocation(Irp
);
124 StackPtr
->FileObject
= FileObject
;
126 Status
= IoCallDriver(FileObject
->DeviceObject
, Irp
);
127 if (Status
== STATUS_PENDING
)
129 KeWaitForSingleObject(&FileObject
->Event
, Executive
, KernelMode
, FALSE
, NULL
);
133 if (FileObject
->FileName
.Buffer
!= NULL
)
135 ExFreePool(FileObject
->FileName
.Buffer
);
136 FileObject
->FileName
.Buffer
= 0;
142 IopSecurityFile(PVOID ObjectBody
,
143 SECURITY_OPERATION_CODE OperationCode
,
144 SECURITY_INFORMATION SecurityInformation
,
145 PSECURITY_DESCRIPTOR SecurityDescriptor
,
148 DPRINT("IopSecurityFile() called\n");
150 switch (OperationCode
)
152 case SetSecurityDescriptor
:
153 DPRINT("Set security descriptor\n");
154 return STATUS_SUCCESS
;
156 case QuerySecurityDescriptor
:
157 DPRINT("Query security descriptor\n");
158 return STATUS_UNSUCCESSFUL
;
160 case DeleteSecurityDescriptor
:
161 DPRINT("Delete security descriptor\n");
162 return STATUS_SUCCESS
;
164 case AssignSecurityDescriptor
:
165 DPRINT("Assign security descriptor\n");
166 return STATUS_SUCCESS
;
169 return STATUS_UNSUCCESSFUL
;
174 IopQueryNameFile(PVOID ObjectBody
,
175 POBJECT_NAME_INFORMATION ObjectNameInfo
,
179 POBJECT_NAME_INFORMATION LocalInfo
;
180 PFILE_NAME_INFORMATION FileNameInfo
;
181 PFILE_OBJECT FileObject
;
182 ULONG LocalReturnLength
;
185 DPRINT ("IopQueryNameFile() called\n");
187 FileObject
= (PFILE_OBJECT
)ObjectBody
;
189 LocalInfo
= ExAllocatePool (NonPagedPool
,
190 sizeof(OBJECT_NAME_INFORMATION
) +
191 MAX_PATH
* sizeof(WCHAR
));
192 if (LocalInfo
== NULL
)
193 return STATUS_INSUFFICIENT_RESOURCES
;
195 Status
= ObQueryNameString (FileObject
->DeviceObject
->Vpb
->RealDevice
,
197 MAX_PATH
* sizeof(WCHAR
),
199 if (!NT_SUCCESS (Status
))
201 ExFreePool (LocalInfo
);
204 DPRINT ("Device path: %wZ\n", &LocalInfo
->Name
);
206 Status
= RtlAppendUnicodeStringToString (&ObjectNameInfo
->Name
,
209 ExFreePool (LocalInfo
);
211 FileNameInfo
= ExAllocatePool (NonPagedPool
,
212 MAX_PATH
* sizeof(WCHAR
) + sizeof(ULONG
));
213 if (FileNameInfo
== NULL
)
214 return STATUS_INSUFFICIENT_RESOURCES
;
216 Status
= IoQueryFileInformation (FileObject
,
218 MAX_PATH
* sizeof(WCHAR
) + sizeof(ULONG
),
221 if (Status
!= STATUS_SUCCESS
)
223 ExFreePool (FileNameInfo
);
227 Status
= RtlAppendUnicodeToString (&ObjectNameInfo
->Name
,
228 FileNameInfo
->FileName
);
230 DPRINT ("Total path: %wZ\n", &ObjectNameInfo
->Name
);
232 ExFreePool (FileNameInfo
);
241 OBJECT_ATTRIBUTES ObjectAttributes
;
242 UNICODE_STRING DirName
;
243 UNICODE_STRING LinkName
;
246 IopInitDriverImplementation();
249 * Register iomgr types: DeviceObjectType
251 IoDeviceObjectType
= ExAllocatePool (NonPagedPool
,
252 sizeof (OBJECT_TYPE
));
254 IoDeviceObjectType
->Tag
= TAG_DEVICE_TYPE
;
255 IoDeviceObjectType
->TotalObjects
= 0;
256 IoDeviceObjectType
->TotalHandles
= 0;
257 IoDeviceObjectType
->MaxObjects
= ULONG_MAX
;
258 IoDeviceObjectType
->MaxHandles
= ULONG_MAX
;
259 IoDeviceObjectType
->PagedPoolCharge
= 0;
260 IoDeviceObjectType
->NonpagedPoolCharge
= sizeof (DEVICE_OBJECT
);
261 IoDeviceObjectType
->Mapping
= &IopFileMapping
;
262 IoDeviceObjectType
->Dump
= NULL
;
263 IoDeviceObjectType
->Open
= NULL
;
264 IoDeviceObjectType
->Close
= NULL
;
265 IoDeviceObjectType
->Delete
= NULL
;
266 IoDeviceObjectType
->Parse
= NULL
;
267 IoDeviceObjectType
->Security
= NULL
;
268 IoDeviceObjectType
->QueryName
= NULL
;
269 IoDeviceObjectType
->OkayToClose
= NULL
;
270 IoDeviceObjectType
->Create
= IopCreateDevice
;
271 IoDeviceObjectType
->DuplicationNotify
= NULL
;
273 RtlRosInitUnicodeStringFromLiteral(&IoDeviceObjectType
->TypeName
, L
"Device");
275 ObpCreateTypeObject(IoDeviceObjectType
);
278 * Register iomgr types: FileObjectType
279 * (alias DriverObjectType)
281 IoFileObjectType
= ExAllocatePool (NonPagedPool
, sizeof (OBJECT_TYPE
));
283 IoFileObjectType
->Tag
= TAG_FILE_TYPE
;
284 IoFileObjectType
->TotalObjects
= 0;
285 IoFileObjectType
->TotalHandles
= 0;
286 IoFileObjectType
->MaxObjects
= ULONG_MAX
;
287 IoFileObjectType
->MaxHandles
= ULONG_MAX
;
288 IoFileObjectType
->PagedPoolCharge
= 0;
289 IoFileObjectType
->NonpagedPoolCharge
= sizeof(FILE_OBJECT
);
290 IoFileObjectType
->Mapping
= &IopFileMapping
;
291 IoFileObjectType
->Dump
= NULL
;
292 IoFileObjectType
->Open
= NULL
;
293 IoFileObjectType
->Close
= IopCloseFile
;
294 IoFileObjectType
->Delete
= IopDeleteFile
;
295 IoFileObjectType
->Parse
= NULL
;
296 IoFileObjectType
->Security
= IopSecurityFile
;
297 IoFileObjectType
->QueryName
= IopQueryNameFile
;
298 IoFileObjectType
->OkayToClose
= NULL
;
299 IoFileObjectType
->Create
= IopCreateFile
;
300 IoFileObjectType
->DuplicationNotify
= NULL
;
302 RtlRosInitUnicodeStringFromLiteral(&IoFileObjectType
->TypeName
, L
"File");
304 ObpCreateTypeObject(IoFileObjectType
);
307 * Create the '\Driver' object directory
309 RtlRosInitUnicodeStringFromLiteral(&DirName
, L
"\\Driver");
310 InitializeObjectAttributes(&ObjectAttributes
,
315 NtCreateDirectoryObject(&Handle
,
320 * Create the '\FileSystem' object directory
322 RtlRosInitUnicodeStringFromLiteral(&DirName
,
324 InitializeObjectAttributes(&ObjectAttributes
,
329 NtCreateDirectoryObject(&Handle
,
334 * Create the '\Device' directory
336 RtlRosInitUnicodeStringFromLiteral(&DirName
,
338 InitializeObjectAttributes(&ObjectAttributes
,
343 ZwCreateDirectoryObject(&Handle
,
348 * Create the '\??' directory
350 RtlRosInitUnicodeStringFromLiteral(&DirName
,
352 InitializeObjectAttributes(&ObjectAttributes
,
357 ZwCreateDirectoryObject(&Handle
,
362 * Create the '\ArcName' directory
364 RtlRosInitUnicodeStringFromLiteral(&DirName
,
366 InitializeObjectAttributes(&ObjectAttributes
,
371 ZwCreateDirectoryObject(&Handle
,
376 * Initialize remaining subsubsystem
378 IoInitCancelHandling();
379 IoInitFileSystemImplementation();
380 IoInitVpbImplementation();
381 IoInitShutdownNotification();
385 * Create link from '\DosDevices' to '\??' directory
387 RtlRosInitUnicodeStringFromLiteral(&LinkName
,
389 RtlRosInitUnicodeStringFromLiteral(&DirName
,
391 IoCreateSymbolicLink(&LinkName
,
395 * Initialize PnP manager
404 PDEVICE_NODE DeviceNode
;
405 PDRIVER_OBJECT DriverObject
;
406 MODULE_OBJECT ModuleObject
;
409 KeInitializeSpinLock (&IoStatisticsLock
);
411 /* Initialize raw filesystem driver */
413 /* Use IopRootDeviceNode for now */
414 Status
= IopCreateDeviceNode(IopRootDeviceNode
,
417 if (!NT_SUCCESS(Status
))
419 CPRINT("IopCreateDeviceNode() failed with status (%x)\n", Status
);
423 ModuleObject
.Base
= NULL
;
424 ModuleObject
.Length
= 0;
425 ModuleObject
.EntryPoint
= RawFsDriverEntry
;
427 Status
= IopInitializeDriverModule(
432 if (!NT_SUCCESS(Status
))
434 IopFreeDeviceNode(DeviceNode
);
435 CPRINT("IopInitializeDriver() failed with status (%x)\n", Status
);
439 Status
= IopInitializeDevice(DeviceNode
, DriverObject
);
440 if (!NT_SUCCESS(Status
))
442 IopFreeDeviceNode(DeviceNode
);
443 CPRINT("IopInitializeDevice() failed with status (%x)\n", Status
);
448 * Initialize PnP root releations
450 IopInvalidateDeviceRelations(
458 PGENERIC_MAPPING STDCALL
459 IoGetFileObjectGenericMapping(VOID
)
461 return(&IopFileMapping
);