对于我的应用程序,我需要确定最佳的驱动器/分区。要求如下:
第 1 点和第 2 点可以使用 C# 中的 DriveInfo 类轻松解析。然而我被困在第 3 点...
使用 ManagementObjectSearch 从 Win32_DiskDrive 类获取 BytesPerSector 值。但是我无法解析特定的驱动器。
例如。假设我想找到 C:\
的 BytesPerSector 值 // Specify the drive letter (change it to the desired letter)
string driveLetter = "C:";
// Get DriveInfo for the specified drive letter
DriveInfo driveInfo = new(driveLetter);
// Check if the drive is ready (mounted)
Assert.IsTrue(driveInfo.IsReady, $"Expected drive to be ready but was not");
Console.WriteLine("Format: " + driveInfo.Name);
// Get the disk drive associated with the partition
var diskDrive = new System.Management.ManagementObjectSearcher(
"SELECT * FROM Win32_DiskDrive WHERE DeviceID = '" + driveInfo.Name + "'"
).Get().OfType<System.Management.ManagementObject>().FirstOrDefault();
// Check if the disk drive is found
Assert.IsNotNull(diskDrive, $"Expected disk drive to be found but was null");
// Get the BytesPerSector information
uint bytesPerSector = Convert.ToUInt32(diskDrive["BytesPerSector"]);
// Print out the BytesPerSector information
Assert.IsTrue(bytesPerSector == 512 || bytesPerSector == 4096, $"Expected 512 or 4096 but was {bytesPerSector}");
此操作失败,但有例外:
留言: 测试方法 TestSectorInfo 抛出异常: System.Management.ManagementException:无效查询
一些挖掘让我发现 Win32_DiskDrive 期望的 DeviceID 看起来像这样:
\\.\PHYSICALDRIVE0
\\.\PHYSICALDRIVE1
等等
但是我无法确定 C:\ 是在 DRIVE0 还是 DRIVE1 上,所以我首先必须以某种方式将分区字母转换到其底层磁盘...我该怎么做?
我还尝试将卷的字母传递给不起作用的查询,并寻找任何可能做我需要的事情的c#类,但无济于事。
您遇到的问题是由于
Win32_DiskDrive
WMI 类的 DeviceID 与驱动器盘符不同所致。 DeviceID 是物理驱动器的唯一标识符,而不是分区或卷。
要获取特定驱动器号的
BytesPerSector
,您需要执行几个步骤:
获取盘符对应的Win32_Volume实例。 获取关联的
Win32_DiskPartition
实例。
获取关联的 Win32_DiskDrive
实例。
具体方法如下:
// Specify the drive letter (change it to the desired letter)
string driveLetter = "C:";
// Get the Win32_Volume instance for the drive letter
var volume = new System.Management.ManagementObjectSearcher(
"SELECT * FROM Win32_Volume WHERE Name = '" + driveLetter + "\\'"
).Get().OfType<System.Management.ManagementObject>().FirstOrDefault();
// Check if the volume is found
Assert.IsNotNull(volume, $"Expected volume to be found but was null");
// Get the associated Win32_DiskPartition instance
var partition = new System.Management.ManagementObjectSearcher(
"ASSOCIATORS OF {Win32_DiskDrive.DeviceID='" + volume["DeviceID"] + "'} WHERE AssocClass = Win32_DiskDriveToDiskPartition"
).Get().OfType<System.Management.ManagementObject>().FirstOrDefault();
// Check if the partition is found
Assert.IsNotNull(partition, $"Expected partition to be found but was null");
// Get the associated Win32_DiskDrive instance
var diskDrive = new System.Management.ManagementObjectSearcher(
"ASSOCIATORS OF {Win32_DiskPartition.DeviceID='" + partition["DeviceID"] + "'} WHERE AssocClass = Win32_DiskDriveToDiskPartition"
).Get().OfType<System.Management.ManagementObject>().FirstOrDefault();
// Check if the disk drive is found
Assert.IsNotNull(diskDrive, $"Expected disk drive to be found but was null");
// Get the BytesPerSector information
uint bytesPerSector = Convert.ToUInt32(diskDrive["BytesPerSector"]);
// Print out the BytesPerSector information
Assert.IsTrue(bytesPerSector == 512 || bytesPerSector == 4096, $"Expected 512 or 4096 but was {bytesPerSector}");
此代码首先获取指定驱动器号的
Win32_Volume
实例。然后,它使用 ASSOCIATORS OF WQL 查询来获取关联的 Win32_DiskPartition
和 Win32_DiskDrive
实例。然后从 Win32_DiskDrive
实例检索 BytesPerSector 信息。
您可能需要以管理权限运行应用程序才能访问某些 WMI 类。另外,请记住将对
System.Management
命名空间和 System.Management
程序集的引用添加到您的项目中。