| From d5ee2ff98322337951c56398e79d51815acbf955 Mon Sep 17 00:00:00 2001 |
| From: Manivannan Sadhasivam <manivannan.sadhasivam@oss.qualcomm.com> |
| Date: Thu, 9 Apr 2026 23:04:12 +0530 |
| Subject: net: qrtr: ns: Limit the maximum server registration per node |
| |
| From: Manivannan Sadhasivam <manivannan.sadhasivam@oss.qualcomm.com> |
| |
| commit d5ee2ff98322337951c56398e79d51815acbf955 upstream. |
| |
| Current code does no bound checking on the number of servers added per |
| node. A malicious client can flood NEW_SERVER messages and exhaust memory. |
| |
| Fix this issue by limiting the maximum number of server registrations to |
| 256 per node. If the NEW_SERVER message is received for an old port, then |
| don't restrict it as it will get replaced. While at it, also rate limit |
| the error messages in the failure path of qrtr_ns_worker(). |
| |
| Note that the limit of 256 is chosen based on the current platform |
| requirements. If requirement changes in the future, this limit can be |
| increased. |
| |
| Cc: stable@vger.kernel.org |
| Fixes: 0c2204a4ad71 ("net: qrtr: Migrate nameservice to kernel from userspace") |
| Reported-by: Yiming Qian <yimingqian591@gmail.com> |
| Reviewed-by: Simon Horman <horms@kernel.org> |
| Signed-off-by: Manivannan Sadhasivam <manivannan.sadhasivam@oss.qualcomm.com> |
| Link: https://patch.msgid.link/20260409-qrtr-fix-v3-1-00a8a5ff2b51@oss.qualcomm.com |
| Signed-off-by: Jakub Kicinski <kuba@kernel.org> |
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |
| --- |
| net/qrtr/ns.c | 26 +++++++++++++++++++++----- |
| 1 file changed, 21 insertions(+), 5 deletions(-) |
| |
| --- a/net/qrtr/ns.c |
| +++ b/net/qrtr/ns.c |
| @@ -68,8 +68,14 @@ struct qrtr_server { |
| struct qrtr_node { |
| unsigned int id; |
| struct xarray servers; |
| + u32 server_count; |
| }; |
| |
| +/* Max server limit is chosen based on the current platform requirements. If the |
| + * requirement changes in the future, this value can be increased. |
| + */ |
| +#define QRTR_NS_MAX_SERVERS 256 |
| + |
| static struct qrtr_node *node_get(unsigned int node_id) |
| { |
| struct qrtr_node *node; |
| @@ -230,6 +236,17 @@ static struct qrtr_server *server_add(un |
| if (!service || !port) |
| return NULL; |
| |
| + node = node_get(node_id); |
| + if (!node) |
| + return NULL; |
| + |
| + /* Make sure the new servers per port are capped at the maximum value */ |
| + old = xa_load(&node->servers, port); |
| + if (!old && node->server_count >= QRTR_NS_MAX_SERVERS) { |
| + pr_err_ratelimited("QRTR client node %u exceeds max server limit!\n", node_id); |
| + return NULL; |
| + } |
| + |
| srv = kzalloc_obj(*srv); |
| if (!srv) |
| return NULL; |
| @@ -239,10 +256,6 @@ static struct qrtr_server *server_add(un |
| srv->node = node_id; |
| srv->port = port; |
| |
| - node = node_get(node_id); |
| - if (!node) |
| - goto err; |
| - |
| /* Delete the old server on the same port */ |
| old = xa_store(&node->servers, port, srv, GFP_KERNEL); |
| if (old) { |
| @@ -253,6 +266,8 @@ static struct qrtr_server *server_add(un |
| } else { |
| kfree(old); |
| } |
| + } else { |
| + node->server_count++; |
| } |
| |
| trace_qrtr_ns_server_add(srv->service, srv->instance, |
| @@ -293,6 +308,7 @@ static int server_del(struct qrtr_node * |
| } |
| |
| kfree(srv); |
| + node->server_count--; |
| |
| return 0; |
| } |
| @@ -671,7 +687,7 @@ static void qrtr_ns_worker(struct work_s |
| } |
| |
| if (ret < 0) |
| - pr_err("failed while handling packet from %d:%d", |
| + pr_err_ratelimited("failed while handling packet from %d:%d", |
| sq.sq_node, sq.sq_port); |
| } |
| |