DeviceIoControl (kernel32)
Last changed: -100.11.86.164

.
Summary

C# Signature:

[DllImport("kernel32.dll", ExactSpelling = true, SetLastError = true, CharSet = CharSet.Auto)]
static extern bool DeviceIoControl(IntPtr hDevice, uint dwIoControlCode,
IntPtr lpInBuffer, uint nInBufferSize,
IntPtr lpOutBuffer, uint nOutBufferSize,
out uint lpBytesReturned, IntPtr lpOverlapped);

C# Signature:

[DllImport("Kernel32.dll", CharSet=CharSet.Auto, SetLastError=true)]
public static extern bool DeviceIoControl( IntPtr hDevice, uint dwIoControlCode, ref long InBuffer,
int nInBufferSize, ref long OutBuffer, int nOutBufferSize,
ref int pBytesReturned, [In] ref NativeOverlapped lpOverlapped);

VB Signature:

<DllImport("kernel32.dll", ExactSpelling:=True, SetLastError:=True, CharSet:=CharSet.Auto)> _
   Private Shared Function DeviceIoControl(ByVal hDevice As IntPtr, _
     ByVal dwIoControlCode As Int32, ByVal lpInBuffer As IntPtr, _
     ByVal nInBufferSize As Int32, ByVal lpOutBuffer As IntPtr, _
     ByVal nOutBufferSize As Int32, ByRef lpBytesReturned As Int32, _
     ByVal lpOverlapped As System.Threading.NativeOverlapped) As Boolean
   End Function

User-Defined Types:

None.

Notes:

hDevice - To retrieve a handle to a volume, call CreateFile with the lpFileName parameter set to a string of the following form: \\.\DriveLetter:. DriveLetter is not case-sensitive and does not require a colon after it.

Example:

tHandle = CreateFile(@"\\.\C:", FileAccess.Read, FileShare.ReadWrite, IntPtr.Zero, FileMode.Open, 0, IntPtr.Zero)

lpOverlapped - Main use in asynchronous deviceIoControl. NativeOverlapped is the managed version of the structure and use is the same.

Tips & Tricks:

This is great for interacting with devices; now perhaps someone can help with the SetupDi calls to actually discover the device handles, etc...? If you are able to conquer it (I wasn't) toss me a mail at dotnet at richardgoodwin dot com

-

Sample Code:

Public ReadOnly Property CardID() As String
  Get
   Dim dwErrorCode As FarcConstants
   Dim dwBytesReceived As Int32
   Dim ip As IntPtr = Marshal.AllocHGlobal(13)
   Dim erg As String
   If DeviceIoControl(hDriver, IOCTL_FARC_GET_CARDID, Nothing, 0, ip, 13, dwBytesReceived, Nothing) Then
     erg = Marshal.PtrToStringAnsi(ip)
     Marshal.FreeHGlobal(ip)
   Else
     dwErrorCode = Marshal.GetLastWin32Error
     Marshal.FreeHGlobal(ip)
     Throw New InvalidOperationException("Get Card ID fails. Errorcode: " & _
       dwErrorCode.ToString, New System.ComponentModel.Win32Exception(dwErrorCode))
   End If
   Return erg
  End Get
End Property

Sample Code:

public bool DeviceIoControl( IntPtr hDevice, uint dwIoControlCode, ref long buffer, int bufferSize, ref NativeOverlapped pOverlapped)
{
    int NoReturn = 0;
    return DeviceIoControl( hDevice, dwIoControlCode, ref buffer, bufferSize, ref buffer, bufferSize, ref NoReturn, ref pOverlapped );
}

public bool PlxIntrAttach(IntPtr handle, PlxIntr intrType)
{
    // Call to PLX card to attach wait event to an Interrupts
    // Declare control code
    uint Control;
    DriverMsgs AttachMsg = DriverMsgs.MsgIntrAttach;
    Control = CtrCode( cFileDeviceUnknown, (int)AttachMsg, cMethodBuffered, cFileAnyAccess );
    // Set return variable up
    bool Status = false;
    // Initialize the "buffer"
    long DeviceBuffer = 0;

    // Fill the buffer with the interrupt bitflag
    DeviceBuffer = (long)intrType;
    // Call the P/Invoked function through masking method
    Status = DeviceIoControl( handle, Control, ref DeviceBuffer, 8, ref AdcOverlapData );
    // Return with Status
    return Status;
}

Alternative Managed API:

Do you know one? Please contribute it!

Documentation