c#-DeviceIoControl无法弹出非空CDROM驱动器?
内容导读
互联网集市收集整理的这篇技术教程文章主要介绍了c#-DeviceIoControl无法弹出非空CDROM驱动器?,小编现在分享给大家,供广大互联网技能从业者学习和参考。文章包含3155字,纯文字阅读大概需要5分钟。
内容图文
![c#-DeviceIoControl无法弹出非空CDROM驱动器?](/upload/InfoBanner/zyjiaocheng/657/1f938fbec5044f0285708aaed6a57b26.jpg)
我尝试使用DeviceIoControl函数(Win32 API函数)弹出CDROM驱动器,当我的CDROM驱动器没有磁盘时,它可以正常运行,但是在插入磁盘后,Marshal.GetLastWin32Error()返回了32(ERROR_SHARING_VIOLATION:该进程无法访问文件,因为它正在被另一个进程使用),则在DeviceIoControl中传递的driveHandle由CreateFile()函数创建.
你能帮我吗?我喜欢这种操作CD ROM相关内容的方法,我可以使用winmm.dll弹出我的CDROM,但我认为这种方法值得尝试.
OK,这是代码:
using System;
using System.ComponentModel;
using System.Text;
using System.Windows.Forms;
using System.IO;
using System.Runtime.InteropServices;
namespace DVD_ejector
{
public partial class Form1 : Form
{
const int OPENEXISTING = 3;
const int IOCTL_STORAGE_EJECT_MEDIA = 2967560;
const uint GENERICREAD = 0x80000000;
const int INVALID_HANDLE = -1;
public Form1()
{
InitializeComponent();
DriveInfo[] drs = DriveInfo.GetDrives();
List<DriveInfo> cdRoms = new List<DriveInfo>();
foreach (DriveInfo dInfo in drs)
{
if (dInfo.DriveType == DriveType.CDRom)
{
cdRoms.Add(dInfo);
}
}
comboBox1.DataSource = cdRoms;
comboBox1.DisplayMember = "Name";
if (comboBox1.Items.Count > 0) comboBox1.SelectedIndex = 0;
button1.Click += (sender, e) =>
{
Eject(@"\\.\" + ((DriveInfo)comboBox1.SelectedItem).Name[0]+":");
};
}
[DllImport("kernel32", SetLastError=true)]
static extern IntPtr CreateFile(string fileName, uint desiredAccess, uint shareMode, IntPtr attributes,uint creationDisposition, uint flagsAndAttribute, IntPtr fileTemplate);
[DllImport("kernel32")]
static extern int CloseHandle(IntPtr fileHandle);
[DllImport("kernel32")]
static extern bool DeviceIoControl(IntPtr driveHandle, int ctrlCode, IntPtr inBuffer, int inBufferSize, IntPtr outBuffer, int outBufferSize, ref int bytesReturned, IntPtr overlapped);
int bytesReturned;
private void Eject(string cdDrive)
{
IntPtr driveHandle = CreateFile(cdDrive, GENERICREAD, 0, IntPtr.Zero, OPENEXISTING, 0, IntPtr.Zero);
try
{
if((int)driveHandle != INVALID_HANDLE)
DeviceIoControl(driveHandle, IOCTL_STORAGE_EJECT_MEDIA, IntPtr.Zero, 0, IntPtr.Zero, 0, ref bytesReturned, IntPtr.Zero);
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
finally
{
CloseHandle(driveHandle);
}
}
}
}
解决方法:
如错误状态所示,该设备正在被其他人使用,但是它在CreateFile调用而不是DeviceIoControl上发生故障,并且您的代码未正确检查故障.
出现共享冲突的原因是因为您试图专门打开设备,如果任何东西试图打开它或其中的文件(包括防病毒,资源管理器,搜索索引器等),该设备都会失败.
此更新的弹出功能修复了共享模式和错误处理,现在可以在正确的位置报告错误.
private void Eject(string cdDrive) {
IntPtr driveHandle = new IntPtr(INVALID_HANDLE);
try {
// Open the device
driveHandle = CreateFile(cdDrive, GENERICREAD, FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE, IntPtr.Zero, OPENEXISTING, 0, IntPtr.Zero);
if ((int)driveHandle == INVALID_HANDLE) { throw new Win32Exception(); }
// Try and eject
bool ejected = DeviceIoControl(driveHandle, IOCTL_STORAGE_EJECT_MEDIA, IntPtr.Zero, 0, IntPtr.Zero, 0, ref bytesReturned, IntPtr.Zero);
if (!ejected) { throw new Win32Exception(); }
} catch (Exception ex) {
MessageBox.Show(ex.Message);
} finally {
if ((int)driveHandle != INVALID_HANDLE) { CloseHandle(driveHandle); }
}
}
内容总结
以上是互联网集市为您收集整理的c#-DeviceIoControl无法弹出非空CDROM驱动器?全部内容,希望文章能够帮你解决c#-DeviceIoControl无法弹出非空CDROM驱动器?所遇到的程序开发问题。 如果觉得互联网集市技术教程内容还不错,欢迎将互联网集市网站推荐给程序员好友。
内容备注
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 gblab@vip.qq.com 举报,一经查实,本站将立刻删除。
内容手机端
扫描二维码推送至手机访问。