Skip to content

Commit

Permalink
Use kmap_local_page instead of kmap_atomic (openzfs#16329)
Browse files Browse the repository at this point in the history
Changed zfs_k(un)map_atomic to zfs_k(un)map_local

Signed-off-by: Jason Lee <jasonlee@lanl.gov>
Reviewed-by: Alexander Motin <mav@FreeBSD.org>
Reviewed-by: Brian Atkinson <batkinson@lanl.gov>
  • Loading branch information
calccrypto committed Jul 17, 2024
1 parent 683ab27 commit ad00ff9
Show file tree
Hide file tree
Showing 5 changed files with 42 additions and 6 deletions.
23 changes: 23 additions & 0 deletions config/kernel-kmap-local-page.m4
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
dnl #
dnl # 5.11 API change
dnl # kmap_atomic() was deprecated in favor of kmap_local_page()
dnl #
AC_DEFUN([ZFS_AC_KERNEL_SRC_KMAP_LOCAL_PAGE], [
ZFS_LINUX_TEST_SRC([kmap_local_page], [
#include <linux/highmem.h>
],[
struct page page;
kmap_local_page(&page);
])
])

AC_DEFUN([ZFS_AC_KERNEL_KMAP_LOCAL_PAGE], [
AC_MSG_CHECKING([whether kmap_local_page exists])
ZFS_LINUX_TEST_RESULT([kmap_local_page], [
AC_MSG_RESULT(yes)
AC_DEFINE(HAVE_KMAP_LOCAL_PAGE, 1,
[kernel has kmap_local_page])
],[
AC_MSG_RESULT(no)
])
])
2 changes: 2 additions & 0 deletions config/kernel.m4
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,7 @@ AC_DEFUN([ZFS_AC_KERNEL_TEST_SRC], [
ZFS_AC_KERNEL_SRC_VFS_DEDUPE_FILE_RANGE
ZFS_AC_KERNEL_SRC_VFS_FILE_OPERATIONS_EXTEND
ZFS_AC_KERNEL_SRC_KMAP_ATOMIC_ARGS
ZFS_AC_KERNEL_SRC_KMAP_LOCAL_PAGE
ZFS_AC_KERNEL_SRC_FOLLOW_DOWN_ONE
ZFS_AC_KERNEL_SRC_MAKE_REQUEST_FN
ZFS_AC_KERNEL_SRC_GENERIC_IO_ACCT
Expand Down Expand Up @@ -280,6 +281,7 @@ AC_DEFUN([ZFS_AC_KERNEL_TEST_RESULT], [
ZFS_AC_KERNEL_VFS_DEDUPE_FILE_RANGE
ZFS_AC_KERNEL_VFS_FILE_OPERATIONS_EXTEND
ZFS_AC_KERNEL_KMAP_ATOMIC_ARGS
ZFS_AC_KERNEL_KMAP_LOCAL_PAGE
ZFS_AC_KERNEL_FOLLOW_DOWN_ONE
ZFS_AC_KERNEL_MAKE_REQUEST_FN
ZFS_AC_KERNEL_GENERIC_IO_ACCT
Expand Down
9 changes: 9 additions & 0 deletions include/os/linux/kernel/linux/kmap_compat.h
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,15 @@
#define zfs_kmap(page) kmap(page)
#define zfs_kunmap(page) kunmap(page)

#ifdef HAVE_KMAP_LOCAL_PAGE
/* 5.11 API change */
#define zfs_kmap_local(page) kmap_local_page(page)
#define zfs_kunmap_local(addr) kunmap_local(addr)
#else
#define zfs_kmap_local(page) kmap_atomic(page)
#define zfs_kunmap_local(addr) kunmap_atomic(addr)
#endif

/* 5.0 API change - no more 'type' argument for access_ok() */
#ifdef HAVE_ACCESS_OK_TYPE
#define zfs_access_ok(type, addr, size) access_ok(type, addr, size)
Expand Down
6 changes: 4 additions & 2 deletions module/os/linux/zfs/abd_os.c
Original file line number Diff line number Diff line change
Expand Up @@ -538,6 +538,8 @@ abd_alloc_zero_scatter(void)
#define zfs_kunmap_atomic(addr) do { (void)(addr); } while (0)
#define zfs_kmap(chunk) ((void *)chunk)
#define zfs_kunmap(chunk) ((void *)chunk)
#define zfs_kmap_local(chunk) ((void *)chunk)
#define zfs_kunmap_local(addr) do { (void)(addr); } while (0)
#define local_irq_save(flags) do { (void)(flags); } while (0)
#define local_irq_restore(flags) do { (void)(flags); } while (0)
#define nth_page(pg, i) \
Expand Down Expand Up @@ -1061,7 +1063,7 @@ abd_iter_map(struct abd_iter *aiter)
aiter->iter_mapsize = MIN(aiter->iter_sg->length - offset,
aiter->iter_abd->abd_size - aiter->iter_pos);

paddr = zfs_kmap_atomic(sg_page(aiter->iter_sg));
paddr = zfs_kmap_local(sg_page(aiter->iter_sg));
}

aiter->iter_mapaddr = (char *)paddr + offset;
Expand All @@ -1080,7 +1082,7 @@ abd_iter_unmap(struct abd_iter *aiter)

if (!abd_is_linear(aiter->iter_abd)) {
/* LINTED E_FUNC_SET_NOT_USED */
zfs_kunmap_atomic(aiter->iter_mapaddr - aiter->iter_offset);
zfs_kunmap_local(aiter->iter_mapaddr - aiter->iter_offset);
}

ASSERT3P(aiter->iter_mapaddr, !=, NULL);
Expand Down
8 changes: 4 additions & 4 deletions module/os/linux/zfs/zfs_uio.c
Original file line number Diff line number Diff line change
Expand Up @@ -143,15 +143,15 @@ zfs_uiomove_bvec_impl(void *p, size_t n, zfs_uio_rw_t rw, zfs_uio_t *uio)
void *paddr;
cnt = MIN(bv->bv_len - skip, n);

paddr = zfs_kmap_atomic(bv->bv_page);
paddr = zfs_kmap_local(bv->bv_page);
if (rw == UIO_READ) {
/* Copy from buffer 'p' to the bvec data */
memcpy(paddr + bv->bv_offset + skip, p, cnt);
} else {
/* Copy from bvec data to buffer 'p' */
memcpy(p, paddr + bv->bv_offset + skip, cnt);
}
zfs_kunmap_atomic(paddr);
zfs_kunmap_local(paddr);

skip += cnt;
if (skip == bv->bv_len) {
Expand All @@ -175,15 +175,15 @@ zfs_copy_bvec(void *p, size_t skip, size_t cnt, zfs_uio_rw_t rw,
{
void *paddr;

paddr = zfs_kmap_atomic(bv->bv_page);
paddr = zfs_kmap_local(bv->bv_page);
if (rw == UIO_READ) {
/* Copy from buffer 'p' to the bvec data */
memcpy(paddr + bv->bv_offset + skip, p, cnt);
} else {
/* Copy from bvec data to buffer 'p' */
memcpy(p, paddr + bv->bv_offset + skip, cnt);
}
zfs_kunmap_atomic(paddr);
zfs_kunmap_local(paddr);
}

/*
Expand Down

0 comments on commit ad00ff9

Please sign in to comment.