From 10e46175347334ab2db19bf53595491d16651902 Mon Sep 17 00:00:00 2001 From: "J. Eric Ivancich" Date: Thu, 5 Jan 2023 13:57:37 -0500 Subject: [PATCH] rgw: fix FP error when calculating enteries per bi shard When calculating how many entries per shard to request during an ordered bucket listing, we divide by the number of bucket index shards. If this value is 0, then a floating point exception is generated, crashing the RGW. This addresses the proximate issue by detecting the situation and returning an error rather than crashing. Signed-off-by: J. Eric Ivancich (cherry picked from commit bd6ee7e78d857bff31b0bb23f0ee8d8737ffef8e) Conflicts: src/rgw/rgw_rados.cc (trivial: __func__ vs __PRETTY_FUNCTION__) --- src/rgw/rgw_rados.cc | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/src/rgw/rgw_rados.cc b/src/rgw/rgw_rados.cc index 958fe5d4538fa..2fbe0471d57b6 100644 --- a/src/rgw/rgw_rados.cc +++ b/src/rgw/rgw_rados.cc @@ -8643,9 +8643,16 @@ int RGWRados::cls_obj_set_bucket_tag_timeout(const DoutPrefixProvider *dpp, RGWB } +// returns 0 if there is an error in calculation uint32_t RGWRados::calc_ordered_bucket_list_per_shard(uint32_t num_entries, uint32_t num_shards) { + if (num_shards == 0) { + // we'll get a floating point exception since we divide by + // num_shards + return 0; + } + // We want to minimize the chances that when num_shards >> // num_entries that we return much fewer than num_entries to the // client. Given all the overhead of making a cls call to the osd, @@ -8723,6 +8730,13 @@ int RGWRados::cls_bucket_list_ordered(const DoutPrefixProvider *dpp, } const uint32_t shard_count = shard_oids.size(); + if (shard_count == 0) { + ldpp_dout(dpp, 0) << "ERROR: " << __func__ << + ": the bucket index shard count appears to be 0, " + "which is an illegal value" << dendl; + return -ERR_INVALID_BUCKET_STATE; + } + uint32_t num_entries_per_shard; if (expansion_factor == 0) { num_entries_per_shard = @@ -8737,6 +8751,13 @@ int RGWRados::cls_bucket_list_ordered(const DoutPrefixProvider *dpp, num_entries_per_shard = num_entries; } + if (num_entries_per_shard == 0) { + ldpp_dout(dpp, 0) << "ERROR: " << __func__ << + ": unable to calculate the number of entries to read from each " + "bucket index shard" << dendl; + return -ERR_INVALID_BUCKET_STATE; + } + ldpp_dout(dpp, 10) << __PRETTY_FUNCTION__ << ": request from each of " << shard_count << " shard(s) for " << num_entries_per_shard << " entries to get " << -- 2.39.5