[RFC PATCH v2 2/9] fs/resctrl: Avoid division by zero in the MBA software controller

From: Jinjie Ruan

Date: Thu Nov 12 2026 - 08:30:32 EST


The software controller raises the control while the target is above
the bandwidth expected after the next step, and it uses min_bw instead
of bw_gran. The two are equal on x86, but when MPAM's maximum control
has 8 or more bits, min_bw rounds to 0% while bw_gran is 1%. The estimate
then falls back to the current bandwidth, so the control steps up
whenever the target is above it and oscillates across the target.

With min_bw at 0% the control can also reach zero, and the estimate
then divides by zero in the MBM overflow worker.

Use bw_gran in the estimate, and step up without evaluating it when the
control is zero. Also require the target to be above the measured
bandwidth, so a zero target does not raise the control.

Signed-off-by: Jinjie Ruan <ruanjinjie@xxxxxxxxxx>
---
fs/resctrl/monitor.c | 9 ++++++---
1 file changed, 6 insertions(+), 3 deletions(-)

diff --git a/fs/resctrl/monitor.c b/fs/resctrl/monitor.c
index 75abbf90d090..f067329e92c6 100644
--- a/fs/resctrl/monitor.c
+++ b/fs/resctrl/monitor.c
@@ -673,6 +673,9 @@ static struct rdt_ctrl_domain *get_sc_ctrl_domain_from_cpu(int cpu,
* with 10% granularity steps, check whether moving to 40% would go past
* the limit by multiplying current bandwidth by "(30 + 10) / 30".
*
+ * A zero min_bw lets the control reach zero, where the ratio is
+ * undefined. Take the step up without evaluating it.
+ *
* Return: true when the control value changes, false otherwise.
*/
static bool mba_sc_next_ctrl_val(struct rdt_resource *r_mba, u32 cur_msr_val,
@@ -683,9 +686,9 @@ static bool mba_sc_next_ctrl_val(struct rdt_resource *r_mba, u32 cur_msr_val,
return true;
}

- if (cur_msr_val < MAX_MBA_BW &&
- user_bw > (cur_bw * (cur_msr_val + r_mba->membw.min_bw) /
- cur_msr_val)) {
+ if (cur_msr_val < MAX_MBA_BW && user_bw > cur_bw &&
+ (cur_msr_val == 0 ||
+ user_bw > (cur_bw * (cur_msr_val + r_mba->membw.bw_gran) / cur_msr_val))) {
*new_msr_val = cur_msr_val + r_mba->membw.bw_gran;
return true;
}
--
2.34.1