Leo*_*d99 5 linux kernel scsi block linux-kernel
我有一个生成大 SCSI 写入的用户空间应用程序(详细信息如下)。然而,当我查看到达 SCSI 目标(即存储,由 FC 连接)的 SCSI 命令时,某些东西将这些写入拆分为 512K 块。
该应用程序基本上会直接向设备进行 1M 大小的直接写入:
fd = open("/dev/sdab", ..|O_DIRECT);
write(fd, ..., 1024 * 1024);
Run Code Online (Sandbox Code Playgroud)
此代码导致发送两个 SCSI WRITE,每个 512K。
但是,如果我发出直接 SCSI 命令,而没有块层,则不会拆分写入。我从命令行发出以下命令:
sg_dd bs=1M count=1 blk_sgio=1 if=/dev/urandom of=/dev/sdab oflag=direct
Run Code Online (Sandbox Code Playgroud)
我可以看到一个 1M 大小的 SCSI WRITE。
问题是,什么是拆分写入,更重要的是,它是否可配置?Linux 块层似乎是有罪的(因为 SG_IO 不通过它)并且 512K 似乎太随意了,不能成为某种可配置的参数。
问题确实在于块层,SCSI 层本身与大小无关。您应该检查底层是否确实能够传递您的请求,特别是对于直接 io,因为它可能会分成许多小页面,并且需要一个比硬件或可以支持的长度更长的分散收集列表。甚至只是驱动程序(libata 是/曾经有些限制)。
您应该查看并调整 /sys/class/block/$DEV/queue 那里有各种各样的文件,最有可能匹配您需要的是 max_sectors_kb 但您可以尝试一下,看看什么适合您。您可能还需要调整分区变量。