[PATCH] fs/hostfs: Replace kmap() with kmap_local_page()

Ira Weiny ira.weiny at intel.com
Fri Dec 30 15:50:16 PST 2022


On Thu, Oct 13, 2022 at 06:17:00PM +0200, Fabio M. De Francesco wrote:
> The use of kmap() is being deprecated in favor of kmap_local_page().
> 
> There are two main problems with kmap(): (1) It comes with an overhead as
> the mapping space is restricted and protected by a global lock for
> synchronization and (2) it also requires global TLB invalidation when the
> kmap’s pool wraps and it might block when the mapping space is fully
> utilized until a slot becomes available.
> 
> With kmap_local_page() the mappings are per thread, CPU local, can take
> page faults, and can be called from any context (including interrupts).
> It is faster than kmap() in kernels with HIGHMEM enabled. Furthermore,
> the tasks can be preempted and, when they are scheduled to run again, the
> kernel virtual addresses are restored and still valid.
> 
> Therefore, replace kmap() with kmap_local_page() in hostfs_kern.c, it
> being the only file with kmap() call sites currently left in fs/hostfs.
> 
> Cc: "Venkataramanan, Anirudh" <anirudh.venkataramanan at intel.com>
> Suggested-by: Ira Weiny <ira.weiny at intel.com>

What can we do to move this patch along?

I'm not an expert but it looks ok to me.

Reviewed-by: Ira Weiny <ira.weiny at intel.com>

> Signed-off-by: Fabio M. De Francesco <fmdefrancesco at gmail.com>
> ---
> 
> These changes are not tested in a 32 bits VM as I use to do with other more
> problematic conversions. Mere code inspection makes me reasonably think
> that the rules of local mappings are not violated by this conversion.
> 
> Furthermore, I have no idea how to test this code. If maintainers think
> that tests are absolutely necessary, any hints about how to perform them
> would be greatly appreciated.
> 
>  fs/hostfs/hostfs_kern.c | 15 ++++++++-------
>  1 file changed, 8 insertions(+), 7 deletions(-)
> 
> diff --git a/fs/hostfs/hostfs_kern.c b/fs/hostfs/hostfs_kern.c
> index 07881b76d42f..0c9f89352601 100644
> --- a/fs/hostfs/hostfs_kern.c
> +++ b/fs/hostfs/hostfs_kern.c
> @@ -412,7 +412,7 @@ static int hostfs_writepage(struct page *page, struct writeback_control *wbc)
>  	if (page->index >= end_index)
>  		count = inode->i_size & (PAGE_SIZE-1);
>  
> -	buffer = kmap(page);
> +	buffer = kmap_local_page(page);
>  
>  	err = write_file(HOSTFS_I(inode)->fd, &base, buffer, count);
>  	if (err != count) {
> @@ -428,9 +428,9 @@ static int hostfs_writepage(struct page *page, struct writeback_control *wbc)
>  	err = 0;
>  
>   out:
> -	kunmap(page);
> -
> +	kunmap_local(buffer);
>  	unlock_page(page);
> +
>  	return err;
>  }
>  
> @@ -441,7 +441,7 @@ static int hostfs_read_folio(struct file *file, struct folio *folio)
>  	loff_t start = page_offset(page);
>  	int bytes_read, ret = 0;
>  
> -	buffer = kmap(page);
> +	buffer = kmap_local_page(page);
>  	bytes_read = read_file(FILE_HOSTFS_I(file)->fd, &start, buffer,
>  			PAGE_SIZE);
>  	if (bytes_read < 0) {
> @@ -458,8 +458,9 @@ static int hostfs_read_folio(struct file *file, struct folio *folio)
>  
>   out:
>  	flush_dcache_page(page);
> -	kunmap(page);
> +	kunmap_local(buffer);
>  	unlock_page(page);
> +
>  	return ret;
>  }
>  
> @@ -484,9 +485,9 @@ static int hostfs_write_end(struct file *file, struct address_space *mapping,
>  	unsigned from = pos & (PAGE_SIZE - 1);
>  	int err;
>  
> -	buffer = kmap(page);
> +	buffer = kmap_local_page(page);
>  	err = write_file(FILE_HOSTFS_I(file)->fd, &pos, buffer + from, copied);
> -	kunmap(page);
> +	kunmap_local(buffer);
>  
>  	if (!PageUptodate(page) && err == PAGE_SIZE)
>  		SetPageUptodate(page);
> -- 
> 2.37.3
> 



More information about the linux-um mailing list