[PATCH 4/4] RAS/amd/fmpm: Fix spurious BUG when ERST record enumeration fails
"Rui Qi" <[email protected]>
| Newsgroups | org.kernel.vger.linux-edac,org.kernel.vger.linux-kernel |
|---|---|
| Message-ID | <[email protected]> |
When erst_get_record_id_begin() returns an error, get_saved_records()
jumps to the out_end label which unconditionally calls
erst_get_record_id_end(). This is wrong because:
- If erst_disable is true, begin() returns -ENODEV without
incrementing the refcount. Then end() hits BUG_ON(erst_disable)
and panics.
- If mutex_lock_interruptible() is interrupted, begin() returns
-EINTR without incrementing the refcount. Then end() decrements
refcount below zero, hitting BUG_ON(refcount < 0).
The comment in erst_get_record_id_end() explicitly states that it
should not be called when erst_get_record_id_begin() failed.
Fix by adding a separate out_free label that only does kfree(),
skipping the erst_get_record_id_end() call when begin() failed.
Fixes: 6f15e617cc99 ("RAS: Introduce a FRU memory poison manager")
Signed-off-by: Rui Qi <[email protected]>
---
drivers/ras/amd/fmpm.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/drivers/ras/amd/fmpm.c b/drivers/ras/amd/fmpm.c
index 14a103de9d62..22627f6278c0 100644
--- a/drivers/ras/amd/fmpm.c
+++ b/drivers/ras/amd/fmpm.c
@@ -675,7 +675,7 @@ static int get_saved_records(void)
ret = erst_get_record_id_begin(&pos);
if (ret < 0)
- goto out_end;
+ goto out_free;
while (!erst_get_record_id_next(&pos, &record_id)) {
if (record_id == APEI_ERST_INVALID_RECORD_ID)
@@ -716,6 +716,7 @@ static int get_saved_records(void)
out_end:
erst_get_record_id_end();
+out_free:
kfree(old);
out:
return ret;
--
2.20.1