[CMAKE]
[reactos.git] / drivers / base / null / null.c
1 /*
2 * PROJECT: ReactOS Kernel
3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: drivers/base/null/null.c
5 * PURPOSE: Null Device Driver
6 * PROGRAMMERS: Alex Ionescu (alex.ionescu@reactos.org)
7 * David Welch (welch@mcmail.com)
8 */
9
10 /* INCLUDES ******************************************************************/
11
12 #include <ntddk.h>
13
14 /* FUNCTIONS *****************************************************************/
15
16 NTSTATUS
17 NTAPI
18 NullQueryFileInformation(OUT PVOID Buffer,
19 IN PULONG Length,
20 IN FILE_INFORMATION_CLASS InformationClass)
21 {
22 PFILE_STANDARD_INFORMATION StandardInfo = Buffer;
23 PAGED_CODE();
24
25 /* We only support one class */
26 if (InformationClass != FileStandardInformation)
27 {
28 /* Fail */
29 return STATUS_INVALID_INFO_CLASS;
30 }
31
32 /* Fill out the information */
33 RtlZeroMemory(StandardInfo, sizeof(FILE_STANDARD_INFORMATION));
34 StandardInfo->NumberOfLinks = 1;
35
36 /* Return the length and success */
37 *Length = sizeof(FILE_STANDARD_INFORMATION);
38 return STATUS_SUCCESS;
39 }
40
41 BOOLEAN
42 NTAPI
43 NullRead(IN PFILE_OBJECT FileObject,
44 IN PLARGE_INTEGER FileOffset,
45 IN ULONG Length,
46 IN BOOLEAN Wait,
47 IN ULONG LockKey,
48 OUT PVOID Buffer,
49 OUT PIO_STATUS_BLOCK IoStatus,
50 IN PDEVICE_OBJECT DeviceObject)
51 {
52 PAGED_CODE();
53
54 /* Complete successfully */
55 IoStatus->Status = STATUS_END_OF_FILE;
56 IoStatus->Information = 0;
57 return TRUE;
58 }
59
60 BOOLEAN
61 NTAPI
62 NullWrite(IN PFILE_OBJECT FileObject,
63 IN PLARGE_INTEGER FileOffset,
64 IN ULONG Length,
65 IN BOOLEAN Wait,
66 IN ULONG LockKey,
67 IN PVOID Buffer,
68 OUT PIO_STATUS_BLOCK IoStatus,
69 IN PDEVICE_OBJECT DeviceObject)
70 {
71 PAGED_CODE();
72
73 /* Complete successfully */
74 IoStatus->Status = STATUS_SUCCESS;
75 IoStatus->Information = Length;
76 return TRUE;
77 }
78
79 NTSTATUS
80 NTAPI
81 NullDispatch(IN PDEVICE_OBJECT DeviceObject,
82 IN PIRP Irp)
83 {
84 PIO_STACK_LOCATION IoStack = IoGetCurrentIrpStackLocation(Irp);
85 NTSTATUS Status;
86 PFILE_OBJECT FileObject;
87 ULONG Length;
88 PAGED_CODE();
89
90 /* Get the file object and check what kind of request this is */
91 FileObject = IoStack->FileObject;
92 switch (IoStack->MajorFunction)
93 {
94 case IRP_MJ_CREATE:
95 case IRP_MJ_CLOSE:
96
97 /* Check if this is synch I/O */
98 if (FileObject->Flags & FO_SYNCHRONOUS_IO)
99 {
100 /* Set distinguished value for Cc */
101 FileObject->PrivateCacheMap = (PVOID)1;
102 }
103
104 /* Complete successfully */
105 Irp->IoStatus.Status = STATUS_SUCCESS;
106 Irp->IoStatus.Information = 0;
107 break;
108
109 case IRP_MJ_READ:
110
111 /* Return as if we read the entire file */
112 Irp->IoStatus.Status = STATUS_END_OF_FILE;
113 Irp->IoStatus.Information = 0;
114 break;
115
116 case IRP_MJ_WRITE:
117
118 /* Return as if we wrote the entire request */
119 Irp->IoStatus.Status = STATUS_SUCCESS;
120 Irp->IoStatus.Information = IoStack->Parameters.Write.Length;
121 break;
122
123 case IRP_MJ_LOCK_CONTROL:
124
125 /* Dummy */
126 Irp->IoStatus.Status = STATUS_SUCCESS;
127 Irp->IoStatus.Information = 0;
128 break;
129
130 case IRP_MJ_QUERY_INFORMATION:
131
132 /* Get the length inputted and do the request */
133 Length = IoStack->Parameters.QueryFile.Length;
134 Irp->IoStatus.Status = NullQueryFileInformation(Irp->AssociatedIrp.
135 SystemBuffer,
136 &Length,
137 IoStack->
138 Parameters.
139 QueryFile.
140 FileInformationClass);
141
142 /* Return the actual length */
143 Irp->IoStatus.Information = Length;
144 break;
145 }
146
147 /* Complete the request */
148 Status = Irp->IoStatus.Status;
149 IoCompleteRequest(Irp, IO_NO_INCREMENT);
150 return Status;
151 }
152
153 NTSTATUS
154 NTAPI
155 DriverEntry(IN PDRIVER_OBJECT DriverObject,
156 IN PUNICODE_STRING RegistryPath)
157 {
158 PDEVICE_OBJECT DeviceObject;
159 UNICODE_STRING DeviceName = RTL_CONSTANT_STRING(L"\\Device\\Null");
160 NTSTATUS Status;
161 PFAST_IO_DISPATCH FastIoDispatch;
162 PAGED_CODE();
163
164 /* Page the driver */
165 MmPageEntireDriver(DriverEntry);
166
167 /* Create null device */
168 Status = IoCreateDevice(DriverObject,
169 0,
170 &DeviceName,
171 FILE_DEVICE_NULL,
172 0,
173 FALSE,
174 &DeviceObject);
175 if (!NT_SUCCESS(Status)) return Status;
176
177 /* Register driver routines */
178 DriverObject->MajorFunction[IRP_MJ_CLOSE] = NullDispatch;
179 DriverObject->MajorFunction[IRP_MJ_CREATE] = NullDispatch;
180 DriverObject->MajorFunction[IRP_MJ_WRITE] = NullDispatch;
181 DriverObject->MajorFunction[IRP_MJ_READ] = NullDispatch;
182 DriverObject->MajorFunction[IRP_MJ_LOCK_CONTROL] = NullDispatch;
183 DriverObject->MajorFunction[IRP_MJ_QUERY_INFORMATION] = NullDispatch;
184
185 /* Allocate the fast I/O dispatch table */
186 FastIoDispatch = ExAllocatePool(NonPagedPool, sizeof(FAST_IO_DISPATCH));
187 if (!FastIoDispatch)
188 {
189 /* Failed, cleanup */
190 IoDeleteDevice(DeviceObject);
191 return STATUS_INSUFFICIENT_RESOURCES;
192 }
193
194 /* Initialize it */
195 RtlZeroMemory(FastIoDispatch, sizeof(FAST_IO_DISPATCH));
196 FastIoDispatch->SizeOfFastIoDispatch = sizeof(FAST_IO_DISPATCH);
197
198 /* Setup our pointers */
199 FastIoDispatch->FastIoRead = NullRead;
200 FastIoDispatch->FastIoWrite = NullWrite;
201 DriverObject->FastIoDispatch = FastIoDispatch;
202
203 /* Return success */
204 return STATUS_SUCCESS;
205 }
206
207 /* EOF */