From: Greg Kroah-Hartman Date: Wed, 30 Jul 2025 08:55:27 +0000 (+0200) Subject: 6.6-stable patches X-Git-Tag: v6.6.101~4 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=7ab4fce1f1e7ea6476cbd0ceaba03e81738e5086;p=thirdparty%2Fkernel%2Fstable-queue.git 6.6-stable patches added patches: erofs-address-d-cache-aliasing.patch mm-khugepaged-fix-call-hpage_collapse_scan_file-for-anonymous-vma.patch --- diff --git a/queue-6.6/erofs-address-d-cache-aliasing.patch b/queue-6.6/erofs-address-d-cache-aliasing.patch new file mode 100644 index 0000000000..60ce60d410 --- /dev/null +++ b/queue-6.6/erofs-address-d-cache-aliasing.patch @@ -0,0 +1,133 @@ +From 27917e8194f91dffd8b4825350c63cb68e98ce58 Mon Sep 17 00:00:00 2001 +From: Gao Xiang +Date: Wed, 9 Jul 2025 11:46:14 +0800 +Subject: erofs: address D-cache aliasing + +From: Gao Xiang + +commit 27917e8194f91dffd8b4825350c63cb68e98ce58 upstream. + +Flush the D-cache before unlocking folios for compressed inodes, as +they are dirtied during decompression. + +Avoid calling flush_dcache_folio() on every CPU write, since it's more +like playing whack-a-mole without real benefit. + +It has no impact on x86 and arm64/risc-v: on x86, flush_dcache_folio() +is a no-op, and on arm64/risc-v, PG_dcache_clean (PG_arch_1) is clear +for new page cache folios. However, certain ARM boards are affected, +as reported. + +Fixes: 3883a79abd02 ("staging: erofs: introduce VLE decompression support") +Closes: https://lore.kernel.org/r/c1e51e16-6cc6-49d0-a63e-4e9ff6c4dd53@pengutronix.de +Closes: https://lore.kernel.org/r/38d43fae-1182-4155-9c5b-ffc7382d9917@siemens.com +Tested-by: Jan Kiszka +Tested-by: Stefan Kerkmann +Signed-off-by: Gao Xiang +Link: https://lore.kernel.org/r/20250709034614.2780117-2-hsiangkao@linux.alibaba.com +Signed-off-by: Gao Xiang +Signed-off-by: Greg Kroah-Hartman +--- + fs/erofs/decompressor.c | 6 ++---- + fs/erofs/zdata.c | 32 +++++++++++++++++++------------- + 2 files changed, 21 insertions(+), 17 deletions(-) + +--- a/fs/erofs/decompressor.c ++++ b/fs/erofs/decompressor.c +@@ -342,14 +342,12 @@ static int z_erofs_transform_plain(struc + + if (outpages > inpages) { + DBG_BUGON(!rq->out[outpages - 1]); +- if (rq->out[outpages - 1] != rq->in[inpages - 1]) { ++ if (rq->out[outpages - 1] != rq->in[inpages - 1]) + memcpy_to_page(rq->out[outpages - 1], 0, src + + (interlaced_offset ? 0 : righthalf), + lefthalf); +- } else if (!interlaced_offset) { ++ else if (!interlaced_offset) + memmove(src, src + righthalf, lefthalf); +- flush_dcache_page(rq->in[inpages - 1]); +- } + } + kunmap_local(src); + return 0; +--- a/fs/erofs/zdata.c ++++ b/fs/erofs/zdata.c +@@ -122,9 +122,11 @@ static inline unsigned int z_erofs_pclus + + /* + * bit 30: I/O error occurred on this page ++ * bit 29: CPU has dirty data in D-cache (needs aliasing handling); + * bit 0 - 29: remaining parts to complete this page + */ +-#define Z_EROFS_PAGE_EIO (1 << 30) ++#define Z_EROFS_ONLINEPAGE_EIO 30 ++#define Z_EROFS_ONLINEPAGE_DIRTY 29 + + static inline void z_erofs_onlinepage_init(struct page *page) + { +@@ -143,7 +145,7 @@ static inline void z_erofs_onlinepage_sp + atomic_inc((atomic_t *)&page->private); + } + +-static void z_erofs_onlinepage_endio(struct page *page, int err) ++static void z_erofs_onlinepage_end(struct page *page, int err, bool dirty) + { + int orig, v; + +@@ -151,16 +153,20 @@ static void z_erofs_onlinepage_endio(str + + do { + orig = atomic_read((atomic_t *)&page->private); +- v = (orig - 1) | (err ? Z_EROFS_PAGE_EIO : 0); ++ DBG_BUGON(orig <= 0); ++ v = dirty << Z_EROFS_ONLINEPAGE_DIRTY; ++ v |= (orig - 1) | (!!err << Z_EROFS_ONLINEPAGE_EIO); + } while (atomic_cmpxchg((atomic_t *)&page->private, orig, v) != orig); + +- if (!(v & ~Z_EROFS_PAGE_EIO)) { +- set_page_private(page, 0); +- ClearPagePrivate(page); +- if (!(v & Z_EROFS_PAGE_EIO)) +- SetPageUptodate(page); +- unlock_page(page); +- } ++ if (v & (BIT(Z_EROFS_ONLINEPAGE_DIRTY) - 1)) ++ return; ++ set_page_private(page, 0); ++ ClearPagePrivate(page); ++ if (v & BIT(Z_EROFS_ONLINEPAGE_DIRTY)) ++ flush_dcache_page(page); ++ if (!(v & BIT(Z_EROFS_ONLINEPAGE_EIO))) ++ SetPageUptodate(page); ++ unlock_page(page); + } + + #define Z_EROFS_ONSTACK_PAGES 32 +@@ -1060,7 +1066,7 @@ next_part: + goto repeat; + + out: +- z_erofs_onlinepage_endio(page, err); ++ z_erofs_onlinepage_end(page, err, false); + return err; + } + +@@ -1163,7 +1169,7 @@ static void z_erofs_fill_other_copies(st + cur += len; + } + kunmap_local(dst); +- z_erofs_onlinepage_endio(bvi->bvec.page, err); ++ z_erofs_onlinepage_end(bvi->bvec.page, err, true); + list_del(p); + kfree(bvi); + } +@@ -1333,7 +1339,7 @@ out: + /* recycle all individual short-lived pages */ + if (z_erofs_put_shortlivedpage(be->pagepool, page)) + continue; +- z_erofs_onlinepage_endio(page, err); ++ z_erofs_onlinepage_end(page, err, true); + } + + if (be->decompressed_pages != be->onstack_pages) diff --git a/queue-6.6/mm-khugepaged-fix-call-hpage_collapse_scan_file-for-anonymous-vma.patch b/queue-6.6/mm-khugepaged-fix-call-hpage_collapse_scan_file-for-anonymous-vma.patch new file mode 100644 index 0000000000..50de9b7582 --- /dev/null +++ b/queue-6.6/mm-khugepaged-fix-call-hpage_collapse_scan_file-for-anonymous-vma.patch @@ -0,0 +1,93 @@ +From f1897f2f08b28ae59476d8b73374b08f856973af Mon Sep 17 00:00:00 2001 +From: Liu Shixin +Date: Sat, 11 Jan 2025 11:45:11 +0800 +Subject: mm: khugepaged: fix call hpage_collapse_scan_file() for anonymous vma + +From: Liu Shixin + +commit f1897f2f08b28ae59476d8b73374b08f856973af upstream. + +syzkaller reported such a BUG_ON(): + + ------------[ cut here ]------------ + kernel BUG at mm/khugepaged.c:1835! + Internal error: Oops - BUG: 00000000f2000800 [#1] SMP + ... + CPU: 6 UID: 0 PID: 8009 Comm: syz.15.106 Kdump: loaded Tainted: G W 6.13.0-rc6 #22 + Tainted: [W]=WARN + Hardware name: QEMU KVM Virtual Machine, BIOS 0.0.0 02/06/2015 + pstate: 00400005 (nzcv daif +PAN -UAO -TCO -DIT -SSBS BTYPE=--) + pc : collapse_file+0xa44/0x1400 + lr : collapse_file+0x88/0x1400 + sp : ffff80008afe3a60 + ... + Call trace: + collapse_file+0xa44/0x1400 (P) + hpage_collapse_scan_file+0x278/0x400 + madvise_collapse+0x1bc/0x678 + madvise_vma_behavior+0x32c/0x448 + madvise_walk_vmas.constprop.0+0xbc/0x140 + do_madvise.part.0+0xdc/0x2c8 + __arm64_sys_madvise+0x68/0x88 + invoke_syscall+0x50/0x120 + el0_svc_common.constprop.0+0xc8/0xf0 + do_el0_svc+0x24/0x38 + el0_svc+0x34/0x128 + el0t_64_sync_handler+0xc8/0xd0 + el0t_64_sync+0x190/0x198 + +This indicates that the pgoff is unaligned. After analysis, I confirm the +vma is mapped to /dev/zero. Such a vma certainly has vm_file, but it is +set to anonymous by mmap_zero(). So even if it's mmapped by 2m-unaligned, +it can pass the check in thp_vma_allowable_order() as it is an +anonymous-mmap, but then be collapsed as a file-mmap. + +It seems the problem has existed for a long time, but actually, since we +have khugepaged_max_ptes_none check before, we will skip collapse it as it +is /dev/zero and so has no present page. But commit d8ea7cc8547c limit +the check for only khugepaged, so the BUG_ON() can be triggered by +madvise_collapse(). + +Add vma_is_anonymous() check to make such vma be processed by +hpage_collapse_scan_pmd(). + +Link: https://lkml.kernel.org/r/20250111034511.2223353-1-liushixin2@huawei.com +Fixes: d8ea7cc8547c ("mm/khugepaged: add flag to predicate khugepaged-only behavior") +Signed-off-by: Liu Shixin +Reviewed-by: Yang Shi +Acked-by: David Hildenbrand +Cc: Chengming Zhou +Cc: Johannes Weiner +Cc: Kefeng Wang +Cc: Mattew Wilcox +Cc: Muchun Song +Cc: Nanyong Sun +Cc: Qi Zheng +Signed-off-by: Andrew Morton +[acsjakub: backport, clean apply] +Signed-off-by: Jakub Acs +Signed-off-by: Greg Kroah-Hartman +--- + mm/khugepaged.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/mm/khugepaged.c ++++ b/mm/khugepaged.c +@@ -2387,7 +2387,7 @@ skip: + VM_BUG_ON(khugepaged_scan.address < hstart || + khugepaged_scan.address + HPAGE_PMD_SIZE > + hend); +- if (IS_ENABLED(CONFIG_SHMEM) && vma->vm_file) { ++ if (IS_ENABLED(CONFIG_SHMEM) && !vma_is_anonymous(vma)) { + struct file *file = get_file(vma->vm_file); + pgoff_t pgoff = linear_page_index(vma, + khugepaged_scan.address); +@@ -2734,7 +2734,7 @@ int madvise_collapse(struct vm_area_stru + mmap_assert_locked(mm); + memset(cc->node_load, 0, sizeof(cc->node_load)); + nodes_clear(cc->alloc_nmask); +- if (IS_ENABLED(CONFIG_SHMEM) && vma->vm_file) { ++ if (IS_ENABLED(CONFIG_SHMEM) && !vma_is_anonymous(vma)) { + struct file *file = get_file(vma->vm_file); + pgoff_t pgoff = linear_page_index(vma, addr); + diff --git a/queue-6.6/series b/queue-6.6/series index ea3cb8301c..db0ccbac3c 100644 --- a/queue-6.6/series +++ b/queue-6.6/series @@ -55,3 +55,5 @@ comedi-comedi_test-fix-possible-deletion-of-uninitialized-timers.patch alsa-hda-tegra-add-tegra264-support.patch alsa-hda-add-missing-nvidia-hda-codec-ids.patch drm-i915-dp-fix-2.7-gbps-dp_link_bw-value-on-g4x.patch +mm-khugepaged-fix-call-hpage_collapse_scan_file-for-anonymous-vma.patch +erofs-address-d-cache-aliasing.patch