From 11d5af151bcbe78f5a579e0faecd3be9cea0399a Mon Sep 17 00:00:00 2001 From: Pengpeng Hou Date: Fri, 14 Aug 2026 16:02:15 +0800 Subject: [PATCH] mailbox: riscv-sbi-mpxy: validate RPMI notification lengths The SBI return value controls how many bytes are copied from shared memory into the RPMI notification buffer. It is not validated against the negotiated shared-memory size before that copy. The event walker also uses a reversed loop condition and can inspect a short event record. Validate the complete notification length before copying it, iterate only while a full event header remains, and stop when a declared event payload extends beyond the copied notification data. Fixes: bf3022a4eb11 ("mailbox: Add RISC-V SBI message proxy (MPXY) based mailbox driver") Assisted-by: Codex:gpt-5 Signed-off-by: Pengpeng Hou Signed-off-by: Jassi Brar --- drivers/mailbox/riscv-sbi-mpxy-mbox.c | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/drivers/mailbox/riscv-sbi-mpxy-mbox.c b/drivers/mailbox/riscv-sbi-mpxy-mbox.c index 7c9c006b7244..714f7fb97a2f 100644 --- a/drivers/mailbox/riscv-sbi-mpxy-mbox.c +++ b/drivers/mailbox/riscv-sbi-mpxy-mbox.c @@ -314,8 +314,13 @@ static int mpxy_get_notifications(u32 channel_id, channel_id, 0, 0, 0, 0, 0); if (sret.error) goto err_put_cpu; + if (sret.value < 0 || mpxy_shmem_size < sizeof(*notif_data) || + sret.value > mpxy_shmem_size - sizeof(*notif_data)) { + put_cpu(); + return -EOVERFLOW; + } - memcpy(notif_data, mpxy->shmem, sret.value + 16); + memcpy(notif_data, mpxy->shmem, sret.value + sizeof(*notif_data)); *events_data_len = sret.value; err_put_cpu: @@ -480,11 +485,14 @@ static void mpxy_mbox_peek_rpmi_data(struct mbox_chan *chan, struct rpmi_mbox_message msg; unsigned long pos = 0; - while (pos < events_data_len && (events_data_len - pos) <= sizeof(*event)) { + while (events_data_len - pos >= sizeof(*event)) { event = (struct rpmi_notification_event *)(notif->events_data + pos); msg.type = RPMI_MBOX_MSG_TYPE_NOTIFICATION_EVENT; msg.notif.event_datalen = le16_to_cpu(event->event_datalen); + if (msg.notif.event_datalen > + events_data_len - pos - sizeof(*event)) + break; msg.notif.event_id = event->event_id; msg.notif.event_data = event->event_data; msg.error = 0;