提交 e280026f 编写于 作者: Z Zhengyuan Liu 提交者: Shile Zhang

io_uring: track io length in async_list based on bytes

commit 9310a7ba6de8cce6209e3e8a3cdf733f824cdd9b upstream.

We are using PAGE_SIZE as the unit to determine if the total len in
async_list has exceeded max_pages, it's not fair for smaller io sizes.
For example, if we are doing 1k-size io streams, we will never exceed
max_pages since len >>= PAGE_SHIFT always gets zero. So use original
bytes to make it more accurate.
Signed-off-by: NZhengyuan Liu <liuzhengyuan@kylinos.cn>
Signed-off-by: NJens Axboe <axboe@kernel.dk>
Signed-off-by: NJoseph Qi <joseph.qi@linux.alibaba.com>
Reviewed-by: NXiaoguang Wang <xiaoguang.wang@linux.alibaba.com>
上级 6117e3bf
......@@ -202,7 +202,7 @@ struct async_list {
struct file *file;
off_t io_end;
size_t io_pages;
size_t io_len;
};
struct io_ring_ctx {
......@@ -1157,28 +1157,26 @@ static void io_async_list_note(int rw, struct io_kiocb *req, size_t len)
off_t io_end = kiocb->ki_pos + len;
if (filp == async_list->file && kiocb->ki_pos == async_list->io_end) {
unsigned long max_pages;
unsigned long max_bytes;
/* Use 8x RA size as a decent limiter for both reads/writes */
max_pages = filp->f_ra.ra_pages;
if (!max_pages)
max_pages = VM_MAX_READAHEAD >> (PAGE_SHIFT - 10);
max_pages *= 8;
/* If max pages are exceeded, reset the state */
len >>= PAGE_SHIFT;
if (async_list->io_pages + len <= max_pages) {
max_bytes = filp->f_ra.ra_pages << (PAGE_SHIFT + 3);
if (!max_bytes)
max_bytes = VM_READAHEAD_PAGES << (PAGE_SHIFT + 3);
/* If max len are exceeded, reset the state */
if (async_list->io_len + len <= max_bytes) {
req->flags |= REQ_F_SEQ_PREV;
async_list->io_pages += len;
async_list->io_len += len;
} else {
io_end = 0;
async_list->io_pages = 0;
async_list->io_len = 0;
}
}
/* New file? Reset state. */
if (async_list->file != filp) {
async_list->io_pages = 0;
async_list->io_len = 0;
async_list->file = filp;
}
async_list->io_end = io_end;
......
......@@ -26,6 +26,7 @@
#include <linux/page_ref.h>
#include <linux/memremap.h>
#include <linux/overflow.h>
#include <linux/sizes.h>
struct mempolicy;
struct anon_vma;
......@@ -2489,6 +2490,7 @@ void task_dirty_inc(struct task_struct *tsk);
/* readahead.c */
#define VM_MAX_READAHEAD 128 /* kbytes */
#define VM_MIN_READAHEAD 16 /* kbytes (includes current page) */
#define VM_READAHEAD_PAGES (SZ_128K / PAGE_SIZE)
int force_page_cache_readahead(struct address_space *mapping, struct file *filp,
pgoff_t offset, unsigned long nr_to_read);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册