如何使用Python获取原始磁盘或阻止设备大小

如果我只知道设备名称是“\。\ PhysicalDrive0”而没有其上的文件系统或卷标,我如何从Windows中的块设备或原始磁盘获取大小?

我尝试了以下内容:

fd = os.open(r“\。\ PhysicalDrive0”,os.O_RDONLY)

os.lseek(fd,0,os.SEEK_END)

它在Linux上工作正常,但总是在Windows上返回“OSError:[Errno 22]无效参数”。

我也尝试了ctypes.windll.kernel32.GetDiskFreeSpaceExW(),但它似乎只适用于磁盘文件系统和分配的卷标。

原始磁盘或块设备的正确方法是什么?

提前致谢。

使用wmi模块

 import wmi c = wmi.WMI() [drive] = c.Win32_DiskDrive(Index=0) print("The disk has %s bytes" % drive.size) print("Or %s GB" % int(int(drive.size) / 1024**3)) 

The disk has 320070320640 bytes
Or 298 GB

此代码查询索引等于0 Win32_DiskDrive对象的WMI接口(以便只有一个结果,结果是PHYSICALDRIVE0 )。 drive对象有一个名为size的属性,它是一个包含驱动器大小的字符串(以字节为单位)。

我有一个解决方案..但它不漂亮。 使用diskpart。 不幸的是,它不会给你一个确切的字节大小,如果这是需要的,但它给你一个人类可读的字符串。

 import tempfile import subprocess import re import os def query_diskpart(command): """Run command script for diskpart. Args: command(str): String of all commands to run against diskpart Returns: String of all diskpart standard output Size Effects: Creates a temporary file(and then deletes it) Creates a subprocess to run diskpart """ with tempfile.NamedTemporaryFile(mode='w', delete=False) as temp_handle: temp_handle.write(command) # The temporary file needs to be closed before opening with diskpart diskpart_handle = subprocess.Popen(["diskpart", '/s', temp_handle.name], stdout=subprocess.PIPE) output, _ = diskpart_handle.communicate() os.remove(temp_handle.name) return output def match_drive_size(diskpart_output, disk_num): """Get drive size from diskpart output. Args: diskpart_output(str): String of diskpart standard output disk_num(int): Number of PhysicalDrive to match against Returns: Human readable size of drive. Raises: ValueError if drive doesn't exist. """ # Break up gigantic output string output_lines = diskpart_output.decode().split(os.linesep) # Apply regular expression to every line, but it should only match one matches = [re.match(".*Disk %s\s*(.*)" % disk_num, line) for line in output_lines] size = None for match in matches: if match: # Get first subgroup (parens above) size_line = match.group(1) # Split by whitespace size_list = re.split("\s*", size_line) # Merge numerical value + units # ['256', 'GB'] becomes 256GB size = ''.join(size_list[1:3]) break else: raise ValueError("PHYSICALDRIVE%s does not exist", disk_num) return size def get_drive_size(disk_num): """Get Windows Drive size. Args: disk_num(int): The Physical Drive Number eg for PHYSICALDRIVE0 put 0 Returns: Human readable string of the drive size """ output = query_diskpart("list disk\n") drive_size = match_drive_size(output, disk_num) return drive_size if __name__ == "__main__": print(get_drive_size(0))