如何在Linux上清除磁盘I / O缓存?

时间:2012-03-04 02:35:01

标签: linux caching io disk

我需要做更多可预测的基准测试。

5 个答案:

答案 0 :(得分:55)

听起来你想要sync命令或sync()功能。

如果您想要磁盘缓存刷新:echo 3 | sudo tee /proc/sys/vm/drop_caches

答案 1 :(得分:35)

你可以这样做:

# sync # (move data, modified through FS -> HDD cache) + flush HDD cache
# echo 3 > /proc/sys/vm/drop_caches # (slab + pagecache) -> HDD (https://www.kernel.org/doc/Documentation/sysctl/vm.txt)
# blockdev --flushbufs /dev/sda
# hdparm -F /dev/sda

# NEXT COMMAND IS NOT FOR BENCHMARKING:
# should be run before unplug, flushes everything possible guaranteed.
# echo 1 > /sys/block/sdX/device/delete

您可以使用strace来查看这三种不同的系统调用

此外,可能需要使用hdparm关闭硬盘缓存,不确定您对基准测试的内容。

无论如何,您无法阻止HDD缓存最近64/32/16 MB的最近使用的数据。为了杀死那个缓存,只需写入一些零(和刷新)+从HDD中读取一些不相关的地方。这是必需的,因为高速缓存可以分为读取部分和写入部分。之后,您可以对HDD进行基准测试。

答案 2 :(得分:21)

磁盘缓存清除:echo 3 | sudo tee /proc/sys/vm/drop_caches

命令文档:https://www.kernel.org/doc/Documentation/sysctl/vm.txt

  

写入此内容将导致内核从内存中删除干净的缓存,dentries和inode,从而导致内存空闲。

     

释放pagecache:

     

echo 1 > /proc/sys/vm/drop_caches

     

要释放dentries和inode:

     

echo 2 > /proc/sys/vm/drop_caches

     

释放pagecache,dentries和inode:

     

echo 3 > /proc/sys/vm/drop_caches

     

由于这是一个非破坏性的操作,并且脏对象不可用,因此用户应首先运行“sync”以确保释放所有缓存的对象。

答案 3 :(得分:8)

简短的回答:(复制粘贴友好)

DISK=/dev/sdX # <===ADJUST THIS===
sync
echo 3 > /proc/sys/vm/drop_caches
blockdev --flushbufs $DISK
hdparm -F $DISK

<强>解释

sync:从手册页:刷新文件系统缓冲区。强制将块更改为磁盘,更新超级块。

echo 3 > /proc/sys/vm/drop_cachefrom the kernel docs 这将导致内核删除干净的缓存

blockdev --flushbufs /dev/sda:从手册页:调用块设备ioctls [to]刷新缓冲区。

hdparm -F /dev/sda:从手册页:刷新驱动器上的写缓存缓冲区(较旧的驱动器可能无法实现此功能)

尽管blockdev和hdparm命令看起来与an answer above类似,但它们会向设备发出不同的ioctl。

可能更好的方式:

(我假设您已经格式化了磁盘,但如果要直接写入磁盘,则可以调整这些命令)

在第一个基准之前只运行一次:

MOUNT=/mnt/test # <===ADJUST THIS===
# create a file with psuedo-random data. We will read it
# to fill the read cache of the HDD with garbage
dd if=/dev/urandom of=$MOUNT/temp-hddread.tmp bs=64M count=16

每次要清空缓存时运行此命令:

DISK=/dev/sdX # <===ADJUST THIS===
MOUNT=/mnt/test # <===AND THIS===
# create a file with psuedo-random data to fill the write cache
# of the disk with garbage. Delete it afterwards it's not useful anymore
dd if=/dev/urandom of=$MOUNT/temp-hddwrite.tmp bs=64M count=16
rm $MOUNT/temp-hddwrite.tmp
# see short good enough answer above
sync
echo 3 > /proc/sys/vm/drop_caches
blockdev --flushbufs $DISK
hdparm -F $DISK
# read the file with pseudo-random data to fill any read-cache
# the disk may have with garbage
dd if=$MOUNT/temp-hddread.tmp of=/dev/null

完成后运行。

MOUNT=/mnt/test # <===ADJUST THIS===
# delete the temporary file with pseudo-random data
rm $MOUNT/temp-hddread.tmp

<强>解释

磁盘可能有一些H / W缓存。在发出blockdevhdparm命令时,某些设计或错误的磁盘可能无法清除其缓存。为了补偿我们写入和读取伪随机数据跳转到填充这些缓存,以便从中删除任何缓存数据。填充缓存需要多少数据取决于其大小。在上面的命令中我使用dd来读/写16 * 64MB = 1024MB,如果你的硬盘可能有更大的缓存,则调整参数(数据表和实验是你的朋友,指定高于实际大小的值没有坏处缓存)。我正在使用/ dev / urandom作为随机数据的来源,因为它很快,我们不关心 true 随机性(我们只关心高熵,因为磁盘固件可能在将数据存储到缓存之前使用压缩)。我从一开始就创建了/mnt/test/temp-hddread.tmp,每次想要读取足够的随机数据时都要使用它。每次我想写足够的随机数据时,我都在创建和删除/mnt/test/temp-hddwrite.tmp。

<强>积分

我根据现有答案的最佳部分写了这个答案。

答案 4 :(得分:2)

卸载并重新安装正在测试的磁盘将重置所有缓存和缓冲区。