From: Greg Kroah-Hartman Date: Fri, 20 Mar 2026 09:01:54 +0000 (+0100) Subject: 6.18-stable patches X-Git-Tag: v6.1.167~92 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=de95e2802aba3c747ee379ac0663eaa50cfbeba3;p=thirdparty%2Fkernel%2Fstable-queue.git 6.18-stable patches added patches: batman-adv-avoid-ogm-aggregation-when-skb-tailroom-is-insufficient.patch bluetooth-l2cap-fix-type-confusion-in-l2cap_ecred_reconf_rsp.patch bluetooth-l2cap-validate-l2cap_info_rsp-payload-length-before-access.patch bnxt_en-fix-oob-access-in-dbg_buf_producer-async-event-handler.patch crash_dump-don-t-log-dm-crypt-key-bytes-in-read_key_from_user_keying.patch crypto-padlock-sha-disable-for-zhaoxin-processor.patch hid-bpf-prevent-buffer-overflow-in-hid_hw_request.patch loongarch-give-more-information-if-kmem-access-failed.patch loongarch-no-need-to-flush-icache-if-text-copy-failed.patch mac80211-fix-crash-in-ieee80211_chan_bw_change-for-ap_vlan-stations.patch mm-huge_memory-fix-early-failure-try_to_migrate-when-split-huge-pmd-for-shared-thp.patch mm-huge_memory-fix-use-of-null-folio-in-move_pages_huge_pmd.patch mm-rmap-fix-incorrect-pte-restoration-for-lazyfree-folios.patch net-macb-fix-use-after-free-access-to-ptp-clock.patch nfc-nxp-nci-allow-gpios-to-sleep.patch nfsd-defer-sub-object-cleanup-in-export-put-callbacks.patch nfsd-fix-heap-overflow-in-nfsv4.0-lock-replay-cache.patch nfsd-hold-net-reference-for-the-lifetime-of-proc-fs-nfs-exports-fd.patch nvdimm-bus-fix-potential-use-after-free-in-asynchronous-initialization.patch parisc-flush-correct-cache-in-cacheflush-syscall.patch selftests-hid-fix-compilation-when-bpf_wq-and-hid_device-are-not-exported.patch series sunrpc-fix-cache_request-leak-in-cache_release.patch --- diff --git a/queue-6.18/batman-adv-avoid-ogm-aggregation-when-skb-tailroom-is-insufficient.patch b/queue-6.18/batman-adv-avoid-ogm-aggregation-when-skb-tailroom-is-insufficient.patch new file mode 100644 index 0000000000..32c6fa7e3a --- /dev/null +++ b/queue-6.18/batman-adv-avoid-ogm-aggregation-when-skb-tailroom-is-insufficient.patch @@ -0,0 +1,45 @@ +From 0d4aef630be9d5f9c1227d07669c26c4383b5ad0 Mon Sep 17 00:00:00 2001 +From: Yang Yang +Date: Sat, 14 Mar 2026 07:11:27 +0000 +Subject: batman-adv: avoid OGM aggregation when skb tailroom is insufficient + +From: Yang Yang + +commit 0d4aef630be9d5f9c1227d07669c26c4383b5ad0 upstream. + +When OGM aggregation state is toggled at runtime, an existing forwarded +packet may have been allocated with only packet_len bytes, while a later +packet can still be selected for aggregation. Appending in this case can +hit skb_put overflow conditions. + +Reject aggregation when the target skb tailroom cannot accommodate the new +packet. The caller then falls back to creating a new forward packet +instead of appending. + +Fixes: c6c8fea29769 ("net: Add batman-adv meshing protocol") +Cc: stable@vger.kernel.org +Reported-by: Yifan Wu +Reported-by: Juefei Pu +Signed-off-by: Yuan Tan +Signed-off-by: Xin Liu +Signed-off-by: Ao Zhou +Signed-off-by: Yang Yang +Signed-off-by: Sven Eckelmann +Signed-off-by: Simon Wunderlich +Signed-off-by: Greg Kroah-Hartman +--- + net/batman-adv/bat_iv_ogm.c | 3 +++ + 1 file changed, 3 insertions(+) + +--- a/net/batman-adv/bat_iv_ogm.c ++++ b/net/batman-adv/bat_iv_ogm.c +@@ -473,6 +473,9 @@ batadv_iv_ogm_can_aggregate(const struct + if (aggregated_bytes > max_bytes) + return false; + ++ if (skb_tailroom(forw_packet->skb) < packet_len) ++ return false; ++ + if (packet_num >= BATADV_MAX_AGGREGATION_PACKETS) + return false; + diff --git a/queue-6.18/bluetooth-l2cap-fix-type-confusion-in-l2cap_ecred_reconf_rsp.patch b/queue-6.18/bluetooth-l2cap-fix-type-confusion-in-l2cap_ecred_reconf_rsp.patch new file mode 100644 index 0000000000..85db869102 --- /dev/null +++ b/queue-6.18/bluetooth-l2cap-fix-type-confusion-in-l2cap_ecred_reconf_rsp.patch @@ -0,0 +1,59 @@ +From 15145675690cab2de1056e7ed68e59cbd0452529 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Lukas=20Johannes=20M=C3=B6ller?= + +Date: Tue, 10 Mar 2026 21:59:46 +0000 +Subject: Bluetooth: L2CAP: Fix type confusion in l2cap_ecred_reconf_rsp() +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Lukas Johannes Möller + +commit 15145675690cab2de1056e7ed68e59cbd0452529 upstream. + +l2cap_ecred_reconf_rsp() casts the incoming data to struct +l2cap_ecred_conn_rsp (the ECRED *connection* response, 8 bytes with +result at offset 6) instead of struct l2cap_ecred_reconf_rsp (2 bytes +with result at offset 0). + +This causes two problems: + + - The sizeof(*rsp) length check requires 8 bytes instead of the + correct 2, so valid L2CAP_ECRED_RECONF_RSP packets are rejected + with -EPROTO. + + - rsp->result reads from offset 6 instead of offset 0, returning + wrong data when the packet is large enough to pass the check. + +Fix by using the correct type. Also pass the already byte-swapped +result variable to BT_DBG instead of the raw __le16 field. + +Fixes: 15f02b910562 ("Bluetooth: L2CAP: Add initial code for Enhanced Credit Based Mode") +Cc: stable@vger.kernel.org +Signed-off-by: Lukas Johannes Möller +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Greg Kroah-Hartman +--- + net/bluetooth/l2cap_core.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/net/bluetooth/l2cap_core.c ++++ b/net/bluetooth/l2cap_core.c +@@ -5408,7 +5408,7 @@ static inline int l2cap_ecred_reconf_rsp + u8 *data) + { + struct l2cap_chan *chan, *tmp; +- struct l2cap_ecred_conn_rsp *rsp = (void *) data; ++ struct l2cap_ecred_reconf_rsp *rsp = (void *)data; + u16 result; + + if (cmd_len < sizeof(*rsp)) +@@ -5416,7 +5416,7 @@ static inline int l2cap_ecred_reconf_rsp + + result = __le16_to_cpu(rsp->result); + +- BT_DBG("result 0x%4.4x", rsp->result); ++ BT_DBG("result 0x%4.4x", result); + + if (!result) + return 0; diff --git a/queue-6.18/bluetooth-l2cap-validate-l2cap_info_rsp-payload-length-before-access.patch b/queue-6.18/bluetooth-l2cap-validate-l2cap_info_rsp-payload-length-before-access.patch new file mode 100644 index 0000000000..31e47cb9fe --- /dev/null +++ b/queue-6.18/bluetooth-l2cap-validate-l2cap_info_rsp-payload-length-before-access.patch @@ -0,0 +1,63 @@ +From dd815e6e3918dc75a49aaabac36e4f024d675101 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Lukas=20Johannes=20M=C3=B6ller?= + +Date: Tue, 10 Mar 2026 21:59:47 +0000 +Subject: Bluetooth: L2CAP: Validate L2CAP_INFO_RSP payload length before access +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Lukas Johannes Möller + +commit dd815e6e3918dc75a49aaabac36e4f024d675101 upstream. + +l2cap_information_rsp() checks that cmd_len covers the fixed +l2cap_info_rsp header (type + result, 4 bytes) but then reads +rsp->data without verifying that the payload is present: + + - L2CAP_IT_FEAT_MASK calls get_unaligned_le32(rsp->data), which reads + 4 bytes past the header (needs cmd_len >= 8). + + - L2CAP_IT_FIXED_CHAN reads rsp->data[0], 1 byte past the header + (needs cmd_len >= 5). + +A truncated L2CAP_INFO_RSP with result == L2CAP_IR_SUCCESS triggers an +out-of-bounds read of adjacent skb data. + +Guard each data access with the required payload length check. If the +payload is too short, skip the read and let the state machine complete +with safe defaults (feat_mask and remote_fixed_chan remain zero from +kzalloc), so the info timer cleanup and l2cap_conn_start() still run +and the connection is not stalled. + +Fixes: 4e8402a3f884 ("[Bluetooth] Retrieve L2CAP features mask on connection setup") +Cc: stable@vger.kernel.org +Signed-off-by: Lukas Johannes Möller +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Greg Kroah-Hartman +--- + net/bluetooth/l2cap_core.c | 6 ++++-- + 1 file changed, 4 insertions(+), 2 deletions(-) + +--- a/net/bluetooth/l2cap_core.c ++++ b/net/bluetooth/l2cap_core.c +@@ -4622,7 +4622,8 @@ static inline int l2cap_information_rsp( + + switch (type) { + case L2CAP_IT_FEAT_MASK: +- conn->feat_mask = get_unaligned_le32(rsp->data); ++ if (cmd_len >= sizeof(*rsp) + sizeof(u32)) ++ conn->feat_mask = get_unaligned_le32(rsp->data); + + if (conn->feat_mask & L2CAP_FEAT_FIXED_CHAN) { + struct l2cap_info_req req; +@@ -4641,7 +4642,8 @@ static inline int l2cap_information_rsp( + break; + + case L2CAP_IT_FIXED_CHAN: +- conn->remote_fixed_chan = rsp->data[0]; ++ if (cmd_len >= sizeof(*rsp) + sizeof(rsp->data[0])) ++ conn->remote_fixed_chan = rsp->data[0]; + conn->info_state |= L2CAP_INFO_FEAT_MASK_REQ_DONE; + conn->info_ident = 0; + diff --git a/queue-6.18/bnxt_en-fix-oob-access-in-dbg_buf_producer-async-event-handler.patch b/queue-6.18/bnxt_en-fix-oob-access-in-dbg_buf_producer-async-event-handler.patch new file mode 100644 index 0000000000..2a2fb3de25 --- /dev/null +++ b/queue-6.18/bnxt_en-fix-oob-access-in-dbg_buf_producer-async-event-handler.patch @@ -0,0 +1,61 @@ +From 64dcbde7f8f870a4f2d9daf24ffb06f9748b5dd3 Mon Sep 17 00:00:00 2001 +From: Junrui Luo +Date: Sat, 14 Mar 2026 17:41:04 +0800 +Subject: bnxt_en: fix OOB access in DBG_BUF_PRODUCER async event handler + +From: Junrui Luo + +commit 64dcbde7f8f870a4f2d9daf24ffb06f9748b5dd3 upstream. + +The ASYNC_EVENT_CMPL_EVENT_ID_DBG_BUF_PRODUCER handler in +bnxt_async_event_process() uses a firmware-supplied 'type' field +directly as an index into bp->bs_trace[] without bounds validation. + +The 'type' field is a 16-bit value extracted from DMA-mapped completion +ring memory that the NIC writes directly to host RAM. A malicious or +compromised NIC can supply any value from 0 to 65535, causing an +out-of-bounds access into kernel heap memory. + +The bnxt_bs_trace_check_wrap() call then dereferences bs_trace->magic_byte +and writes to bs_trace->last_offset and bs_trace->wrapped, leading to +kernel memory corruption or a crash. + +Fix by adding a bounds check and defining BNXT_TRACE_MAX as +DBG_LOG_BUFFER_FLUSH_REQ_TYPE_ERR_QPC_TRACE + 1 to cover all currently +defined firmware trace types (0x0 through 0xc). + +Fixes: 84fcd9449fd7 ("bnxt_en: Manage the FW trace context memory") +Reported-by: Yuhao Jiang +Cc: stable@vger.kernel.org +Signed-off-by: Junrui Luo +Reviewed-by: Michael Chan +Link: https://patch.msgid.link/SYBPR01MB7881A253A1C9775D277F30E9AF42A@SYBPR01MB7881.ausprd01.prod.outlook.com +Signed-off-by: Jakub Kicinski +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/ethernet/broadcom/bnxt/bnxt.c | 2 ++ + drivers/net/ethernet/broadcom/bnxt/bnxt.h | 2 +- + 2 files changed, 3 insertions(+), 1 deletion(-) + +--- a/drivers/net/ethernet/broadcom/bnxt/bnxt.c ++++ b/drivers/net/ethernet/broadcom/bnxt/bnxt.c +@@ -2927,6 +2927,8 @@ static int bnxt_async_event_process(stru + u16 type = (u16)BNXT_EVENT_BUF_PRODUCER_TYPE(data1); + u32 offset = BNXT_EVENT_BUF_PRODUCER_OFFSET(data2); + ++ if (type >= ARRAY_SIZE(bp->bs_trace)) ++ goto async_event_process_exit; + bnxt_bs_trace_check_wrap(&bp->bs_trace[type], offset); + goto async_event_process_exit; + } +--- a/drivers/net/ethernet/broadcom/bnxt/bnxt.h ++++ b/drivers/net/ethernet/broadcom/bnxt/bnxt.h +@@ -2134,7 +2134,7 @@ enum board_idx { + }; + + #define BNXT_TRACE_BUF_MAGIC_BYTE ((u8)0xbc) +-#define BNXT_TRACE_MAX 11 ++#define BNXT_TRACE_MAX (DBG_LOG_BUFFER_FLUSH_REQ_TYPE_ERR_QPC_TRACE + 1) + + struct bnxt_bs_trace_info { + u8 *magic_byte; diff --git a/queue-6.18/crash_dump-don-t-log-dm-crypt-key-bytes-in-read_key_from_user_keying.patch b/queue-6.18/crash_dump-don-t-log-dm-crypt-key-bytes-in-read_key_from_user_keying.patch new file mode 100644 index 0000000000..de17338372 --- /dev/null +++ b/queue-6.18/crash_dump-don-t-log-dm-crypt-key-bytes-in-read_key_from_user_keying.patch @@ -0,0 +1,45 @@ +From 36f46b0e36892eba08978eef7502ff3c94ddba77 Mon Sep 17 00:00:00 2001 +From: Thorsten Blum +Date: Sat, 28 Feb 2026 00:00:09 +0100 +Subject: crash_dump: don't log dm-crypt key bytes in read_key_from_user_keying + +From: Thorsten Blum + +commit 36f46b0e36892eba08978eef7502ff3c94ddba77 upstream. + +When debug logging is enabled, read_key_from_user_keying() logs the first +8 bytes of the key payload and partially exposes the dm-crypt key. Stop +logging any key bytes. + +Link: https://lkml.kernel.org/r/20260227230008.858641-2-thorsten.blum@linux.dev +Fixes: 479e58549b0f ("crash_dump: store dm crypt keys in kdump reserved memory") +Signed-off-by: Thorsten Blum +Cc: Baoquan He +Cc: Coiby Xu +Cc: Dave Young +Cc: Vivek Goyal +Cc: +Signed-off-by: Andrew Morton +Signed-off-by: Greg Kroah-Hartman +--- + kernel/crash_dump_dm_crypt.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/kernel/crash_dump_dm_crypt.c b/kernel/crash_dump_dm_crypt.c +index 1f4067fbdb94..a20d4097744a 100644 +--- a/kernel/crash_dump_dm_crypt.c ++++ b/kernel/crash_dump_dm_crypt.c +@@ -168,8 +168,8 @@ static int read_key_from_user_keying(struct dm_crypt_key *dm_key) + + memcpy(dm_key->data, ukp->data, ukp->datalen); + dm_key->key_size = ukp->datalen; +- kexec_dprintk("Get dm crypt key (size=%u) %s: %8ph\n", dm_key->key_size, +- dm_key->key_desc, dm_key->data); ++ kexec_dprintk("Get dm crypt key (size=%u) %s\n", dm_key->key_size, ++ dm_key->key_desc); + + out: + up_read(&key->sem); +-- +2.53.0 + diff --git a/queue-6.18/crypto-padlock-sha-disable-for-zhaoxin-processor.patch b/queue-6.18/crypto-padlock-sha-disable-for-zhaoxin-processor.patch new file mode 100644 index 0000000000..7f53425f1e --- /dev/null +++ b/queue-6.18/crypto-padlock-sha-disable-for-zhaoxin-processor.patch @@ -0,0 +1,64 @@ +From ebba09f198078b7a2565004104ef762d1148e7f0 Mon Sep 17 00:00:00 2001 +From: AlanSong-oc +Date: Fri, 13 Mar 2026 16:01:49 +0800 +Subject: crypto: padlock-sha - Disable for Zhaoxin processor + +From: AlanSong-oc + +commit ebba09f198078b7a2565004104ef762d1148e7f0 upstream. + +For Zhaoxin processors, the XSHA1 instruction requires the total memory +allocated at %rdi register must be 32 bytes, while the XSHA1 and +XSHA256 instruction doesn't perform any operation when %ecx is zero. + +Due to these requirements, the current padlock-sha driver does not work +correctly with Zhaoxin processors. It cannot pass the self-tests and +therefore does not activate the driver on Zhaoxin processors. This issue +has been reported in Debian [1]. The self-tests fail with the +following messages [2]: + +alg: shash: sha1-padlock-nano test failed (wrong result) on test vector 0, cfg="init+update+final aligned buffer" +alg: self-tests for sha1 using sha1-padlock-nano failed (rc=-22) + +alg: shash: sha256-padlock-nano test failed (wrong result) on test vector 0, cfg="init+update+final aligned buffer" +alg: self-tests for sha256 using sha256-padlock-nano failed (rc=-22) + +Disable the padlock-sha driver on Zhaoxin processors with the CPU family +0x07 and newer. Following the suggestion in [3], support for PHE will be +added to lib/crypto/ instead. + +[1] https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=1113996 +[2] https://linux-hardware.org/?probe=271fabb7a4&log=dmesg +[3] https://lore.kernel.org/linux-crypto/aUI4CGp6kK7mxgEr@gondor.apana.org.au/ + +Fixes: 63dc06cd12f9 ("crypto: padlock-sha - Use API partial block handling") +Cc: stable@vger.kernel.org +Signed-off-by: AlanSong-oc +Link: https://lore.kernel.org/r/20260313080150.9393-2-AlanSong-oc@zhaoxin.com +Signed-off-by: Eric Biggers +Signed-off-by: Greg Kroah-Hartman +--- + drivers/crypto/padlock-sha.c | 7 +++++++ + 1 file changed, 7 insertions(+) + +diff --git a/drivers/crypto/padlock-sha.c b/drivers/crypto/padlock-sha.c +index 329f60ad422e..9214bbfc868f 100644 +--- a/drivers/crypto/padlock-sha.c ++++ b/drivers/crypto/padlock-sha.c +@@ -332,6 +332,13 @@ static int __init padlock_init(void) + if (!x86_match_cpu(padlock_sha_ids) || !boot_cpu_has(X86_FEATURE_PHE_EN)) + return -ENODEV; + ++ /* ++ * Skip family 0x07 and newer used by Zhaoxin processors, ++ * as the driver's self-tests fail on these CPUs. ++ */ ++ if (c->x86 >= 0x07) ++ return -ENODEV; ++ + /* Register the newly added algorithm module if on * + * VIA Nano processor, or else just do as before */ + if (c->x86_model < 0x0f) { +-- +2.53.0 + diff --git a/queue-6.18/hid-bpf-prevent-buffer-overflow-in-hid_hw_request.patch b/queue-6.18/hid-bpf-prevent-buffer-overflow-in-hid_hw_request.patch new file mode 100644 index 0000000000..ce77ee5103 --- /dev/null +++ b/queue-6.18/hid-bpf-prevent-buffer-overflow-in-hid_hw_request.patch @@ -0,0 +1,35 @@ +From 2b658c1c442ec1cd9eec5ead98d68662c40fe645 Mon Sep 17 00:00:00 2001 +From: Benjamin Tissoires +Date: Fri, 13 Mar 2026 08:40:25 +0100 +Subject: HID: bpf: prevent buffer overflow in hid_hw_request + +From: Benjamin Tissoires + +commit 2b658c1c442ec1cd9eec5ead98d68662c40fe645 upstream. + +right now the returned value is considered to be always valid. However, +when playing with HID-BPF, the return value can be arbitrary big, +because it's the return value of dispatch_hid_bpf_raw_requests(), which +calls the struct_ops and we have no guarantees that the value makes +sense. + +Fixes: 8bd0488b5ea5 ("HID: bpf: add HID-BPF hooks for hid_hw_raw_requests") +Cc: stable@vger.kernel.org +Acked-by: Jiri Kosina +Signed-off-by: Benjamin Tissoires +Signed-off-by: Greg Kroah-Hartman +--- + drivers/hid/bpf/hid_bpf_dispatch.c | 2 ++ + 1 file changed, 2 insertions(+) + +--- a/drivers/hid/bpf/hid_bpf_dispatch.c ++++ b/drivers/hid/bpf/hid_bpf_dispatch.c +@@ -447,6 +447,8 @@ hid_bpf_hw_request(struct hid_bpf_ctx *c + (u64)(long)ctx, + true); /* prevent infinite recursions */ + ++ if (ret > size) ++ ret = size; + if (ret > 0) + memcpy(buf, dma_data, ret); + diff --git a/queue-6.18/loongarch-give-more-information-if-kmem-access-failed.patch b/queue-6.18/loongarch-give-more-information-if-kmem-access-failed.patch new file mode 100644 index 0000000000..0b32a22923 --- /dev/null +++ b/queue-6.18/loongarch-give-more-information-if-kmem-access-failed.patch @@ -0,0 +1,64 @@ +From a47f0754bdd01f971c9715acdbdd3a07515c8f83 Mon Sep 17 00:00:00 2001 +From: Tiezhu Yang +Date: Mon, 16 Mar 2026 10:36:01 +0800 +Subject: LoongArch: Give more information if kmem access failed + +From: Tiezhu Yang + +commit a47f0754bdd01f971c9715acdbdd3a07515c8f83 upstream. + +If memory access such as copy_{from, to}_kernel_nofault() failed, its +users do not know what happened, so it is very useful to print the +exception code for such cases. Furthermore, it is better to print the +caller function to know where is the entry. + +Here are the low level call chains: + + copy_from_kernel_nofault() + copy_from_kernel_nofault_loop() + __get_kernel_nofault() + + copy_to_kernel_nofault() + copy_to_kernel_nofault_loop() + __put_kernel_nofault() + +Cc: stable@vger.kernel.org +Signed-off-by: Tiezhu Yang +Signed-off-by: Huacai Chen +Signed-off-by: Greg Kroah-Hartman +--- + arch/loongarch/include/asm/uaccess.h | 14 ++++++++++++-- + 1 file changed, 12 insertions(+), 2 deletions(-) + +--- a/arch/loongarch/include/asm/uaccess.h ++++ b/arch/loongarch/include/asm/uaccess.h +@@ -196,8 +196,13 @@ do { \ + \ + __get_kernel_common(*((type *)(dst)), sizeof(type), \ + (__force type *)(src)); \ +- if (unlikely(__gu_err)) \ ++ if (unlikely(__gu_err)) { \ ++ pr_info("%s: memory access failed, ecode 0x%x\n", \ ++ __func__, read_csr_excode()); \ ++ pr_info("%s: the caller is %pS\n", \ ++ __func__, __builtin_return_address(0)); \ + goto err_label; \ ++ } \ + } while (0) + + #define __put_kernel_nofault(dst, src, type, err_label) \ +@@ -207,8 +212,13 @@ do { \ + \ + __pu_val = *(__force type *)(src); \ + __put_kernel_common(((type *)(dst)), sizeof(type)); \ +- if (unlikely(__pu_err)) \ ++ if (unlikely(__pu_err)) { \ ++ pr_info("%s: memory access failed, ecode 0x%x\n", \ ++ __func__, read_csr_excode()); \ ++ pr_info("%s: the caller is %pS\n", \ ++ __func__, __builtin_return_address(0)); \ + goto err_label; \ ++ } \ + } while (0) + + extern unsigned long __copy_user(void *to, const void *from, __kernel_size_t n); diff --git a/queue-6.18/loongarch-no-need-to-flush-icache-if-text-copy-failed.patch b/queue-6.18/loongarch-no-need-to-flush-icache-if-text-copy-failed.patch new file mode 100644 index 0000000000..3f7114d103 --- /dev/null +++ b/queue-6.18/loongarch-no-need-to-flush-icache-if-text-copy-failed.patch @@ -0,0 +1,40 @@ +From d3b8491961207ac967795c34375890407fd51a45 Mon Sep 17 00:00:00 2001 +From: Tiezhu Yang +Date: Mon, 16 Mar 2026 10:36:01 +0800 +Subject: LoongArch: No need to flush icache if text copy failed + +From: Tiezhu Yang + +commit d3b8491961207ac967795c34375890407fd51a45 upstream. + +If copy_to_kernel_nofault() failed, no need to flush icache and just +return immediately. + +Cc: stable@vger.kernel.org +Signed-off-by: Tiezhu Yang +Signed-off-by: Huacai Chen +Signed-off-by: Greg Kroah-Hartman +--- + arch/loongarch/kernel/inst.c | 6 ++++-- + 1 file changed, 4 insertions(+), 2 deletions(-) + +--- a/arch/loongarch/kernel/inst.c ++++ b/arch/loongarch/kernel/inst.c +@@ -246,13 +246,15 @@ static int text_copy_cb(void *data) + + if (smp_processor_id() == copy->cpu) { + ret = copy_to_kernel_nofault(copy->dst, copy->src, copy->len); +- if (ret) ++ if (ret) { + pr_err("%s: operation failed\n", __func__); ++ return ret; ++ } + } + + flush_icache_range((unsigned long)copy->dst, (unsigned long)copy->dst + copy->len); + +- return ret; ++ return 0; + } + + int larch_insn_text_copy(void *dst, void *src, size_t len) diff --git a/queue-6.18/mac80211-fix-crash-in-ieee80211_chan_bw_change-for-ap_vlan-stations.patch b/queue-6.18/mac80211-fix-crash-in-ieee80211_chan_bw_change-for-ap_vlan-stations.patch new file mode 100644 index 0000000000..cd183b5e96 --- /dev/null +++ b/queue-6.18/mac80211-fix-crash-in-ieee80211_chan_bw_change-for-ap_vlan-stations.patch @@ -0,0 +1,51 @@ +From 672e5229e1ecfc2a3509b53adcb914d8b024a853 Mon Sep 17 00:00:00 2001 +From: Felix Fietkau +Date: Thu, 5 Mar 2026 17:08:12 +0000 +Subject: mac80211: fix crash in ieee80211_chan_bw_change for AP_VLAN stations + +From: Felix Fietkau + +commit 672e5229e1ecfc2a3509b53adcb914d8b024a853 upstream. + +ieee80211_chan_bw_change() iterates all stations and accesses +link->reserved.oper via sta->sdata->link[link_id]. For stations on +AP_VLAN interfaces (e.g. 4addr WDS clients), sta->sdata points to +the VLAN sdata, whose link never participates in chanctx reservations. +This leaves link->reserved.oper zero-initialized with chan == NULL, +causing a NULL pointer dereference in __ieee80211_sta_cap_rx_bw() +when accessing chandef->chan->band during CSA. + +Resolve the VLAN sdata to its parent AP sdata using get_bss_sdata() +before accessing link data. + +Cc: stable@vger.kernel.org +Signed-off-by: Felix Fietkau +Link: https://patch.msgid.link/20260305170812.2904208-1-nbd@nbd.name +[also change sta->sdata in ARRAY_SIZE even if it doesn't matter] +Signed-off-by: Johannes Berg +Signed-off-by: Greg Kroah-Hartman +--- + net/mac80211/chan.c | 6 ++++-- + 1 file changed, 4 insertions(+), 2 deletions(-) + +--- a/net/mac80211/chan.c ++++ b/net/mac80211/chan.c +@@ -441,14 +441,16 @@ static void ieee80211_chan_bw_change(str + rcu_read_lock(); + list_for_each_entry_rcu(sta, &local->sta_list, + list) { +- struct ieee80211_sub_if_data *sdata = sta->sdata; ++ struct ieee80211_sub_if_data *sdata; + enum ieee80211_sta_rx_bandwidth new_sta_bw; + unsigned int link_id; + + if (!ieee80211_sdata_running(sta->sdata)) + continue; + +- for (link_id = 0; link_id < ARRAY_SIZE(sta->sdata->link); link_id++) { ++ sdata = get_bss_sdata(sta->sdata); ++ ++ for (link_id = 0; link_id < ARRAY_SIZE(sdata->link); link_id++) { + struct ieee80211_link_data *link = + rcu_dereference(sdata->link[link_id]); + struct ieee80211_bss_conf *link_conf; diff --git a/queue-6.18/mm-huge_memory-fix-early-failure-try_to_migrate-when-split-huge-pmd-for-shared-thp.patch b/queue-6.18/mm-huge_memory-fix-early-failure-try_to_migrate-when-split-huge-pmd-for-shared-thp.patch new file mode 100644 index 0000000000..de31ae236c --- /dev/null +++ b/queue-6.18/mm-huge_memory-fix-early-failure-try_to_migrate-when-split-huge-pmd-for-shared-thp.patch @@ -0,0 +1,103 @@ +From 939080834fef3ce42fdbcfef33fd29c9ffe5bbed Mon Sep 17 00:00:00 2001 +From: Wei Yang +Date: Thu, 5 Mar 2026 01:50:06 +0000 +Subject: mm/huge_memory: fix early failure try_to_migrate() when split huge pmd for shared THP + +From: Wei Yang + +commit 939080834fef3ce42fdbcfef33fd29c9ffe5bbed upstream. + +Commit 60fbb14396d5 ("mm/huge_memory: adjust try_to_migrate_one() and +split_huge_pmd_locked()") return false unconditionally after +split_huge_pmd_locked(). This may fail try_to_migrate() early when +TTU_SPLIT_HUGE_PMD is specified. + +The reason is the above commit adjusted try_to_migrate_one() to, when a +PMD-mapped THP entry is found, and TTU_SPLIT_HUGE_PMD is specified (for +example, via unmap_folio()), return false unconditionally. This breaks +the rmap walk and fail try_to_migrate() early, if this PMD-mapped THP is +mapped in multiple processes. + +The user sensible impact of this bug could be: + + * On memory pressure, shrink_folio_list() may split partially mapped + folio with split_folio_to_list(). Then free unmapped pages without IO. + If failed, it may not be reclaimed. + * On memory failure, memory_failure() would call try_to_split_thp_page() + to split folio contains the bad page. If succeed, the PG_has_hwpoisoned + bit is only set in the after-split folio contains @split_at. By doing + so, we limit bad memory. If failed to split, the whole folios is not + usable. + +One way to reproduce: + + Create an anonymous THP range and fork 512 children, so we have a + THP shared mapped in 513 processes. Then trigger folio split with + /sys/kernel/debug/split_huge_pages debugfs to split the THP folio to + order 0. + +Without the above commit, we can successfully split to order 0. With the +above commit, the folio is still a large folio. + +And currently there are two core users of TTU_SPLIT_HUGE_PMD: + + * try_to_unmap_one() + * try_to_migrate_one() + +try_to_unmap_one() would restart the rmap walk, so only +try_to_migrate_one() is affected. + +We can't simply revert commit 60fbb14396d5 ("mm/huge_memory: adjust +try_to_migrate_one() and split_huge_pmd_locked()"), since it removed some +duplicated check covered by page_vma_mapped_walk(). + +This patch fixes this by restart page_vma_mapped_walk() after +split_huge_pmd_locked(). Since we cannot simply return "true" to fix the +problem, as that would affect another case: + + When invoking folio_try_share_anon_rmap_pmd() from + split_huge_pmd_locked(), the latter can fail and leave a large folio + mapped through PTEs, in which case we ought to return true from + try_to_migrate_one(). This might result in unnecessary walking of the + rmap but is relatively harmless. + +Link: https://lkml.kernel.org/r/20260305015006.27343-1-richard.weiyang@gmail.com +Fixes: 60fbb14396d5 ("mm/huge_memory: adjust try_to_migrate_one() and split_huge_pmd_locked()") +Signed-off-by: Wei Yang +Reviewed-by: Baolin Wang +Reviewed-by: Zi Yan +Tested-by: Lance Yang +Reviewed-by: Lance Yang +Reviewed-by: Gavin Guo +Acked-by: David Hildenbrand (arm) +Reviewed-by: Lorenzo Stoakes (Oracle) +Cc: +Signed-off-by: Andrew Morton +Signed-off-by: Greg Kroah-Hartman +--- + mm/rmap.c | 12 +++++++++--- + 1 file changed, 9 insertions(+), 3 deletions(-) + +--- a/mm/rmap.c ++++ b/mm/rmap.c +@@ -2346,11 +2346,17 @@ static bool try_to_migrate_one(struct fo + /* PMD-mapped THP migration entry */ + if (!pvmw.pte) { + if (flags & TTU_SPLIT_HUGE_PMD) { ++ /* ++ * split_huge_pmd_locked() might leave the ++ * folio mapped through PTEs. Retry the walk ++ * so we can detect this scenario and properly ++ * abort the walk. ++ */ + split_huge_pmd_locked(vma, pvmw.address, + pvmw.pmd, true); +- ret = false; +- page_vma_mapped_walk_done(&pvmw); +- break; ++ flags &= ~TTU_SPLIT_HUGE_PMD; ++ page_vma_mapped_walk_restart(&pvmw); ++ continue; + } + #ifdef CONFIG_ARCH_ENABLE_THP_MIGRATION + subpage = folio_page(folio, diff --git a/queue-6.18/mm-huge_memory-fix-use-of-null-folio-in-move_pages_huge_pmd.patch b/queue-6.18/mm-huge_memory-fix-use-of-null-folio-in-move_pages_huge_pmd.patch new file mode 100644 index 0000000000..f69ef448b0 --- /dev/null +++ b/queue-6.18/mm-huge_memory-fix-use-of-null-folio-in-move_pages_huge_pmd.patch @@ -0,0 +1,64 @@ +From fae654083bfa409bb2244f390232e2be47f05bfc Mon Sep 17 00:00:00 2001 +From: Chris Down +Date: Tue, 3 Mar 2026 07:21:21 +0000 +Subject: mm/huge_memory: fix use of NULL folio in move_pages_huge_pmd() + +From: Chris Down + +commit fae654083bfa409bb2244f390232e2be47f05bfc upstream. + +move_pages_huge_pmd() handles UFFDIO_MOVE for both normal THPs and huge +zero pages. For the huge zero page path, src_folio is explicitly set to +NULL, and is used as a sentinel to skip folio operations like lock and +rmap. + +In the huge zero page branch, src_folio is NULL, so folio_mk_pmd(NULL, +pgprot) passes NULL through folio_pfn() and page_to_pfn(). With +SPARSEMEM_VMEMMAP this silently produces a bogus PFN, installing a PMD +pointing to non-existent physical memory. On other memory models it is a +NULL dereference. + +Use page_folio(src_page) to obtain the valid huge zero folio from the +page, which was obtained from pmd_page() and remains valid throughout. + +After commit d82d09e48219 ("mm/huge_memory: mark PMD mappings of the huge +zero folio special"), moved huge zero PMDs must remain special so +vm_normal_page_pmd() continues to treat them as special mappings. + +move_pages_huge_pmd() currently reconstructs the destination PMD in the +huge zero page branch, which drops PMD state such as pmd_special() on +architectures with CONFIG_ARCH_HAS_PTE_SPECIAL. As a result, +vm_normal_page_pmd() can treat the moved huge zero PMD as a normal page +and corrupt its refcount. + +Instead of reconstructing the PMD from the folio, derive the destination +entry from src_pmdval after pmdp_huge_clear_flush(), then handle the PMD +metadata the same way move_huge_pmd() does for moved entries by marking it +soft-dirty and clearing uffd-wp. + +Link: https://lkml.kernel.org/r/a1e787dd-b911-474d-8570-f37685357d86@lucifer.local +Fixes: e3981db444a0 ("mm: add folio_mk_pmd()") +Signed-off-by: Chris Down +Signed-off-by: Lorenzo Stoakes +Reviewed-by: Lorenzo Stoakes +Tested-by: Lorenzo Stoakes +Acked-by: David Hildenbrand (Arm) +Cc: +Signed-off-by: Andrew Morton +Signed-off-by: Greg Kroah-Hartman +--- + mm/huge_memory.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +--- a/mm/huge_memory.c ++++ b/mm/huge_memory.c +@@ -2639,7 +2639,8 @@ int move_pages_huge_pmd(struct mm_struct + _dst_pmd = pmd_mkwrite(pmd_mkdirty(_dst_pmd), dst_vma); + } else { + src_pmdval = pmdp_huge_clear_flush(src_vma, src_addr, src_pmd); +- _dst_pmd = folio_mk_pmd(src_folio, dst_vma->vm_page_prot); ++ _dst_pmd = move_soft_dirty_pmd(src_pmdval); ++ _dst_pmd = clear_uffd_wp_pmd(_dst_pmd); + } + set_pmd_at(mm, dst_addr, dst_pmd, _dst_pmd); + diff --git a/queue-6.18/mm-rmap-fix-incorrect-pte-restoration-for-lazyfree-folios.patch b/queue-6.18/mm-rmap-fix-incorrect-pte-restoration-for-lazyfree-folios.patch new file mode 100644 index 0000000000..4809bcd785 --- /dev/null +++ b/queue-6.18/mm-rmap-fix-incorrect-pte-restoration-for-lazyfree-folios.patch @@ -0,0 +1,203 @@ +From 29f40594a28114b9a9bc87f6cf7bbee9609628f2 Mon Sep 17 00:00:00 2001 +From: Dev Jain +Date: Tue, 3 Mar 2026 11:45:28 +0530 +Subject: mm/rmap: fix incorrect pte restoration for lazyfree folios + +From: Dev Jain + +commit 29f40594a28114b9a9bc87f6cf7bbee9609628f2 upstream. + +We batch unmap anonymous lazyfree folios by folio_unmap_pte_batch. If the +batch has a mix of writable and non-writable bits, we may end up setting +the entire batch writable. Fix this by respecting writable bit during +batching. + +Although on a successful unmap of a lazyfree folio, the soft-dirty bit is +lost, preserve it on pte restoration by respecting the bit during +batching, to make the fix consistent w.r.t both writable bit and +soft-dirty bit. + +I was able to write the below reproducer and crash the kernel. +Explanation of reproducer (set 64K mTHP to always): + +Fault in a 64K large folio. Split the VMA at mid-point with +MADV_DONTFORK. fork() - parent points to the folio with 8 writable ptes +and 8 non-writable ptes. Merge the VMAs with MADV_DOFORK so that +folio_unmap_pte_batch() can determine all the 16 ptes as a batch. Do +MADV_FREE on the range to mark the folio as lazyfree. Write to the memory +to dirty the pte, eventually rmap will dirty the folio. Then trigger +reclaim, we will hit the pte restoration path, and the kernel will crash +with the trace given below. + +The BUG happens at: + + BUG_ON(atomic_inc_return(&ptc->anon_map_count) > 1 && rw); + +The code path is asking for anonymous page to be mapped writable into the +pagetable. The BUG_ON() firing implies that such a writable page has been +mapped into the pagetables of more than one process, which breaks +anonymous memory/CoW semantics. + +[ 21.134473] kernel BUG at mm/page_table_check.c:118! +[ 21.134497] Internal error: Oops - BUG: 00000000f2000800 [#1] SMP +[ 21.135917] Modules linked in: +[ 21.136085] CPU: 1 UID: 0 PID: 1735 Comm: dup-lazyfree Not tainted 7.0.0-rc1-00116-g018018a17770 #1028 PREEMPT +[ 21.136858] Hardware name: linux,dummy-virt (DT) +[ 21.137019] pstate: 21400005 (nzCv daif +PAN -UAO -TCO +DIT -SSBS BTYPE=--) +[ 21.137308] pc : page_table_check_set+0x28c/0x2a8 +[ 21.137607] lr : page_table_check_set+0x134/0x2a8 +[ 21.137885] sp : ffff80008a3b3340 +[ 21.138124] x29: ffff80008a3b3340 x28: fffffdffc3d14400 x27: ffffd1a55e03d000 +[ 21.138623] x26: 0040000000000040 x25: ffffd1a55f7dd000 x24: 0000000000000001 +[ 21.139045] x23: 0000000000000001 x22: 0000000000000001 x21: ffffd1a55f217f30 +[ 21.139629] x20: 0000000000134521 x19: 0000000000134519 x18: 005c43e000040000 +[ 21.140027] x17: 0001400000000000 x16: 0001700000000000 x15: 000000000000ffff +[ 21.140578] x14: 000000000000000c x13: 005c006000000000 x12: 0000000000000020 +[ 21.140828] x11: 0000000000000000 x10: 005c000000000000 x9 : ffffd1a55c079ee0 +[ 21.141077] x8 : 0000000000000001 x7 : 005c03e000040000 x6 : 000000004000ffff +[ 21.141490] x5 : ffff00017fffce00 x4 : 0000000000000001 x3 : 0000000000000002 +[ 21.141741] x2 : 0000000000134510 x1 : 0000000000000000 x0 : ffff0000c08228c0 +[ 21.141991] Call trace: +[ 21.142093] page_table_check_set+0x28c/0x2a8 (P) +[ 21.142265] __page_table_check_ptes_set+0x144/0x1e8 +[ 21.142441] __set_ptes_anysz.constprop.0+0x160/0x1a8 +[ 21.142766] contpte_set_ptes+0xe8/0x140 +[ 21.142907] try_to_unmap_one+0x10c4/0x10d0 +[ 21.143177] rmap_walk_anon+0x100/0x250 +[ 21.143315] try_to_unmap+0xa0/0xc8 +[ 21.143441] shrink_folio_list+0x59c/0x18a8 +[ 21.143759] shrink_lruvec+0x664/0xbf0 +[ 21.144043] shrink_node+0x218/0x878 +[ 21.144285] __node_reclaim.constprop.0+0x98/0x338 +[ 21.144763] user_proactive_reclaim+0x2a4/0x340 +[ 21.145056] reclaim_store+0x3c/0x60 +[ 21.145216] dev_attr_store+0x20/0x40 +[ 21.145585] sysfs_kf_write+0x84/0xa8 +[ 21.145835] kernfs_fop_write_iter+0x130/0x1c8 +[ 21.145994] vfs_write+0x2b8/0x368 +[ 21.146119] ksys_write+0x70/0x110 +[ 21.146240] __arm64_sys_write+0x24/0x38 +[ 21.146380] invoke_syscall+0x50/0x120 +[ 21.146513] el0_svc_common.constprop.0+0x48/0xf8 +[ 21.146679] do_el0_svc+0x28/0x40 +[ 21.146798] el0_svc+0x34/0x110 +[ 21.146926] el0t_64_sync_handler+0xa0/0xe8 +[ 21.147074] el0t_64_sync+0x198/0x1a0 +[ 21.147225] Code: f9400441 b4fff241 17ffff94 d4210000 (d4210000) +[ 21.147440] ---[ end trace 0000000000000000 ]--- + +#define _GNU_SOURCE +#include +#include +#include +#include +#include +#include +#include +#include + +void write_to_reclaim() { + const char *path = "/sys/devices/system/node/node0/reclaim"; + const char *value = "409600000000"; + int fd = open(path, O_WRONLY); + if (fd == -1) { + perror("open"); + exit(EXIT_FAILURE); + } + + if (write(fd, value, sizeof("409600000000") - 1) == -1) { + perror("write"); + close(fd); + exit(EXIT_FAILURE); + } + + printf("Successfully wrote %s to %s\n", value, path); + close(fd); +} + +int main() +{ + char *ptr = mmap((void *)(1UL << 30), 1UL << 16, PROT_READ | PROT_WRITE, + MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); + if ((unsigned long)ptr != (1UL << 30)) { + perror("mmap"); + return 1; + } + + /* a 64K folio gets faulted in */ + memset(ptr, 0, 1UL << 16); + + /* 32K half will not be shared into child */ + if (madvise(ptr, 1UL << 15, MADV_DONTFORK)) { + perror("madvise madv dontfork"); + return 1; + } + + pid_t pid = fork(); + + if (pid < 0) { + perror("fork"); + return 1; + } else if (pid == 0) { + sleep(15); + } else { + /* merge VMAs. now first half of the 16 ptes are writable, the other half not. */ + if (madvise(ptr, 1UL << 15, MADV_DOFORK)) { + perror("madvise madv fork"); + return 1; + } + if (madvise(ptr, (1UL << 16), MADV_FREE)) { + perror("madvise madv free"); + return 1; + } + + /* dirty the large folio */ + (*ptr) += 10; + + write_to_reclaim(); + // sleep(10); + waitpid(pid, NULL, 0); + + } +} + +Link: https://lkml.kernel.org/r/20260303061528.2429162-1-dev.jain@arm.com +Fixes: 354dffd29575 ("mm: support batched unmap for lazyfree large folios during reclamation") +Signed-off-by: Dev Jain +Acked-by: David Hildenbrand (Arm) +Reviewed-by: Lorenzo Stoakes +Reviewed-by: Barry Song +Reviewed-by: Wei Yang +Tested-by: Lance Yang +Cc: Anshuman Khandual +Cc: Harry Yoo +Cc: Jann Horn +Cc: Liam Howlett +Cc: Rik van Riel +Cc: Ryan Roberts +Cc: Vlastimil Babka +Cc: +Signed-off-by: Andrew Morton +Signed-off-by: Greg Kroah-Hartman +--- + mm/rmap.c | 9 ++++++++- + 1 file changed, 8 insertions(+), 1 deletion(-) + +--- a/mm/rmap.c ++++ b/mm/rmap.c +@@ -1856,7 +1856,14 @@ static inline unsigned int folio_unmap_p + if (pte_unused(pte)) + return 1; + +- return folio_pte_batch(folio, pvmw->pte, pte, max_nr); ++ /* ++ * If unmap fails, we need to restore the ptes. To avoid accidentally ++ * upgrading write permissions for ptes that were not originally ++ * writable, and to avoid losing the soft-dirty bit, use the ++ * appropriate FPB flags. ++ */ ++ return folio_pte_batch_flags(folio, vma, pvmw->pte, &pte, max_nr, ++ FPB_RESPECT_WRITE | FPB_RESPECT_SOFT_DIRTY); + } + + /* diff --git a/queue-6.18/net-macb-fix-use-after-free-access-to-ptp-clock.patch b/queue-6.18/net-macb-fix-use-after-free-access-to-ptp-clock.patch new file mode 100644 index 0000000000..56f449cdc1 --- /dev/null +++ b/queue-6.18/net-macb-fix-use-after-free-access-to-ptp-clock.patch @@ -0,0 +1,128 @@ +From 8da13e6d63c1a97f7302d342c89c4a56a55c7015 Mon Sep 17 00:00:00 2001 +From: Fedor Pchelkin +Date: Mon, 16 Mar 2026 13:38:24 +0300 +Subject: net: macb: fix use-after-free access to PTP clock + +From: Fedor Pchelkin + +commit 8da13e6d63c1a97f7302d342c89c4a56a55c7015 upstream. + +PTP clock is registered on every opening of the interface and destroyed on +every closing. However it may be accessed via get_ts_info ethtool call +which is possible while the interface is just present in the kernel. + +BUG: KASAN: use-after-free in ptp_clock_index+0x47/0x50 drivers/ptp/ptp_clock.c:426 +Read of size 4 at addr ffff8880194345cc by task syz.0.6/948 + +CPU: 1 PID: 948 Comm: syz.0.6 Not tainted 6.1.164+ #109 +Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS rel-1.16.1-0-g3208b098f51a-prebuilt.qemu.org 04/01/2014 +Call Trace: + + __dump_stack lib/dump_stack.c:88 [inline] + dump_stack_lvl+0x8d/0xba lib/dump_stack.c:106 + print_address_description mm/kasan/report.c:316 [inline] + print_report+0x17f/0x496 mm/kasan/report.c:420 + kasan_report+0xd9/0x180 mm/kasan/report.c:524 + ptp_clock_index+0x47/0x50 drivers/ptp/ptp_clock.c:426 + gem_get_ts_info+0x138/0x1e0 drivers/net/ethernet/cadence/macb_main.c:3349 + macb_get_ts_info+0x68/0xb0 drivers/net/ethernet/cadence/macb_main.c:3371 + __ethtool_get_ts_info+0x17c/0x260 net/ethtool/common.c:558 + ethtool_get_ts_info net/ethtool/ioctl.c:2367 [inline] + __dev_ethtool net/ethtool/ioctl.c:3017 [inline] + dev_ethtool+0x2b05/0x6290 net/ethtool/ioctl.c:3095 + dev_ioctl+0x637/0x1070 net/core/dev_ioctl.c:510 + sock_do_ioctl+0x20d/0x2c0 net/socket.c:1215 + sock_ioctl+0x577/0x6d0 net/socket.c:1320 + vfs_ioctl fs/ioctl.c:51 [inline] + __do_sys_ioctl fs/ioctl.c:870 [inline] + __se_sys_ioctl fs/ioctl.c:856 [inline] + __x64_sys_ioctl+0x18c/0x210 fs/ioctl.c:856 + do_syscall_x64 arch/x86/entry/common.c:46 [inline] + do_syscall_64+0x35/0x80 arch/x86/entry/common.c:76 + entry_SYSCALL_64_after_hwframe+0x6e/0xd8 + + +Allocated by task 457: + kmalloc include/linux/slab.h:563 [inline] + kzalloc include/linux/slab.h:699 [inline] + ptp_clock_register+0x144/0x10e0 drivers/ptp/ptp_clock.c:235 + gem_ptp_init+0x46f/0x930 drivers/net/ethernet/cadence/macb_ptp.c:375 + macb_open+0x901/0xd10 drivers/net/ethernet/cadence/macb_main.c:2920 + __dev_open+0x2ce/0x500 net/core/dev.c:1501 + __dev_change_flags+0x56a/0x740 net/core/dev.c:8651 + dev_change_flags+0x92/0x170 net/core/dev.c:8722 + do_setlink+0xaf8/0x3a80 net/core/rtnetlink.c:2833 + __rtnl_newlink+0xbf4/0x1940 net/core/rtnetlink.c:3608 + rtnl_newlink+0x63/0xa0 net/core/rtnetlink.c:3655 + rtnetlink_rcv_msg+0x3c6/0xed0 net/core/rtnetlink.c:6150 + netlink_rcv_skb+0x15d/0x430 net/netlink/af_netlink.c:2511 + netlink_unicast_kernel net/netlink/af_netlink.c:1318 [inline] + netlink_unicast+0x6d7/0xa30 net/netlink/af_netlink.c:1344 + netlink_sendmsg+0x97e/0xeb0 net/netlink/af_netlink.c:1872 + sock_sendmsg_nosec net/socket.c:718 [inline] + __sock_sendmsg+0x14b/0x180 net/socket.c:730 + __sys_sendto+0x320/0x3b0 net/socket.c:2152 + __do_sys_sendto net/socket.c:2164 [inline] + __se_sys_sendto net/socket.c:2160 [inline] + __x64_sys_sendto+0xdc/0x1b0 net/socket.c:2160 + do_syscall_x64 arch/x86/entry/common.c:46 [inline] + do_syscall_64+0x35/0x80 arch/x86/entry/common.c:76 + entry_SYSCALL_64_after_hwframe+0x6e/0xd8 + +Freed by task 938: + kasan_slab_free include/linux/kasan.h:177 [inline] + slab_free_hook mm/slub.c:1729 [inline] + slab_free_freelist_hook mm/slub.c:1755 [inline] + slab_free mm/slub.c:3687 [inline] + __kmem_cache_free+0xbc/0x320 mm/slub.c:3700 + device_release+0xa0/0x240 drivers/base/core.c:2507 + kobject_cleanup lib/kobject.c:681 [inline] + kobject_release lib/kobject.c:712 [inline] + kref_put include/linux/kref.h:65 [inline] + kobject_put+0x1cd/0x350 lib/kobject.c:729 + put_device+0x1b/0x30 drivers/base/core.c:3805 + ptp_clock_unregister+0x171/0x270 drivers/ptp/ptp_clock.c:391 + gem_ptp_remove+0x4e/0x1f0 drivers/net/ethernet/cadence/macb_ptp.c:404 + macb_close+0x1c8/0x270 drivers/net/ethernet/cadence/macb_main.c:2966 + __dev_close_many+0x1b9/0x310 net/core/dev.c:1585 + __dev_close net/core/dev.c:1597 [inline] + __dev_change_flags+0x2bb/0x740 net/core/dev.c:8649 + dev_change_flags+0x92/0x170 net/core/dev.c:8722 + dev_ifsioc+0x151/0xe00 net/core/dev_ioctl.c:326 + dev_ioctl+0x33e/0x1070 net/core/dev_ioctl.c:572 + sock_do_ioctl+0x20d/0x2c0 net/socket.c:1215 + sock_ioctl+0x577/0x6d0 net/socket.c:1320 + vfs_ioctl fs/ioctl.c:51 [inline] + __do_sys_ioctl fs/ioctl.c:870 [inline] + __se_sys_ioctl fs/ioctl.c:856 [inline] + __x64_sys_ioctl+0x18c/0x210 fs/ioctl.c:856 + do_syscall_x64 arch/x86/entry/common.c:46 [inline] + do_syscall_64+0x35/0x80 arch/x86/entry/common.c:76 + entry_SYSCALL_64_after_hwframe+0x6e/0xd8 + +Set the PTP clock pointer to NULL after unregistering. + +Fixes: c2594d804d5c ("macb: Common code to enable ptp support for MACB/GEM") +Cc: stable@vger.kernel.org +Signed-off-by: Fedor Pchelkin +Link: https://patch.msgid.link/20260316103826.74506-1-pchelkin@ispras.ru +Signed-off-by: Jakub Kicinski +Signed-off-by: Greg Kroah-Hartman +--- + drivers/net/ethernet/cadence/macb_ptp.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +--- a/drivers/net/ethernet/cadence/macb_ptp.c ++++ b/drivers/net/ethernet/cadence/macb_ptp.c +@@ -355,8 +355,10 @@ void gem_ptp_remove(struct net_device *n + { + struct macb *bp = netdev_priv(ndev); + +- if (bp->ptp_clock) ++ if (bp->ptp_clock) { + ptp_clock_unregister(bp->ptp_clock); ++ bp->ptp_clock = NULL; ++ } + + gem_ptp_clear_timer(bp); + diff --git a/queue-6.18/nfc-nxp-nci-allow-gpios-to-sleep.patch b/queue-6.18/nfc-nxp-nci-allow-gpios-to-sleep.patch new file mode 100644 index 0000000000..a129ecc39a --- /dev/null +++ b/queue-6.18/nfc-nxp-nci-allow-gpios-to-sleep.patch @@ -0,0 +1,41 @@ +From 55dc632ab2ac2889b15995a9eef56c753d48ebc7 Mon Sep 17 00:00:00 2001 +From: Ian Ray +Date: Tue, 17 Mar 2026 10:53:36 +0200 +Subject: NFC: nxp-nci: allow GPIOs to sleep + +From: Ian Ray + +commit 55dc632ab2ac2889b15995a9eef56c753d48ebc7 upstream. + +Allow the firmware and enable GPIOs to sleep. + +This fixes a `WARN_ON' and allows the driver to operate GPIOs which are +connected to I2C GPIO expanders. + +-- >8 -- +kernel: WARNING: CPU: 3 PID: 2636 at drivers/gpio/gpiolib.c:3880 gpiod_set_value+0x88/0x98 +-- >8 -- + +Fixes: 43201767b44c ("NFC: nxp-nci: Convert to use GPIO descriptor") +Cc: stable@vger.kernel.org +Signed-off-by: Ian Ray +Link: https://patch.msgid.link/20260317085337.146545-1-ian.ray@gehealthcare.com +Signed-off-by: Jakub Kicinski +Signed-off-by: Greg Kroah-Hartman +--- + drivers/nfc/nxp-nci/i2c.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/drivers/nfc/nxp-nci/i2c.c ++++ b/drivers/nfc/nxp-nci/i2c.c +@@ -47,8 +47,8 @@ static int nxp_nci_i2c_set_mode(void *ph + { + struct nxp_nci_i2c_phy *phy = (struct nxp_nci_i2c_phy *) phy_id; + +- gpiod_set_value(phy->gpiod_fw, (mode == NXP_NCI_MODE_FW) ? 1 : 0); +- gpiod_set_value(phy->gpiod_en, (mode != NXP_NCI_MODE_COLD) ? 1 : 0); ++ gpiod_set_value_cansleep(phy->gpiod_fw, (mode == NXP_NCI_MODE_FW) ? 1 : 0); ++ gpiod_set_value_cansleep(phy->gpiod_en, (mode != NXP_NCI_MODE_COLD) ? 1 : 0); + usleep_range(10000, 15000); + + if (mode == NXP_NCI_MODE_COLD) diff --git a/queue-6.18/nfsd-defer-sub-object-cleanup-in-export-put-callbacks.patch b/queue-6.18/nfsd-defer-sub-object-cleanup-in-export-put-callbacks.patch new file mode 100644 index 0000000000..76d87e11e0 --- /dev/null +++ b/queue-6.18/nfsd-defer-sub-object-cleanup-in-export-put-callbacks.patch @@ -0,0 +1,235 @@ +From 48db892356d6cb80f6942885545de4a6dd8d2a29 Mon Sep 17 00:00:00 2001 +From: Chuck Lever +Date: Thu, 19 Feb 2026 16:50:16 -0500 +Subject: NFSD: Defer sub-object cleanup in export put callbacks + +From: Chuck Lever + +commit 48db892356d6cb80f6942885545de4a6dd8d2a29 upstream. + +svc_export_put() calls path_put() and auth_domain_put() immediately +when the last reference drops, before the RCU grace period. RCU +readers in e_show() and c_show() access both ex_path (via +seq_path/d_path) and ex_client->name (via seq_escape) without +holding a reference. If cache_clean removes the entry and drops the +last reference concurrently, the sub-objects are freed while still +in use, producing a NULL pointer dereference in d_path. + +Commit 2530766492ec ("nfsd: fix UAF when access ex_uuid or +ex_stats") moved kfree of ex_uuid and ex_stats into the +call_rcu callback, but left path_put() and auth_domain_put() running +before the grace period because both may sleep and call_rcu +callbacks execute in softirq context. + +Replace call_rcu/kfree_rcu with queue_rcu_work(), which defers the +callback until after the RCU grace period and executes it in process +context where sleeping is permitted. This allows path_put() and +auth_domain_put() to be moved into the deferred callback alongside +the other resource releases. Apply the same fix to expkey_put(), +which has the identical pattern with ek_path and ek_client. + +A dedicated workqueue scopes the shutdown drain to only NFSD +export release work items; flushing the shared +system_unbound_wq would stall on unrelated work from other +subsystems. nfsd_export_shutdown() uses rcu_barrier() followed +by flush_workqueue() to ensure all deferred release callbacks +complete before the export caches are destroyed. + +Reported-by: Misbah Anjum N +Closes: https://lore.kernel.org/linux-nfs/dcd371d3a95815a84ba7de52cef447b8@linux.ibm.com/ +Fixes: c224edca7af0 ("nfsd: no need get cache ref when protected by rcu") +Fixes: 1b10f0b603c0 ("SUNRPC: no need get cache ref when protected by rcu") +Cc: stable@vger.kernel.org +Reviwed-by: Jeff Layton +Reviewed-by: NeilBrown +Tested-by: Olga Kornievskaia +Signed-off-by: Chuck Lever +Signed-off-by: Greg Kroah-Hartman +--- + fs/nfsd/export.c | 63 +++++++++++++++++++++++++++++++++++++++++++++++-------- + fs/nfsd/export.h | 7 ++++-- + fs/nfsd/nfsctl.c | 8 ++++++ + 3 files changed, 66 insertions(+), 12 deletions(-) + +--- a/fs/nfsd/export.c ++++ b/fs/nfsd/export.c +@@ -36,19 +36,30 @@ + * second map contains a reference to the entry in the first map. + */ + ++static struct workqueue_struct *nfsd_export_wq; ++ + #define EXPKEY_HASHBITS 8 + #define EXPKEY_HASHMAX (1 << EXPKEY_HASHBITS) + #define EXPKEY_HASHMASK (EXPKEY_HASHMAX -1) + +-static void expkey_put(struct kref *ref) ++static void expkey_release(struct work_struct *work) + { +- struct svc_expkey *key = container_of(ref, struct svc_expkey, h.ref); ++ struct svc_expkey *key = container_of(to_rcu_work(work), ++ struct svc_expkey, ek_rwork); + + if (test_bit(CACHE_VALID, &key->h.flags) && + !test_bit(CACHE_NEGATIVE, &key->h.flags)) + path_put(&key->ek_path); + auth_domain_put(key->ek_client); +- kfree_rcu(key, ek_rcu); ++ kfree(key); ++} ++ ++static void expkey_put(struct kref *ref) ++{ ++ struct svc_expkey *key = container_of(ref, struct svc_expkey, h.ref); ++ ++ INIT_RCU_WORK(&key->ek_rwork, expkey_release); ++ queue_rcu_work(nfsd_export_wq, &key->ek_rwork); + } + + static int expkey_upcall(struct cache_detail *cd, struct cache_head *h) +@@ -353,11 +364,13 @@ static void export_stats_destroy(struct + EXP_STATS_COUNTERS_NUM); + } + +-static void svc_export_release(struct rcu_head *rcu_head) ++static void svc_export_release(struct work_struct *work) + { +- struct svc_export *exp = container_of(rcu_head, struct svc_export, +- ex_rcu); ++ struct svc_export *exp = container_of(to_rcu_work(work), ++ struct svc_export, ex_rwork); + ++ path_put(&exp->ex_path); ++ auth_domain_put(exp->ex_client); + nfsd4_fslocs_free(&exp->ex_fslocs); + export_stats_destroy(exp->ex_stats); + kfree(exp->ex_stats); +@@ -369,9 +382,8 @@ static void svc_export_put(struct kref * + { + struct svc_export *exp = container_of(ref, struct svc_export, h.ref); + +- path_put(&exp->ex_path); +- auth_domain_put(exp->ex_client); +- call_rcu(&exp->ex_rcu, svc_export_release); ++ INIT_RCU_WORK(&exp->ex_rwork, svc_export_release); ++ queue_rcu_work(nfsd_export_wq, &exp->ex_rwork); + } + + static int svc_export_upcall(struct cache_detail *cd, struct cache_head *h) +@@ -1478,6 +1490,36 @@ const struct seq_operations nfs_exports_ + .show = e_show, + }; + ++/** ++ * nfsd_export_wq_init - allocate the export release workqueue ++ * ++ * Called once at module load. The workqueue runs deferred svc_export and ++ * svc_expkey release work scheduled by queue_rcu_work() in the cache put ++ * callbacks. ++ * ++ * Return values: ++ * %0: workqueue allocated ++ * %-ENOMEM: allocation failed ++ */ ++int nfsd_export_wq_init(void) ++{ ++ nfsd_export_wq = alloc_workqueue("nfsd_export", WQ_UNBOUND, 0); ++ if (!nfsd_export_wq) ++ return -ENOMEM; ++ return 0; ++} ++ ++/** ++ * nfsd_export_wq_shutdown - drain and free the export release workqueue ++ * ++ * Called once at module unload. Per-namespace teardown in ++ * nfsd_export_shutdown() has already drained all deferred work. ++ */ ++void nfsd_export_wq_shutdown(void) ++{ ++ destroy_workqueue(nfsd_export_wq); ++} ++ + /* + * Initialize the exports module. + */ +@@ -1539,6 +1581,9 @@ nfsd_export_shutdown(struct net *net) + + cache_unregister_net(nn->svc_expkey_cache, net); + cache_unregister_net(nn->svc_export_cache, net); ++ /* Drain deferred export and expkey release work. */ ++ rcu_barrier(); ++ flush_workqueue(nfsd_export_wq); + cache_destroy_net(nn->svc_expkey_cache, net); + cache_destroy_net(nn->svc_export_cache, net); + svcauth_unix_purge(net); +--- a/fs/nfsd/export.h ++++ b/fs/nfsd/export.h +@@ -7,6 +7,7 @@ + + #include + #include ++#include + #include + #include + +@@ -75,7 +76,7 @@ struct svc_export { + u32 ex_layout_types; + struct nfsd4_deviceid_map *ex_devid_map; + struct cache_detail *cd; +- struct rcu_head ex_rcu; ++ struct rcu_work ex_rwork; + unsigned long ex_xprtsec_modes; + struct export_stats *ex_stats; + }; +@@ -92,7 +93,7 @@ struct svc_expkey { + u32 ek_fsid[6]; + + struct path ek_path; +- struct rcu_head ek_rcu; ++ struct rcu_work ek_rwork; + }; + + #define EX_ISSYNC(exp) (!((exp)->ex_flags & NFSEXP_ASYNC)) +@@ -110,6 +111,8 @@ __be32 check_nfsd_access(struct svc_expo + /* + * Function declarations + */ ++int nfsd_export_wq_init(void); ++void nfsd_export_wq_shutdown(void); + int nfsd_export_init(struct net *); + void nfsd_export_shutdown(struct net *); + void nfsd_export_flush(struct net *); +--- a/fs/nfsd/nfsctl.c ++++ b/fs/nfsd/nfsctl.c +@@ -2252,9 +2252,12 @@ static int __init init_nfsd(void) + if (retval) + goto out_free_pnfs; + nfsd_lockd_init(); /* lockd->nfsd callbacks */ ++ retval = nfsd_export_wq_init(); ++ if (retval) ++ goto out_free_lockd; + retval = register_pernet_subsys(&nfsd_net_ops); + if (retval < 0) +- goto out_free_lockd; ++ goto out_free_export_wq; + retval = register_cld_notifier(); + if (retval) + goto out_free_subsys; +@@ -2283,6 +2286,8 @@ out_free_cld: + unregister_cld_notifier(); + out_free_subsys: + unregister_pernet_subsys(&nfsd_net_ops); ++out_free_export_wq: ++ nfsd_export_wq_shutdown(); + out_free_lockd: + nfsd_lockd_shutdown(); + nfsd_drc_slab_free(); +@@ -2303,6 +2308,7 @@ static void __exit exit_nfsd(void) + nfsd4_destroy_laundry_wq(); + unregister_cld_notifier(); + unregister_pernet_subsys(&nfsd_net_ops); ++ nfsd_export_wq_shutdown(); + nfsd_drc_slab_free(); + nfsd_lockd_shutdown(); + nfsd4_free_slabs(); diff --git a/queue-6.18/nfsd-fix-heap-overflow-in-nfsv4.0-lock-replay-cache.patch b/queue-6.18/nfsd-fix-heap-overflow-in-nfsv4.0-lock-replay-cache.patch new file mode 100644 index 0000000000..30a6e6c4ef --- /dev/null +++ b/queue-6.18/nfsd-fix-heap-overflow-in-nfsv4.0-lock-replay-cache.patch @@ -0,0 +1,92 @@ +From 5133b61aaf437e5f25b1b396b14242a6bb0508e2 Mon Sep 17 00:00:00 2001 +From: Jeff Layton +Date: Tue, 24 Feb 2026 11:33:35 -0500 +Subject: nfsd: fix heap overflow in NFSv4.0 LOCK replay cache + +From: Jeff Layton + +commit 5133b61aaf437e5f25b1b396b14242a6bb0508e2 upstream. + +The NFSv4.0 replay cache uses a fixed 112-byte inline buffer +(rp_ibuf[NFSD4_REPLAY_ISIZE]) to store encoded operation responses. +This size was calculated based on OPEN responses and does not account +for LOCK denied responses, which include the conflicting lock owner as +a variable-length field up to 1024 bytes (NFS4_OPAQUE_LIMIT). + +When a LOCK operation is denied due to a conflict with an existing lock +that has a large owner, nfsd4_encode_operation() copies the full encoded +response into the undersized replay buffer via read_bytes_from_xdr_buf() +with no bounds check. This results in a slab-out-of-bounds write of up +to 944 bytes past the end of the buffer, corrupting adjacent heap memory. + +This can be triggered remotely by an unauthenticated attacker with two +cooperating NFSv4.0 clients: one sets a lock with a large owner string, +then the other requests a conflicting lock to provoke the denial. + +We could fix this by increasing NFSD4_REPLAY_ISIZE to allow for a full +opaque, but that would increase the size of every stateowner, when most +lockowners are not that large. + +Instead, fix this by checking the encoded response length against +NFSD4_REPLAY_ISIZE before copying into the replay buffer. If the +response is too large, set rp_buflen to 0 to skip caching the replay +payload. The status is still cached, and the client already received the +correct response on the original request. + +Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2") +Cc: stable@kernel.org +Reported-by: Nicholas Carlini +Tested-by: Nicholas Carlini +Signed-off-by: Jeff Layton +Signed-off-by: Chuck Lever +Signed-off-by: Greg Kroah-Hartman +--- + fs/nfsd/nfs4xdr.c | 9 +++++++-- + fs/nfsd/state.h | 17 ++++++++++++----- + 2 files changed, 19 insertions(+), 7 deletions(-) + +--- a/fs/nfsd/nfs4xdr.c ++++ b/fs/nfsd/nfs4xdr.c +@@ -5934,9 +5934,14 @@ nfsd4_encode_operation(struct nfsd4_comp + int len = xdr->buf->len - (op_status_offset + XDR_UNIT); + + so->so_replay.rp_status = op->status; +- so->so_replay.rp_buflen = len; +- read_bytes_from_xdr_buf(xdr->buf, op_status_offset + XDR_UNIT, ++ if (len <= NFSD4_REPLAY_ISIZE) { ++ so->so_replay.rp_buflen = len; ++ read_bytes_from_xdr_buf(xdr->buf, ++ op_status_offset + XDR_UNIT, + so->so_replay.rp_buf, len); ++ } else { ++ so->so_replay.rp_buflen = 0; ++ } + } + status: + op->status = nfsd4_map_status(op->status, +--- a/fs/nfsd/state.h ++++ b/fs/nfsd/state.h +@@ -541,11 +541,18 @@ struct nfs4_client_reclaim { + struct xdr_netobj cr_princhash; + }; + +-/* A reasonable value for REPLAY_ISIZE was estimated as follows: +- * The OPEN response, typically the largest, requires +- * 4(status) + 8(stateid) + 20(changeinfo) + 4(rflags) + 8(verifier) + +- * 4(deleg. type) + 8(deleg. stateid) + 4(deleg. recall flag) + +- * 20(deleg. space limit) + ~32(deleg. ace) = 112 bytes ++/* ++ * REPLAY_ISIZE is sized for an OPEN response with delegation: ++ * 4(status) + 8(stateid) + 20(changeinfo) + 4(rflags) + ++ * 8(verifier) + 4(deleg. type) + 8(deleg. stateid) + ++ * 4(deleg. recall flag) + 20(deleg. space limit) + ++ * ~32(deleg. ace) = 112 bytes ++ * ++ * Some responses can exceed this. A LOCK denial includes the conflicting ++ * lock owner, which can be up to 1024 bytes (NFS4_OPAQUE_LIMIT). Responses ++ * larger than REPLAY_ISIZE are not cached in rp_ibuf; only rp_status is ++ * saved. Enlarging this constant increases the size of every ++ * nfs4_stateowner. + */ + + #define NFSD4_REPLAY_ISIZE 112 diff --git a/queue-6.18/nfsd-hold-net-reference-for-the-lifetime-of-proc-fs-nfs-exports-fd.patch b/queue-6.18/nfsd-hold-net-reference-for-the-lifetime-of-proc-fs-nfs-exports-fd.patch new file mode 100644 index 0000000000..a36f769bc9 --- /dev/null +++ b/queue-6.18/nfsd-hold-net-reference-for-the-lifetime-of-proc-fs-nfs-exports-fd.patch @@ -0,0 +1,80 @@ +From e7fcf179b82d3a3730fd8615da01b087cc654d0b Mon Sep 17 00:00:00 2001 +From: Chuck Lever +Date: Thu, 19 Feb 2026 16:50:17 -0500 +Subject: NFSD: Hold net reference for the lifetime of /proc/fs/nfs/exports fd + +From: Chuck Lever + +commit e7fcf179b82d3a3730fd8615da01b087cc654d0b upstream. + +The /proc/fs/nfs/exports proc entry is created at module init +and persists for the module's lifetime. exports_proc_open() +captures the caller's current network namespace and stores +its svc_export_cache in seq->private, but takes no reference +on the namespace. If the namespace is subsequently torn down +(e.g. container destruction after the opener does setns() to a +different namespace), nfsd_net_exit() calls nfsd_export_shutdown() +which frees the cache. Subsequent reads on the still-open fd +dereference the freed cache_detail, walking a freed hash table. + +Hold a reference on the struct net for the lifetime of the open +file descriptor. This prevents nfsd_net_exit() from running -- +and thus prevents nfsd_export_shutdown() from freeing the cache +-- while any exports fd is open. cache_detail already stores +its net pointer (cd->net, set by cache_create_net()), so +exports_release() can retrieve it without additional per-file +storage. + +Reported-by: Misbah Anjum N +Closes: https://lore.kernel.org/linux-nfs/dcd371d3a95815a84ba7de52cef447b8@linux.ibm.com/ +Fixes: 96d851c4d28d ("nfsd: use proper net while reading "exports" file") +Cc: stable@vger.kernel.org +Reviewed-by: Jeff Layton +Reviewed-by: NeilBrown +Tested-by: Olga Kornievskaia +Signed-off-by: Chuck Lever +Signed-off-by: Greg Kroah-Hartman +--- + fs/nfsd/nfsctl.c | 14 ++++++++++++-- + 1 file changed, 12 insertions(+), 2 deletions(-) + +--- a/fs/nfsd/nfsctl.c ++++ b/fs/nfsd/nfsctl.c +@@ -149,9 +149,19 @@ static int exports_net_open(struct net * + + seq = file->private_data; + seq->private = nn->svc_export_cache; ++ get_net(net); + return 0; + } + ++static int exports_release(struct inode *inode, struct file *file) ++{ ++ struct seq_file *seq = file->private_data; ++ struct cache_detail *cd = seq->private; ++ ++ put_net(cd->net); ++ return seq_release(inode, file); ++} ++ + static int exports_nfsd_open(struct inode *inode, struct file *file) + { + return exports_net_open(inode->i_sb->s_fs_info, file); +@@ -161,7 +171,7 @@ static const struct file_operations expo + .open = exports_nfsd_open, + .read = seq_read, + .llseek = seq_lseek, +- .release = seq_release, ++ .release = exports_release, + }; + + static int export_features_show(struct seq_file *m, void *v) +@@ -1375,7 +1385,7 @@ static const struct proc_ops exports_pro + .proc_open = exports_proc_open, + .proc_read = seq_read, + .proc_lseek = seq_lseek, +- .proc_release = seq_release, ++ .proc_release = exports_release, + }; + + static int create_proc_exports_entry(void) diff --git a/queue-6.18/nvdimm-bus-fix-potential-use-after-free-in-asynchronous-initialization.patch b/queue-6.18/nvdimm-bus-fix-potential-use-after-free-in-asynchronous-initialization.patch new file mode 100644 index 0000000000..9bf333597f --- /dev/null +++ b/queue-6.18/nvdimm-bus-fix-potential-use-after-free-in-asynchronous-initialization.patch @@ -0,0 +1,55 @@ +From a8aec14230322ed8f1e8042b6d656c1631d41163 Mon Sep 17 00:00:00 2001 +From: Ira Weiny +Date: Fri, 6 Mar 2026 12:33:05 -0600 +Subject: nvdimm/bus: Fix potential use after free in asynchronous initialization + +From: Ira Weiny + +commit a8aec14230322ed8f1e8042b6d656c1631d41163 upstream. + +Dingisoul with KASAN reports a use after free if device_add() fails in +nd_async_device_register(). + +Commit b6eae0f61db2 ("libnvdimm: Hold reference on parent while +scheduling async init") correctly added a reference on the parent device +to be held until asynchronous initialization was complete. However, if +device_add() results in an allocation failure the ref count of the +device drops to 0 prior to the parent pointer being accessed. Thus +resulting in use after free. + +The bug bot AI correctly identified the fix. Save a reference to the +parent pointer to be used to drop the parent reference regardless of the +outcome of device_add(). + +Reported-by: Dingisoul +Closes: http://lore.kernel.org/8855544b-be9e-4153-aa55-0bc328b13733@gmail.com +Fixes: b6eae0f61db2 ("libnvdimm: Hold reference on parent while scheduling async init") +Cc: stable@vger.kernel.org +Reviewed-by: Dave Jiang +Link: https://patch.msgid.link/20260306-fix-uaf-async-init-v1-1-a28fd7526723@intel.com +Signed-off-by: Ira Weiny +Signed-off-by: Greg Kroah-Hartman +--- + drivers/nvdimm/bus.c | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +--- a/drivers/nvdimm/bus.c ++++ b/drivers/nvdimm/bus.c +@@ -486,14 +486,15 @@ EXPORT_SYMBOL_GPL(nd_synchronize); + static void nd_async_device_register(void *d, async_cookie_t cookie) + { + struct device *dev = d; ++ struct device *parent = dev->parent; + + if (device_add(dev) != 0) { + dev_err(dev, "%s: failed\n", __func__); + put_device(dev); + } + put_device(dev); +- if (dev->parent) +- put_device(dev->parent); ++ if (parent) ++ put_device(parent); + } + + static void nd_async_device_unregister(void *d, async_cookie_t cookie) diff --git a/queue-6.18/parisc-flush-correct-cache-in-cacheflush-syscall.patch b/queue-6.18/parisc-flush-correct-cache-in-cacheflush-syscall.patch new file mode 100644 index 0000000000..5db07988ca --- /dev/null +++ b/queue-6.18/parisc-flush-correct-cache-in-cacheflush-syscall.patch @@ -0,0 +1,51 @@ +From 2c98a8fbd6aa647414c6248dacf254ebe91c79ad Mon Sep 17 00:00:00 2001 +From: Helge Deller +Date: Mon, 9 Mar 2026 15:16:37 +0100 +Subject: parisc: Flush correct cache in cacheflush() syscall + +From: Helge Deller + +commit 2c98a8fbd6aa647414c6248dacf254ebe91c79ad upstream. + +The assembly flush instructions were swapped for I- and D-cache flags: + +SYSCALL_DEFINE3(cacheflush, ...) +{ + if (cache & DCACHE) { + "fic ...\n" + } + if (cache & ICACHE && error == 0) { + "fdc ...\n" + } + +Fix it by using fdc for DCACHE, and fic for ICACHE flushing. + +Reported-by: Felix Lechner +Fixes: c6d96328fecd ("parisc: Add cacheflush() syscall") +Cc: # v6.5+ +Signed-off-by: Helge Deller +Signed-off-by: Greg Kroah-Hartman +--- + arch/parisc/kernel/cache.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/arch/parisc/kernel/cache.c ++++ b/arch/parisc/kernel/cache.c +@@ -953,7 +953,7 @@ SYSCALL_DEFINE3(cacheflush, unsigned lon + #else + "1: cmpb,<<,n %0,%2,1b\n" + #endif +- " fic,m %3(%4,%0)\n" ++ " fdc,m %3(%4,%0)\n" + "2: sync\n" + ASM_EXCEPTIONTABLE_ENTRY_EFAULT(1b, 2b, "%1") + : "+r" (start), "+r" (error) +@@ -968,7 +968,7 @@ SYSCALL_DEFINE3(cacheflush, unsigned lon + #else + "1: cmpb,<<,n %0,%2,1b\n" + #endif +- " fdc,m %3(%4,%0)\n" ++ " fic,m %3(%4,%0)\n" + "2: sync\n" + ASM_EXCEPTIONTABLE_ENTRY_EFAULT(1b, 2b, "%1") + : "+r" (start), "+r" (error) diff --git a/queue-6.18/selftests-hid-fix-compilation-when-bpf_wq-and-hid_device-are-not-exported.patch b/queue-6.18/selftests-hid-fix-compilation-when-bpf_wq-and-hid_device-are-not-exported.patch new file mode 100644 index 0000000000..fee65d133c --- /dev/null +++ b/queue-6.18/selftests-hid-fix-compilation-when-bpf_wq-and-hid_device-are-not-exported.patch @@ -0,0 +1,69 @@ +From 5d4c6c132ea9a967d48890dd03e6a786c060e968 Mon Sep 17 00:00:00 2001 +From: Benjamin Tissoires +Date: Fri, 13 Mar 2026 08:40:24 +0100 +Subject: selftests/hid: fix compilation when bpf_wq and hid_device are not exported +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Benjamin Tissoires + +commit 5d4c6c132ea9a967d48890dd03e6a786c060e968 upstream. + +This can happen in situations when CONFIG_HID_SUPPORT is set to no, or +some complex situations where struct bpf_wq is not exported. + +So do the usual dance of hiding them before including vmlinux.h, and +then redefining them and make use of CO-RE to have the correct offsets. + +Reported-by: kernel test robot +Closes: https://lore.kernel.org/oe-kbuild-all/202603111558.KLCIxsZB-lkp@intel.com/ +Fixes: fe8d561db3e8 ("selftests/hid: add wq test for hid_bpf_input_report()") +Cc: stable@vger.kernel.org +Acked-by: Jiri Kosina +Reviewed-by: Thomas Weißschuh +Signed-off-by: Benjamin Tissoires +Signed-off-by: Greg Kroah-Hartman +--- + tools/testing/selftests/hid/progs/hid_bpf_helpers.h | 12 ++++++++++++ + 1 file changed, 12 insertions(+) + +--- a/tools/testing/selftests/hid/progs/hid_bpf_helpers.h ++++ b/tools/testing/selftests/hid/progs/hid_bpf_helpers.h +@@ -6,8 +6,10 @@ + #define __HID_BPF_HELPERS_H + + /* "undefine" structs and enums in vmlinux.h, because we "override" them below */ ++#define bpf_wq bpf_wq___not_used + #define hid_bpf_ctx hid_bpf_ctx___not_used + #define hid_bpf_ops hid_bpf_ops___not_used ++#define hid_device hid_device___not_used + #define hid_report_type hid_report_type___not_used + #define hid_class_request hid_class_request___not_used + #define hid_bpf_attach_flags hid_bpf_attach_flags___not_used +@@ -27,8 +29,10 @@ + + #include "vmlinux.h" + ++#undef bpf_wq + #undef hid_bpf_ctx + #undef hid_bpf_ops ++#undef hid_device + #undef hid_report_type + #undef hid_class_request + #undef hid_bpf_attach_flags +@@ -55,6 +59,14 @@ enum hid_report_type { + HID_REPORT_TYPES, + }; + ++struct hid_device { ++ unsigned int id; ++} __attribute__((preserve_access_index)); ++ ++struct bpf_wq { ++ __u64 __opaque[2]; ++}; ++ + struct hid_bpf_ctx { + struct hid_device *hid; + __u32 allocated_size; diff --git a/queue-6.18/series b/queue-6.18/series new file mode 100644 index 0000000000..b227b4cc69 --- /dev/null +++ b/queue-6.18/series @@ -0,0 +1,22 @@ +nfsd-defer-sub-object-cleanup-in-export-put-callbacks.patch +nfsd-hold-net-reference-for-the-lifetime-of-proc-fs-nfs-exports-fd.patch +nfsd-fix-heap-overflow-in-nfsv4.0-lock-replay-cache.patch +selftests-hid-fix-compilation-when-bpf_wq-and-hid_device-are-not-exported.patch +hid-bpf-prevent-buffer-overflow-in-hid_hw_request.patch +sunrpc-fix-cache_request-leak-in-cache_release.patch +nvdimm-bus-fix-potential-use-after-free-in-asynchronous-initialization.patch +crash_dump-don-t-log-dm-crypt-key-bytes-in-read_key_from_user_keying.patch +mm-rmap-fix-incorrect-pte-restoration-for-lazyfree-folios.patch +mm-huge_memory-fix-use-of-null-folio-in-move_pages_huge_pmd.patch +mm-huge_memory-fix-early-failure-try_to_migrate-when-split-huge-pmd-for-shared-thp.patch +loongarch-give-more-information-if-kmem-access-failed.patch +loongarch-no-need-to-flush-icache-if-text-copy-failed.patch +nfc-nxp-nci-allow-gpios-to-sleep.patch +net-macb-fix-use-after-free-access-to-ptp-clock.patch +bnxt_en-fix-oob-access-in-dbg_buf_producer-async-event-handler.patch +parisc-flush-correct-cache-in-cacheflush-syscall.patch +batman-adv-avoid-ogm-aggregation-when-skb-tailroom-is-insufficient.patch +mac80211-fix-crash-in-ieee80211_chan_bw_change-for-ap_vlan-stations.patch +crypto-padlock-sha-disable-for-zhaoxin-processor.patch +bluetooth-l2cap-fix-type-confusion-in-l2cap_ecred_reconf_rsp.patch +bluetooth-l2cap-validate-l2cap_info_rsp-payload-length-before-access.patch diff --git a/queue-6.18/sunrpc-fix-cache_request-leak-in-cache_release.patch b/queue-6.18/sunrpc-fix-cache_request-leak-in-cache_release.patch new file mode 100644 index 0000000000..11111d6893 --- /dev/null +++ b/queue-6.18/sunrpc-fix-cache_request-leak-in-cache_release.patch @@ -0,0 +1,86 @@ +From 17ad31b3a43b72aec3a3d83605891e1397d0d065 Mon Sep 17 00:00:00 2001 +From: Jeff Layton +Date: Mon, 23 Feb 2026 12:09:58 -0500 +Subject: sunrpc: fix cache_request leak in cache_release + +From: Jeff Layton + +commit 17ad31b3a43b72aec3a3d83605891e1397d0d065 upstream. + +When a reader's file descriptor is closed while in the middle of reading +a cache_request (rp->offset != 0), cache_release() decrements the +request's readers count but never checks whether it should free the +request. + +In cache_read(), when readers drops to 0 and CACHE_PENDING is clear, the +cache_request is removed from the queue and freed along with its buffer +and cache_head reference. cache_release() lacks this cleanup. + +The only other path that frees requests with readers == 0 is +cache_dequeue(), but it runs only when CACHE_PENDING transitions from +set to clear. If that transition already happened while readers was +still non-zero, cache_dequeue() will have skipped the request, and no +subsequent call will clean it up. + +Add the same cleanup logic from cache_read() to cache_release(): after +decrementing readers, check if it reached 0 with CACHE_PENDING clear, +and if so, dequeue and free the cache_request. + +Reported-by: NeilBrown +Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2") +Cc: stable@kernel.org +Signed-off-by: Jeff Layton +Signed-off-by: Chuck Lever +Signed-off-by: Greg Kroah-Hartman +--- + net/sunrpc/cache.c | 26 +++++++++++++++++++++----- + 1 file changed, 21 insertions(+), 5 deletions(-) + +--- a/net/sunrpc/cache.c ++++ b/net/sunrpc/cache.c +@@ -1061,14 +1061,25 @@ static int cache_release(struct inode *i + struct cache_reader *rp = filp->private_data; + + if (rp) { ++ struct cache_request *rq = NULL; ++ + spin_lock(&queue_lock); + if (rp->offset) { + struct cache_queue *cq; +- for (cq= &rp->q; &cq->list != &cd->queue; +- cq = list_entry(cq->list.next, struct cache_queue, list)) ++ for (cq = &rp->q; &cq->list != &cd->queue; ++ cq = list_entry(cq->list.next, ++ struct cache_queue, list)) + if (!cq->reader) { +- container_of(cq, struct cache_request, q) +- ->readers--; ++ struct cache_request *cr = ++ container_of(cq, ++ struct cache_request, q); ++ cr->readers--; ++ if (cr->readers == 0 && ++ !test_bit(CACHE_PENDING, ++ &cr->item->flags)) { ++ list_del(&cr->q.list); ++ rq = cr; ++ } + break; + } + rp->offset = 0; +@@ -1076,9 +1087,14 @@ static int cache_release(struct inode *i + list_del(&rp->q.list); + spin_unlock(&queue_lock); + ++ if (rq) { ++ cache_put(rq->item, cd); ++ kfree(rq->buf); ++ kfree(rq); ++ } ++ + filp->private_data = NULL; + kfree(rp); +- + } + if (filp->f_mode & FMODE_WRITE) { + atomic_dec(&cd->writers);