在 Linux 中确定扇区大小的便携式方法

Posted

技术标签:

【中文标题】在 Linux 中确定扇区大小的便携式方法【英文标题】:Portable way to determine sector size in Linux 【发布时间】:2017-02-25 09:43:38 【问题描述】:

我想用 C 语言编写一个小程序,它可以确定硬盘的扇区大小。我想阅读位于/sys/block/sd[X]/queue/hw_sector_size 的文件,它在 CentOS 6/7 中工作。

但是当我在 CentOS 5.11 中测试时,文件hw_sector_size 丢失了,我只找到了max_hw_sectors_kbmax_sectors_kb

因此,我想知道如何确定(API)CentOS 5 中的扇区大小,或者是否有其他更好的方法来确定。谢谢。

【问题讨论】:

Block device information without mounting in Linux的可能重复 【参考方案1】:

fdisk 实用程序会显示此信息(并且可以在比 CentOS 5 上的 2.6.x 年份更早的内核上成功运行),因此这似乎是一个寻找答案的地方。幸运的是,我们生活在开源的美好世界中,所以只需要一点调查。

fdisk 程序由 util-linux 包提供,所以我们首先需要它。

扇区大小显示在fdisk 的输出中,如下所示:

Disk /dev/sda: 477 GiB, 512110190592 bytes, 1000215216 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes

如果我们在util-linux 代码中查找Sector size,我们会在disk-utils/fdisk-list.c 中找到它:

fdisk_info(cxt, _("Sector size (logical/physical): %lu bytes / %lu bytes"),
            fdisk_get_sector_size(cxt),
            fdisk_get_physector_size(cxt));

所以,看来我们需要找到fdisk_get_sector_size,它在libfdisk/src/context.c中定义:

unsigned long fdisk_get_sector_size(struct fdisk_context *cxt)

    assert(cxt);
    return cxt->sector_size;

嗯,这不是很有帮助。我们需要找出cxt->sector_size 的设置位置:

$ grep -lri 'cxt->sector_size.*=' | grep -v tests
libfdisk/src/alignment.c
libfdisk/src/context.c
libfdisk/src/dos.c
libfdisk/src/gpt.c
libfdisk/src/utils.c

我将从alignment.c 开始,因为该文件名听起来很有希望。查看该文件以查找我用来列出文件的相同正则表达式,我们发现this:

cxt->sector_size = get_sector_size(cxt->dev_fd);

这导致我:

static unsigned long get_sector_size(int fd)

    int sect_sz;

    if (!blkdev_get_sector_size(fd, &sect_sz))
        return (unsigned long) sect_sz;
    return DEFAULT_SECTOR_SIZE;

这反过来又让我找到了blkdev_get_sector_size 在lib/blkdev.c 中的定义:

#ifdef BLKSSZGET
int blkdev_get_sector_size(int fd, int *sector_size)

    if (ioctl(fd, BLKSSZGET, sector_size) >= 0)
        return 0;
    return -1;

#else
int blkdev_get_sector_size(int fd __attribute__((__unused__)), int *sector_size)

    *sector_size = DEFAULT_SECTOR_SIZE;
    return 0;

#endif

然后我们开始了。有一个 BLKSSZGET ioctl 似乎很有用。搜索BLKSSZGET 将我们引向this *** question,其中在评论中包含以下信息:

记录:BLKSSZGET = 逻辑块大小,BLKBSZGET = 物理 块大小,BLKGETSIZE64 = 设备大小(以字节为单位),BLKGETSIZE = 设备 尺寸/512。至少如果 fs.h 中的 cmets 和我的实验可以 信任。 – Edward Falk 2012 年 7 月 10 日 19:33

【讨论】:

这真是太棒了!非常感谢 larsks!

以上是关于在 Linux 中确定扇区大小的便携式方法的主要内容,如果未能解决你的问题,请参考以下文章

Windows XP 上用于高级格式硬盘的物理扇区大小

在向量 GENy 中配置闪存块表

在linux内核级别,如何读取和写入一个硬[重复]的扇区

Linux物理机添加新磁盘并格式化

4KB 扇区磁盘上的 Linux:实际建议

我可以使用扇区级数据确定安装在硬盘中的操作系统吗?