c#实现禁用u盘再启用

将u盘量产为CDROM后,刷入ISO后需要重新插拔u盘才能访问新内容。此文展示的代码可以实现模拟这种行为,免插拔使windows重新读取cdrom。

网上参考资料有限,自行试验了很多种方法,终于成功了。

 

首先调用DeviceIoControl卸载设备。然后用CM_Disable_DevNode禁用设备,最后用CM_Enable_DevNode启用设备。

关键代码:

public const uint GENERIC_READ = 0x80000000;
public const uint GENERIC_WRITE = 0x40000000;
public const int FILE_SHARE_READ = 1;
public const int OPEN_EXISTING = 3;
public const int FILE_ATTRIBUTE_NORMAL = 0x80;

public const int FSCTL_IS_VOLUME_MOUNTED = 0x00090028;
public const int CM_DISABLE_HARDWARE = 0x00000002;

public struct DiskExtent
{
    public uint DiskNumber;
    public long StartingOffset;
    public long ExtentLength;
}

public struct DiskExtents
{
    public int numberOfExtents;
    public DiskExtent[] first;
}

[StructLayout(LayoutKind.Sequential)]
class SP_DEVINFO_DATA
{
    public int cbSize;
    public Guid ClassGuid;
    public int DevInst;
    public ulong Reserved;
}

[DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Unicode)]
static extern SafeFileHandle CreateFile(string lpFileName, uint dwDesiredAccess,
    uint dwShareMode, IntPtr lpSecurityAttributes, uint dwCreationDisposition,
    uint dwFlagsAndAttributes, IntPtr hTemplateFile);

[DllImport("CfgMgr32.dll", SetLastError = true)]
public static extern int CM_Enable_DevNode(ref SafeFileHandle pdnDevInst, int ulFlags);

[DllImport("CfgMgr32.dll", SetLastError = true)]
public static extern int CM_Disable_DevNode(ref SafeFileHandle pdnDevInst, int ulFlags);

private SafeFileHandle getHandleByLetter(char letter)
{           
    string lpFileName;
    lpFileName = "\\\\.\\" + letter.ToString() + ":";
    SafeFileHandle hDevice = CreateFile(lpFileName, GENERIC_WRITE, 0, IntPtr.Zero, OPEN_EXISTING, 0, IntPtr.Zero);
    return hDevice;
}

SafeFileHandle hDevice = getHandleByLetter(CDROMLetter[i]);
int bytesReturned = 0;
DiskExtents diskExtents = new DiskExtents();
DeviceIoControl(hDevice, FSCTL_DISMOUNT_VOLUME, IntPtr.Zero, 0, ref diskExtents, Marshal.SizeOf(diskExtents), ref bytesReturned, IntPtr.Zero);
                       
CM_Disable_DevNode(ref hDevice, CM_DISABLE_HARDWARE);
CM_Enable_DevNode(ref hDevice, 0);
hDevice.Close();

  参考链接:

https://blog.csdn.net/bhw98/article/details/19662?tdsourcetag=s_pctim_aiomsg

https://docs.microsoft.com/en-us/windows/desktop/api/cfgmgr32/nf-cfgmgr32-cm_disable_devnode

https://docs.microsoft.com/zh-cn/dotnet/api/microsoft.win32.safehandles.safefilehandle?view=netframework-4.8

https://stackoverflow.com/questions/37532548/deviceiocontrol-with-ioctl-volume-get-volume-disk-extents-c-sharp

转载于:https://www.cnblogs.com/sherlock-merlin/p/11066285.html

你可能感兴趣的:(c#实现禁用u盘再启用)