diff --git a/0001-LU-9859-libcfs-refactor-libcfs-initialization.patch b/0001-LU-9859-libcfs-refactor-libcfs-initialization.patch new file mode 100644 index 0000000000000000000000000000000000000000..1a5451a2e06f6621008c5cb4028b66b3c2cccff7 --- /dev/null +++ b/0001-LU-9859-libcfs-refactor-libcfs-initialization.patch @@ -0,0 +1,697 @@ +From 5d03173706ffa9cb934b25be98b7a7c952434e12 Mon Sep 17 00:00:00 2001 +From: "Mr. NeilBrown" +Date: Wed, 8 Nov 2023 21:15:09 -0500 +Subject: [PATCH 1/6] LU-9859 libcfs: refactor libcfs initialization. + +Many lustre modules depend on libcfs having initialized +properly, but do not explicit check that it did. +When lustre is built as discrete modules, this does not +cause a problem because if the libcfs module fails +initialization, the other modules don't even get loaded. + +When lustre is compiled into the kernel, all module_init() +routines get run, so they need to check the required initialization +succeeded. + +This patch splits out the initialization of libcfs into a new +libcfs_setup(), and has all modules call that. + +The misc_register() call is kept separate as it does not allocate any +resources and if it fails, it fails hard - no point in retrying. +Other set-up allocates resources and so is best delayed until they +are needed, and can be worth retrying. + +Ideally, the initialization would happen at mount time (or similar) +rather than at load time. Doing this requires each module to +check dependencies when they are activated rather than when +they are loaded. Achieving that is a much larger job that would +have to progress in stages. + +For now, this change ensures that if some initialization in libcfs +fails, other modules will fail-safe. + +Linux-commit: 64bf0b1a079d61e9e059b9dc7a58e064c7d994ae + +Change-Id: I6b5ecdba0defc6e033f78d8fc2b9be9e26c7f720 +Signed-off-by: Mr. NeilBrown +Signed-off-by: Greg Kroah-Hartman +Reviewed-on: https://review.whamcloud.com/c/fs/lustre-release/+/52700 +Tested-by: jenkins +Tested-by: Maloo +Reviewed-by: Timothy Day +Reviewed-by: Oleg Drokin +Signed-off-by: Xinliang Liu +--- + libcfs/include/libcfs/libcfs.h | 1 + + libcfs/include/libcfs/linux/linux-misc.h | 2 +- + libcfs/libcfs/linux/linux-prim.c | 6 ++- + libcfs/libcfs/module.c | 66 ++++++++++++++---------- + lnet/klnds/gnilnd/gnilnd.c | 4 ++ + lnet/klnds/kfilnd/kfilnd.c | 4 ++ + lnet/klnds/o2iblnd/o2iblnd.c | 4 ++ + lnet/klnds/socklnd/socklnd.c | 4 ++ + lnet/lnet/module.c | 4 ++ + lnet/selftest/module.c | 4 ++ + lustre/fid/fid_request.c | 7 ++- + lustre/fld/fld_request.c | 6 ++- + lustre/lfsck/lfsck_lib.c | 4 ++ + lustre/llite/super25.c | 4 ++ + lustre/lmv/lmv_obd.c | 6 +++ + lustre/lod/lod_dev.c | 4 ++ + lustre/lov/lov_obd.c | 4 ++ + lustre/mdc/mdc_request.c | 5 ++ + lustre/mdd/mdd_device.c | 4 ++ + lustre/mdt/mdt_handler.c | 5 ++ + lustre/mgc/mgc_request.c | 6 +++ + lustre/mgs/mgs_handler.c | 6 +++ + lustre/obdclass/class_obd.c | 4 ++ + lustre/obdecho/echo_client.c | 4 ++ + lustre/ofd/ofd_dev.c | 4 ++ + lustre/osc/osc_request.c | 4 ++ + lustre/osd-ldiskfs/osd_handler.c | 4 ++ + lustre/osd-zfs/osd_handler.c | 4 ++ + lustre/osp/osp_dev.c | 4 ++ + lustre/ost/ost_handler.c | 3 ++ + lustre/ptlrpc/ptlrpc_module.c | 4 ++ + lustre/quota/lquota_lib.c | 4 ++ + 32 files changed, 167 insertions(+), 32 deletions(-) + +diff --git a/libcfs/include/libcfs/libcfs.h b/libcfs/include/libcfs/libcfs.h +index 12d9dfd983..0c646f94cf 100644 +--- a/libcfs/include/libcfs/libcfs.h ++++ b/libcfs/include/libcfs/libcfs.h +@@ -67,6 +67,7 @@ + + typedef s32 timeout_t; + ++int libcfs_setup(void); + int libcfs_ioctl(unsigned int cmd, struct libcfs_ioctl_data *data); + + extern struct workqueue_struct *cfs_rehash_wq; +diff --git a/libcfs/include/libcfs/linux/linux-misc.h b/libcfs/include/libcfs/linux/linux-misc.h +index 2f285a53f6..9e4c7879de 100644 +--- a/libcfs/include/libcfs/linux/linux-misc.h ++++ b/libcfs/include/libcfs/linux/linux-misc.h +@@ -119,7 +119,7 @@ static inline int kref_read(const struct kref *kref) + } + #endif /* HAVE_KREF_READ */ + +-void cfs_arch_init(void); ++int cfs_arch_init(void); + void cfs_arch_exit(void); + + #ifndef container_of_safe +diff --git a/libcfs/libcfs/linux/linux-prim.c b/libcfs/libcfs/linux/linux-prim.c +index 8e0ee07eaa..660d328eed 100644 +--- a/libcfs/libcfs/linux/linux-prim.c ++++ b/libcfs/libcfs/linux/linux-prim.c +@@ -47,6 +47,7 @@ + #endif + + #include ++#include + #include + #include + #include +@@ -202,7 +203,7 @@ void __init init_libcfs_vfree_atomic(void) + } + } + +-void __init cfs_arch_init(void) ++int __init cfs_arch_init(void) + { + init_libcfs_vfree_atomic(); + +@@ -221,12 +222,15 @@ void __init cfs_arch_init(void) + SLAB_PANIC | SLAB_RECLAIM_ACCOUNT, + xarray_node_ctor); + #endif ++ return llcrypt_init(); + } + + void __exit cfs_arch_exit(void) + { + /* exit_libcfs_vfree_atomic */ + flush_scheduled_work(); ++ ++ llcrypt_exit(); + } + + int cfs_kernel_write(struct file *filp, const void *buf, size_t count, +diff --git a/libcfs/libcfs/module.c b/libcfs/libcfs/module.c +index 201b5e3056..fb7e8617a0 100644 +--- a/libcfs/libcfs/module.c ++++ b/libcfs/libcfs/module.c +@@ -660,17 +660,23 @@ void lnet_remove_debugfs(struct ctl_table *table) + } + EXPORT_SYMBOL_GPL(lnet_remove_debugfs); + ++static DEFINE_MUTEX(libcfs_startup); ++static int libcfs_active; ++ + static void *debugfs_state; +-static int __init libcfs_init(void) ++ ++int libcfs_setup(void) + { +- int rc; ++ int rc = -EINVAL; + +- cfs_arch_init(); ++ mutex_lock(&libcfs_startup); ++ if (libcfs_active) ++ goto out; + + rc = libcfs_debug_init(5 * 1024 * 1024); + if (rc < 0) { + pr_err("LustreError: libcfs_debug_init: rc = %d\n", rc); +- return (rc); ++ goto cleanup_lock; + } + + rc = cfs_cpu_init(); +@@ -687,30 +693,16 @@ static int __init libcfs_init(void) + + rc = cfs_crypto_register(); + if (rc) { +- CERROR("cfs_crypto_regster: error %d\n", rc); ++ CERROR("cfs_crypto_register: error %d\n", rc); + goto cleanup_wq; + } + +- lnet_insert_debugfs(lnet_table, THIS_MODULE, &debugfs_state); +- if (!IS_ERR_OR_NULL(lnet_debugfs_root)) +- lnet_insert_debugfs_links(lnet_debugfs_symlinks); +- +- rc = llcrypt_init(); +- if (rc) { +- CERROR("llcrypt_init: error %d\n", rc); +- goto cleanup_lnet; +- } +- +- CDEBUG(D_OTHER, "portals setup OK\n"); ++ CDEBUG(D_OTHER, "libcfs setup OK\n"); ++out: ++ libcfs_active = 1; ++ mutex_unlock(&libcfs_startup); + return 0; + +-cleanup_lnet: +- if (!IS_ERR_OR_NULL(lnet_debugfs_root)) { +- debugfs_remove_recursive(lnet_debugfs_root); +- lnet_debugfs_root = NULL; +- lnet_debugfs_fini(&debugfs_state); +- } +- cfs_crypto_unregister(); + cleanup_wq: + destroy_workqueue(cfs_rehash_wq); + cfs_rehash_wq = NULL; +@@ -718,6 +710,26 @@ cleanup_cpu: + cfs_cpu_fini(); + cleanup_debug: + libcfs_debug_cleanup(); ++cleanup_lock: ++ mutex_unlock(&libcfs_startup); ++ return rc; ++} ++EXPORT_SYMBOL(libcfs_setup); ++ ++static int __init libcfs_init(void) ++{ ++ int rc; ++ ++ rc = cfs_arch_init(); ++ if (rc < 0) { ++ CERROR("cfs_arch_init: error %d\n", rc); ++ return rc; ++ } ++ ++ lnet_insert_debugfs(lnet_table, THIS_MODULE, &debugfs_state); ++ if (!IS_ERR_OR_NULL(lnet_debugfs_root)) ++ lnet_insert_debugfs_links(lnet_debugfs_symlinks); ++ + return rc; + } + +@@ -734,12 +746,8 @@ static void __exit libcfs_exit(void) + CDEBUG(D_MALLOC, "before Portals cleanup: kmem %lld\n", + libcfs_kmem_read()); + +- llcrypt_exit(); +- +- if (cfs_rehash_wq) { ++ if (cfs_rehash_wq) + destroy_workqueue(cfs_rehash_wq); +- cfs_rehash_wq = NULL; +- } + + cfs_crypto_unregister(); + +@@ -753,6 +761,8 @@ static void __exit libcfs_exit(void) + rc = libcfs_debug_cleanup(); + if (rc) + pr_err("LustreError: libcfs_debug_cleanup: rc = %d\n", rc); ++ ++ cfs_arch_exit(); + } + + MODULE_AUTHOR("OpenSFS, Inc. "); +diff --git a/lnet/klnds/gnilnd/gnilnd.c b/lnet/klnds/gnilnd/gnilnd.c +index c320d7db41..d9bc39dc70 100644 +--- a/lnet/klnds/gnilnd/gnilnd.c ++++ b/lnet/klnds/gnilnd/gnilnd.c +@@ -2821,6 +2821,10 @@ static int __init kgnilnd_init(void) + kgnilnd_insert_sysctl(); + kgnilnd_proc_init(); + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + lnet_register_lnd(&the_kgnilnd); + + return 0; +diff --git a/lnet/klnds/kfilnd/kfilnd.c b/lnet/klnds/kfilnd/kfilnd.c +index e3d7732790..69cc3ceb5e 100644 +--- a/lnet/klnds/kfilnd/kfilnd.c ++++ b/lnet/klnds/kfilnd/kfilnd.c +@@ -511,6 +511,10 @@ static int __init kfilnd_init(void) + if (rc) + goto err; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + /* Do any initialization of the transaction system */ + rc = kfilnd_tn_init(); + if (rc) { +diff --git a/lnet/klnds/o2iblnd/o2iblnd.c b/lnet/klnds/o2iblnd/o2iblnd.c +index 4f321b67d3..a5eb2ebf0b 100644 +--- a/lnet/klnds/o2iblnd/o2iblnd.c ++++ b/lnet/klnds/o2iblnd/o2iblnd.c +@@ -3932,6 +3932,10 @@ static int __init ko2iblnd_init(void) + if (rc != 0) + return rc; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + lnet_register_lnd(&the_o2iblnd); + + return 0; +diff --git a/lnet/klnds/socklnd/socklnd.c b/lnet/klnds/socklnd/socklnd.c +index e48a1d7b73..936a176f9c 100644 +--- a/lnet/klnds/socklnd/socklnd.c ++++ b/lnet/klnds/socklnd/socklnd.c +@@ -2640,6 +2640,10 @@ static int __init ksocklnd_init(void) + if (rc != 0) + return rc; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + lnet_register_lnd(&the_ksocklnd); + + return 0; +diff --git a/lnet/lnet/module.c b/lnet/lnet/module.c +index aac5522aa4..b0fe719241 100644 +--- a/lnet/lnet/module.c ++++ b/lnet/lnet/module.c +@@ -429,7 +429,11 @@ static struct miscdevice lnet_dev = { + static int __init lnet_init(void) + { + int rc; ++ + ENTRY; ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; + + rc = lnet_lib_init(); + if (rc != 0) { +diff --git a/lnet/selftest/module.c b/lnet/selftest/module.c +index 93cb266369..ee958d8dc6 100644 +--- a/lnet/selftest/module.c ++++ b/lnet/selftest/module.c +@@ -92,6 +92,10 @@ lnet_selftest_init(void) + int rc = -ENOMEM; + int i; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + lst_serial_wq = alloc_ordered_workqueue("lst_s", 0); + if (!lst_serial_wq) { + CERROR("Failed to create serial WI scheduler for LST\n"); +diff --git a/lustre/fid/fid_request.c b/lustre/fid/fid_request.c +index ed6cd8526d..3fe55eb931 100644 +--- a/lustre/fid/fid_request.c ++++ b/lustre/fid/fid_request.c +@@ -493,8 +493,13 @@ EXPORT_SYMBOL(client_fid_fini); + static int __init fid_init(void) + { + struct dentry *de; ++ int rc; ++ ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; + #ifdef HAVE_SERVER_SUPPORT +- int rc = fid_server_mod_init(); ++ rc = fid_server_mod_init(); + + if (rc) + return rc; +diff --git a/lustre/fld/fld_request.c b/lustre/fld/fld_request.c +index 5210efeb66..f5460e0a53 100644 +--- a/lustre/fld/fld_request.c ++++ b/lustre/fld/fld_request.c +@@ -515,9 +515,13 @@ void fld_client_flush(struct lu_client_fld *fld) + + static int __init fld_init(void) + { +-#ifdef HAVE_SERVER_SUPPORT + int rc; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ ++#ifdef HAVE_SERVER_SUPPORT + rc = fld_server_mod_init(); + if (rc) + return rc; +diff --git a/lustre/lfsck/lfsck_lib.c b/lustre/lfsck/lfsck_lib.c +index 4126509b8e..7617aa41a8 100644 +--- a/lustre/lfsck/lfsck_lib.c ++++ b/lustre/lfsck/lfsck_lib.c +@@ -3964,6 +3964,10 @@ static int __init lfsck_init(void) + { + int rc; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + lfsck_key_init_generic(&lfsck_thread_key, NULL); + rc = lu_context_key_register(&lfsck_thread_key); + if (!rc) { +diff --git a/lustre/llite/super25.c b/lustre/llite/super25.c +index 6622625544..367b34ff20 100644 +--- a/lustre/llite/super25.c ++++ b/lustre/llite/super25.c +@@ -230,6 +230,10 @@ static int __init lustre_init(void) + BUILD_BUG_ON(sizeof(LUSTRE_VOLATILE_HDR) != + LUSTRE_VOLATILE_HDR_LEN + 1); + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + /* print an address of _any_ initialized kernel symbol from this + * module, to allow debugging with gdb that doesn't support data + * symbols from modules.*/ +diff --git a/lustre/lmv/lmv_obd.c b/lustre/lmv/lmv_obd.c +index 8a6fb6c3a7..2841ba33bd 100644 +--- a/lustre/lmv/lmv_obd.c ++++ b/lustre/lmv/lmv_obd.c +@@ -4263,6 +4263,12 @@ static const struct md_ops lmv_md_ops = { + + static int __init lmv_init(void) + { ++ int rc; ++ ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + return class_register_type(&lmv_obd_ops, &lmv_md_ops, true, + LUSTRE_LMV_NAME, NULL); + } +diff --git a/lustre/lod/lod_dev.c b/lustre/lod/lod_dev.c +index 25bfb80515..b70245f5c2 100644 +--- a/lustre/lod/lod_dev.c ++++ b/lustre/lod/lod_dev.c +@@ -2799,6 +2799,10 @@ static int __init lod_init(void) + struct obd_type *sym; + int rc; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + rc = lu_kmem_init(lod_caches); + if (rc) + return rc; +diff --git a/lustre/lov/lov_obd.c b/lustre/lov/lov_obd.c +index a0c0cf7dda..8ef710d9f7 100644 +--- a/lustre/lov/lov_obd.c ++++ b/lustre/lov/lov_obd.c +@@ -1357,6 +1357,10 @@ static int __init lov_init(void) + * symbols from modules.*/ + CDEBUG(D_INFO, "Lustre LOV module (%p).\n", &lov_caches); + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + rc = lu_kmem_init(lov_caches); + if (rc) + return rc; +diff --git a/lustre/mdc/mdc_request.c b/lustre/mdc/mdc_request.c +index 6e501d1e6a..f878df5693 100644 +--- a/lustre/mdc/mdc_request.c ++++ b/lustre/mdc/mdc_request.c +@@ -3065,6 +3065,11 @@ struct class *mdc_changelog_class; + static int __init mdc_init(void) + { + int rc = 0; ++ ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + rc = alloc_chrdev_region(&mdc_changelog_dev, 0, + MDC_CHANGELOG_DEV_COUNT, + MDC_CHANGELOG_DEV_NAME); +diff --git a/lustre/mdd/mdd_device.c b/lustre/mdd/mdd_device.c +index f2374684d0..21b5f57366 100644 +--- a/lustre/mdd/mdd_device.c ++++ b/lustre/mdd/mdd_device.c +@@ -2426,6 +2426,10 @@ static int __init mdd_init(void) + { + int rc; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + rc = lu_kmem_init(mdd_caches); + if (rc) + return rc; +diff --git a/lustre/mdt/mdt_handler.c b/lustre/mdt/mdt_handler.c +index 24b9e81e75..55ac2b7a18 100644 +--- a/lustre/mdt/mdt_handler.c ++++ b/lustre/mdt/mdt_handler.c +@@ -7994,6 +7994,11 @@ static int __init mdt_init(void) + FID_NOBRACE_LEN + 1); + BUILD_BUG_ON(sizeof("[0x0123456789ABCDEF:0x01234567:0x01234567]") != + FID_LEN + 1); ++ ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + rc = lu_kmem_init(mdt_caches); + if (rc) + return rc; +diff --git a/lustre/mgc/mgc_request.c b/lustre/mgc/mgc_request.c +index 0d4777cf02..6e38a7fc72 100644 +--- a/lustre/mgc/mgc_request.c ++++ b/lustre/mgc/mgc_request.c +@@ -1970,6 +1970,12 @@ MODULE_PARM_DESC(mgc_requeue_timeout_min, "Minimal requeue time to refresh logs" + + static int __init mgc_init(void) + { ++ int rc; ++ ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + return class_register_type(&mgc_obd_ops, NULL, false, + LUSTRE_MGC_NAME, NULL); + } +diff --git a/lustre/mgs/mgs_handler.c b/lustre/mgs/mgs_handler.c +index e8452e091d..2c1ed34fd9 100644 +--- a/lustre/mgs/mgs_handler.c ++++ b/lustre/mgs/mgs_handler.c +@@ -1756,6 +1756,12 @@ static const struct obd_ops mgs_obd_device_ops = { + + static int __init mgs_init(void) + { ++ int rc; ++ ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + return class_register_type(&mgs_obd_device_ops, NULL, true, + LUSTRE_MGS_NAME, &mgs_device_type); + } +diff --git a/lustre/obdclass/class_obd.c b/lustre/obdclass/class_obd.c +index 8d2ebc203e..43deebdfd8 100644 +--- a/lustre/obdclass/class_obd.c ++++ b/lustre/obdclass/class_obd.c +@@ -707,6 +707,10 @@ static int __init obdclass_init(void) + + register_oom_notifier(&obdclass_oom); + ++ err = libcfs_setup(); ++ if (err) ++ return err; ++ + err = obd_init_checks(); + if (err) + return err; +diff --git a/lustre/obdecho/echo_client.c b/lustre/obdecho/echo_client.c +index 6c2f925054..1cf1a75399 100644 +--- a/lustre/obdecho/echo_client.c ++++ b/lustre/obdecho/echo_client.c +@@ -2585,6 +2585,10 @@ static int __init obdecho_init(void) + + LASSERT(PAGE_SIZE % OBD_ECHO_BLOCK_SIZE == 0); + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + # ifdef HAVE_SERVER_SUPPORT + rc = echo_persistent_pages_init(); + if (rc != 0) +diff --git a/lustre/ofd/ofd_dev.c b/lustre/ofd/ofd_dev.c +index fe5660d445..bcdae06f1b 100644 +--- a/lustre/ofd/ofd_dev.c ++++ b/lustre/ofd/ofd_dev.c +@@ -3263,6 +3263,10 @@ static int __init ofd_init(void) + { + int rc; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + rc = lu_kmem_init(ofd_caches); + if (rc) + return rc; +diff --git a/lustre/osc/osc_request.c b/lustre/osc/osc_request.c +index 2d5afc8b79..d64e54c71f 100644 +--- a/lustre/osc/osc_request.c ++++ b/lustre/osc/osc_request.c +@@ -3947,6 +3947,10 @@ static int __init osc_init(void) + * symbols from modules.*/ + CDEBUG(D_INFO, "Lustre OSC module (%p).\n", &osc_caches); + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + rc = lu_kmem_init(osc_caches); + if (rc) + RETURN(rc); +diff --git a/lustre/osd-ldiskfs/osd_handler.c b/lustre/osd-ldiskfs/osd_handler.c +index 68ae68a271..e42fff125b 100644 +--- a/lustre/osd-ldiskfs/osd_handler.c ++++ b/lustre/osd-ldiskfs/osd_handler.c +@@ -9000,6 +9000,10 @@ static int __init osd_init(void) + BUILD_BUG_ON(sizeof(struct osd_thread_info) > PAGE_SIZE); + #endif + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + osd_oi_mod_init(); + + rc = lu_kmem_init(ldiskfs_caches); +diff --git a/lustre/osd-zfs/osd_handler.c b/lustre/osd-zfs/osd_handler.c +index c29bae6a91..9c24dd423e 100644 +--- a/lustre/osd-zfs/osd_handler.c ++++ b/lustre/osd-zfs/osd_handler.c +@@ -1655,6 +1655,10 @@ static int __init osd_init(void) + { + int rc; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + rc = osd_options_init(); + if (rc) + return rc; +diff --git a/lustre/osp/osp_dev.c b/lustre/osp/osp_dev.c +index 5460ff7fa6..69c9068569 100644 +--- a/lustre/osp/osp_dev.c ++++ b/lustre/osp/osp_dev.c +@@ -1892,6 +1892,10 @@ static int __init osp_init(void) + struct obd_type *sym; + int rc; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + rc = lu_kmem_init(osp_caches); + if (rc) + return rc; +diff --git a/lustre/ost/ost_handler.c b/lustre/ost/ost_handler.c +index 87934043a3..b9e8ff8c3c 100644 +--- a/lustre/ost/ost_handler.c ++++ b/lustre/ost/ost_handler.c +@@ -424,6 +424,9 @@ static int __init ost_init(void) + int rc; + + ENTRY; ++ rc = libcfs_setup(); ++ if (rc) ++ RETURN(rc); + + rc = class_register_type(&ost_obd_ops, NULL, false, + LUSTRE_OSS_NAME, NULL); +diff --git a/lustre/ptlrpc/ptlrpc_module.c b/lustre/ptlrpc/ptlrpc_module.c +index c21fa627fe..21a1ae0500 100644 +--- a/lustre/ptlrpc/ptlrpc_module.c ++++ b/lustre/ptlrpc/ptlrpc_module.c +@@ -55,6 +55,10 @@ static __init int ptlrpc_init(void) + ptlrpc_init_xid(); + lustre_msg_early_size_init(); + ++ rc = libcfs_setup(); ++ if (rc) ++ RETURN(rc); ++ + rc = req_layout_init(); + if (rc) + RETURN(rc); +diff --git a/lustre/quota/lquota_lib.c b/lustre/quota/lquota_lib.c +index 8bbc58b359..12f175d4aa 100644 +--- a/lustre/quota/lquota_lib.c ++++ b/lustre/quota/lquota_lib.c +@@ -356,6 +356,10 @@ static int __init lquota_init(void) + int rc; + ENTRY; + ++ rc = libcfs_setup(); ++ if (rc) ++ return rc; ++ + lquota_key_init_generic(&lquota_thread_key, NULL); + lu_context_key_register(&lquota_thread_key); + +-- +2.33.0 + diff --git a/LU-16802-build-iov_iter_iovec-class_create-get_expir.patch b/0002-LU-16802-build-compatibility-for-6.4-kernels.patch similarity index 72% rename from LU-16802-build-iov_iter_iovec-class_create-get_expir.patch rename to 0002-LU-16802-build-compatibility-for-6.4-kernels.patch index d8dd89071f916b0e6c56c87a69090cbf6f6e0722..4a288df124ab1ca344ec69cd707781f186be21fa 100644 --- a/LU-16802-build-iov_iter_iovec-class_create-get_expir.patch +++ b/0002-LU-16802-build-compatibility-for-6.4-kernels.patch @@ -1,7 +1,7 @@ -From 13bab88098587ad08e5b56450a21f34003eaf6d3 Mon Sep 17 00:00:00 2001 +From 5567d2bf8ab9841842ec875ffe9dc01efe1396ac Mon Sep 17 00:00:00 2001 From: Shaun Tancheff -Date: Tue, 11 Jul 2023 18:41:13 +0700 -Subject: [PATCH] LU-16802 build: iov_iter_iovec, class_create, get_expiry +Date: Fri, 27 Oct 2023 01:21:13 -0500 +Subject: [PATCH 2/6] LU-16802 build: compatibility for 6.4 kernels linux kernel v6.3-rc4-32-g6eb203e1a868 iov_iter: remove iov_iter_iovec() @@ -11,8 +11,10 @@ Provide a replacement iov_iter_iovec() when one is not provided. linux kernel v6.3-rc4-34-g747b1f65d39a iov_iter: overlay struct iovec and ubuf/len -This renames iov_iter member iov to __iov. +This renames iov_iter member iov to __iov and provides the +iov_iter() accessor. Define __iov as iov when __iov not present. +Provide an iov_iter() for older kernels. linux kernel v6.3-rc1-13-g1aaba11da9aa driver core: class: remove module * from class_create() @@ -38,19 +40,28 @@ Test-Parameters: trivial HPE-bug-id: LUS-11614 Signed-off-by: Shaun Tancheff Change-Id: I765d6257eec8b5a9bf1bd5947f03370eb9df1625 +Reviewed-on: https://review.whamcloud.com/c/fs/lustre-release/+/50875 +Tested-by: jenkins +Tested-by: Maloo +Reviewed-by: Oleg Drokin +Reviewed-by: Andreas Dilger +Reviewed-by: Petros Koutoupis +Reviewed-by: xinliang --- - lustre/autoconf/lustre-core.m4 | 117 +++++++++++++++++++++ + lustre/autoconf/lustre-core.m4 | 122 ++++++++++++++++++++++ lustre/include/lustre_compat.h | 18 ++-- + lustre/llite/rw26.c | 2 +- lustre/mdc/mdc_request.c | 2 +- + lustre/obdclass/cl_io.c | 12 +-- lustre/ofd/ofd_access_log.c | 2 +- - lustre/ptlrpc/gss/gss_svc_upcall.c | 159 +++++++++++++++-------------- - 5 files changed, 213 insertions(+), 85 deletions(-) + lustre/ptlrpc/gss/gss_svc_upcall.c | 161 +++++++++++++++-------------- + 7 files changed, 227 insertions(+), 92 deletions(-) diff --git a/lustre/autoconf/lustre-core.m4 b/lustre/autoconf/lustre-core.m4 -index b2b9ebcd86..38c3906abf 100644 +index d71694c46f..664419bcab 100644 --- a/lustre/autoconf/lustre-core.m4 +++ b/lustre/autoconf/lustre-core.m4 -@@ -3866,6 +3866,111 @@ AC_DEFUN([LC_HAVE_LOCKS_LOCK_FILE_WAIT_IN_FILELOCK], [ +@@ -3983,6 +3983,116 @@ AC_DEFUN([LC_HAVE_LOCKS_LOCK_FILE_WAIT_IN_FILELOCK], [ ]) ]) # LC_HAVE_LOCKS_LOCK_FILE_WAIT_IN_FILELOCK @@ -84,6 +95,7 @@ index b2b9ebcd86..38c3906abf 100644 +# linux kernel v6.3-rc4-34-g747b1f65d39a +# iov_iter: overlay struct iovec and ubuf/len +# This renames iov_iter member iov to __iov and now __iov == __ubuf_iovec ++# And provides the iov_iter() accessor to return __iov or __ubuf_iovec +# +AC_DEFUN([LC_SRC_HAVE_IOVEC_WITH_IOV_MEMBER], [ + LB2_LINUX_TEST_SRC([iov_iter_has___iov_member], [ @@ -92,17 +104,21 @@ index b2b9ebcd86..38c3906abf 100644 + struct iov_iter iter = { }; + size_t len __attribute__ ((unused)); + -+ len = iter->__iov->iov_len; ++ len = iter.__iov->iov_len; + ],[-Werror]) +]) +AC_DEFUN([LC_HAVE_IOVEC_WITH_IOV_MEMBER], [ + AC_MSG_CHECKING([if 'iov_iter_iovec' is available]) + LB2_LINUX_TEST_RESULT([iov_iter_has___iov_member], [ + AC_DEFINE(HAVE___IOV_MEMBER, __iov, -+ ['iov_iter' has '__iov' member]) ++ ['struct iov_iter' has '__iov' member]) ++ AC_DEFINE(HAVE_ITER_IOV, 1, ++ [iter_iov() is available]) + ],[ ++ AC_DEFINE(iter_iov(iter), (iter)->__iov, ++ ['iov_iter()' provides iov]) + AC_DEFINE(__iov, iov, -+ ['iov_iter' has 'iov' member]) ++ ['struct iov_iter' has 'iov' member]) + ]) +]) # LC_HAVE_IOVEC_WITH_IOV_MEMBER + @@ -134,7 +150,7 @@ index b2b9ebcd86..38c3906abf 100644 + [class_create(THIS_MODULE, (name))], + ['class_create' expects module arg]) + ]) -+]) # LC_HAVE_IOVEC_WITH_IOV_MEMBER ++]) # LC_HAVE_CLASS_CREATE_MODULE_ARG + +# +# LC_HAVE_GET_EXPIRY_TIME64_T @@ -157,12 +173,12 @@ index b2b9ebcd86..38c3906abf 100644 + AC_DEFINE(HAVE_GET_EXPIRY_2ARGS, 1, + ['get_expiry' takes time64_t]) + ]) -+]) # LC_HAVE_IOVEC_WITH_IOV_MEMBER ++]) # LC_HAVE_GET_EXPIRY_TIME64_T + # # LC_PROG_LINUX # -@@ -4116,6 +4221,12 @@ AC_DEFUN([LC_PROG_LINUX_SRC], [ +@@ -4242,6 +4352,12 @@ AC_DEFUN([LC_PROG_LINUX_SRC], [ LC_SRC_HAVE_LOCKS_LOCK_FILE_WAIT_IN_FILELOCK LC_SRC_HAVE_U64_CAPABILITY @@ -175,7 +191,7 @@ index b2b9ebcd86..38c3906abf 100644 # kernel patch to extend integrity interface LC_SRC_BIO_INTEGRITY_PREP_FN ]) -@@ -4384,6 +4495,12 @@ AC_DEFUN([LC_PROG_LINUX_RESULTS], [ +@@ -4521,6 +4637,12 @@ AC_DEFUN([LC_PROG_LINUX_RESULTS], [ LC_HAVE_LOCKS_LOCK_FILE_WAIT_IN_FILELOCK LC_HAVE_U64_CAPABILITY @@ -189,11 +205,11 @@ index b2b9ebcd86..38c3906abf 100644 LC_BIO_INTEGRITY_PREP_FN ]) diff --git a/lustre/include/lustre_compat.h b/lustre/include/lustre_compat.h -index 3040cc22ce..c99c8d3730 100644 +index 1d05e871c7..3c5c0a000e 100644 --- a/lustre/include/lustre_compat.h +++ b/lustre/include/lustre_compat.h -@@ -313,20 +313,22 @@ static inline void iov_iter_truncate(struct iov_iter *i, u64 count) - # define SB_NODIRATIME MS_NODIRATIME +@@ -336,20 +336,22 @@ static inline void iov_iter_truncate(struct iov_iter *i, u64 count) + # define SB_KERNMOUNT MS_KERNMOUNT #endif -#ifndef HAVE_FILE_OPERATIONS_READ_WRITE_ITER @@ -223,11 +239,24 @@ index 3040cc22ce..c99c8d3730 100644 #define iov_for_each(iov, iter, start) \ for (iter = (start); \ +diff --git a/lustre/llite/rw26.c b/lustre/llite/rw26.c +index 142a69381b..a22fa10e3a 100644 +--- a/lustre/llite/rw26.c ++++ b/lustre/llite/rw26.c +@@ -596,7 +596,7 @@ ll_direct_IO_impl(struct kiocb *iocb, struct iov_iter *iter, int rw) + count = result; + } else { + /* same calculation used in ll_get_user_pages */ +- count = min_t(size_t, count, iter->iov->iov_len); ++ count = min_t(size_t, count, iter_iov(iter)->iov_len); + result = ll_allocate_dio_buffer(pvec, count); + /* allocate_dio_buffer returns number of pages or + * error, so do not set count = result diff --git a/lustre/mdc/mdc_request.c b/lustre/mdc/mdc_request.c -index 086d13e670..2680d941f5 100644 +index f878df5693..a54260b1fe 100644 --- a/lustre/mdc/mdc_request.c +++ b/lustre/mdc/mdc_request.c -@@ -3037,7 +3037,7 @@ static int __init mdc_init(void) +@@ -3076,7 +3076,7 @@ static int __init mdc_init(void) if (rc) return rc; @@ -236,6 +265,54 @@ index 086d13e670..2680d941f5 100644 if (IS_ERR(mdc_changelog_class)) { rc = PTR_ERR(mdc_changelog_class); goto out_dev; +diff --git a/lustre/obdclass/cl_io.c b/lustre/obdclass/cl_io.c +index 0cf0943adf..40350080a4 100644 +--- a/lustre/obdclass/cl_io.c ++++ b/lustre/obdclass/cl_io.c +@@ -1211,7 +1211,7 @@ static void cl_sub_dio_end(const struct lu_env *env, struct cl_sync_io *anchor) + /* save the iovec pointer before it's modified by + * ll_dio_user_copy + */ +- struct iovec *tmp = (struct iovec *) sdio->csd_iter.iov; ++ struct iovec *tmp = (struct iovec *) sdio->csd_iter.__iov; + + CDEBUG(D_VFSTRACE, + "finishing unaligned dio %s aio->cda_bytes %ld\n", +@@ -1227,7 +1227,7 @@ static void cl_sub_dio_end(const struct lu_env *env, struct cl_sync_io *anchor) + * because we have the unmodified iovec pointer + */ + OBD_FREE_PTR(tmp); +- sdio->csd_iter.iov = NULL; ++ sdio->csd_iter.__iov = NULL; + } else { + /* unaligned DIO does not get user pages, so it doesn't have to + * release them, but aligned I/O must +@@ -1306,13 +1306,13 @@ struct cl_sub_dio *cl_sub_dio_alloc(struct cl_dio_aio *ll_aio, + * separate thread requires a local copy of the iovec + */ + memcpy(&sdio->csd_iter, iter, sizeof(struct iov_iter)); +- OBD_ALLOC_PTR(sdio->csd_iter.iov); +- if (sdio->csd_iter.iov == NULL) { ++ OBD_ALLOC_PTR(sdio->csd_iter.__iov); ++ if (sdio->csd_iter.__iov == NULL) { + cl_sub_dio_free(sdio); + sdio = NULL; + goto out; + } +- memcpy((void *) sdio->csd_iter.iov, iter->iov, ++ memcpy((void *) sdio->csd_iter.__iov, iter->__iov, + sizeof(struct iovec)); + } + } +@@ -1335,7 +1335,7 @@ EXPORT_SYMBOL(cl_dio_aio_free); + void cl_sub_dio_free(struct cl_sub_dio *sdio) + { + if (sdio) { +- void *tmp = (void *)sdio->csd_iter.iov; ++ void *tmp = (void *)sdio->csd_iter.__iov; + + if (tmp) { + LASSERT(sdio->csd_unaligned); diff --git a/lustre/ofd/ofd_access_log.c b/lustre/ofd/ofd_access_log.c index 088ec66a2a..1024c08ad1 100644 --- a/lustre/ofd/ofd_access_log.c @@ -250,10 +327,10 @@ index 088ec66a2a..1024c08ad1 100644 rc = PTR_ERR(oal_log_class); goto out_dev; diff --git a/lustre/ptlrpc/gss/gss_svc_upcall.c b/lustre/ptlrpc/gss/gss_svc_upcall.c -index ea94cb663f..b82e6f7cb9 100644 +index dbd9efd7bc..d7f2c8c6f5 100644 --- a/lustre/ptlrpc/gss/gss_svc_upcall.c +++ b/lustre/ptlrpc/gss/gss_svc_upcall.c -@@ -71,6 +71,15 @@ +@@ -73,6 +73,15 @@ #include "gss_api.h" #include "gss_crypto.h" @@ -269,7 +346,7 @@ index ea94cb663f..b82e6f7cb9 100644 #define GSS_SVC_UPCALL_TIMEOUT (20) static DEFINE_SPINLOCK(__ctx_index_lock); -@@ -339,13 +348,13 @@ static int rsi_parse(struct cache_detail *cd, char *mesg, int mlen) +@@ -673,13 +682,13 @@ static int rsi_parse(struct cache_detail *cd, char *mesg, int mlen) * Directly return -EINVAL in this case. */ status = -EINVAL; @@ -286,7 +363,7 @@ index ea94cb663f..b82e6f7cb9 100644 goto out; len = qword_get(&mesg, buf, mlen); -@@ -582,36 +591,36 @@ static struct cache_head * rsc_alloc(void) +@@ -916,36 +925,38 @@ static struct cache_head * rsc_alloc(void) static int rsc_parse(struct cache_detail *cd, char *mesg, int mlen) { @@ -328,7 +405,9 @@ index ea94cb663f..b82e6f7cb9 100644 - rsci.ctx.gsc_remote = (tmp_int != 0); + /* context handle */ + len = qword_get(&mesg, buf, mlen); -+ if (len < 0) goto out; ++ if (len < 0) ++ goto out; ++ + status = -ENOMEM; + if (rawobj_alloc(&rsci.handle, buf, len)) + goto out; @@ -350,7 +429,7 @@ index ea94cb663f..b82e6f7cb9 100644 /* root user flag */ rv = get_int(&mesg, &tmp_int); -@@ -621,41 +630,41 @@ static int rsc_parse(struct cache_detail *cd, char *mesg, int mlen) +@@ -955,41 +966,41 @@ static int rsc_parse(struct cache_detail *cd, char *mesg, int mlen) } rsci.ctx.gsc_usr_root = (tmp_int != 0); @@ -423,7 +502,7 @@ index ea94cb663f..b82e6f7cb9 100644 rawobj_t tmp_buf; time64_t ctx_expiry; -@@ -699,23 +708,23 @@ static int rsc_parse(struct cache_detail *cd, char *mesg, int mlen) +@@ -1033,23 +1044,23 @@ static int rsc_parse(struct cache_detail *cd, char *mesg, int mlen) * We want just the number of seconds into the future. */ expiry += ctx_expiry - ktime_get_real_seconds(); diff --git a/0003-LU-17085-llite-safely-duplicate-iov_iter.patch b/0003-LU-17085-llite-safely-duplicate-iov_iter.patch new file mode 100644 index 0000000000000000000000000000000000000000..bc34778f541a57ef1aba15e612665e3936a07444 --- /dev/null +++ b/0003-LU-17085-llite-safely-duplicate-iov_iter.patch @@ -0,0 +1,140 @@ +From c0db20cefa91c5b6ebcbac824794fcf075a98813 Mon Sep 17 00:00:00 2001 +From: Shaun Tancheff +Date: Fri, 8 Dec 2023 00:24:18 -0600 +Subject: [PATCH 3/6] LU-17085 llite: safely duplicate iov_iter + +When duplicating iov_iter the target needs to be sized +appropriately based on the type of iter pointed to by +__iov. + +Signed-off-by: Shaun Tancheff +Change-Id: I9f68eaa14abc8915d543dba91eea598edbd9872d +--- + lustre/include/cl_object.h | 6 +++++ + lustre/obdclass/cl_io.c | 46 ++++++++++++++++++++++++-------------- + 2 files changed, 35 insertions(+), 17 deletions(-) + +diff --git a/lustre/include/cl_object.h b/lustre/include/cl_object.h +index 6689a30868..585b1a4828 100644 +--- a/lustre/include/cl_object.h ++++ b/lustre/include/cl_object.h +@@ -2579,6 +2579,11 @@ struct cl_dio_aio { + cda_creator_free:1; + }; + ++struct cl_iter_dup { ++ void *id_vec; /* dup'd vec (iov/bvec/kvec) */ ++ size_t id_vec_size; /* bytes allocated for id_vec */ ++}; ++ + /* Sub-dio used for splitting DIO (and AIO, because AIO is DIO) according to + * the layout/striping, so we can do parallel submit of DIO RPCs + */ +@@ -2589,6 +2594,7 @@ struct cl_sub_dio { + struct cl_dio_aio *csd_ll_aio; + struct ll_dio_pages csd_dio_pages; + struct iov_iter csd_iter; ++ struct cl_iter_dup csd_dup; + unsigned csd_creator_free:1, + csd_write:1, + csd_unaligned:1; +diff --git a/lustre/obdclass/cl_io.c b/lustre/obdclass/cl_io.c +index 40350080a4..c20cfda760 100644 +--- a/lustre/obdclass/cl_io.c ++++ b/lustre/obdclass/cl_io.c +@@ -1192,6 +1192,14 @@ static void cl_dio_aio_end(const struct lu_env *env, struct cl_sync_io *anchor) + EXIT; + } + ++static inline void csd_dup_free(struct cl_iter_dup *dup) ++{ ++ void *tmp = dup->id_vec; ++ ++ dup->id_vec = NULL; ++ OBD_FREE(tmp, dup->id_vec_size); ++} ++ + static void cl_sub_dio_end(const struct lu_env *env, struct cl_sync_io *anchor) + { + struct cl_sub_dio *sdio = container_of(anchor, typeof(*sdio), csd_sync); +@@ -1208,11 +1216,6 @@ static void cl_sub_dio_end(const struct lu_env *env, struct cl_sync_io *anchor) + } + + if (sdio->csd_unaligned) { +- /* save the iovec pointer before it's modified by +- * ll_dio_user_copy +- */ +- struct iovec *tmp = (struct iovec *) sdio->csd_iter.__iov; +- + CDEBUG(D_VFSTRACE, + "finishing unaligned dio %s aio->cda_bytes %ld\n", + sdio->csd_write ? "write" : "read", sdio->csd_bytes); +@@ -1226,8 +1229,7 @@ static void cl_sub_dio_end(const struct lu_env *env, struct cl_sync_io *anchor) + /* handle the freeing here rather than in cl_sub_dio_free + * because we have the unmodified iovec pointer + */ +- OBD_FREE_PTR(tmp); +- sdio->csd_iter.__iov = NULL; ++ csd_dup_free(&sdio->csd_dup); + } else { + /* unaligned DIO does not get user pages, so it doesn't have to + * release them, but aligned I/O must +@@ -1294,7 +1296,9 @@ struct cl_sub_dio *cl_sub_dio_alloc(struct cl_dio_aio *ll_aio, + + atomic_add(1, &ll_aio->cda_sync.csi_sync_nr); + +- if (unaligned) { ++ if (sdio->csd_unaligned) { ++ size_t len = 0; ++ + /* we need to make a copy of the user iovec at this + * point in time, in order to: + * +@@ -1305,15 +1309,24 @@ struct cl_sub_dio *cl_sub_dio_alloc(struct cl_dio_aio *ll_aio, + * modifies the iovec, so to process each chunk from a + * separate thread requires a local copy of the iovec + */ +- memcpy(&sdio->csd_iter, iter, sizeof(struct iov_iter)); +- OBD_ALLOC_PTR(sdio->csd_iter.__iov); +- if (sdio->csd_iter.__iov == NULL) { ++ sdio->csd_iter = *iter; ++ if (iov_iter_is_bvec(iter)) ++ len = iter->nr_segs * sizeof(struct bio_vec); ++ else if (iov_iter_is_kvec(iter) || iter_is_iovec(iter)) ++ len = iter->nr_segs * sizeof(struct iovec); ++ /* xarray and discard do not need vec to be dup'd */ ++ if (!len) ++ goto out; ++ ++ OBD_ALLOC(sdio->csd_dup.id_vec, len); ++ if (sdio->csd_dup.id_vec == NULL) { + cl_sub_dio_free(sdio); + sdio = NULL; + goto out; + } +- memcpy((void *) sdio->csd_iter.__iov, iter->__iov, +- sizeof(struct iovec)); ++ memcpy(sdio->csd_dup.id_vec, iter->__iov, len); ++ sdio->csd_dup.id_vec_size = len; ++ sdio->csd_iter.__iov = sdio->csd_dup.id_vec; + } + } + out: +@@ -1335,11 +1348,10 @@ EXPORT_SYMBOL(cl_dio_aio_free); + void cl_sub_dio_free(struct cl_sub_dio *sdio) + { + if (sdio) { +- void *tmp = (void *)sdio->csd_iter.__iov; +- +- if (tmp) { ++ if (sdio->csd_dup.id_vec) { + LASSERT(sdio->csd_unaligned); +- OBD_FREE_PTR(tmp); ++ csd_dup_free(&sdio->csd_dup); ++ sdio->csd_iter.__iov = NULL; + } + OBD_SLAB_FREE_PTR(sdio, cl_sub_dio_kmem); + } +-- +2.33.0 + diff --git a/0004-LU-17081-build-compatibility-for-6.5-kernels.patch b/0004-LU-17081-build-compatibility-for-6.5-kernels.patch new file mode 100644 index 0000000000000000000000000000000000000000..4c45fbdd2ed9d93fbde579a8f57cfbc41d92c8af --- /dev/null +++ b/0004-LU-17081-build-compatibility-for-6.5-kernels.patch @@ -0,0 +1,382 @@ +From 20fff2d144d71b24ee9bbc926da8a4088a6bf483 Mon Sep 17 00:00:00 2001 +From: Shaun Tancheff +Date: Sun, 3 Sep 2023 22:29:02 -0500 +Subject: [PATCH 4/6] LU-17081 build: compatibility for 6.5 kernels + +Linux commit v6.4-rc2-29-gc6585011bc1d + splice: Remove generic_file_splice_read() + +Prefer filemap_splice_read and provide alternates for older kernels. + +Linux commit v6.4-rc2-30-g3fc40265ae2b + iov_iter: Kill ITER_PIPE + +ITER_PIPE and iov_iter_is_pipe() are removed, provide a replacement +for iov_iter_is_pipe + +Linux commit v6.4-rc4-53-g54d020692b34 + mm/gup: remove unused vmas parameter from get_user_pages() + +Use vma_lookup() to acquire the vma following get_user_pages() + +Linux commit v6.4-rc7-1884-gdc97391e6610 + sock: Remove ->sendpage*() in favour of sendmsg(MSG_SPLICE_PAGES) +Use sendmsg when MSG_SPLICE_PAGES is defined. Provide a wrapper +using sendpage() for older kernels. + +HPE-bug-id: LUS-11811 +Signed-off-by: Shaun Tancheff +Change-Id: I95a0954a602c8db08d30b38a50dcd50107c8f268 +--- + libcfs/include/libcfs/linux/linux-misc.h | 36 +++++++---- + lnet/klnds/socklnd/socklnd_lib.c | 30 ++++++--- + lustre/autoconf/lustre-core.m4 | 82 ++++++++++++++++++++++++ + lustre/llite/file.c | 29 ++++----- + lustre/obdclass/jobid.c | 10 ++- + lustre/osd-ldiskfs/osd_internal.h | 6 +- + 6 files changed, 148 insertions(+), 45 deletions(-) + +diff --git a/libcfs/include/libcfs/linux/linux-misc.h b/libcfs/include/libcfs/linux/linux-misc.h +index 9e4c7879de..9e8bd167d2 100644 +--- a/libcfs/include/libcfs/linux/linux-misc.h ++++ b/libcfs/include/libcfs/linux/linux-misc.h +@@ -48,25 +48,33 @@ + * iter_is_iovec() and iov_iter_is_* are available, supply the missing + * functionality for older kernels. + */ +-#ifndef HAVE_IOV_ITER_TYPE ++#ifdef HAVE_IOV_ITER_TYPE ++# ifndef HAVE_ENUM_ITER_PIPE ++# define iov_iter_is_pipe(iter) 0 ++# endif ++#else + /* + * Since 3.15-rc4 commit 71d8e532b1549a478e6a6a8a44f309d050294d00 + * The iov iterator has a type and can iterate over numerous vector types. + * Prior to this only iovec is supported, so all iov_iter_is_* are false. + */ +-#ifdef HAVE_IOV_ITER_HAS_TYPE_MEMBER +-#define iter_is_iovec(iter) ((iter)->type & ITER_IOVEC) +-#define iov_iter_is_kvec(iter) ((iter)->type & ITER_KVEC) +-#define iov_iter_is_bvec(iter) ((iter)->type & ITER_BVEC) +-#define iov_iter_is_pipe(iter) ((iter)->type & ITER_PIPE) +-#define iov_iter_is_discard(iter) ((iter)->type & ITER_DISCARD) +-#else +-#define iter_is_iovec(iter) 1 +-#define iov_iter_is_kvec(iter) 0 +-#define iov_iter_is_bvec(iter) 0 +-#define iov_iter_is_pipe(iter) 0 +-#define iov_iter_is_discard(iter) 0 +-#endif ++# ifdef HAVE_IOV_ITER_HAS_TYPE_MEMBER ++# define iter_is_iovec(iter) ((iter)->type & ITER_IOVEC) ++# define iov_iter_is_kvec(iter) ((iter)->type & ITER_KVEC) ++# define iov_iter_is_bvec(iter) ((iter)->type & ITER_BVEC) ++# if defined HAVE_ENUM_ITER_PIPE ++# define iov_iter_is_pipe(iter) ((iter)->type & ITER_PIPE) ++# else ++# define iov_iter_is_pipe(iter) 0 ++# endif ++# define iov_iter_is_discard(iter) ((iter)->type & ITER_DISCARD) ++# else ++# define iter_is_iovec(iter) 1 ++# define iov_iter_is_kvec(iter) 0 ++# define iov_iter_is_bvec(iter) 0 ++# define iov_iter_is_pipe(iter) 0 ++# define iov_iter_is_discard(iter) 0 ++# endif + #endif /* HAVE_IOV_ITER_TYPE */ + + int cfs_kernel_write(struct file *filp, const void *buf, size_t count, +diff --git a/lnet/klnds/socklnd/socklnd_lib.c b/lnet/klnds/socklnd/socklnd_lib.c +index 605777a96a..640963944f 100644 +--- a/lnet/klnds/socklnd/socklnd_lib.c ++++ b/lnet/klnds/socklnd/socklnd_lib.c +@@ -109,6 +109,25 @@ ksocknal_lib_send_hdr(struct ksock_conn *conn, struct ksock_tx *tx, + return rc; + } + ++static int ++ksocknal_lib_sendpage(struct socket *sock, struct bio_vec *kiov, int msgflg) ++{ ++#ifdef MSG_SPLICE_PAGES ++ struct msghdr msg = {.msg_flags = msgflg | MSG_SPLICE_PAGES}; ++ ++ iov_iter_bvec(&msg.msg_iter, ITER_SOURCE, kiov, 1, kiov->bv_len); ++ ++ return sock_sendmsg(sock, &msg); ++#else ++ struct sock *sk = sock->sk; ++ struct page *page = kiov->bv_page; ++ int offset = kiov->bv_offset; ++ int fragsize = kiov->bv_len; ++ ++ return sk->sk_prot->sendpage(sk, page, offset, fragsize, msgflg); ++#endif ++} ++ + int + ksocknal_lib_send_kiov(struct ksock_conn *conn, struct ksock_tx *tx, + struct kvec *scratchiov) +@@ -125,21 +144,16 @@ ksocknal_lib_send_kiov(struct ksock_conn *conn, struct ksock_tx *tx, + * or leave them alone. */ + if (tx->tx_msg.ksm_zc_cookies[0] != 0) { + /* Zero copy is enabled */ +- struct sock *sk = sock->sk; +- struct page *page = kiov->bv_page; +- int offset = kiov->bv_offset; +- int fragsize = kiov->bv_len; + int msgflg = MSG_DONTWAIT; + + CDEBUG(D_NET, "page %p + offset %x for %d\n", +- page, offset, kiov->bv_len); ++ kiov->bv_page, kiov->bv_offset, kiov->bv_len); + + if (!list_empty(&conn->ksnc_tx_queue) || +- fragsize < tx->tx_resid) ++ kiov->bv_len < tx->tx_resid) + msgflg |= MSG_MORE; + +- rc = sk->sk_prot->sendpage(sk, page, +- offset, fragsize, msgflg); ++ rc = ksocknal_lib_sendpage(sock, kiov, msgflg); + } else { + #if SOCKNAL_SINGLE_FRAG_TX || !SOCKNAL_RISK_KMAP_DEADLOCK + struct kvec scratch; +diff --git a/lustre/autoconf/lustre-core.m4 b/lustre/autoconf/lustre-core.m4 +index 664419bcab..c5584cacba 100644 +--- a/lustre/autoconf/lustre-core.m4 ++++ b/lustre/autoconf/lustre-core.m4 +@@ -4093,6 +4093,78 @@ AC_DEFUN([LC_HAVE_GET_EXPIRY_TIME64_T], [ + ]) + ]) # LC_HAVE_GET_EXPIRY_TIME64_T + ++# ++# LC_HAVE_FILEMAP_SPLICE_READ ++# ++# linux kernel v6.4-rc2-29-gc6585011bc1d ++# splice: Remove generic_file_splice_read() ++# ++AC_DEFUN([LC_SRC_HAVE_FILEMAP_SPLICE_READ], [ ++ LB2_LINUX_TEST_SRC([filemap_splice_read], [ ++ #include ++ ],[ ++ struct file *in = NULL; ++ loff_t pos = 0; ++ struct pipe_inode_info *pipe = NULL; ++ ssize_t count __attribute__ ((unused)); ++ ++ count = filemap_splice_read(in, &pos, pipe, 0, 0); ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_FILEMAP_SPLICE_READ], [ ++ AC_MSG_CHECKING([if 'filemap_splice_read' is available]) ++ LB2_LINUX_TEST_RESULT([filemap_splice_read], [ ++ AC_DEFINE(HAVE_FILEMAP_SPLICE_READ, 1, ++ ['filemap_splice_read' is available]) ++ ]) ++]) # LC_HAVE_FILEMAP_SPLICE_READ ++ ++# ++# LC_HAVE_ENUM_ITER_PIPE ++# ++# linux kernel v6.4-rc2-30-g3fc40265ae2b ++# iov_iter: Kill ITER_PIPE ++# ++AC_DEFUN([LC_SRC_HAVE_ENUM_ITER_PIPE], [ ++ LB2_LINUX_TEST_SRC([enum_iter_type_iter_pipe], [ ++ #include ++ ],[ ++ enum iter_type iter_type = ITER_PIPE; ++ ++ (void)iter_type; ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_ENUM_ITER_PIPE], [ ++ AC_MSG_CHECKING([if enum iter_type has member 'iter_pipe']) ++ LB2_LINUX_TEST_RESULT([enum_iter_type_iter_pipe], [ ++ AC_DEFINE(HAVE_ENUM_ITER_PIPE, 1, ++ [enum iter_type has member 'iter_pipe']) ++ ]) ++]) # LC_HAVE_ENUM_ITER_PIPE ++ ++# ++# LC_HAVE_GET_USER_PAGES_WITHOUT_VMA ++# ++# linux kernel v6.4-rc2-30-g3fc40265ae2b ++# iov_iter: Kill ITER_PIPE ++# ++AC_DEFUN([LC_SRC_HAVE_GET_USER_PAGES_WITHOUT_VMA], [ ++ LB2_LINUX_TEST_SRC([get_user_pages_without_vma], [ ++ #include ++ ],[ ++ struct page *pages __attribute__ ((unused)); ++ ++ (void)get_user_pages(0, 0, 0, &pages); ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_GET_USER_PAGES_WITHOUT_VMA], [ ++ AC_MSG_CHECKING([if get_user_pages removed 'vma' parameter]) ++ LB2_LINUX_TEST_RESULT([get_user_pages_without_vma], [ ++ AC_DEFINE(HAVE_GET_USER_PAGES_WITHOUT_VMA, 1, ++ [get_user_pages removed 'vma' parameter]) ++ ]) ++]) # LC_HAVE_GET_USER_PAGES_WITHOUT_VMA ++ + # + # LC_PROG_LINUX + # +@@ -4358,6 +4430,11 @@ AC_DEFUN([LC_PROG_LINUX_SRC], [ + LC_SRC_HAVE_CLASS_CREATE_MODULE_ARG + LC_SRC_HAVE_GET_EXPIRY_TIME64_T + ++ # 6.5 ++ LC_SRC_HAVE_FILEMAP_SPLICE_READ ++ LC_SRC_HAVE_ENUM_ITER_PIPE ++ LC_SRC_HAVE_GET_USER_PAGES_WITHOUT_VMA ++ + # kernel patch to extend integrity interface + LC_SRC_BIO_INTEGRITY_PREP_FN + ]) +@@ -4643,6 +4720,11 @@ AC_DEFUN([LC_PROG_LINUX_RESULTS], [ + LC_HAVE_CLASS_CREATE_MODULE_ARG + LC_HAVE_GET_EXPIRY_TIME64_T + ++ # 6.5 ++ LC_HAVE_FILEMAP_SPLICE_READ ++ LC_HAVE_ENUM_ITER_PIPE ++ LC_HAVE_GET_USER_PAGES_WITHOUT_VMA ++ + # kernel patch to extend integrity interface + LC_BIO_INTEGRITY_PREP_FN + ]) +diff --git a/lustre/llite/file.c b/lustre/llite/file.c +index 5178a276e7..a33502ccb9 100644 +--- a/lustre/llite/file.c ++++ b/lustre/llite/file.c +@@ -50,6 +50,7 @@ + + #include + #include ++#include + + #include "cl_object.h" + #include "llite_internal.h" +@@ -1749,7 +1750,7 @@ ll_file_io_generic(const struct lu_env *env, struct vvp_io_args *args, + * to pipes + */ + is_parallel_dio = !iov_iter_is_pipe(args->u.normal.via_iter) && +- !is_aio; ++ !is_aio; + + if (!ll_sbi_has_parallel_dio(sbi)) + is_parallel_dio = false; +@@ -5875,6 +5876,14 @@ int ll_inode_permission(struct mnt_idmap *idmap, struct inode *inode, int mask) + RETURN(rc); + } + ++#if defined(HAVE_FILEMAP_SPLICE_READ) ++# define ll_splice_read filemap_splice_read ++#elif !defined(HAVE_DEFAULT_FILE_SPLICE_READ_EXPORT) ++# define ll_splice_read generic_file_splice_read ++#else ++# define ll_splice_read pcc_file_splice_read ++#endif ++ + /* -o localflock - only provides locally consistent flock locks */ + static const struct file_operations ll_file_operations = { + #ifdef HAVE_FILE_OPERATIONS_READ_WRITE_ITER +@@ -5895,11 +5904,7 @@ static const struct file_operations ll_file_operations = { + .release = ll_file_release, + .mmap = ll_file_mmap, + .llseek = ll_file_seek, +-#ifndef HAVE_DEFAULT_FILE_SPLICE_READ_EXPORT +- .splice_read = generic_file_splice_read, +-#else +- .splice_read = pcc_file_splice_read, +-#endif ++ .splice_read = ll_splice_read, + #ifdef HAVE_ITER_FILE_SPLICE_WRITE + .splice_write = iter_file_splice_write, + #endif +@@ -5927,11 +5932,7 @@ static const struct file_operations ll_file_operations_flock = { + .release = ll_file_release, + .mmap = ll_file_mmap, + .llseek = ll_file_seek, +-#ifndef HAVE_DEFAULT_FILE_SPLICE_READ_EXPORT +- .splice_read = generic_file_splice_read, +-#else +- .splice_read = pcc_file_splice_read, +-#endif ++ .splice_read = ll_splice_read, + #ifdef HAVE_ITER_FILE_SPLICE_WRITE + .splice_write = iter_file_splice_write, + #endif +@@ -5962,11 +5963,7 @@ static const struct file_operations ll_file_operations_noflock = { + .release = ll_file_release, + .mmap = ll_file_mmap, + .llseek = ll_file_seek, +-#ifndef HAVE_DEFAULT_FILE_SPLICE_READ_EXPORT +- .splice_read = generic_file_splice_read, +-#else +- .splice_read = pcc_file_splice_read, +-#endif ++ .splice_read = ll_splice_read, + #ifdef HAVE_ITER_FILE_SPLICE_WRITE + .splice_write = iter_file_splice_write, + #endif +diff --git a/lustre/obdclass/jobid.c b/lustre/obdclass/jobid.c +index 1fccfdd25e..3bda56f170 100644 +--- a/lustre/obdclass/jobid.c ++++ b/lustre/obdclass/jobid.c +@@ -222,7 +222,7 @@ static int cfs_access_process_vm(struct task_struct *tsk, + /* Just copied from kernel for the kernels which doesn't + * have access_process_vm() exported + */ +- struct vm_area_struct *vma; ++ struct vm_area_struct *vma = NULL; + struct page *page; + void *old_buf = buf; + +@@ -239,7 +239,11 @@ static int cfs_access_process_vm(struct task_struct *tsk, + int bytes, rc, offset; + void *maddr; + +-#if defined(HAVE_GET_USER_PAGES_GUP_FLAGS) ++#if defined(HAVE_GET_USER_PAGES_WITHOUT_VMA) ++ rc = get_user_pages(addr, 1, write ? FOLL_WRITE : 0, &page); ++ if (rc > 0) ++ vma = vma_lookup(mm, addr); ++#elif defined(HAVE_GET_USER_PAGES_GUP_FLAGS) + rc = get_user_pages(addr, 1, write ? FOLL_WRITE : 0, &page, + &vma); + #elif defined(HAVE_GET_USER_PAGES_6ARG) +@@ -247,7 +251,7 @@ static int cfs_access_process_vm(struct task_struct *tsk, + #else + rc = get_user_pages(tsk, mm, addr, 1, write, 1, &page, &vma); + #endif +- if (rc <= 0) ++ if (rc <= 0 || !vma) + break; + + bytes = len; +diff --git a/lustre/osd-ldiskfs/osd_internal.h b/lustre/osd-ldiskfs/osd_internal.h +index 3051ab1fb5..76a7a2fd04 100644 +--- a/lustre/osd-ldiskfs/osd_internal.h ++++ b/lustre/osd-ldiskfs/osd_internal.h +@@ -67,10 +67,8 @@ + #include "osd_scrub.h" + #include "osd_quota_fmt.h" + +-#if IS_ENABLED(CONFIG_BLK_DEV_INTEGRITY) +- #ifdef HAVE_LINUX_BLK_INTEGRITY_HEADER +- #include +- #endif ++#ifdef HAVE_LINUX_BLK_INTEGRITY_HEADER ++ #include + #endif + + struct inode; +-- +2.33.0 + diff --git a/0005-LU-17081-build-Prefer-folio_batch-to-pagevec.patch b/0005-LU-17081-build-Prefer-folio_batch-to-pagevec.patch new file mode 100644 index 0000000000000000000000000000000000000000..d413f7478177ab6cf320a04f224dae9536e4deb4 --- /dev/null +++ b/0005-LU-17081-build-Prefer-folio_batch-to-pagevec.patch @@ -0,0 +1,783 @@ +From 4b7bf4181c28ec15ac5d0f8e7762514373b70bc8 Mon Sep 17 00:00:00 2001 +From: Shaun Tancheff +Date: Tue, 31 Oct 2023 01:02:56 -0500 +Subject: [PATCH 5/6] LU-17081 build: Prefer folio_batch to pagevec + +Linux commit v5.16-rc4-36-g10331795fb79 + pagevec: Add folio_batch + +Linux commit v6.2-rc4-254-g811561288397 + mm: pagevec: add folio_batch_reinit() + +Linux commit v6.4-rc4-438-g1e0877d58b1e + mm: remove struct pagevec + +Use folio_batch and provide wrappers for older kernels to use +pagevec handling, conditionally provide a folio_batch_reinit + +Add macros to ease adding pages to folio_batch(es) as well +as unwinding batches of struct folio where struct page is +needed. + +HPE-bug-id: LUS-11811 +Signed-off-by: Shaun Tancheff +Change-Id: Ie70e4851df00a73f194aaa6631678b54b5d128a1 +--- + lustre/autoconf/lustre-core.m4 | 74 ++++++++++++++++++++++ + lustre/include/cl_object.h | 7 ++- + lustre/include/lustre_compat.h | 44 +++++++++++-- + lustre/include/lustre_osc.h | 2 +- + lustre/llite/vvp_io.c | 109 +++++++++++++++++++++------------ + lustre/obdclass/cl_page.c | 24 ++++---- + lustre/osc/osc_cache.c | 31 +++++----- + lustre/osc/osc_io.c | 24 ++++---- + lustre/osc/osc_page.c | 18 +++--- + lustre/osd-ldiskfs/osd_io.c | 12 ++-- + 10 files changed, 241 insertions(+), 104 deletions(-) + +diff --git a/lustre/autoconf/lustre-core.m4 b/lustre/autoconf/lustre-core.m4 +index c5584cacba..480f9f5245 100644 +--- a/lustre/autoconf/lustre-core.m4 ++++ b/lustre/autoconf/lustre-core.m4 +@@ -3983,6 +3983,29 @@ AC_DEFUN([LC_HAVE_LOCKS_LOCK_FILE_WAIT_IN_FILELOCK], [ + ]) + ]) # LC_HAVE_LOCKS_LOCK_FILE_WAIT_IN_FILELOCK + ++# ++# LC_HAVE_FOLIO_BATCH_REINIT ++# ++# linux kernel v6.2-rc4-254-g811561288397 ++# mm: pagevec: add folio_batch_reinit() ++# ++AC_DEFUN([LC_SRC_HAVE_FOLIO_BATCH_REINIT], [ ++ LB2_LINUX_TEST_SRC([folio_batch_reinit_exists], [ ++ #include ++ ],[ ++ struct folio_batch fbatch __attribute__ ((unused)); ++ ++ folio_batch_reinit(&fbatch); ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_FOLIO_BATCH_REINIT], [ ++ AC_MSG_CHECKING([if 'folio_batch_reinit' is available]) ++ LB2_LINUX_TEST_RESULT([folio_batch_reinit_exists], [ ++ AC_DEFINE(HAVE_FOLIO_BATCH_REINIT, 1, ++ ['folio_batch_reinit' is available]) ++ ]) ++]) # LC_HAVE_FOLIO_BATCH_REINIT ++ + # + # LC_HAVE_IOV_ITER_IOVEC + # +@@ -4165,6 +4188,51 @@ AC_DEFUN([LC_HAVE_GET_USER_PAGES_WITHOUT_VMA], [ + ]) + ]) # LC_HAVE_GET_USER_PAGES_WITHOUT_VMA + ++# ++# LC_HAVE_FOLIO_BATCH ++# ++# linux kernel v5.16-rc4-36-g10331795fb79 ++# pagevec: Add folio_batch ++# ++AC_DEFUN([LC_SRC_HAVE_FOLIO_BATCH], [ ++ LB2_LINUX_TEST_SRC([struct_folio_batch_exists], [ ++ #include ++ ],[ ++ struct folio_batch fbatch __attribute__ ((unused)); ++ ++ folio_batch_init(&fbatch); ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_FOLIO_BATCH], [ ++ AC_MSG_CHECKING([if 'struct folio_batch' is available]) ++ LB2_LINUX_TEST_RESULT([struct_folio_batch_exists], [ ++ AC_DEFINE(HAVE_FOLIO_BATCH, 1, ++ ['struct folio_batch' is available]) ++ ]) ++]) # LC_HAVE_FOLIO_BATCH ++ ++# ++# LC_HAVE_STRUCT_PAGEVEC ++# ++# linux kernel v6.4-rc4-438-g1e0877d58b1e ++# mm: remove struct pagevec ++# ++AC_DEFUN([LC_SRC_HAVE_STRUCT_PAGEVEC], [ ++ LB2_LINUX_TEST_SRC([struct_pagevec_exists], [ ++ #include ++ ],[ ++ struct pagevec *pvec = NULL; ++ (void)pvec; ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_STRUCT_PAGEVEC], [ ++ AC_MSG_CHECKING([if 'struct pagevec' is available]) ++ LB2_LINUX_TEST_RESULT([struct_pagevec_exists], [ ++ AC_DEFINE(HAVE_PAGEVEC, 1, ++ ['struct pagevec' is available]) ++ ]) ++]) # LC_HAVE_STRUCT_PAGEVEC ++ + # + # LC_PROG_LINUX + # +@@ -4423,6 +4491,7 @@ AC_DEFUN([LC_PROG_LINUX_SRC], [ + LC_SRC_HAVE_MNT_IDMAP_ARG + LC_SRC_HAVE_LOCKS_LOCK_FILE_WAIT_IN_FILELOCK + LC_SRC_HAVE_U64_CAPABILITY ++ LC_SRC_HAVE_FOLIO_BATCH_REINIT + + # 6.4 + LC_SRC_HAVE_IOV_ITER_IOVEC +@@ -4434,6 +4503,8 @@ AC_DEFUN([LC_PROG_LINUX_SRC], [ + LC_SRC_HAVE_FILEMAP_SPLICE_READ + LC_SRC_HAVE_ENUM_ITER_PIPE + LC_SRC_HAVE_GET_USER_PAGES_WITHOUT_VMA ++ LC_SRC_HAVE_FOLIO_BATCH ++ LC_SRC_HAVE_STRUCT_PAGEVEC + + # kernel patch to extend integrity interface + LC_SRC_BIO_INTEGRITY_PREP_FN +@@ -4713,6 +4784,7 @@ AC_DEFUN([LC_PROG_LINUX_RESULTS], [ + LC_HAVE_MNT_IDMAP_ARG + LC_HAVE_LOCKS_LOCK_FILE_WAIT_IN_FILELOCK + LC_HAVE_U64_CAPABILITY ++ LC_HAVE_FOLIO_BATCH_REINIT + + # 6.4 + LC_HAVE_IOV_ITER_IOVEC +@@ -4724,6 +4796,8 @@ AC_DEFUN([LC_PROG_LINUX_RESULTS], [ + LC_HAVE_FILEMAP_SPLICE_READ + LC_HAVE_ENUM_ITER_PIPE + LC_HAVE_GET_USER_PAGES_WITHOUT_VMA ++ LC_HAVE_FOLIO_BATCH ++ LC_HAVE_STRUCT_PAGEVEC + + # kernel patch to extend integrity interface + LC_BIO_INTEGRITY_PREP_FN +diff --git a/lustre/include/cl_object.h b/lustre/include/cl_object.h +index 585b1a4828..7a8b2094c6 100644 +--- a/lustre/include/cl_object.h ++++ b/lustre/include/cl_object.h +@@ -100,6 +100,7 @@ + #include + #include + #include ++#include + + struct obd_info; + struct inode; +@@ -1412,7 +1413,7 @@ struct cl_io_slice { + }; + + typedef void (*cl_commit_cbt)(const struct lu_env *, struct cl_io *, +- struct pagevec *); ++ struct folio_batch *); + + struct cl_read_ahead { + /* Maximum page index the readahead window will end. +@@ -2219,9 +2220,9 @@ struct cl_page *cl_page_alloc (const struct lu_env *env, + void cl_page_get (struct cl_page *page); + void cl_page_put (const struct lu_env *env, + struct cl_page *page); +-void cl_pagevec_put (const struct lu_env *env, ++void cl_batch_put (const struct lu_env *env, + struct cl_page *page, +- struct pagevec *pvec); ++ struct folio_batch *fbatch); + void cl_page_print (const struct lu_env *env, void *cookie, + lu_printer_t printer, + const struct cl_page *pg); +diff --git a/lustre/include/lustre_compat.h b/lustre/include/lustre_compat.h +index 3c5c0a000e..9adf41ca5e 100644 +--- a/lustre/include/lustre_compat.h ++++ b/lustre/include/lustre_compat.h +@@ -44,6 +44,7 @@ + #include + #include + #include ++#include + #include + #ifdef HAVE_XARRAY_SUPPORT + #include +@@ -484,12 +485,6 @@ static inline struct timespec current_time(struct inode *inode) + #define smp_store_mb(var, value) set_mb(var, value) + #endif + +-#ifdef HAVE_PAGEVEC_INIT_ONE_PARAM +-#define ll_pagevec_init(pvec, n) pagevec_init(pvec) +-#else +-#define ll_pagevec_init(pvec, n) pagevec_init(pvec, n) +-#endif +- + #ifdef HAVE_D_COUNT + # define ll_d_count(d) d_count(d) + #else +@@ -747,4 +742,41 @@ static inline struct page *ll_read_cache_page(struct address_space *mapping, + #endif /* HAVE_READ_CACHE_PAGE_WANTS_FILE */ + } + ++#ifdef HAVE_FOLIO_BATCH ++# define ll_folio_batch_init(batch, n) folio_batch_init(batch) ++# define fbatch_at(fbatch, f) ((fbatch)->folios[(f)]) ++# define fbatch_at_npgs(fbatch, f) folio_nr_pages((fbatch)->folios[(f)]) ++# define fbatch_at_pg(fbatch, f, pg) folio_page((fbatch)->folios[(f)], (pg)) ++# define folio_batch_add_page(fbatch, page) \ ++ folio_batch_add(fbatch, page_folio(page)) ++# ifndef HAVE_FOLIO_BATCH_REINIT ++static inline void folio_batch_reinit(struct folio_batch *fbatch) ++{ ++ fbatch->nr = 0; ++} ++# endif /* HAVE_FOLIO_BATCH_REINIT */ ++ ++#else /* !HAVE_FOLIO_BATCH */ ++ ++# ifdef HAVE_PAGEVEC ++# define folio_batch pagevec ++# endif ++# define folio_batch_init(pvec) pagevec_init(pvec) ++# define folio_batch_reinit(pvec) pagevec_reinit(pvec) ++# define folio_batch_count(pvec) pagevec_count(pvec) ++# define folio_batch_space(pvec) pagevec_space(pvec) ++# define folio_batch_add_page(pvec, page) \ ++ pagevec_add(pvec, page) ++# define folio_batch_release(pvec) \ ++ pagevec_release(((struct pagevec *)pvec)) ++# ifdef HAVE_PAGEVEC_INIT_ONE_PARAM ++# define ll_folio_batch_init(pvec, n) pagevec_init(pvec) ++# else ++# define ll_folio_batch_init(pvec, n) pagevec_init(pvec, n) ++# endif ++# define fbatch_at(pvec, n) ((pvec)->pages[(n)]) ++# define fbatch_at_npgs(pvec, n) 1 ++# define fbatch_at_pg(pvec, n, pg) ((pvec)->pages[(n)]) ++#endif /* HAVE_FOLIO_BATCH */ ++ + #endif /* _LUSTRE_COMPAT_H */ +diff --git a/lustre/include/lustre_osc.h b/lustre/include/lustre_osc.h +index 37cd7a4d60..43c571855a 100644 +--- a/lustre/include/lustre_osc.h ++++ b/lustre/include/lustre_osc.h +@@ -161,7 +161,7 @@ struct osc_thread_info { + union ldlm_policy_data oti_policy; + struct cl_attr oti_attr; + struct cl_io oti_io; +- struct pagevec oti_pagevec; ++ struct folio_batch oti_fbatch; + void *oti_pvec[OTI_PVEC_SIZE]; + /** + * Fields used by cl_lock_discard_pages(). +diff --git a/lustre/llite/vvp_io.c b/lustre/llite/vvp_io.c +index 4b27decef8..0043edcd9b 100644 +--- a/lustre/llite/vvp_io.c ++++ b/lustre/llite/vvp_io.c +@@ -43,6 +43,7 @@ + + #include "llite_internal.h" + #include "vvp_internal.h" ++#include + #include + + static struct vvp_io *cl2vvp_io(const struct lu_env *env, +@@ -1034,15 +1035,19 @@ static inline void ll_account_page_dirtied(struct page *page, + * Backwards compat for 3.x, 5.x kernels relating to memcg handling + * & rename of radix tree to xarray. + */ +-static void vvp_set_pagevec_dirty(struct pagevec *pvec) ++static void vvp_set_batch_dirty(struct folio_batch *fbatch) + { +- struct page *page = pvec->pages[0]; +- int count = pagevec_count(pvec); ++ struct page *page = fbatch_at_pg(fbatch, 0, 0); ++ int count = folio_batch_count(fbatch); + int i; ++#ifndef HAVE_FOLIO_BATCH ++ int pg, npgs; ++#endif + #ifdef HAVE_KALLSYMS_LOOKUP_NAME + struct address_space *mapping = page->mapping; + unsigned long flags; + unsigned long skip_pages = 0; ++ int pgno; + int dirtied = 0; + #endif + +@@ -1061,25 +1066,38 @@ static void vvp_set_pagevec_dirty(struct pagevec *pvec) + */ + #ifndef HAVE_ACCOUNT_PAGE_DIRTIED_EXPORT + if (!vvp_account_page_dirtied) { +- for (i = 0; i < count; i++) +- __set_page_dirty_nobuffers(pvec->pages[i]); ++ for (i = 0; i < count; i++) { ++#ifdef HAVE_FOLIO_BATCH ++ filemap_dirty_folio(page->mapping, fbatch->folios[i]); ++#else ++ npgs = fbatch_at_npgs(fbatch, i); ++ for (pg = 0; pg < npgs; pg++) { ++ page = fbatch_at_pg(fbatch, i, pg); ++ __set_page_dirty_nobuffers(page); ++ } ++#endif ++ } + EXIT; + } + #endif + + #ifdef HAVE_KALLSYMS_LOOKUP_NAME +- for (i = 0; i < count; i++) { +- page = pvec->pages[i]; ++ for (pgno = i = 0; i < count; i++) { ++ npgs = fbatch_at_npgs(fbatch, i); ++ for (pg = 0; pg < npgs; pg++) { ++ page = fbatch_at_pg(fbatch, i, pg); + +- ClearPageReclaim(page); ++ ClearPageReclaim(page); + +- vvp_lock_page_memcg(page); +- if (TestSetPageDirty(page)) { +- /* page is already dirty .. no extra work needed +- * set a flag for the i'th page to be skipped +- */ +- vvp_unlock_page_memcg(page); +- skip_pages |= (1 << i); ++ vvp_lock_page_memcg(page); ++ if (TestSetPageDirty(page)) { ++ /* page is already dirty .. no extra work needed ++ * set a flag for the i'th page to be skipped ++ */ ++ vvp_unlock_page_memcg(page); ++ skip_pages |= (1 << pgno++); ++ BUG_ON(pgno > BITS_PER_LONG); ++ } + } + } + +@@ -1094,19 +1112,23 @@ static void vvp_set_pagevec_dirty(struct pagevec *pvec) + * dirty_nobuffers should be impossible because we hold the page lock.) + * 4. All mappings are the same because i/o is only to one file. + */ +- for (i = 0; i < count; i++) { +- page = pvec->pages[i]; +- /* if the i'th page was unlocked above, skip it here */ +- if ((skip_pages >> i) & 1) +- continue; +- +- LASSERTF(page->mapping == mapping, +- "all pages must have the same mapping. page %p, mapping %p, first mapping %p\n", +- page, page->mapping, mapping); +- WARN_ON_ONCE(!PagePrivate(page) && !PageUptodate(page)); +- ll_account_page_dirtied(page, mapping); +- dirtied++; +- vvp_unlock_page_memcg(page); ++ for (pgno = i = 0; i < count; i++) { ++ npgs = fbatch_at_npgs(fbatch, f); ++ for (pg = 0; pg < npgs; pg++) { ++ page = fbatch_at_pg(fbatch, i, pg); ++ ++ /* if the i'th page was unlocked above, skip it here */ ++ if ((skip_pages >> pgno++) & 1) ++ continue; ++ ++ LASSERTF(page->mapping == mapping, ++ "all pages must have the same mapping. page %p, mapping %p, first mapping %p\n", ++ page, page->mapping, mapping); ++ WARN_ON_ONCE(!PagePrivate(page) && !PageUptodate(page)); ++ ll_account_page_dirtied(page, mapping); ++ dirtied++; ++ vvp_unlock_page_memcg(page); ++ } + } + ll_xa_unlock_irqrestore(&mapping->i_pages, flags); + +@@ -1122,29 +1144,36 @@ static void vvp_set_pagevec_dirty(struct pagevec *pvec) + } + + static void write_commit_callback(const struct lu_env *env, struct cl_io *io, +- struct pagevec *pvec) ++ struct folio_batch *fbatch) + { ++ struct page *vmpage; ++ struct cl_page *page; ++ int pg, npgs; + int count = 0; + int i = 0; + + ENTRY; + +- count = pagevec_count(pvec); ++ count = folio_batch_count(fbatch); + LASSERT(count > 0); + + for (i = 0; i < count; i++) { +- struct page *vmpage = pvec->pages[i]; +- SetPageUptodate(vmpage); ++ npgs = fbatch_at_npgs(fbatch, i); ++ for (pg = 0; pg < npgs; pg++) ++ SetPageUptodate(fbatch_at_pg(fbatch, i, pg)); + } + +- vvp_set_pagevec_dirty(pvec); ++ vvp_set_batch_dirty(fbatch); + + for (i = 0; i < count; i++) { +- struct page *vmpage = pvec->pages[i]; +- struct cl_page *page = (struct cl_page *) vmpage->private; +- cl_page_disown(env, io, page); +- lu_ref_del(&page->cp_reference, "cl_io", cl_io_top(io)); +- cl_page_put(env, page); ++ npgs = fbatch_at_npgs(fbatch, i); ++ for (pg = 0; pg < npgs; pg++) { ++ vmpage = fbatch_at_pg(fbatch, i, pg); ++ page = (struct cl_page *) vmpage->private; ++ cl_page_disown(env, io, page); ++ lu_ref_del(&page->cp_reference, "cl_io", cl_io_top(io)); ++ cl_page_put(env, page); ++ } + } + + EXIT; +@@ -1475,9 +1504,9 @@ static int vvp_io_kernel_fault(struct vvp_fault_io *cfio) + } + + static void mkwrite_commit_callback(const struct lu_env *env, struct cl_io *io, +- struct pagevec *pvec) ++ struct folio_batch *fbatch) + { +- vvp_set_pagevec_dirty(pvec); ++ vvp_set_batch_dirty(fbatch); + } + + static int vvp_io_fault_start(const struct lu_env *env, +diff --git a/lustre/obdclass/cl_page.c b/lustre/obdclass/cl_page.c +index 44c364d375..8d4ceeb931 100644 +--- a/lustre/obdclass/cl_page.c ++++ b/lustre/obdclass/cl_page.c +@@ -159,7 +159,7 @@ static void __cl_page_free(struct cl_page *cl_page, unsigned short bufsize) + } + + static void cl_page_free(const struct lu_env *env, struct cl_page *cp, +- struct pagevec *pvec) ++ struct folio_batch *fbatch) + { + struct cl_object *obj = cp->cp_obj; + unsigned short bufsize = cl_object_header(obj)->coh_page_bufsize; +@@ -177,9 +177,9 @@ static void cl_page_free(const struct lu_env *env, struct cl_page *cp, + LASSERT(vmpage != NULL); + LASSERT((struct cl_page *)vmpage->private != cp); + +- if (pvec != NULL) { +- if (!pagevec_add(pvec, vmpage)) +- pagevec_release(pvec); ++ if (fbatch != NULL) { ++ if (!folio_batch_add_page(fbatch, vmpage)) ++ folio_batch_release(fbatch); + } else { + put_page(vmpage); + } +@@ -460,13 +460,13 @@ void cl_page_get(struct cl_page *page) + EXPORT_SYMBOL(cl_page_get); + + /** +- * Releases a reference to a page, use the pagevec to release the pages ++ * Releases a reference to a page, use the folio_batch to release the pages + * in batch if provided. + * +- * Users need to do a final pagevec_release() to release any trailing pages. ++ * Users need to do a final folio_batch_release() to release any trailing pages. + */ +-void cl_pagevec_put(const struct lu_env *env, struct cl_page *page, +- struct pagevec *pvec) ++void cl_batch_put(const struct lu_env *env, struct cl_page *page, ++ struct folio_batch *fbatch) + { + ENTRY; + CL_PAGE_HEADER(D_TRACE, env, page, "%d\n", +@@ -482,15 +482,15 @@ void cl_pagevec_put(const struct lu_env *env, struct cl_page *page, + * Page is no longer reachable by other threads. Tear + * it down. + */ +- cl_page_free(env, page, pvec); ++ cl_page_free(env, page, fbatch); + } + + EXIT; + } +-EXPORT_SYMBOL(cl_pagevec_put); ++EXPORT_SYMBOL(cl_batch_put); + + /** +- * Releases a reference to a page, wrapper to cl_pagevec_put ++ * Releases a reference to a page, wrapper to cl_batch_put + * + * When last reference is released, page is returned to the cache, unless it + * is in cl_page_state::CPS_FREEING state, in which case it is immediately +@@ -500,7 +500,7 @@ EXPORT_SYMBOL(cl_pagevec_put); + */ + void cl_page_put(const struct lu_env *env, struct cl_page *page) + { +- cl_pagevec_put(env, page, NULL); ++ cl_batch_put(env, page, NULL); + } + EXPORT_SYMBOL(cl_page_put); + +diff --git a/lustre/osc/osc_cache.c b/lustre/osc/osc_cache.c +index a40e0b47f1..4a9e8ca5b8 100644 +--- a/lustre/osc/osc_cache.c ++++ b/lustre/osc/osc_cache.c +@@ -946,7 +946,7 @@ static int osc_extent_truncate(struct osc_extent *ext, pgoff_t trunc_index, + struct client_obd *cli = osc_cli(obj); + struct osc_async_page *oap; + struct osc_async_page *tmp; +- struct pagevec *pvec; ++ struct folio_batch *fbatch; + int pages_in_chunk = 0; + int ppc_bits = cli->cl_chunkbits - + PAGE_SHIFT; +@@ -971,8 +971,8 @@ static int osc_extent_truncate(struct osc_extent *ext, pgoff_t trunc_index, + io = osc_env_thread_io(env); + io->ci_obj = cl_object_top(osc2cl(obj)); + io->ci_ignore_layout = 1; +- pvec = &osc_env_info(env)->oti_pagevec; +- ll_pagevec_init(pvec, 0); ++ fbatch = &osc_env_info(env)->oti_fbatch; ++ ll_folio_batch_init(fbatch, 0); + rc = cl_io_init(env, io, CIT_MISC, io->ci_obj); + if (rc < 0) + GOTO(out, rc); +@@ -1010,12 +1010,12 @@ static int osc_extent_truncate(struct osc_extent *ext, pgoff_t trunc_index, + } + + lu_ref_del(&page->cp_reference, "truncate", current); +- cl_pagevec_put(env, page, pvec); ++ cl_batch_put(env, page, fbatch); + + --ext->oe_nr_pages; + ++nr_pages; + } +- pagevec_release(pvec); ++ folio_batch_release(fbatch); + + EASSERTF(ergo(ext->oe_start >= trunc_index + !!partial, + ext->oe_nr_pages == 0), +@@ -2272,7 +2272,7 @@ int osc_queue_async_io(const struct lu_env *env, struct cl_io *io, + struct osc_async_page *oap = &ops->ops_oap; + struct osc_object *osc = oap->oap_obj; + struct client_obd *cli = osc_cli(osc); +- struct pagevec *pvec = &osc_env_info(env)->oti_pagevec; ++ struct folio_batch *fbatch = &osc_env_info(env)->oti_fbatch; + pgoff_t index; + unsigned int tmp; + unsigned int grants = 0; +@@ -2400,10 +2400,11 @@ int osc_queue_async_io(const struct lu_env *env, struct cl_io *io, + + /* We must not hold a page lock while we do osc_enter_cache() + * or osc_extent_find(), so we must mark dirty & unlock +- * any pages in the write commit pagevec. */ +- if (pagevec_count(pvec)) { +- cb(env, io, pvec); +- pagevec_reinit(pvec); ++ * any pages in the write commit folio_batch. ++ */ ++ if (folio_batch_count(fbatch)) { ++ cb(env, io, fbatch); ++ folio_batch_reinit(fbatch); + } + + if (grants == 0) { +@@ -3051,7 +3052,7 @@ bool osc_page_gang_lookup(const struct lu_env *env, struct cl_io *io, + osc_page_gang_cbt cb, void *cbdata) + { + struct osc_page *ops; +- struct pagevec *pagevec; ++ struct folio_batch *fbatch; + void **pvec; + pgoff_t idx; + unsigned int nr; +@@ -3063,8 +3064,8 @@ bool osc_page_gang_lookup(const struct lu_env *env, struct cl_io *io, + + idx = start; + pvec = osc_env_info(env)->oti_pvec; +- pagevec = &osc_env_info(env)->oti_pagevec; +- ll_pagevec_init(pagevec, 0); ++ fbatch = &osc_env_info(env)->oti_fbatch; ++ ll_folio_batch_init(fbatch, 0); + spin_lock(&osc->oo_tree_lock); + while ((nr = radix_tree_gang_lookup(&osc->oo_tree, pvec, + idx, OTI_PVEC_SIZE)) > 0) { +@@ -3110,9 +3111,9 @@ bool osc_page_gang_lookup(const struct lu_env *env, struct cl_io *io, + ops = pvec[i]; + page = ops->ops_cl.cpl_page; + lu_ref_del(&page->cp_reference, "gang_lookup", current); +- cl_pagevec_put(env, page, pagevec); ++ cl_batch_put(env, page, fbatch); + } +- pagevec_release(pagevec); ++ folio_batch_release(fbatch); + + if (nr < OTI_PVEC_SIZE || end_of_region) + break; +diff --git a/lustre/osc/osc_io.c b/lustre/osc/osc_io.c +index 50304272cc..6e1ee58616 100644 +--- a/lustre/osc/osc_io.c ++++ b/lustre/osc/osc_io.c +@@ -301,13 +301,13 @@ int osc_io_commit_async(const struct lu_env *env, + struct cl_page_list *qin, int from, int to, + cl_commit_cbt cb) + { +- struct cl_io *io = ios->cis_io; +- struct osc_io *oio = cl2osc_io(env, ios); ++ struct cl_io *io = ios->cis_io; ++ struct osc_io *oio = cl2osc_io(env, ios); + struct osc_object *osc = cl2osc(ios->cis_obj); +- struct cl_page *page; +- struct cl_page *last_page; ++ struct cl_page *page; ++ struct cl_page *last_page; + struct osc_page *opg; +- struct pagevec *pvec = &osc_env_info(env)->oti_pagevec; ++ struct folio_batch *fbatch = &osc_env_info(env)->oti_fbatch; + int result = 0; + ENTRY; + +@@ -327,7 +327,7 @@ int osc_io_commit_async(const struct lu_env *env, + } + } + +- ll_pagevec_init(pvec, 0); ++ ll_folio_batch_init(fbatch, 0); + + while (qin->pl_nr > 0) { + struct osc_async_page *oap; +@@ -359,9 +359,9 @@ int osc_io_commit_async(const struct lu_env *env, + cl_page_list_del(env, qin, page); + + /* if there are no more slots, do the callback & reinit */ +- if (pagevec_add(pvec, page->cp_vmpage) == 0) { +- (*cb)(env, io, pvec); +- pagevec_reinit(pvec); ++ if (!folio_batch_add_page(fbatch, page->cp_vmpage)) { ++ (*cb)(env, io, fbatch); ++ folio_batch_reinit(fbatch); + } + } + /* The shrink interval is in seconds, so we can update it once per +@@ -370,9 +370,9 @@ int osc_io_commit_async(const struct lu_env *env, + osc_update_next_shrink(osc_cli(osc)); + + +- /* Clean up any partially full pagevecs */ +- if (pagevec_count(pvec) != 0) +- (*cb)(env, io, pvec); ++ /* Clean up any partially full folio_batches */ ++ if (folio_batch_count(fbatch) != 0) ++ (*cb)(env, io, fbatch); + + /* Can't access these pages any more. Page can be in transfer and + * complete at any time. */ +diff --git a/lustre/osc/osc_page.c b/lustre/osc/osc_page.c +index 0e7559795b..5861723c24 100644 +--- a/lustre/osc/osc_page.c ++++ b/lustre/osc/osc_page.c +@@ -487,24 +487,24 @@ static void osc_lru_use(struct client_obd *cli, struct osc_page *opg) + } + } + +-static void discard_pagevec(const struct lu_env *env, struct cl_io *io, +- struct cl_page **pvec, int max_index) ++static void discard_cl_pages(const struct lu_env *env, struct cl_io *io, ++ struct cl_page **pvec, int max_index) + { +- struct pagevec *pagevec = &osc_env_info(env)->oti_pagevec; ++ struct folio_batch *fbatch = &osc_env_info(env)->oti_fbatch; + int i; + +- ll_pagevec_init(pagevec, 0); ++ ll_folio_batch_init(fbatch, 0); + for (i = 0; i < max_index; i++) { + struct cl_page *page = pvec[i]; + + LASSERT(cl_page_is_owned(page, io)); + cl_page_discard(env, io, page); + cl_page_disown(env, io, page); +- cl_pagevec_put(env, page, pagevec); ++ cl_batch_put(env, page, fbatch); + + pvec[i] = NULL; + } +- pagevec_release(pagevec); ++ folio_batch_release(fbatch); + } + + /** +@@ -596,7 +596,7 @@ long osc_lru_shrink(const struct lu_env *env, struct client_obd *cli, + spin_unlock(&cli->cl_lru_list_lock); + + if (clobj != NULL) { +- discard_pagevec(env, io, pvec, index); ++ discard_cl_pages(env, io, pvec, index); + index = 0; + + cl_io_fini(env, io); +@@ -641,7 +641,7 @@ long osc_lru_shrink(const struct lu_env *env, struct client_obd *cli, + pvec[index++] = page; + if (unlikely(index == OTI_PVEC_SIZE)) { + spin_unlock(&cli->cl_lru_list_lock); +- discard_pagevec(env, io, pvec, index); ++ discard_cl_pages(env, io, pvec, index); + index = 0; + + spin_lock(&cli->cl_lru_list_lock); +@@ -653,7 +653,7 @@ long osc_lru_shrink(const struct lu_env *env, struct client_obd *cli, + spin_unlock(&cli->cl_lru_list_lock); + + if (clobj != NULL) { +- discard_pagevec(env, io, pvec, index); ++ discard_cl_pages(env, io, pvec, index); + + cl_io_fini(env, io); + cl_object_put(env, clobj); +diff --git a/lustre/osd-ldiskfs/osd_io.c b/lustre/osd-ldiskfs/osd_io.c +index e8a3e0b5c0..9a1eb0485d 100644 +--- a/lustre/osd-ldiskfs/osd_io.c ++++ b/lustre/osd-ldiskfs/osd_io.c +@@ -663,11 +663,11 @@ static int osd_bufs_put(const struct lu_env *env, struct dt_object *dt, + struct osd_device *osd = osd_obj2dev(osd_dt_obj(dt)); + struct osd_thread_info *oti = osd_oti_get(env); + struct osd_iobuf *iobuf = &oti->oti_iobuf; +- struct pagevec pvec; ++ struct folio_batch fbatch; + int i; + + osd_brw_stats_update(osd, iobuf); +- ll_pagevec_init(&pvec, 0); ++ ll_folio_batch_init(&fbatch, 0); + + for (i = 0; i < npages; i++) { + struct page *page = lnb[i].lnb_page; +@@ -683,8 +683,8 @@ static int osd_bufs_put(const struct lu_env *env, struct dt_object *dt, + } else { + if (lnb[i].lnb_locked) + unlock_page(page); +- if (pagevec_add(&pvec, page) == 0) +- pagevec_release(&pvec); ++ if (folio_batch_add_page(&fbatch, page) == 0) ++ folio_batch_release(&fbatch); + } + + lnb[i].lnb_page = NULL; +@@ -692,8 +692,8 @@ static int osd_bufs_put(const struct lu_env *env, struct dt_object *dt, + + LASSERTF(oti->oti_dio_pages_used == 0, "%d\n", oti->oti_dio_pages_used); + +- /* Release any partial pagevec */ +- pagevec_release(&pvec); ++ /* Release any partial folio_batch */ ++ folio_batch_release(&fbatch); + + RETURN(0); + } +-- +2.33.0 + diff --git a/0006-LU-17243-build-compatibility-updates-for-kernel-6.6.patch b/0006-LU-17243-build-compatibility-updates-for-kernel-6.6.patch new file mode 100644 index 0000000000000000000000000000000000000000..e8b97a4e3c58c3704aa1f9631127453124fd1a66 --- /dev/null +++ b/0006-LU-17243-build-compatibility-updates-for-kernel-6.6.patch @@ -0,0 +1,916 @@ +From 6c84b3fa3765f8229c7f7f96a392aee27f44bfaa Mon Sep 17 00:00:00 2001 +From: Shaun Tancheff +Date: Thu, 7 Dec 2023 08:47:09 -0600 +Subject: [PATCH 6/6] LU-17243 build: compatibility updates for kernel 6.6 + +linux kernel v5.19-rc1-4-gc4f135d64382 + workqueue: Wrap flush_workqueue() using a macro +linux kernel v6.5-rc1-7-g20bdedafd2f6 + workqueue: Warn attempt to flush system-wide workqueues. +If __flush_workqueue(system_wq) is not available fall back to +flush_scheduled_work() + +linux kernel v6.5-rc1-92-g13bc24457850 + fs: rename i_ctime field to __i_ctime +Use accessors for ctime. Provide replacements for older +kernels. + +linux kernel v6.5-rc1-95-g0d72b92883c6 + fs: pass the request_mask to generic_fillattr +Provide request_mask argument where needed. + +Linux commit v6.5-rc2-20-g2ddd3cac1fa9 + nsproxy: Convert nsproxy.count to refcount_t +Provide a wrapper for inc/dec of nsproxy.count + +linux kernel v6.5-rc4-110-gcf95e337cb63 + mm: delete mmap_write_trylock() and vma_try_start_write() +Use down_write_trylock directly mmap_write_trylock + +In preparation for kernel 6.7 the remaining inode time +accessors will be preferred: + +linux kernel v6.6-rc5-86-g12cd44023651 + fs: rename inode i_atime and i_mtime fields +Use accessors for atime and mtime. Provide replacements for +older kernels. + +Test-Parameters: trivial +Signed-off-by: Shaun Tancheff +Change-Id: Ide6c2e3e8db532449850b145c2d61b972d21f649 +--- + config/lustre-build.m4 | 2 + + libcfs/autoconf/lustre-libcfs.m4 | 2 - + libcfs/include/libcfs/linux/linux-mem.h | 8 ++ + libcfs/libcfs/linux/linux-prim.c | 2 +- + lustre/autoconf/lustre-core.m4 | 166 ++++++++++++++++++++++++ + lustre/include/lustre_compat.h | 56 ++++++++ + lustre/llite/file.c | 55 ++++---- + lustre/llite/llite_lib.c | 26 ++-- + lustre/llite/namei.c | 10 +- + lustre/llite/pcc.c | 20 +-- + lustre/llite/vvp_io.c | 2 +- + lustre/llite/vvp_object.c | 18 +-- + lustre/lmv/lmv_intent.c | 6 +- + lustre/lmv/lmv_obd.c | 17 +-- + lustre/obdclass/llog.c | 2 +- + lustre/obdclass/obdo.c | 10 +- + lustre/osd-ldiskfs/osd_handler.c | 24 ++-- + lustre/osd-ldiskfs/osd_io.c | 5 +- + lustre/osd-ldiskfs/osd_scrub.c | 4 +- + lustre/target/tgt_mount.c | 2 +- + 20 files changed, 340 insertions(+), 97 deletions(-) + +diff --git a/config/lustre-build.m4 b/config/lustre-build.m4 +index 9cca76dc0c..ec41108190 100644 +--- a/config/lustre-build.m4 ++++ b/config/lustre-build.m4 +@@ -173,6 +173,7 @@ AS_IF([test "x$enable_modules" = xyes], [ + LIBCFS_SRC_LOCKDEP_IS_HELD + LIBCFS_SRC_HAVE_WAIT_BIT_HEADER + LIBCFS_SRC_LINUX_BLK_INTEGRITY_HEADER ++ LIBCFS_SRC_HAVE_MMAP_LOCK + + LB2_LINUX_TEST_COMPILE_ALL([early], + [for available lustre kapi interfaces]) +@@ -180,6 +181,7 @@ AS_IF([test "x$enable_modules" = xyes], [ + LIBCFS_LOCKDEP_IS_HELD + LIBCFS_HAVE_WAIT_BIT_HEADER + LIBCFS_LINUX_BLK_INTEGRITY_HEADER ++ LIBCFS_HAVE_MMAP_LOCK + + # Run any parallel compile tests + LB_PROG_LINUX_SRC +diff --git a/libcfs/autoconf/lustre-libcfs.m4 b/libcfs/autoconf/lustre-libcfs.m4 +index ac6db4a2d7..8f00bc5e4e 100644 +--- a/libcfs/autoconf/lustre-libcfs.m4 ++++ b/libcfs/autoconf/lustre-libcfs.m4 +@@ -2484,7 +2484,6 @@ AC_DEFUN([LIBCFS_PROG_LINUX_SRC], [ + LIBCFS_SRC_IP6_SET_PREF + LIBCFS_SRC_VMALLOC_2ARGS + LIBCFS_SRC_HAVE_NR_UNSTABLE_NFS +- LIBCFS_SRC_HAVE_MMAP_LOCK + LIBCFS_SRC_KERNEL_SETSOCKOPT + LIBCFS_SRC_KEY_NEED_UNLINK + LIBCFS_SRC_SEC_RELEASE_SECCTX +@@ -2634,7 +2633,6 @@ AC_DEFUN([LIBCFS_PROG_LINUX_RESULTS], [ + LIBCFS_IP6_SET_PREF + LIBCFS_VMALLOC_2ARGS + LIBCFS_HAVE_NR_UNSTABLE_NFS +- LIBCFS_HAVE_MMAP_LOCK + LIBCFS_KERNEL_SETSOCKOPT + LIBCFS_KEY_NEED_UNLINK + LIBCFS_SEC_RELEASE_SECCTX +diff --git a/libcfs/include/libcfs/linux/linux-mem.h b/libcfs/include/libcfs/linux/linux-mem.h +index 3847cae326..55011f25ba 100644 +--- a/libcfs/include/libcfs/linux/linux-mem.h ++++ b/libcfs/include/libcfs/linux/linux-mem.h +@@ -128,6 +128,14 @@ static inline void mmap_read_unlock(struct mm_struct *mm) + { + up_read(&mm->mmap_sem); + } ++#else ++ #ifndef HAVE_MMAP_WRITE_TRYLOCK ++/* Replacement for mmap_write_trylock() */ ++static inline bool mmap_write_trylock(struct mm_struct *mm) ++{ ++ return down_write_trylock(&mm->mmap_lock) != 0; ++} ++ #endif /* HAVE_MMAP_WRITE_TRYLOCK */ + #endif + + #ifdef HAVE_VMALLOC_2ARGS +diff --git a/libcfs/libcfs/linux/linux-prim.c b/libcfs/libcfs/linux/linux-prim.c +index 660d328eed..dc42a06b1f 100644 +--- a/libcfs/libcfs/linux/linux-prim.c ++++ b/libcfs/libcfs/linux/linux-prim.c +@@ -228,7 +228,7 @@ int __init cfs_arch_init(void) + void __exit cfs_arch_exit(void) + { + /* exit_libcfs_vfree_atomic */ +- flush_scheduled_work(); ++ __flush_workqueue(system_wq); + + llcrypt_exit(); + } +diff --git a/lustre/autoconf/lustre-core.m4 b/lustre/autoconf/lustre-core.m4 +index 480f9f5245..d05c2d96f7 100644 +--- a/lustre/autoconf/lustre-core.m4 ++++ b/lustre/autoconf/lustre-core.m4 +@@ -4233,6 +4233,152 @@ AC_DEFUN([LC_HAVE_STRUCT_PAGEVEC], [ + ]) + ]) # LC_HAVE_STRUCT_PAGEVEC + ++# ++# LC_HAVE_FLUSH___WORKQUEUE ++# ++# linux kernel v6.5-rc1-7-g20bdedafd2f6 ++# workqueue: Warn attempt to flush system-wide workqueues. ++# ++AC_DEFUN([LC_SRC_HAVE_FLUSH___WORKQUEUE], [ ++ LB2_LINUX_TEST_SRC([flush_scheduled_work_warning], [ ++ #include ++ ],[ ++ __flush_workqueue(system_wq); ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_FLUSH___WORKQUEUE], [ ++ AC_MSG_CHECKING([if 'flush_scheduled_work()' throws warning]) ++ LB2_LINUX_TEST_RESULT([flush_scheduled_work_warning], [ ++ AC_DEFINE(HAVE_FLUSH___WORKQUEUE, 1, ++ ['__flush_workqueue(system_wq)' is available]) ++ ]) ++]) # LC_HAVE_FLUSH___WORKQUEUE ++ ++# ++# LC_HAVE_INODE_GET_CTIME ++# ++# linux kernel v6.5-rc1-92-g13bc24457850 ++# fs: rename i_ctime field to __i_ctime ++# ++AC_DEFUN([LC_SRC_HAVE_INODE_GET_CTIME], [ ++ LB2_LINUX_TEST_SRC([inode_get_ctime_exists], [ ++ #include ++ ],[ ++ struct inode *inode = NULL; ++ struct timespec64 ts __attribute__ ((unused)); ++ ++ ts = inode_get_ctime(inode); ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_INODE_GET_CTIME], [ ++ AC_MSG_CHECKING([if 'inode_get_ctime()' exists]) ++ LB2_LINUX_TEST_RESULT([inode_get_ctime_exists], [ ++ AC_DEFINE(HAVE_INODE_GET_CTIME, 1, ++ ['inode_get_ctime()' exists]) ++ ]) ++]) # LC_HAVE_INODE_GET_CTIME ++ ++# ++# LC_HAVE_MMAP_WRITE_TRYLOCK ++# ++# linux kernel v6.5-rc4-110-gcf95e337cb63 ++# mm: delete mmap_write_trylock() and vma_try_start_write() ++# ++AC_DEFUN([LC_SRC_HAVE_MMAP_WRITE_TRYLOCK], [ ++ LB2_LINUX_TEST_SRC([mmap_write_trylock_removed], [ ++ #include ++ ],[ ++ struct mm_struct *mm = NULL; ++ ++ (void)mmap_write_trylock(mm); ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_MMAP_WRITE_TRYLOCK], [ ++ AC_MSG_CHECKING([if 'mmap_write_trylock()' is available]) ++ LB2_LINUX_TEST_RESULT([mmap_write_trylock_removed], [ ++ AC_DEFINE(HAVE_MMAP_WRITE_TRYLOCK, 1, ++ ['mmap_write_trylock()' is available]) ++ ]) ++]) # LC_HAVE_MMAP_WRITE_TRYLOCK ++ ++# ++# LC_HAVE_GENERIC_FILEATTR_HAS_MASK_ARG ++# ++# linux kernel v6.5-rc1-95-g0d72b92883c6 ++# fs: pass the request_mask to generic_fillattr ++# ++AC_DEFUN([LC_SRC_HAVE_GENERIC_FILEATTR_HAS_MASK_ARG], [ ++ LB2_LINUX_TEST_SRC([generic_fillattr_has_request_mask_arg], [ ++ #include ++ ],[ ++ struct inode *inode = NULL; ++ struct mnt_idmap *map = NULL; ++ struct kstat *kstat = NULL; ++ ++ generic_fillattr(map, 0, inode, kstat); ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_GENERIC_FILEATTR_HAS_MASK_ARG], [ ++ AC_MSG_CHECKING([if 'generic_fillattr()' has request_mask argument]) ++ LB2_LINUX_TEST_RESULT([generic_fillattr_has_request_mask_arg], [ ++ AC_DEFINE(HAVE_GENERIC_FILEATTR_HAS_MASK_ARG, 1, ++ ['generic_fillattr()' has request_mask argument]) ++ AC_DEFINE([RQMASK_ARG], [0,], [default request_mask argument]) ++ ], [ ++ AC_DEFINE([RQMASK_ARG], [], [no request_mask argument needed]) ++ ]) ++]) # LC_HAVE_GENERIC_FILEATTR_HAS_MASK_ARG ++ ++# ++# LC_HAVE_NSPROXY_COUNT_AS_REFCOUNT ++# ++# Linux commit v6.5-rc2-20-g2ddd3cac1fa9 ++# nsproxy: Convert nsproxy.count to refcount_t ++# ++AC_DEFUN([LC_SRC_HAVE_NSPROXY_COUNT_AS_REFCOUNT], [ ++ LB2_LINUX_TEST_SRC([struct_nsproxy_count_refcount_t], [ ++ #include ++ ],[ ++ struct nsproxy *nsproxy = NULL; ++ ++ refcount_dec(&nsproxy->count); ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_NSPROXY_COUNT_AS_REFCOUNT], [ ++ AC_MSG_CHECKING([if 'struct nsproxy.count' is refcount_t]) ++ LB2_LINUX_TEST_RESULT([struct_nsproxy_count_refcount_t], [ ++ AC_DEFINE(HAVE_NSPROXY_COUNT_AS_REFCOUNT, 1, ++ ['struct nsproxy.count' is refcount_t]) ++ ]) ++]) # LC_HAVE_NSPROXY_COUNT_AS_REFCOUNT ++ ++# ++# LC_HAVE_INODE_GET_MTIME_SEC ++# ++# v6.6-rc5-1-g077c212f0344 ++# fs: new accessor methods for atime and mtime ++# ++# linux kernel v6.6-rc5-86-g12cd44023651 ++# fs: rename inode i_atime and i_mtime fields ++# ++AC_DEFUN([LC_SRC_HAVE_INODE_GET_MTIME_SEC], [ ++ LB2_LINUX_TEST_SRC([inode_get_mtime_exists], [ ++ #include ++ ],[ ++ struct inode *inode = NULL; ++ struct timespec64 ts __attribute__ ((unused)); ++ ++ ts = inode_get_mtime_sec(inode); ++ ],[-Werror]) ++]) ++AC_DEFUN([LC_HAVE_INODE_GET_MTIME_SEC], [ ++ AC_MSG_CHECKING([if 'inode_get_mtime()' exists]) ++ LB2_LINUX_TEST_RESULT([inode_get_mtime_exists], [ ++ AC_DEFINE(HAVE_INODE_GET_MTIME, 1, ++ ['inode_get_mtime()' exists]) ++ ]) ++]) # LC_HAVE_INODE_GET_MTIME_SEC ++ + # + # LC_PROG_LINUX + # +@@ -4506,6 +4652,16 @@ AC_DEFUN([LC_PROG_LINUX_SRC], [ + LC_SRC_HAVE_FOLIO_BATCH + LC_SRC_HAVE_STRUCT_PAGEVEC + ++ # 6.6 ++ LC_SRC_HAVE_FLUSH___WORKQUEUE ++ LC_SRC_HAVE_INODE_GET_CTIME ++ LC_SRC_HAVE_MMAP_WRITE_TRYLOCK ++ LC_SRC_HAVE_GENERIC_FILEATTR_HAS_MASK_ARG ++ LC_SRC_HAVE_NSPROXY_COUNT_AS_REFCOUNT ++ ++ # 6.7 ++ LC_SRC_HAVE_INODE_GET_MTIME_SEC ++ + # kernel patch to extend integrity interface + LC_SRC_BIO_INTEGRITY_PREP_FN + ]) +@@ -4799,6 +4955,16 @@ AC_DEFUN([LC_PROG_LINUX_RESULTS], [ + LC_HAVE_FOLIO_BATCH + LC_HAVE_STRUCT_PAGEVEC + ++ # 6.6 ++ LC_HAVE_FLUSH___WORKQUEUE ++ LC_HAVE_INODE_GET_CTIME ++ LC_HAVE_MMAP_WRITE_TRYLOCK ++ LC_HAVE_GENERIC_FILEATTR_HAS_MASK_ARG ++ LC_HAVE_NSPROXY_COUNT_AS_REFCOUNT ++ ++ # 6.7 ++ LC_HAVE_INODE_GET_MTIME_SEC ++ + # kernel patch to extend integrity interface + LC_BIO_INTEGRITY_PREP_FN + ]) +diff --git a/lustre/include/lustre_compat.h b/lustre/include/lustre_compat.h +index 9adf41ca5e..5547ff92fa 100644 +--- a/lustre/include/lustre_compat.h ++++ b/lustre/include/lustre_compat.h +@@ -45,6 +45,7 @@ + #include + #include + #include ++#include + #include + #ifdef HAVE_XARRAY_SUPPORT + #include +@@ -779,4 +780,59 @@ static inline void folio_batch_reinit(struct folio_batch *fbatch) + # define fbatch_at_pg(pvec, n, pg) ((pvec)->pages[(n)]) + #endif /* HAVE_FOLIO_BATCH */ + ++#ifndef HAVE_FLUSH___WORKQUEUE ++#define __flush_workqueue(wq) flush_scheduled_work() ++#endif ++ ++#ifdef HAVE_NSPROXY_COUNT_AS_REFCOUNT ++#define nsproxy_dec(ns) refcount_dec(&(ns)->count) ++#else ++#define nsproxy_dec(ns) atomic_dec(&(ns)->count) ++#endif ++ ++#ifndef HAVE_INODE_GET_CTIME ++#define inode_get_ctime(i) ((i)->i_ctime) ++#define inode_set_ctime_to_ts(i, ts) ((i)->i_ctime = ts) ++#define inode_set_ctime_current(i) \ ++ inode_set_ctime_to_ts((i), current_time((i))) ++ ++static inline struct timespec64 inode_set_ctime(struct inode *inode, ++ time64_t sec, long nsec) ++{ ++ struct timespec64 ts = { .tv_sec = sec, ++ .tv_nsec = nsec }; ++ ++ return inode_set_ctime_to_ts(inode, ts); ++} ++#endif /* !HAVE_INODE_GET_CTIME */ ++ ++#ifndef HAVE_INODE_GET_MTIME_SEC ++ ++#define inode_get_ctime_sec(i) (inode_get_ctime((i)).tv_sec) ++ ++#define inode_get_atime(i) ((i)->i_atime) ++#define inode_get_atime_sec(i) ((i)->i_atime.tv_sec) ++#define inode_set_atime_to_ts(i, ts) ((i)->i_atime = ts) ++ ++static inline struct timespec64 inode_set_atime(struct inode *inode, ++ time64_t sec, long nsec) ++{ ++ struct timespec64 ts = { .tv_sec = sec, ++ .tv_nsec = nsec }; ++ return inode_set_atime_to_ts(inode, ts); ++} ++ ++#define inode_get_mtime(i) ((i)->i_mtime) ++#define inode_get_mtime_sec(i) ((i)->i_mtime.tv_sec) ++#define inode_set_mtime_to_ts(i, ts) ((i)->i_mtime = ts) ++ ++static inline struct timespec64 inode_set_mtime(struct inode *inode, ++ time64_t sec, long nsec) ++{ ++ struct timespec64 ts = { .tv_sec = sec, ++ .tv_nsec = nsec }; ++ return inode_set_mtime_to_ts(inode, ts); ++} ++#endif /* !HAVE_INODE_GET_MTIME_SEC */ ++ + #endif /* _LUSTRE_COMPAT_H */ +diff --git a/lustre/llite/file.c b/lustre/llite/file.c +index a33502ccb9..6a1c45b9a6 100644 +--- a/lustre/llite/file.c ++++ b/lustre/llite/file.c +@@ -105,9 +105,9 @@ static void ll_prepare_close(struct inode *inode, struct md_op_data *op_data, + 0, 0, LUSTRE_OPC_ANY, NULL); + + op_data->op_attr.ia_mode = inode->i_mode; +- op_data->op_attr.ia_atime = inode->i_atime; +- op_data->op_attr.ia_mtime = inode->i_mtime; +- op_data->op_attr.ia_ctime = inode->i_ctime; ++ op_data->op_attr.ia_atime = inode_get_atime(inode); ++ op_data->op_attr.ia_mtime = inode_get_mtime(inode); ++ op_data->op_attr.ia_ctime = inode_get_ctime(inode); + /* In case of encrypted file without the key, visible size was rounded + * up to next LUSTRE_ENCRYPTION_UNIT_SIZE, and clear text size was + * stored into lli_lazysize in ll_merge_attr(), so set proper file size +@@ -1458,15 +1458,15 @@ static int ll_merge_attr_nolock(const struct lu_env *env, struct inode *inode) + * read, this will hurt performance. + */ + if (test_and_clear_bit(LLIF_UPDATE_ATIME, &lli->lli_flags) || +- inode->i_atime.tv_sec < lli->lli_atime) +- inode->i_atime.tv_sec = lli->lli_atime; ++ inode_get_atime_sec(inode) < lli->lli_atime) ++ inode_set_atime(inode, lli->lli_atime, 0); + +- inode->i_mtime.tv_sec = lli->lli_mtime; +- inode->i_ctime.tv_sec = lli->lli_ctime; ++ inode_set_mtime(inode, lli->lli_mtime, 0); ++ inode_set_ctime(inode, lli->lli_ctime, 0); + +- mtime = inode->i_mtime.tv_sec; +- atime = inode->i_atime.tv_sec; +- ctime = inode->i_ctime.tv_sec; ++ mtime = inode_get_mtime_sec(inode); ++ atime = inode_get_atime_sec(inode); ++ ctime = inode_get_ctime_sec(inode); + + cl_object_attr_lock(obj); + if (CFS_FAIL_CHECK(OBD_FAIL_MDC_MERGE)) +@@ -1503,9 +1503,9 @@ static int ll_merge_attr_nolock(const struct lu_env *env, struct inode *inode) + i_size_write(inode, attr->cat_size); + inode->i_blocks = attr->cat_blocks; + +- inode->i_mtime.tv_sec = mtime; +- inode->i_atime.tv_sec = atime; +- inode->i_ctime.tv_sec = ctime; ++ inode_set_mtime(inode, mtime, 0); ++ inode_set_atime(inode, atime, 0); ++ inode_set_ctime(inode, ctime, 0); + + EXIT; + out: +@@ -1568,25 +1568,30 @@ void ll_io_set_mirror(struct cl_io *io, const struct file *file) + static int relatime_need_update(struct vfsmount *mnt, struct inode *inode, + struct timespec64 now) + { ++ struct timespec64 ts; ++ struct timespec64 atime; + + if (!(mnt->mnt_flags & MNT_RELATIME)) + return 1; + /* + * Is mtime younger than atime? If yes, update atime: + */ +- if (timespec64_compare(&inode->i_mtime, &inode->i_atime) >= 0) ++ atime = inode_get_atime(inode); ++ ts = inode_get_mtime(inode); ++ if (timespec64_compare(&ts, &atime) >= 0) + return 1; + /* + * Is ctime younger than atime? If yes, update atime: + */ +- if (timespec64_compare(&inode->i_ctime, &inode->i_atime) >= 0) ++ ts = inode_get_ctime(inode); ++ if (timespec64_compare(&ts, &atime) >= 0) + return 1; + + /* + * Is the previous atime value older than a day? If yes, + * update atime: + */ +- if ((long)(now.tv_sec - inode->i_atime.tv_sec) >= 24*60*60) ++ if ((long)(now.tv_sec - atime.tv_sec) >= 24*60*60) + return 1; + /* + * Good, we can skip the atime update: +@@ -5529,11 +5534,11 @@ int ll_getattr_dentry(struct dentry *de, struct kstat *stat, u32 request_mask, + if (lli->lli_attr_valid & OBD_MD_FLSIZE && + lli->lli_attr_valid & OBD_MD_FLBLOCKS && + lli->lli_attr_valid & OBD_MD_FLMTIME) { +- inode->i_mtime.tv_sec = lli->lli_mtime; ++ inode_set_mtime(inode, lli->lli_mtime, 0); + if (lli->lli_attr_valid & OBD_MD_FLATIME) +- inode->i_atime.tv_sec = lli->lli_atime; ++ inode_set_atime(inode, lli->lli_atime, 0); + if (lli->lli_attr_valid & OBD_MD_FLCTIME) +- inode->i_ctime.tv_sec = lli->lli_ctime; ++ inode_set_ctime(inode, lli->lli_ctime, 0); + GOTO(fill_attr, rc); + } + +@@ -5559,11 +5564,11 @@ int ll_getattr_dentry(struct dentry *de, struct kstat *stat, u32 request_mask, + } + + if (lli->lli_attr_valid & OBD_MD_FLATIME) +- inode->i_atime.tv_sec = lli->lli_atime; ++ inode_set_atime(inode, lli->lli_atime, 0); + if (lli->lli_attr_valid & OBD_MD_FLMTIME) +- inode->i_mtime.tv_sec = lli->lli_mtime; ++ inode_set_mtime(inode, lli->lli_mtime, 0); + if (lli->lli_attr_valid & OBD_MD_FLCTIME) +- inode->i_ctime.tv_sec = lli->lli_ctime; ++ inode_set_ctime(inode, lli->lli_ctime, 0); + } + + fill_attr: +@@ -5587,9 +5592,9 @@ fill_attr: + + stat->uid = inode->i_uid; + stat->gid = inode->i_gid; +- stat->atime = inode->i_atime; +- stat->mtime = inode->i_mtime; +- stat->ctime = inode->i_ctime; ++ stat->atime = inode_get_atime(inode); ++ stat->mtime = inode_get_mtime(inode); ++ stat->ctime = inode_get_ctime(inode); + /* stat->blksize is used to tell about preferred IO size */ + if (sbi->ll_stat_blksize) + stat->blksize = sbi->ll_stat_blksize; +diff --git a/lustre/llite/llite_lib.c b/lustre/llite/llite_lib.c +index 1baa5071fc..438a7b48d0 100644 +--- a/lustre/llite/llite_lib.c ++++ b/lustre/llite/llite_lib.c +@@ -1650,9 +1650,9 @@ static struct inode *ll_iget_anon_dir(struct super_block *sb, + LASSERTF(S_ISDIR(inode->i_mode), "Not slave inode "DFID"\n", + PFID(fid)); + +- inode->i_mtime.tv_sec = 0; +- inode->i_atime.tv_sec = 0; +- inode->i_ctime.tv_sec = 0; ++ inode_set_mtime(inode, 0, 0); ++ inode_set_atime(inode, 0, 0); ++ inode_set_ctime(inode, 0, 0); + inode->i_rdev = 0; + + #ifdef HAVE_BACKING_DEV_INFO +@@ -2738,25 +2738,25 @@ int ll_update_inode(struct inode *inode, struct lustre_md *md) + inode->i_generation = cl_fid_build_gen(&body->mbo_fid1); + + if (body->mbo_valid & OBD_MD_FLATIME) { +- if (body->mbo_atime > inode->i_atime.tv_sec) +- inode->i_atime.tv_sec = body->mbo_atime; ++ if (body->mbo_atime > inode_get_atime_sec(inode)) ++ inode_set_atime(inode, body->mbo_atime, 0); + lli->lli_atime = body->mbo_atime; + } + + if (body->mbo_valid & OBD_MD_FLMTIME) { +- if (body->mbo_mtime > inode->i_mtime.tv_sec) { ++ if (body->mbo_mtime > inode_get_mtime_sec(inode)) { + CDEBUG(D_INODE, + "setting ino %lu mtime from %lld to %llu\n", +- inode->i_ino, (s64)inode->i_mtime.tv_sec, ++ inode->i_ino, (s64) inode_get_mtime_sec(inode), + body->mbo_mtime); +- inode->i_mtime.tv_sec = body->mbo_mtime; ++ inode_set_mtime(inode, body->mbo_mtime, 0); + } + lli->lli_mtime = body->mbo_mtime; + } + + if (body->mbo_valid & OBD_MD_FLCTIME) { +- if (body->mbo_ctime > inode->i_ctime.tv_sec) +- inode->i_ctime.tv_sec = body->mbo_ctime; ++ if (body->mbo_ctime > inode_get_ctime_sec(inode)) ++ inode_set_ctime(inode, body->mbo_ctime, 0); + lli->lli_ctime = body->mbo_ctime; + } + +@@ -3065,9 +3065,9 @@ int ll_read_inode2(struct inode *inode, void *opaque) + * it ourselves. They will be overwritten by either MDS or OST + * attributes - we just need to make sure they aren't newer. + */ +- inode->i_mtime.tv_sec = 0; +- inode->i_atime.tv_sec = 0; +- inode->i_ctime.tv_sec = 0; ++ inode_set_mtime(inode, 0, 0); ++ inode_set_atime(inode, 0, 0); ++ inode_set_ctime(inode, 0, 0); + inode->i_rdev = 0; + rc = ll_update_inode(inode, md); + if (rc != 0) +diff --git a/lustre/llite/namei.c b/lustre/llite/namei.c +index 5f5dc1280c..79e9e294ff 100644 +--- a/lustre/llite/namei.c ++++ b/lustre/llite/namei.c +@@ -1481,17 +1481,17 @@ void ll_update_times(struct ptlrpc_request *request, struct inode *inode) + + LASSERT(body); + if (body->mbo_valid & OBD_MD_FLMTIME && +- body->mbo_mtime > inode->i_mtime.tv_sec) { ++ body->mbo_mtime > inode_get_mtime_sec(inode)) { + CDEBUG(D_INODE, + "setting fid " DFID " mtime from %lld to %llu\n", + PFID(ll_inode2fid(inode)), +- (s64)inode->i_mtime.tv_sec, body->mbo_mtime); +- inode->i_mtime.tv_sec = body->mbo_mtime; ++ (s64)inode_get_mtime_sec(inode), body->mbo_mtime); ++ inode_set_mtime(inode, body->mbo_mtime, 0); + } + + if (body->mbo_valid & OBD_MD_FLCTIME && +- body->mbo_ctime > inode->i_ctime.tv_sec) +- inode->i_ctime.tv_sec = body->mbo_ctime; ++ body->mbo_ctime > inode_get_ctime_sec(inode)) ++ inode_set_ctime(inode, body->mbo_ctime, 0); + } + + /* once default LMV (space balanced) is set on ROOT, it should take effect if +diff --git a/lustre/llite/pcc.c b/lustre/llite/pcc.c +index 9471e1097a..4b7f1f5778 100644 +--- a/lustre/llite/pcc.c ++++ b/lustre/llite/pcc.c +@@ -1792,15 +1792,15 @@ int pcc_inode_getattr(struct inode *inode, u32 request_mask, + + ll_inode_size_lock(inode); + if (test_and_clear_bit(LLIF_UPDATE_ATIME, &lli->lli_flags) || +- inode->i_atime.tv_sec < lli->lli_atime) +- inode->i_atime.tv_sec = lli->lli_atime; ++ inode_get_atime_sec(inode) < lli->lli_atime) ++ inode_set_atime(inode, lli->lli_atime, 0); + +- inode->i_mtime.tv_sec = lli->lli_mtime; +- inode->i_ctime.tv_sec = lli->lli_ctime; ++ inode_set_mtime(inode, lli->lli_mtime, 0); ++ inode_set_ctime(inode, lli->lli_ctime, 0); + +- atime = inode->i_atime.tv_sec; +- mtime = inode->i_mtime.tv_sec; +- ctime = inode->i_ctime.tv_sec; ++ atime = inode_get_atime_sec(inode); ++ mtime = inode_get_mtime_sec(inode); ++ ctime = inode_get_ctime_sec(inode); + + if (atime < stat.atime.tv_sec) + atime = stat.atime.tv_sec; +@@ -1814,9 +1814,9 @@ int pcc_inode_getattr(struct inode *inode, u32 request_mask, + i_size_write(inode, stat.size); + inode->i_blocks = stat.blocks; + +- inode->i_atime.tv_sec = atime; +- inode->i_mtime.tv_sec = mtime; +- inode->i_ctime.tv_sec = ctime; ++ inode_set_atime(inode, atime, 0); ++ inode_set_mtime(inode, mtime, 0); ++ inode_set_ctime(inode, ctime, 0); + + ll_inode_size_unlock(inode); + out: +diff --git a/lustre/llite/vvp_io.c b/lustre/llite/vvp_io.c +index 0043edcd9b..63fd50b262 100644 +--- a/lustre/llite/vvp_io.c ++++ b/lustre/llite/vvp_io.c +@@ -794,7 +794,7 @@ static void vvp_io_setattr_end(const struct lu_env *env, + i_size_write(inode, size); + ll_inode_size_unlock(inode); + } +- inode->i_ctime = current_time(inode); ++ inode_set_ctime_current(inode); + mutex_unlock(&lli->lli_setattr_mutex); + trunc_sem_up_write(&lli->lli_trunc_sem); + } else { +diff --git a/lustre/llite/vvp_object.c b/lustre/llite/vvp_object.c +index 42a5148192..5febda942a 100644 +--- a/lustre/llite/vvp_object.c ++++ b/lustre/llite/vvp_object.c +@@ -91,9 +91,9 @@ static int vvp_attr_get(const struct lu_env *env, struct cl_object *obj, + */ + + attr->cat_size = i_size_read(inode); +- attr->cat_mtime = inode->i_mtime.tv_sec; +- attr->cat_atime = inode->i_atime.tv_sec; +- attr->cat_ctime = inode->i_ctime.tv_sec; ++ attr->cat_mtime = inode_get_mtime_sec(inode); ++ attr->cat_atime = inode_get_atime_sec(inode); ++ attr->cat_ctime = inode_get_ctime_sec(inode); + attr->cat_blocks = inode->i_blocks; + attr->cat_uid = from_kuid(&init_user_ns, inode->i_uid); + attr->cat_gid = from_kgid(&init_user_ns, inode->i_gid); +@@ -112,11 +112,11 @@ static int vvp_attr_update(const struct lu_env *env, struct cl_object *obj, + if (valid & CAT_GID) + inode->i_gid = make_kgid(&init_user_ns, attr->cat_gid); + if (valid & CAT_ATIME) +- inode->i_atime.tv_sec = attr->cat_atime; ++ inode_set_atime(inode, attr->cat_atime, 0); + if (valid & CAT_MTIME) +- inode->i_mtime.tv_sec = attr->cat_mtime; ++ inode_set_mtime(inode, attr->cat_mtime, 0); + if (valid & CAT_CTIME) +- inode->i_ctime.tv_sec = attr->cat_ctime; ++ inode_set_ctime(inode, attr->cat_ctime, 0); + if (0 && valid & CAT_SIZE) + i_size_write(inode, attr->cat_size); + if (valid & CAT_PROJID) +@@ -193,9 +193,9 @@ static int vvp_object_glimpse(const struct lu_env *env, + struct inode *inode = vvp_object_inode(obj); + + ENTRY; +- lvb->lvb_mtime = inode->i_mtime.tv_sec; +- lvb->lvb_atime = inode->i_atime.tv_sec; +- lvb->lvb_ctime = inode->i_ctime.tv_sec; ++ lvb->lvb_mtime = inode_get_mtime_sec(inode); ++ lvb->lvb_atime = inode_get_atime_sec(inode); ++ lvb->lvb_ctime = inode_get_ctime_sec(inode); + + /* + * LU-417: Add dirty pages block count lest i_blocks reports 0, some +diff --git a/lustre/lmv/lmv_intent.c b/lustre/lmv/lmv_intent.c +index 1acdd84fae..ee55128825 100644 +--- a/lustre/lmv/lmv_intent.c ++++ b/lustre/lmv/lmv_intent.c +@@ -255,9 +255,9 @@ int lmv_revalidate_slaves(struct obd_export *exp, + spin_lock(&inode->i_lock); + set_nlink(inode, body->mbo_nlink); + spin_unlock(&inode->i_lock); +- inode->i_atime.tv_sec = body->mbo_atime; +- inode->i_ctime.tv_sec = body->mbo_ctime; +- inode->i_mtime.tv_sec = body->mbo_mtime; ++ inode_set_atime(inode, body->mbo_atime, 0); ++ inode_set_ctime(inode, body->mbo_ctime, 0); ++ inode_set_mtime(inode, body->mbo_mtime, 0); + } + + md_set_lock_data(tgt->ltd_exp, lockh, inode, NULL); +diff --git a/lustre/lmv/lmv_obd.c b/lustre/lmv/lmv_obd.c +index 2841ba33bd..1e3b96b653 100644 +--- a/lustre/lmv/lmv_obd.c ++++ b/lustre/lmv/lmv_obd.c +@@ -3965,8 +3965,9 @@ static int lmv_merge_attr(struct obd_export *exp, + "" DFID " size %llu, blocks %llu nlink %u, atime %lld ctime %lld, mtime %lld.\n", + PFID(&lsm->lsm_md_oinfo[i].lmo_fid), + i_size_read(inode), (unsigned long long)inode->i_blocks, +- inode->i_nlink, (s64)inode->i_atime.tv_sec, +- (s64)inode->i_ctime.tv_sec, (s64)inode->i_mtime.tv_sec); ++ inode->i_nlink, (s64)inode_get_atime_sec(inode), ++ (s64)inode_get_ctime_sec(inode), ++ (s64)inode_get_mtime_sec(inode)); + + /* for slave stripe, it needs to subtract nlink for . and .. */ + if (i != 0) +@@ -3977,14 +3978,14 @@ static int lmv_merge_attr(struct obd_export *exp, + attr->cat_size += i_size_read(inode); + attr->cat_blocks += inode->i_blocks; + +- if (attr->cat_atime < inode->i_atime.tv_sec) +- attr->cat_atime = inode->i_atime.tv_sec; ++ if (attr->cat_atime < inode_get_atime_sec(inode)) ++ attr->cat_atime = inode_get_atime_sec(inode); + +- if (attr->cat_ctime < inode->i_ctime.tv_sec) +- attr->cat_ctime = inode->i_ctime.tv_sec; ++ if (attr->cat_ctime < inode_get_ctime_sec(inode)) ++ attr->cat_ctime = inode_get_ctime_sec(inode); + +- if (attr->cat_mtime < inode->i_mtime.tv_sec) +- attr->cat_mtime = inode->i_mtime.tv_sec; ++ if (attr->cat_mtime < inode_get_mtime_sec(inode)) ++ attr->cat_mtime = inode_get_mtime_sec(inode); + } + return 0; + } +diff --git a/lustre/obdclass/llog.c b/lustre/obdclass/llog.c +index 61e836e331..35a75a3785 100644 +--- a/lustre/obdclass/llog.c ++++ b/lustre/obdclass/llog.c +@@ -849,7 +849,7 @@ static int llog_process_thread_daemonize(void *arg) + * free_nsproxy() which is not exported by the kernel + * (defined in kernel/nsproxy.c) */ + if (curr_ns) +- atomic_dec(&curr_ns->count); ++ nsproxy_dec(curr_ns); + } + task_unlock(lpi->lpi_reftask); + +diff --git a/lustre/obdclass/obdo.c b/lustre/obdclass/obdo.c +index b1d7337b94..35f707fd7b 100644 +--- a/lustre/obdclass/obdo.c ++++ b/lustre/obdclass/obdo.c +@@ -69,19 +69,19 @@ void obdo_from_inode(struct obdo *dst, struct inode *src, u64 valid) + + if (valid & (OBD_MD_FLCTIME | OBD_MD_FLMTIME)) + CDEBUG(D_INODE, "valid %#llx, new time %lld/%lld\n", +- valid, (s64) src->i_mtime.tv_sec, +- (s64) src->i_ctime.tv_sec); ++ valid, (s64) inode_get_mtime_sec(src), ++ (s64) inode_get_ctime_sec(src)); + + if (valid & OBD_MD_FLATIME) { +- dst->o_atime = src->i_atime.tv_sec; ++ dst->o_atime = inode_get_atime_sec(src); + newvalid |= OBD_MD_FLATIME; + } + if (valid & OBD_MD_FLMTIME) { +- dst->o_mtime = src->i_mtime.tv_sec; ++ dst->o_mtime = inode_get_mtime_sec(src); + newvalid |= OBD_MD_FLMTIME; + } + if (valid & OBD_MD_FLCTIME) { +- dst->o_ctime = src->i_ctime.tv_sec; ++ dst->o_ctime = inode_get_ctime_sec(src); + newvalid |= OBD_MD_FLCTIME; + } + if (valid & OBD_MD_FLSIZE) { +diff --git a/lustre/osd-ldiskfs/osd_handler.c b/lustre/osd-ldiskfs/osd_handler.c +index e42fff125b..234fddd164 100644 +--- a/lustre/osd-ldiskfs/osd_handler.c ++++ b/lustre/osd-ldiskfs/osd_handler.c +@@ -2852,9 +2852,9 @@ static void osd_inode_getattr(const struct lu_env *env, + LA_PROJID | LA_FLAGS | LA_NLINK | LA_RDEV | + LA_BLKSIZE | LA_TYPE | LA_BTIME; + +- attr->la_atime = inode->i_atime.tv_sec; +- attr->la_mtime = inode->i_mtime.tv_sec; +- attr->la_ctime = inode->i_ctime.tv_sec; ++ attr->la_atime = inode_get_atime_sec(inode); ++ attr->la_mtime = inode_get_mtime_sec(inode); ++ attr->la_ctime = inode_get_ctime_sec(inode); + attr->la_btime = LDISKFS_I(inode)->i_crtime.tv_sec; + attr->la_mode = inode->i_mode; + attr->la_size = i_size_read(inode); +@@ -3124,11 +3124,14 @@ static int osd_inode_setattr(const struct lu_env *env, + return 0; + + if (bits & LA_ATIME) +- inode->i_atime = osd_inode_time(inode, attr->la_atime); ++ inode_set_atime_to_ts(inode, ++ osd_inode_time(inode, attr->la_atime)); + if (bits & LA_CTIME) +- inode->i_ctime = osd_inode_time(inode, attr->la_ctime); ++ inode_set_ctime_to_ts(inode, ++ osd_inode_time(inode, attr->la_ctime)); + if (bits & LA_MTIME) +- inode->i_mtime = osd_inode_time(inode, attr->la_mtime); ++ inode_set_mtime_to_ts(inode, ++ osd_inode_time(inode, attr->la_mtime)); + if (bits & LA_SIZE) { + spin_lock(&inode->i_lock); + LDISKFS_I(inode)->i_disksize = attr->la_size; +@@ -3686,11 +3689,14 @@ static void osd_attr_init(struct osd_thread_info *info, struct osd_object *obj, + + if (dof->dof_type != DFT_NODE) + attr->la_valid &= ~LA_RDEV; +- if ((valid & LA_ATIME) && (attr->la_atime == inode->i_atime.tv_sec)) ++ if ((valid & LA_ATIME) && ++ (attr->la_atime == inode_get_atime_sec(inode))) + attr->la_valid &= ~LA_ATIME; +- if ((valid & LA_CTIME) && (attr->la_ctime == inode->i_ctime.tv_sec)) ++ if ((valid & LA_CTIME) && ++ (attr->la_ctime == inode_get_ctime_sec(inode))) + attr->la_valid &= ~LA_CTIME; +- if ((valid & LA_MTIME) && (attr->la_mtime == inode->i_mtime.tv_sec)) ++ if ((valid & LA_MTIME) && ++ (attr->la_mtime == inode_get_mtime_sec(inode))) + attr->la_valid &= ~LA_MTIME; + + result = osd_quota_transfer(inode, attr, handle); +diff --git a/lustre/osd-ldiskfs/osd_io.c b/lustre/osd-ldiskfs/osd_io.c +index 9a1eb0485d..948caef639 100644 +--- a/lustre/osd-ldiskfs/osd_io.c ++++ b/lustre/osd-ldiskfs/osd_io.c +@@ -2245,12 +2245,13 @@ static int osd_fallocate_preallocate(const struct lu_env *env, + map.m_lblk += rc; + map.m_len = blen = blen - rc; + epos = (loff_t)map.m_lblk << inode->i_blkbits; +- inode->i_ctime = current_time(inode); ++ inode_set_ctime_current(inode); + if (new_size) { + if (epos > end) + epos = end; + if (ldiskfs_update_inode_size(inode, epos) & 0x1) +- inode->i_mtime = inode->i_ctime; ++ inode_set_mtime_to_ts(inode, ++ inode_get_ctime(inode)); + #ifdef LDISKFS_EOFBLOCKS_FL + } else { + if (epos > inode->i_size) +diff --git a/lustre/osd-ldiskfs/osd_scrub.c b/lustre/osd-ldiskfs/osd_scrub.c +index f99798c836..2ca06dc4c8 100644 +--- a/lustre/osd-ldiskfs/osd_scrub.c ++++ b/lustre/osd-ldiskfs/osd_scrub.c +@@ -415,8 +415,8 @@ osd_scrub_check_update(struct osd_thread_info *info, struct osd_device *dev, + fid2 = &info->oti_ost_attrs.loa_lma.lma_self_fid; + if ((rc == 0 && lu_fid_eq(fid, fid2)) && + ((inode->i_size == 0 && inode2->i_size > 0 && +- inode->i_mtime.tv_sec == inode2->i_mtime.tv_sec) || +- inode->i_mtime.tv_sec < inode2->i_mtime.tv_sec)) { ++ inode_get_mtime_sec(inode) == inode_get_mtime_sec(inode2)) || ++ inode_get_mtime_sec(inode) < inode_get_mtime_sec(inode2))) { + iput(inode2); + GOTO(skip, rc); + } +diff --git a/lustre/target/tgt_mount.c b/lustre/target/tgt_mount.c +index eeab3c1600..1aa29f9822 100644 +--- a/lustre/target/tgt_mount.c ++++ b/lustre/target/tgt_mount.c +@@ -1966,7 +1966,7 @@ static int server_getattr(struct vfsmount *mnt, struct dentry *de, + CDEBUG(D_SUPER, "%s: root_inode from %s ino=%lu, dev=%x\n", + lsi->lsi_svname, root_inode == inode ? "lsi" : "vfsmnt", + root_inode->i_ino, root_inode->i_rdev); +- generic_fillattr(IDMAP_ARG root_inode, stat); ++ generic_fillattr(IDMAP_ARG RQMASK_ARG root_inode, stat); + iput(root_inode); + + return 0; +-- +2.33.0 + diff --git a/2.15.57.tar.gz b/2.15.59.tar.gz similarity index 78% rename from 2.15.57.tar.gz rename to 2.15.59.tar.gz index 0d0d1a9b9836fe05d7a3de830bc54f4757d48cc1..a904503e91f8b666e469d652e85fcfc474db94e0 100644 Binary files a/2.15.57.tar.gz and b/2.15.59.tar.gz differ diff --git a/kmp-lustre-tests.files b/kmp-lustre-tests.files index fd7aed8a68e362295e0f2b07749a6708d3140507..bc1838e85e222eff1f8246aa0c90e52ce487c81c 100644 --- a/kmp-lustre-tests.files +++ b/kmp-lustre-tests.files @@ -1,3 +1,4 @@ %dir %{modules_fs_path}/%{lustre_name}-tests %dir %{modules_fs_path}/%{lustre_name}-tests/fs %{modules_fs_path}/%{lustre_name}-tests/fs/llog_test.ko +%{modules_fs_path}/%{lustre_name}-tests/fs/obd_test.ko diff --git a/lustre.spec b/lustre.spec index b066313bc524f187b7f4e0c20ccd6597c8f0747e..51d93c6d07038914d367fc23c5fe67e4037e1a88 100644 --- a/lustre.spec +++ b/lustre.spec @@ -16,7 +16,6 @@ %bcond_without lustre_utils %bcond_without lustre_iokit %bcond_without lustre_modules -%bcond_with snmp %bcond_with gss %bcond_with gss_keyring %bcond_without manpages @@ -57,7 +56,7 @@ %undefine with_lustre_tests %endif -%{!?version: %global version 2.15.57} +%{!?version: %global version 2.15.59} # if you want a custom kernel version set it variable with $ver.$arch %{!?kver: %global kver %(rpm -q --qf '%%{VERSION}-%%{RELEASE}.%%{ARCH}' `rpm -q kernel-devel | sort -rV|head -n 1`)} # cut epoch for kmodtool @@ -192,7 +191,7 @@ Summary: Lustre File System Name: %{lustre_name} -Version: 2.15.57 +Version: 2.15.59 Release: 1 License: GPL-2.0-only AND LGPL-2.1-or-later %if 0%{?suse_version} >= 1310 @@ -214,7 +213,12 @@ URL: https://wiki.whamcloud.com/ BuildRoot: %{_tmppath}/lustre-%{version}-root # patches -Patch1: LU-16802-build-iov_iter_iovec-class_create-get_expir.patch +Patch1: 0001-LU-9859-libcfs-refactor-libcfs-initialization.patch +Patch2: 0002-LU-16802-build-compatibility-for-6.4-kernels.patch +Patch3: 0003-LU-17085-llite-safely-duplicate-iov_iter.patch +Patch4: 0004-LU-17081-build-compatibility-for-6.5-kernels.patch +Patch5: 0005-LU-17081-build-Prefer-folio_batch-to-pagevec.patch +Patch6: 0006-LU-17243-build-compatibility-updates-for-kernel-6.6.patch %if %{with lustre_modules} Requires: %{requires_kmod_name} = %{requires_kmod_version} @@ -449,7 +453,10 @@ to be used by the Lustre testing framework. %if %{with lustre_iokit} %package -n lustre-iokit Summary: Collection of benchmark tools for a cluster with the Lustre file system -Requires: perl, sg3_utils +Requires: sg3_utils +%if 0%{?rhel} > 7 || 0%{?fedora} > 33 || 0%{?rhel} < 1 +Recommends: perl +%endif %description -n lustre-iokit This package includes five tools: @@ -517,7 +524,7 @@ export UTILS_CFLAGS="${UTILS_CFLAGS} -D__SANE_USERSPACE_TYPES__=1" # Disable any hardening or annotation since this doesn't make sense for # kernel code, and reset "optflags" so that the vendor's overzealous flags don't # create build failures. -%define optflags -g -O2 -Werror -Wno-stringop-overflow -Wno-format-truncation -Wno-use-after-free +%define optflags -g -O2 -Werror %undefine _annotated_build %undefine _hardened_build @@ -586,7 +593,6 @@ fi %{!?with_ldiskfs:--disable-ldiskfs} \ %{!?with_servers:--disable-server} \ %{!?with_zfs:--without-zfs} \ - %{!?with_snmp:--disable-snmp} \ %{!?with_gss:--disable-gss} \ %{!?with_gss_keyring:--disable-gss-keyring} \ %{!?with_manpages:--disable-manpages} \ @@ -652,6 +658,7 @@ mv $basemodpath/fs/osd_zfs.ko $basemodpath-osd-zfs/fs/osd_zfs.ko %if %{with lustre_tests} mkdir -p $basemodpath-tests/fs mv $basemodpath/fs/llog_test.ko $basemodpath-tests/fs/llog_test.ko +mv $basemodpath/fs/obd_test.ko $basemodpath-tests/fs/obd_test.ko mkdir -p $RPM_BUILD_ROOT%{_libdir}/lustre/tests/kernel/ mv $basemodpath/fs/kinode.ko $RPM_BUILD_ROOT%{_libdir}/lustre/tests/kernel/ %endif @@ -719,11 +726,6 @@ echo '%attr(-, root, root) %{_libdir}/liblnetconfig.so.*' >>lustre.files echo '%{_libdir}/libiam.a' >>lustre.files %endif -%if %{with snmp} -mkdir -p $RPM_BUILD_ROOT/%{_libdir}/lustre/snmp -echo '%{_libdir}/lustre/snmp' >>lustre.files -%endif - %if %{with lustre_utils} mkdir -p $RPM_BUILD_ROOT/%{_datadir}/lustre if [ -d $RPM_BUILD_ROOT%{_libdir}/lustre ] ; then @@ -754,7 +756,6 @@ echo '%dir %{_libdir}/lustre' >>lustre-tests.files echo '%dir %{_libdir}/lustre/tests' >>lustre-tests.files echo '%{_libdir}/lustre/tests/*' >>lustre-tests.files echo '%{_bindir}/mcreate' >>lustre-tests.files -echo '%{_bindir}/munlink' >>lustre-tests.files echo '%{_bindir}/statx' >>lustre-tests.files echo '%{_sbindir}/wirecheck' >>lustre-tests.files echo '%{_sbindir}/wiretest' >>lustre-tests.files @@ -931,6 +932,11 @@ rm -rf $RPM_BUILD_ROOT rm -rf %{_tmppath}/kmp %changelog +* Fri Dec 15 2023 Xinliang Liu - 2.15.59-1 +- Update to master v2.15.59 +- With kernel v6.6 support patches +- Update lustre.spec + * Thu Aug 03 2023 Xinliang Liu - 2.15.57-1 - Update to 2.15.57 with kernel 6.4 support patch.