In the Linux kernel, the following vulnerability has been resolved:
ubifs: ubifsreleasepage: Remove ubifsassert(0) to valid this process
There are two states for ubifs writing pages: 1. Dirty, Private 2. Not Dirty, Not Private
The normal process cannot go to ubifs_releasepage() which means there exists pages being private but not dirty. Reproducer[1] shows that it could occur (which maybe related to [2]) with following process:
PA PB PC
lock(page)[PA] ubifswriteend attachpageprivate // set Private _setpagedirtynobuffers // set Dirty unlock(page)
writecachepages[PA] lock(page) clearpagedirtyforio(page) // clear Dirty ubifs_writepage
do_truncation[PB]
truncate_setsize
i_size_write(inode, newsize) // newsize = 0
i_size = i_size_read(inode) // i_size = 0
end_index = i_size >> PAGE_SHIFT
if (page->index > end_index)
goto out // jump
out: unlock(page) // Private, Not Dirty
generic_fadvise[PC]
lock(page)
invalidate_inode_page
try_to_release_page
ubifs_releasepage
ubifs_assert(c, 0)
// bad assertion!
unlock(page)
truncate_pagecache[PB]
Then we may get following assertion failed: UBIFS error (ubi0:0 pid 1683): ubifsassertfailed [ubifs]: UBIFS assert failed: 0, in fs/ubifs/file.c:1513 UBIFS warning (ubi0:0 pid 1683): ubifsromode [ubifs]: switched to read-only mode, error -22 CPU: 2 PID: 1683 Comm: aa Not tainted 5.16.0-rc5-00184-g0bca5994cacc-dirty #308 Call Trace: dumpstack+0x13/0x1b ubifsromode+0x54/0x60 [ubifs] ubifsassertfailed+0x4b/0x80 [ubifs] ubifsreleasepage+0x67/0x1d0 [ubifs] trytoreleasepage+0x57/0xe0 invalidateinode_page+0xfb/0x130 _invalidatemappingpages+0xb9/0x280 invalidatemappingpagevec+0x12/0x20 genericfadvise+0x303/0x3c0 ksysfadvise6464+0x4c/0xb0
[1] https://bugzilla.kernel.org/show_bug.cgi?id=215373 [2] https://linux-mtd.infradead.narkive.com/NQoBeT1u/patch-rfc-ubifs-fix-assert-failed-in-ubifs-set-page-dirty
{
"osv_generated_from": "https://github.com/CVEProject/cvelistV5/tree/main/cves/2023/53xxx/CVE-2023-53584.json",
"cna_assigner": "Linux"
}