Commit 8fa8e538 authored by Matthew Wilcox's avatar Matthew Wilcox
Browse files

page cache: Convert filemap_range_has_page to XArray



Instead of calling find_get_pages_range() and putting any reference,
use xas_find() to iterate over any entries in the range, skipping the
shadow/swap entries.

Signed-off-by: default avatarMatthew Wilcox <willy@infradead.org>
parent 22ecdb4f
Loading
Loading
Loading
Loading
+19 −8
Original line number Diff line number Diff line
@@ -455,20 +455,31 @@ EXPORT_SYMBOL(filemap_flush);
bool filemap_range_has_page(struct address_space *mapping,
			   loff_t start_byte, loff_t end_byte)
{
	pgoff_t index = start_byte >> PAGE_SHIFT;
	pgoff_t end = end_byte >> PAGE_SHIFT;
	struct page *page;
	XA_STATE(xas, &mapping->i_pages, start_byte >> PAGE_SHIFT);
	pgoff_t max = end_byte >> PAGE_SHIFT;

	if (end_byte < start_byte)
		return false;

	if (mapping->nrpages == 0)
		return false;
	rcu_read_lock();
	for (;;) {
		page = xas_find(&xas, max);
		if (xas_retry(&xas, page))
			continue;
		/* Shadow entries don't count */
		if (xa_is_value(page))
			continue;
		/*
		 * We don't need to try to pin this page; we're about to
		 * release the RCU lock anyway.  It is enough to know that
		 * there was a page here recently.
		 */
		break;
	}
	rcu_read_unlock();

	if (!find_get_pages_range(mapping, &index, end, 1, &page))
		return false;
	put_page(page);
	return true;
	return page != NULL;
}
EXPORT_SYMBOL(filemap_range_has_page);