summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMukesh Ojha <mukesh.ojha@oss.qualcomm.com>2026-06-16 15:53:02 -0400
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2026-07-04 13:39:40 +0200
commit0d8c64511fd45690c5326f013710efcb4f73a97e (patch)
treea9c4bb5699bfb7e0b8e8e71da0e95edb6d0fb357
parent00703b96d7eb08bacefae5248639079b83c2863d (diff)
downloadlinux-0d8c64511fd45690c5326f013710efcb4f73a97e.tar.gz
linux-0d8c64511fd45690c5326f013710efcb4f73a97e.zip
misc: fastrpc: Fix NULL pointer dereference in rpmsg callback
[ Upstream commit 5401fb4fe10fac6134c308495df18ed74aebb9c4 ] A NULL pointer dereference was observed on Hawi at boot when the DSP sends a glink message before fastrpc_rpmsg_probe() has completed initialization: Unable to handle kernel NULL pointer dereference at virtual address 0000000000000178 pc : _raw_spin_lock_irqsave+0x34/0x8c lr : fastrpc_rpmsg_callback+0x3c/0xcc [fastrpc] ... Call trace: _raw_spin_lock_irqsave+0x34/0x8c (P) fastrpc_rpmsg_callback+0x3c/0xcc [fastrpc] qcom_glink_native_rx+0x538/0x6a4 qcom_glink_smem_intr+0x14/0x24 [qcom_glink_smem] The faulting address 0x178 corresponds to the lock variable inside struct fastrpc_channel_ctx, confirming that cctx is NULL when fastrpc_rpmsg_callback() attempts to take the spinlock. There are two issues here. First, dev_set_drvdata() is called before spin_lock_init() and idr_init(), leaving a window where the callback can retrieve a valid cctx pointer but operate on an uninitialized spinlock. Second, the rpmsg channel becomes live as soon as the driver is bound, so fastrpc_rpmsg_callback() can fire before dev_set_drvdata() is called at all, resulting in dev_get_drvdata() returning NULL. Fix both issues by moving all cctx initialization ahead of dev_set_drvdata() so the structure is fully initialized before it becomes visible to the callback, and add a NULL check in fastrpc_rpmsg_callback() as a guard against any remaining window. Fixes: f6f9279f2bf0 ("misc: fastrpc: Add Qualcomm fastrpc basic driver model") Cc: stable@vger.kernel.org Signed-off-by: Mukesh Ojha <mukesh.ojha@oss.qualcomm.com> Reviewed-by: Bjorn Andersson <andersson@kernel.org> Signed-off-by: Srinivas Kandagatla <srini@kernel.org> Link: https://patch.msgid.link/20260530204528.116920-4-srini@kernel.org Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> Signed-off-by: Sasha Levin <sashal@kernel.org> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-rw-r--r--drivers/misc/fastrpc.c5
1 files changed, 4 insertions, 1 deletions
diff --git a/drivers/misc/fastrpc.c b/drivers/misc/fastrpc.c
index 5bab8c457507..1f5a95d19d9f 100644
--- a/drivers/misc/fastrpc.c
+++ b/drivers/misc/fastrpc.c
@@ -1691,7 +1691,6 @@ static int fastrpc_rpmsg_probe(struct rpmsg_device *rpdev)
kref_init(&data->refcount);
- dev_set_drvdata(&rpdev->dev, data);
rdev->dma_mask = &data->dma_mask;
dma_set_mask_and_coherent(rdev, DMA_BIT_MASK(32));
INIT_LIST_HEAD(&data->users);
@@ -1699,6 +1698,7 @@ static int fastrpc_rpmsg_probe(struct rpmsg_device *rpdev)
idr_init(&data->ctx_idr);
data->domain_id = domain_id;
data->rpdev = rpdev;
+ dev_set_drvdata(&rpdev->dev, data);
return of_platform_populate(rdev->of_node, NULL, NULL, rdev);
}
@@ -1746,6 +1746,9 @@ static int fastrpc_rpmsg_callback(struct rpmsg_device *rpdev, void *data,
if (len < sizeof(*rsp))
return -EINVAL;
+ if (!cctx)
+ return -ENODEV;
+
ctxid = ((rsp->ctx & FASTRPC_CTXID_MASK) >> 4);
spin_lock_irqsave(&cctx->lock, flags);