Function DeviceIoControl [src]

A Zig wrapper around NtDeviceIoControlFile and NtFsControlFile syscalls. It implements similar behavior to DeviceIoControl and is meant to serve as a direct substitute for that call. TODO work out if we need to expose other arguments to the underlying syscalls.

Prototype

pub fn DeviceIoControl( h: HANDLE, ioControlCode: ULONG, in: ?[]const u8, out: ?[]u8, ) DeviceIoControlError!void

Parameters

h: HANDLEioControlCode: ULONGin: ?[]const u8out: ?[]u8

Possible Errors

AccessDenied
Unexpected
UnrecognizedVolume

The volume does not contain a recognized file system. File system drivers might not be loaded, or the volume may be corrupt.

Source

pub fn DeviceIoControl( h: HANDLE, ioControlCode: ULONG, in: ?[]const u8, out: ?[]u8, ) DeviceIoControlError!void { // Logic from: https://doxygen.reactos.org/d3/d74/deviceio_8c.html const is_fsctl = (ioControlCode >> 16) == FILE_DEVICE_FILE_SYSTEM; var io: IO_STATUS_BLOCK = undefined; const in_ptr = if (in) |i| i.ptr else null; const in_len = if (in) |i| @as(ULONG, @intCast(i.len)) else 0; const out_ptr = if (out) |o| o.ptr else null; const out_len = if (out) |o| @as(ULONG, @intCast(o.len)) else 0; const rc = blk: { if (is_fsctl) { break :blk ntdll.NtFsControlFile( h, null, null, null, &io, ioControlCode, in_ptr, in_len, out_ptr, out_len, ); } else { break :blk ntdll.NtDeviceIoControlFile( h, null, null, null, &io, ioControlCode, in_ptr, in_len, out_ptr, out_len, ); } }; switch (rc) { .SUCCESS => {}, .PRIVILEGE_NOT_HELD => return error.AccessDenied, .ACCESS_DENIED => return error.AccessDenied, .INVALID_DEVICE_REQUEST => return error.AccessDenied, // Not supported by the underlying filesystem .INVALID_PARAMETER => unreachable, .UNRECOGNIZED_VOLUME => return error.UnrecognizedVolume, else => return unexpectedStatus(rc), } }