mm/filemap: Pass the file_ra_state in the ractl

For readahead_expand(), we need to modify the file ra_state, so pass it
down by adding it to the ractl.  We have to do this because it's not always
the same as f_ra in the struct file that is already being passed.

Signed-off-by: Matthew Wilcox (Oracle) <willy@infradead.org>
Signed-off-by: David Howells <dhowells@redhat.com>
Tested-by: Jeff Layton <jlayton@kernel.org>
Tested-by: Dave Wysochanski <dwysocha@redhat.com>
Tested-By: Marc Dionne <marc.dionne@auristor.com>
Link: https://lore.kernel.org/r/20210407201857.3582797-2-willy@infradead.org/
Link: https://lore.kernel.org/r/161789067431.6155.8063840447229665720.stgit@warthog.procyon.org.uk/ # v6
This commit is contained in:
Matthew Wilcox (Oracle) 2021-04-07 21:18:55 +01:00 committed by David Howells
parent 73e10ded33
commit fcd9ae4f7f
7 changed files with 30 additions and 29 deletions

View File

@ -370,7 +370,7 @@ static struct page *ext4_read_merkle_tree_page(struct inode *inode,
pgoff_t index, pgoff_t index,
unsigned long num_ra_pages) unsigned long num_ra_pages)
{ {
DEFINE_READAHEAD(ractl, NULL, inode->i_mapping, index); DEFINE_READAHEAD(ractl, NULL, NULL, inode->i_mapping, index);
struct page *page; struct page *page;
index += ext4_verity_metadata_pos(inode) >> PAGE_SHIFT; index += ext4_verity_metadata_pos(inode) >> PAGE_SHIFT;

View File

@ -4051,7 +4051,7 @@ out:
static int redirty_blocks(struct inode *inode, pgoff_t page_idx, int len) static int redirty_blocks(struct inode *inode, pgoff_t page_idx, int len)
{ {
DEFINE_READAHEAD(ractl, NULL, inode->i_mapping, page_idx); DEFINE_READAHEAD(ractl, NULL, NULL, inode->i_mapping, page_idx);
struct address_space *mapping = inode->i_mapping; struct address_space *mapping = inode->i_mapping;
struct page *page; struct page *page;
pgoff_t redirty_idx = page_idx; pgoff_t redirty_idx = page_idx;

View File

@ -228,7 +228,7 @@ static struct page *f2fs_read_merkle_tree_page(struct inode *inode,
pgoff_t index, pgoff_t index,
unsigned long num_ra_pages) unsigned long num_ra_pages)
{ {
DEFINE_READAHEAD(ractl, NULL, inode->i_mapping, index); DEFINE_READAHEAD(ractl, NULL, NULL, inode->i_mapping, index);
struct page *page; struct page *page;
index += f2fs_verity_metadata_pos(inode) >> PAGE_SHIFT; index += f2fs_verity_metadata_pos(inode) >> PAGE_SHIFT;

View File

@ -812,20 +812,23 @@ static inline int add_to_page_cache(struct page *page,
* @file: The file, used primarily by network filesystems for authentication. * @file: The file, used primarily by network filesystems for authentication.
* May be NULL if invoked internally by the filesystem. * May be NULL if invoked internally by the filesystem.
* @mapping: Readahead this filesystem object. * @mapping: Readahead this filesystem object.
* @ra: File readahead state. May be NULL.
*/ */
struct readahead_control { struct readahead_control {
struct file *file; struct file *file;
struct address_space *mapping; struct address_space *mapping;
struct file_ra_state *ra;
/* private: use the readahead_* accessors instead */ /* private: use the readahead_* accessors instead */
pgoff_t _index; pgoff_t _index;
unsigned int _nr_pages; unsigned int _nr_pages;
unsigned int _batch_count; unsigned int _batch_count;
}; };
#define DEFINE_READAHEAD(rac, f, m, i) \ #define DEFINE_READAHEAD(ractl, f, r, m, i) \
struct readahead_control rac = { \ struct readahead_control ractl = { \
.file = f, \ .file = f, \
.mapping = m, \ .mapping = m, \
.ra = r, \
._index = i, \ ._index = i, \
} }
@ -833,10 +836,9 @@ struct readahead_control {
void page_cache_ra_unbounded(struct readahead_control *, void page_cache_ra_unbounded(struct readahead_control *,
unsigned long nr_to_read, unsigned long lookahead_count); unsigned long nr_to_read, unsigned long lookahead_count);
void page_cache_sync_ra(struct readahead_control *, struct file_ra_state *, void page_cache_sync_ra(struct readahead_control *, unsigned long req_count);
void page_cache_async_ra(struct readahead_control *, struct page *,
unsigned long req_count); unsigned long req_count);
void page_cache_async_ra(struct readahead_control *, struct file_ra_state *,
struct page *, unsigned long req_count);
/** /**
* page_cache_sync_readahead - generic file readahead * page_cache_sync_readahead - generic file readahead
@ -856,8 +858,8 @@ void page_cache_sync_readahead(struct address_space *mapping,
struct file_ra_state *ra, struct file *file, pgoff_t index, struct file_ra_state *ra, struct file *file, pgoff_t index,
unsigned long req_count) unsigned long req_count)
{ {
DEFINE_READAHEAD(ractl, file, mapping, index); DEFINE_READAHEAD(ractl, file, ra, mapping, index);
page_cache_sync_ra(&ractl, ra, req_count); page_cache_sync_ra(&ractl, req_count);
} }
/** /**
@ -879,8 +881,8 @@ void page_cache_async_readahead(struct address_space *mapping,
struct file_ra_state *ra, struct file *file, struct file_ra_state *ra, struct file *file,
struct page *page, pgoff_t index, unsigned long req_count) struct page *page, pgoff_t index, unsigned long req_count)
{ {
DEFINE_READAHEAD(ractl, file, mapping, index); DEFINE_READAHEAD(ractl, file, ra, mapping, index);
page_cache_async_ra(&ractl, ra, page, req_count); page_cache_async_ra(&ractl, page, req_count);
} }
/** /**

View File

@ -2832,7 +2832,7 @@ static struct file *do_sync_mmap_readahead(struct vm_fault *vmf)
struct file *file = vmf->vma->vm_file; struct file *file = vmf->vma->vm_file;
struct file_ra_state *ra = &file->f_ra; struct file_ra_state *ra = &file->f_ra;
struct address_space *mapping = file->f_mapping; struct address_space *mapping = file->f_mapping;
DEFINE_READAHEAD(ractl, file, mapping, vmf->pgoff); DEFINE_READAHEAD(ractl, file, ra, mapping, vmf->pgoff);
struct file *fpin = NULL; struct file *fpin = NULL;
unsigned int mmap_miss; unsigned int mmap_miss;
@ -2844,7 +2844,7 @@ static struct file *do_sync_mmap_readahead(struct vm_fault *vmf)
if (vmf->vma->vm_flags & VM_SEQ_READ) { if (vmf->vma->vm_flags & VM_SEQ_READ) {
fpin = maybe_unlock_mmap_for_io(vmf, fpin); fpin = maybe_unlock_mmap_for_io(vmf, fpin);
page_cache_sync_ra(&ractl, ra, ra->ra_pages); page_cache_sync_ra(&ractl, ra->ra_pages);
return fpin; return fpin;
} }

View File

@ -51,13 +51,12 @@ void unmap_page_range(struct mmu_gather *tlb,
void do_page_cache_ra(struct readahead_control *, unsigned long nr_to_read, void do_page_cache_ra(struct readahead_control *, unsigned long nr_to_read,
unsigned long lookahead_size); unsigned long lookahead_size);
void force_page_cache_ra(struct readahead_control *, struct file_ra_state *, void force_page_cache_ra(struct readahead_control *, unsigned long nr);
unsigned long nr);
static inline void force_page_cache_readahead(struct address_space *mapping, static inline void force_page_cache_readahead(struct address_space *mapping,
struct file *file, pgoff_t index, unsigned long nr_to_read) struct file *file, pgoff_t index, unsigned long nr_to_read)
{ {
DEFINE_READAHEAD(ractl, file, mapping, index); DEFINE_READAHEAD(ractl, file, &file->f_ra, mapping, index);
force_page_cache_ra(&ractl, &file->f_ra, nr_to_read); force_page_cache_ra(&ractl, nr_to_read);
} }
unsigned find_lock_entries(struct address_space *mapping, pgoff_t start, unsigned find_lock_entries(struct address_space *mapping, pgoff_t start,

View File

@ -272,9 +272,10 @@ void do_page_cache_ra(struct readahead_control *ractl,
* memory at once. * memory at once.
*/ */
void force_page_cache_ra(struct readahead_control *ractl, void force_page_cache_ra(struct readahead_control *ractl,
struct file_ra_state *ra, unsigned long nr_to_read) unsigned long nr_to_read)
{ {
struct address_space *mapping = ractl->mapping; struct address_space *mapping = ractl->mapping;
struct file_ra_state *ra = ractl->ra;
struct backing_dev_info *bdi = inode_to_bdi(mapping->host); struct backing_dev_info *bdi = inode_to_bdi(mapping->host);
unsigned long max_pages, index; unsigned long max_pages, index;
@ -433,10 +434,10 @@ static int try_context_readahead(struct address_space *mapping,
* A minimal readahead algorithm for trivial sequential/random reads. * A minimal readahead algorithm for trivial sequential/random reads.
*/ */
static void ondemand_readahead(struct readahead_control *ractl, static void ondemand_readahead(struct readahead_control *ractl,
struct file_ra_state *ra, bool hit_readahead_marker, bool hit_readahead_marker, unsigned long req_size)
unsigned long req_size)
{ {
struct backing_dev_info *bdi = inode_to_bdi(ractl->mapping->host); struct backing_dev_info *bdi = inode_to_bdi(ractl->mapping->host);
struct file_ra_state *ra = ractl->ra;
unsigned long max_pages = ra->ra_pages; unsigned long max_pages = ra->ra_pages;
unsigned long add_pages; unsigned long add_pages;
unsigned long index = readahead_index(ractl); unsigned long index = readahead_index(ractl);
@ -550,7 +551,7 @@ readit:
} }
void page_cache_sync_ra(struct readahead_control *ractl, void page_cache_sync_ra(struct readahead_control *ractl,
struct file_ra_state *ra, unsigned long req_count) unsigned long req_count)
{ {
bool do_forced_ra = ractl->file && (ractl->file->f_mode & FMODE_RANDOM); bool do_forced_ra = ractl->file && (ractl->file->f_mode & FMODE_RANDOM);
@ -560,7 +561,7 @@ void page_cache_sync_ra(struct readahead_control *ractl,
* read-ahead will do the right thing and limit the read to just the * read-ahead will do the right thing and limit the read to just the
* requested range, which we'll set to 1 page for this case. * requested range, which we'll set to 1 page for this case.
*/ */
if (!ra->ra_pages || blk_cgroup_congested()) { if (!ractl->ra->ra_pages || blk_cgroup_congested()) {
if (!ractl->file) if (!ractl->file)
return; return;
req_count = 1; req_count = 1;
@ -569,21 +570,20 @@ void page_cache_sync_ra(struct readahead_control *ractl,
/* be dumb */ /* be dumb */
if (do_forced_ra) { if (do_forced_ra) {
force_page_cache_ra(ractl, ra, req_count); force_page_cache_ra(ractl, req_count);
return; return;
} }
/* do read-ahead */ /* do read-ahead */
ondemand_readahead(ractl, ra, false, req_count); ondemand_readahead(ractl, false, req_count);
} }
EXPORT_SYMBOL_GPL(page_cache_sync_ra); EXPORT_SYMBOL_GPL(page_cache_sync_ra);
void page_cache_async_ra(struct readahead_control *ractl, void page_cache_async_ra(struct readahead_control *ractl,
struct file_ra_state *ra, struct page *page, struct page *page, unsigned long req_count)
unsigned long req_count)
{ {
/* no read-ahead */ /* no read-ahead */
if (!ra->ra_pages) if (!ractl->ra->ra_pages)
return; return;
/* /*
@ -604,7 +604,7 @@ void page_cache_async_ra(struct readahead_control *ractl,
return; return;
/* do read-ahead */ /* do read-ahead */
ondemand_readahead(ractl, ra, true, req_count); ondemand_readahead(ractl, true, req_count);
} }
EXPORT_SYMBOL_GPL(page_cache_async_ra); EXPORT_SYMBOL_GPL(page_cache_async_ra);