如何避免内核页面缓存,在应用程序可以直接从磁盘读写数据?在内核中,如何设置?
A semantically similar (but deprecated) interface for block
devices is described in raw(8).
规范中的写缓存与页面缓存
无关。这里的缓存实际上是指集成在磁盘控制器中的RAM/NVRAM,这种内存不应与页面缓存混淆!
SET FEATURES(写缓存启用/禁用):由子命令代码02h或82h的SET FEATURES命令建立的写缓存启用/禁用设置。
HDIO_SET_WCACHE
ioctl可以控制它:static DEFINE_MUTEX(ide_disk_ioctl_mutex);
static const struct ide_ioctl_devset ide_disk_ioctl_settings[] = {
{ HDIO_GET_ADDRESS, HDIO_SET_ADDRESS, &ide_devset_address },
{ HDIO_GET_MULTCOUNT, HDIO_SET_MULTCOUNT, &ide_devset_multcount },
{ HDIO_GET_NOWERR, HDIO_SET_NOWERR, &ide_devset_nowerr },
{ HDIO_GET_WCACHE, HDIO_SET_WCACHE, &ide_devset_wcache },
{ HDIO_GET_ACOUSTIC, HDIO_SET_ACOUSTIC, &ide_devset_acoustic },
{ 0 }
};
int ide_disk_ioctl(ide_drive_t *drive, struct block_device *bdev, fmode_t mode,
unsigned int cmd, unsigned long arg)
{
int err;
mutex_lock(&ide_disk_ioctl_mutex);
err = ide_setting_ioctl(drive, bdev, cmd, arg, ide_disk_ioctl_settings);
if (err != -EOPNOTSUPP)
goto out;
err = generic_ide_ioctl(drive, bdev, cmd, arg);
out:
mutex_unlock(&ide_disk_ioctl_mutex);
return err;
}
hdparm -W0/1 /dev/sdx
方便地禁用/启用写缓存,这也会在内部调用HDIO_SET_WCACHE
:}
if (!wcache)
err = flush_wcache(fd);
if (ioctl(fd, HDIO_SET_WCACHE, wcache)) {
__u8 setcache[4] = {ATA_OP_SETFEATURES,0,0,0};
setcache[2] = wcache ? 0x02 : 0x82;
if (do_drive_cmd(fd, setcache, 0)) {
err = errno;
perror(" HDIO_DRIVE_CMD(setcache) failed");
}
}
static ssize_t queue_wc_show(struct request_queue *q, char *page)
{
if (test_bit(QUEUE_FLAG_WC, &q->queue_flags))
return sprintf(page, "write back\n");
return sprintf(page, "write through\n");
}
static ssize_t queue_wc_store(struct request_queue *q, const char *page,
size_t count)
{
int set = -1;
if (!strncmp(page, "write back", 10))
set = 1;
else if (!strncmp(page, "write through", 13) ||
!strncmp(page, "none", 4))
set = 0;
if (set == -1)
return -EINVAL;
if (set)
blk_queue_flag_set(QUEUE_FLAG_WC, q);
else
blk_queue_flag_clear(QUEUE_FLAG_WC, q);
return count;
}