[PATCH v2] libceph: Assign requests to homeless osd if calculated osd exceeds max_osd

Raphael Zimmer <[email protected]>
Newsgroups org.kernel.vger.ceph-devel
Message-ID <[email protected]>
A corrupted osdmap received from a Ceph monitor or OSD may contain
placement groups with osd indices that don't exist, i.e., that are
greater than max_osd or smaller than CEPH_HOMELESS_OSD (-1).
Subsequently, this may lead to calc_target() returning such an index as
target osd for a (linger) request. Because the osd_state, osd_weight,
and osd_addr arrays only contain max_osd entries (with indices 0 to
max_osd -1), this leads to out-of-bounds accesses when trying to read
values from these arrays.

This patch fixes the issue by adding a check to calc_target() assigning
the request to the homeless osd if the target osd index read from the
osdmap falls outside the valid osd index range.

Fixes: 63244fa123a7 ("libceph: introduce ceph_osd_request_target, calc_target()")
Signed-off-by: Raphael Zimmer <[email protected]>
---
 net/ceph/osd_client.c | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/net/ceph/osd_client.c b/net/ceph/osd_client.c
index a4d3cbfd27a3..3d13226a5d1f 100644
--- a/net/ceph/osd_client.c
+++ b/net/ceph/osd_client.c
@@ -1707,6 +1707,12 @@ static enum calc_target_result calc_target(struct ceph_osd_client *osdc,
 		}
 	}
 
+	if (t->osd != CEPH_HOMELESS_OSD && (u32)t->osd >= osdc->osdmap->max_osd) {
+		t->osd = CEPH_HOMELESS_OSD;
+		ct_res = CALC_TARGET_NEED_RESEND;
+		goto out;
+	}
+
 	if (unpaused || legacy_change || force_resend || split)
 		ct_res = CALC_TARGET_NEED_RESEND;
 	else
-- 
2.47.3
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.