ReactOS 0.4.17-dev-243-g1369312
DeviceIoControl.c File Reference
#include "precomp.h"
#include <winioctl.h>
#include <mountdev.h>
Include dependency graph for DeviceIoControl.c:

Go to the source code of this file.

Macros

#define ok_type(condition, format, ...)   ok(condition, "(%d): " format, DriveType, ##__VA_ARGS__)
 
#define skip_type(format, ...)   skip("(%d): " format, DriveType, ##__VA_ARGS__)
 
#define IOCTL_KSEC_RANDOM_FILL_BUFFER    CTL_CODE(FILE_DEVICE_KSEC, 0x02, METHOD_BUFFERED, FILE_ANY_ACCESS)
 

Functions

static void Test_DeviceIoControl_Parameters (void)
 
static BOOL GetDiskGeometry (VOID)
 
static VOID QueryDeviceName (VOID)
 
static VOID QueryUniqueId (VOID)
 
static VOID QuerySuggestedLinkName (VOID)
 
 START_TEST (DeviceIoControl)
 

Variables

WCHAR Letter
 
HANDLE Device
 
UINT DriveType
 

Macro Definition Documentation

◆ IOCTL_KSEC_RANDOM_FILL_BUFFER

#define IOCTL_KSEC_RANDOM_FILL_BUFFER    CTL_CODE(FILE_DEVICE_KSEC, 0x02, METHOD_BUFFERED, FILE_ANY_ACCESS)

Definition at line 20 of file DeviceIoControl.c.

◆ ok_type

#define ok_type (   condition,
  format,
  ... 
)    ok(condition, "(%d): " format, DriveType, ##__VA_ARGS__)

Definition at line 17 of file DeviceIoControl.c.

◆ skip_type

#define skip_type (   format,
  ... 
)    skip("(%d): " format, DriveType, ##__VA_ARGS__)

Definition at line 18 of file DeviceIoControl.c.

Function Documentation

◆ GetDiskGeometry()

static BOOL GetDiskGeometry ( VOID  )
static

Definition at line 58 of file DeviceIoControl.c.

59{
60 UINT Ret;
64
65 Size = 0;
67 ok_type(Ret == 0, "DeviceIoControl succeed\n");
69 ok_type(Error == ERROR_INSUFFICIENT_BUFFER, "Expecting ERROR_INSUFFICIENT_BUFFER, got %ld\n", Error);
70 ok_type(Size == 0, "Invalid output size: %ld\n", Size);
71
72 Size = 0;
74 /* Specific for CDROM, no disk present */
75 if (Ret == 0 && GetLastError() == ERROR_NOT_READY)
76 {
77 skip_type("No CDROM present\n");
78 return FALSE;
79 }
80 ok_type(Ret != 0, "DeviceIoControl failed: %ld\n", GetLastError());
81 ok_type(Size == sizeof(DG), "Invalid output size: %ld\n", Size);
82
83 Size = 0;
85 ok_type(Ret == 0, "DeviceIoControl succeed\n");
87 ok_type(Error == ERROR_INSUFFICIENT_BUFFER, "Expecting ERROR_INSUFFICIENT_BUFFER, got %ld\n", Error);
88 ok_type(Size == 0, "Invalid output size: %ld\n", Size);
89
90 Size = 0;
92 ok_type(Ret != 0, "DeviceIoControl failed: %ld\n", GetLastError());
93 ok_type(Size == FIELD_OFFSET(DISK_GEOMETRY_EX, Data), "Invalid output size: %ld\n", Size);
94
95 Size = 0;
96 Ret = DeviceIoControl(Device, IOCTL_DISK_GET_DRIVE_GEOMETRY_EX, NULL, 0, &DGE, sizeof(DGE), &Size, NULL);
97 ok_type(Ret != 0, "DeviceIoControl failed: %ld\n", GetLastError());
99 {
100 ok_type(Size == sizeof(DGE), "Invalid output size: %ld\n", Size);
101 }
102 else
103 {
104 ok_type(Size == FIELD_OFFSET(DISK_GEOMETRY_EX, Data), "Invalid output size: %ld\n", Size);
105 }
106
107 return TRUE;
108}
#define ok_type(condition, format,...)
#define skip_type(format,...)
UINT DriveType
BOOL Error
Definition: chkdsk.c:66
#define IOCTL_DISK_GET_DRIVE_GEOMETRY
Definition: cdrw_usr.h:169
#define ERROR_INSUFFICIENT_BUFFER
Definition: dderror.h:10
BOOL WINAPI DeviceIoControl(IN HANDLE hDevice, IN DWORD dwIoControlCode, IN LPVOID lpInBuffer OPTIONAL, IN DWORD nInBufferSize OPTIONAL, OUT LPVOID lpOutBuffer OPTIONAL, IN DWORD nOutBufferSize OPTIONAL, OUT LPDWORD lpBytesReturned OPTIONAL, IN LPOVERLAPPED lpOverlapped OPTIONAL)
Definition: deviceio.c:136
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define IOCTL_DISK_GET_DRIVE_GEOMETRY_EX
Definition: ntddk_ex.h:208
unsigned long DWORD
Definition: ntddk_ex.h:95
unsigned int UINT
Definition: ndis.h:50
TW_UINT32 DG
Definition: twain.h:1827
#define FIELD_OFFSET(t, f)
Definition: typedefs.h:255
_Must_inspect_result_ _In_ WDFDEVICE Device
Definition: wdfchildlist.h:474
_Must_inspect_result_ _In_ WDFDEVICE _In_ PWDF_DEVICE_PROPERTY_DATA _In_ DEVPROPTYPE _In_ ULONG Size
Definition: wdfdevice.h:4539
DWORD WINAPI GetLastError(void)
Definition: except.c:1042
#define DRIVE_FIXED
Definition: winbase.h:276
#define ERROR_NOT_READY
Definition: winerror.h:246

Referenced by START_TEST().

◆ QueryDeviceName()

static VOID QueryDeviceName ( VOID  )
static

Definition at line 112 of file DeviceIoControl.c.

113{
114 UINT Ret;
115 BOOL IsValid;
117 MOUNTDEV_NAME MDN, *AllocatedMDN;
118
119 Size = 0;
120 Ret = DeviceIoControl(Device, IOCTL_MOUNTDEV_QUERY_DEVICE_NAME, NULL, 0, &MDN, sizeof(MDN) - 1, &Size, NULL);
121 ok_type(Ret == 0, "DeviceIoControl succeed\n");
123 if (DriveType == DRIVE_FIXED)
124 {
125 ok_type(Error == ERROR_INVALID_PARAMETER, "Expecting ERROR_INVALID_PARAMETER, got %ld\n", Error);
126 }
127 else
128 {
129 ok_type(Error == ERROR_INSUFFICIENT_BUFFER, "Expecting ERROR_INSUFFICIENT_BUFFER, got %ld\n", Error);
130 }
131 ok_type(Size == 0, "Invalid output size: %ld\n", Size);
132
133 Ret = DeviceIoControl(Device, IOCTL_MOUNTDEV_QUERY_DEVICE_NAME, NULL, 0, &MDN, sizeof(MDN), &Size, NULL);
134 ok_type(Ret == 0, "DeviceIoControl succeed\n");
136 ok_type(Error == ERROR_MORE_DATA, "Expecting ERROR_MORE_DATA, got %ld\n", Error);
137 ok_type(Size == sizeof(MOUNTDEV_NAME), "Invalid output size: %ld\n", Size);
138
139 AllocatedMDN = HeapAlloc(GetProcessHeap(), 0, FIELD_OFFSET(MOUNTDEV_NAME, Name) + MDN.NameLength + sizeof(UNICODE_NULL));
140 if (AllocatedMDN == NULL)
141 {
142 skip_type("Memory allocation failure\n");
143 return;
144 }
145
146 Size = 0;
148 ok_type(Ret != 0, "DeviceIoControl failed: %ld\n", GetLastError());
149 ok_type(Size == FIELD_OFFSET(MOUNTDEV_NAME, Name) + MDN.NameLength, "Invalid output size: %ld\n", Size);
150 ok_type(AllocatedMDN->NameLength == MDN.NameLength, "Mismatching sizes: %d %d\n", AllocatedMDN->NameLength, MDN.NameLength);
151
152 if (Ret != 0)
153 {
154 IsValid = FALSE;
155 AllocatedMDN->Name[AllocatedMDN->NameLength / sizeof(WCHAR) - 1] = UNICODE_NULL;
156
157 if ((DriveType == DRIVE_FIXED && wcsstr(AllocatedMDN->Name, L"\\Device\\HarddiskVolume") != NULL) ||
158 (DriveType == DRIVE_CDROM && wcsstr(AllocatedMDN->Name, L"\\Device\\CdRom") != NULL))
159 {
160 IsValid = TRUE;
161 }
162 else if (wcsstr(AllocatedMDN->Name, L"\\DosDevices\\") != NULL)
163 {
164 IsValid = (AllocatedMDN->Name[12] == Letter && AllocatedMDN->Name[13] == L':');
165 }
166
167 ok_type(IsValid, "Invalid name: %.*S\n", AllocatedMDN->NameLength, AllocatedMDN->Name);
168 }
169 else
170 {
171 skip_type("Failed to query device name\n");
172 }
173
174 HeapFree(GetProcessHeap(), 0, AllocatedMDN);
175}
WCHAR Letter
#define ERROR_MORE_DATA
Definition: dderror.h:13
LPWSTR Name
Definition: desk.c:124
#define GetProcessHeap()
Definition: compat.h:736
#define ERROR_INVALID_PARAMETER
Definition: compat.h:101
#define HeapAlloc
Definition: compat.h:733
#define HeapFree(x, y, z)
Definition: compat.h:735
_ACRTIMP wchar_t *__cdecl wcsstr(const wchar_t *, const wchar_t *)
Definition: wcs.c:2993
#define L(x)
Definition: resources.c:13
unsigned int BOOL
Definition: ntddk_ex.h:94
#define IOCTL_MOUNTDEV_QUERY_DEVICE_NAME
Definition: imports.h:91
#define UNICODE_NULL
short WCHAR
Definition: pedump.c:58
USHORT NameLength
Definition: imports.h:141
WCHAR Name[1]
Definition: imports.h:142
#define DRIVE_CDROM
Definition: winbase.h:278

Referenced by START_TEST().

◆ QuerySuggestedLinkName()

static VOID QuerySuggestedLinkName ( VOID  )
static

Definition at line 223 of file DeviceIoControl.c.

224{
225 UINT Ret;
228
229 Size = 0;
230 Ret = DeviceIoControl(Device, IOCTL_MOUNTDEV_QUERY_SUGGESTED_LINK_NAME, NULL, 0, &MSLN, sizeof(MSLN) - 1, &Size, NULL);
231 ok_type(Ret == 0, "DeviceIoControl succeed\n");
233 if (DriveType == DRIVE_FIXED)
234 {
235 ok_type(Error == ERROR_INVALID_PARAMETER, "Expecting ERROR_INVALID_PARAMETER, got %ld\n", Error);
236 }
237 else
238 {
239 ok_type(Error == ERROR_INSUFFICIENT_BUFFER, "Expecting ERROR_INSUFFICIENT_BUFFER, got %ld\n", Error);
240 }
241 ok_type(Size == 0, "Invalid output size: %ld\n", Size);
242
244 ok_type(Ret == 0, "DeviceIoControl succeed\n");
246 if (DriveType == DRIVE_FIXED)
247 {
248 ok_type(Error == ERROR_NOT_FOUND, "Expecting ERROR_NOT_FOUND, got %ld\n", Error);
249 }
250 else
251 {
252 ok_type(Error == ERROR_FILE_NOT_FOUND, "Expecting ERROR_FILE_NOT_FOUND, got %ld\n", Error);
253 }
254 ok_type(Size == 0, "Invalid output size: %ld\n", Size);
255}
#define ERROR_FILE_NOT_FOUND
Definition: disk.h:79
#define IOCTL_MOUNTDEV_QUERY_SUGGESTED_LINK_NAME
Definition: imports.h:97
#define ERROR_NOT_FOUND
Definition: winerror.h:1014

Referenced by START_TEST().

◆ QueryUniqueId()

static VOID QueryUniqueId ( VOID  )
static

Definition at line 179 of file DeviceIoControl.c.

180{
181 UINT Ret;
183 MOUNTDEV_UNIQUE_ID MUI, *AllocatedMUI;
184
185 Size = 0;
186 Ret = DeviceIoControl(Device, IOCTL_MOUNTDEV_QUERY_UNIQUE_ID, NULL, 0, &MUI, sizeof(MUI) - 1, &Size, NULL);
187 ok_type(Ret == 0, "DeviceIoControl succeed\n");
189 if (DriveType == DRIVE_FIXED)
190 {
191 ok_type(Error == ERROR_INVALID_PARAMETER, "Expecting ERROR_INVALID_PARAMETER, got %ld\n", Error);
192 }
193 else
194 {
195 ok_type(Error == ERROR_INSUFFICIENT_BUFFER, "Expecting ERROR_INSUFFICIENT_BUFFER, got %ld\n", Error);
196 }
197 ok_type(Size == 0, "Invalid output size: %ld\n", Size);
198
199 Ret = DeviceIoControl(Device, IOCTL_MOUNTDEV_QUERY_UNIQUE_ID, NULL, 0, &MUI, sizeof(MUI), &Size, NULL);
200 ok_type(Ret == 0, "DeviceIoControl succeed\n");
202 ok_type(Error == ERROR_MORE_DATA, "Expecting ERROR_MORE_DATA, got %ld\n", Error);
203 ok_type(Size == sizeof(MOUNTDEV_UNIQUE_ID), "Invalid output size: %ld\n", Size);
204
205 AllocatedMUI = HeapAlloc(GetProcessHeap(), 0, FIELD_OFFSET(MOUNTDEV_UNIQUE_ID, UniqueId) + MUI.UniqueIdLength + sizeof(UNICODE_NULL));
206 if (AllocatedMUI == NULL)
207 {
208 skip_type("Memory allocation failure\n");
209 return;
210 }
211
212 Size = 0;
214 ok_type(Ret != 0, "DeviceIoControl failed: %ld\n", GetLastError());
215 ok_type(Size == FIELD_OFFSET(MOUNTDEV_UNIQUE_ID, UniqueId) + MUI.UniqueIdLength, "Invalid output size: %ld\n", Size);
216 ok_type(AllocatedMUI->UniqueIdLength == MUI.UniqueIdLength, "Mismatching sizes: %d %d\n", AllocatedMUI->UniqueIdLength, MUI.UniqueIdLength);
217
218 HeapFree(GetProcessHeap(), 0, AllocatedMUI);
219}
#define IOCTL_MOUNTDEV_QUERY_UNIQUE_ID
Definition: imports.h:78
USHORT UniqueIdLength
Definition: imports.h:136

Referenced by START_TEST().

◆ START_TEST()

START_TEST ( DeviceIoControl  )

Definition at line 257 of file DeviceIoControl.c.

258{
259 UINT Ret;
261 DWORD DriveMap, Current;
262 BOOL DiskDone, CdRomDone;
263
265
266 DiskDone = FALSE;
267 CdRomDone = FALSE;
268 DriveMap = GetLogicalDrives();
269 for (Current = 0; Current < 26; ++Current)
270 {
271 if (DriveMap & (1 << Current))
272 {
273 Ret = StringCchPrintfW(Path, MAX_PATH, L"%c:\\", Current + L'A');
274 ok(Ret == S_OK, "StringCchPrintfW failed: %d\n", Ret);
275
277 if ((DriveType == DRIVE_FIXED && !DiskDone) ||
278 (DriveType == DRIVE_CDROM && !CdRomDone))
279 {
280 Ret = StringCchPrintfW(Path, MAX_PATH, L"\\\\?\\%c:", Current + L'A');
281 ok(Ret == S_OK, "StringCchPrintfW failed: %d\n", Ret);
282
285 {
286 skip_type("CreateFileW for %S failed: %ld\n", Path, GetLastError());
287 continue;
288 }
289
290 DiskDone = (DiskDone || (DriveType == DRIVE_FIXED));
291 CdRomDone = (CdRomDone || (DriveType == DRIVE_CDROM));
292
293 if (GetDiskGeometry())
294 {
298 }
299
301 }
302
303 if (CdRomDone && DiskDone)
304 {
305 break;
306 }
307 }
308 }
309
310 if (!DiskDone)
311 {
312 skip("No disk drive found\n");
313 }
314
315 if (!CdRomDone)
316 {
317 skip("No CDROM drive found\n");
318 }
319}
static VOID QueryUniqueId(VOID)
static BOOL GetDiskGeometry(VOID)
static VOID QuerySuggestedLinkName(VOID)
static VOID QueryDeviceName(VOID)
static void Test_DeviceIoControl_Parameters(void)
PRTL_UNICODE_STRING_BUFFER Path
#define ok(value,...)
Definition: atltest.h:57
#define skip(...)
Definition: atltest.h:64
#define CloseHandle
Definition: compat.h:739
#define OPEN_EXISTING
Definition: compat.h:775
#define INVALID_HANDLE_VALUE
Definition: compat.h:731
#define MAX_PATH
Definition: compat.h:34
#define CreateFileW
Definition: compat.h:741
#define FILE_ATTRIBUTE_NORMAL
Definition: compat.h:137
#define FILE_SHARE_READ
Definition: compat.h:136
UINT WINAPI GetDriveTypeW(IN LPCWSTR lpRootPathName)
Definition: disk.c:497
DWORD WINAPI DECLSPEC_HOTPATCH GetLogicalDrives(void)
Definition: volume.c:513
#define S_OK
Definition: intsafe.h:52
#define FILE_SHARE_WRITE
Definition: nt_native.h:681
#define FILE_SHARE_DELETE
Definition: nt_native.h:682
STRSAFEAPI StringCchPrintfW(STRSAFE_LPWSTR pszDest, size_t cchDest, STRSAFE_LPCWSTR pszFormat,...)
Definition: strsafe.h:530

◆ Test_DeviceIoControl_Parameters()

static void Test_DeviceIoControl_Parameters ( void  )
static

Definition at line 23 of file DeviceIoControl.c.

24{
25 static const PWSTR KsecDevicePath = L"\\\\.\\Global\\GLOBALROOT\\Device\\KsecDD";
26 UCHAR Buffer[16];
27 HANDLE hDevice;
28 BOOL ret;
29
30 /* Open ksecdd device */
31 hDevice = CreateFileW(KsecDevicePath, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, NULL);
32 if (hDevice == INVALID_HANDLE_VALUE)
33 {
34 skip("CreateFile failed: %lu\n", GetLastError());
35 return;
36 }
37
38 /* Test NULL lpBytesReturned (used by wine's wbemprox) */
39 SetLastError(0xDEADBEEF);
40 StartSeh()
41 ret = DeviceIoControl(hDevice,
43 NULL,
44 0,
45 Buffer,
47 NULL, /* lpBytesReturned */
48 NULL);
50 ok_eq_ulong(GetLastError(), 0xDEADBEEF);
52
53 CloseHandle(hDevice);
54}
#define IOCTL_KSEC_RANDOM_FILL_BUFFER
#define ok_eq_ulong(value, expected)
Definition: apitest.h:120
#define GetNTVersion()
Definition: apitest.h:17
#define StartSeh()
Definition: apitest.h:93
#define ok_eq_bool(value, expected)
Definition: apitest.h:137
#define EndSeh(ExpectedStatus)
Definition: apitest.h:99
Definition: bufpool.h:45
#define SetLastError(x)
Definition: compat.h:752
#define GENERIC_READ
Definition: compat.h:135
return ret
Definition: mutex.c:146
#define _WIN32_WINNT_WIN8
Definition: sdkddkver.h:29
#define STATUS_SUCCESS
Definition: shellext.h:65
uint16_t * PWSTR
Definition: typedefs.h:56
unsigned char UCHAR
Definition: typedefs.h:53
#define STATUS_INVALID_PARAMETER
Definition: udferr_usr.h:135
ActualNumberDriverObjects * sizeof(PDRIVER_OBJECT)) PDRIVER_OBJECT *DriverObjectList

Referenced by START_TEST().

Variable Documentation

◆ Device

Definition at line 14 of file DeviceIoControl.c.

◆ DriveType

◆ Letter