A vulnerability in the Linux kernel's raid5d() implementation has recently been resolved, addressing a deadlock that caused an lvm2 test to hang occasionally. The issue was first identified by Xiao, who noticed the lvm2 test lvconvert-raid-takeover.sh could hang due to the same root cause as commit bed9e27baf52 ("Revert "md/raid5: Wait for MD_SB_CHANGE_PENDING in raid5d"").
Original references for this issue can be found in the following links
- Commit bed9e27baf52: https://github.com/torvalds/linux/commit/bed9e27baf5209cd7e5c585f16059342db9eeb81
- Lvm2 test case: https://github.com/lvmteam/lvm2/blob/master/test/shell/lvconvert-raid-takeover.sh
After the initial fix, Dan reported another hang in the raid5d() implementation. Junxiao investigated and discovered that the hang was caused by plugged bio not being issued from raid5d().
IO from raid5d() must wait for MD_SB_CHANGE_PENDING to be cleared
This behavior was introduced prior to version 2.6 of the Linux kernel. As a result, if another context holds the 'reconfig_mutex' lock and md_check_recovery() cannot update the super_block, the raid5d() loop will consume 100% of a CPU until the 'reconfig_mutex' is released.
Referencing the implementations used in raid1 and raid10, the issue was resolved by skipping the IO process if MD_SB_CHANGE_PENDING is still set after md_check_recovery(). The daemon thread will now be woken up when the 'reconfig_mutex' is released, fixing the hang issue as well.
Here's a code snippet of the fix
//raid5d() function
while (!kthread_should_stop() && !conf->inactive) {
//...omitted for brevity...
md_check_recovery(mddev);
if (!test_bit(MD_SB_CHANGE_PENDING, &mddev->suspended)) {
//... IO handling code ...
}
//...omitted for brevity...
}
In conclusion, the CVE-2024-39476 vulnerability in the Linux kernel's raid5d() implementation has been fixed. The deadlock issue has been addressed, significantly reducing the likelihood of any lvm2 tests hanging. The fix follows best practices from raid1 and raid10, ensuring a more reliable and efficient Linux kernel.
Timeline
Published on: 07/05/2024 07:15:10 UTC
Last modified on: 08/02/2024 04:26:15 UTC