- vusage = max(vusage, vtime - vdone);
-
- /* calculate hweight based usage ratio and record */
- if (vusage) {
- usage = DIV64_U64_ROUND_UP(vusage * hw_inuse,
- period_vtime);
- iocg->usage_idx = (iocg->usage_idx + 1) % NR_USAGE_SLOTS;
- iocg->usages[iocg->usage_idx] = usage;
+ usage_us = iocg->usage_delta_us;
+ if (waitqueue_active(&iocg->waitq) && time_before64(vtime, now.vnow))
+ usage_us += DIV64_U64_ROUND_UP(
+ cost_to_abs_cost(now.vnow - vtime, hw_inuse),
+ now.vrate);
+ if (vdone != vtime) {
+ u64 inflight_us = DIV64_U64_ROUND_UP(
+ cost_to_abs_cost(vtime - vdone, hw_inuse),
+ now.vrate);
+ usage_us = max(usage_us, inflight_us);
+ }
+
+ /* convert to hweight based usage ratio and record */
+ uidx = (iocg->usage_idx + 1) % NR_USAGE_SLOTS;
+
+ if (time_after64(vtime, now.vnow - ioc->margins.min)) {
+ iocg->usage_idx = uidx;
+ iocg->usages[uidx] = WEIGHT_ONE;
+ } else if (usage_us) {
+ u64 started_at, dur;
+
+ if (time_after64(iocg->activated_at, ioc->period_at))
+ started_at = iocg->activated_at;
+ else
+ started_at = ioc->period_at;
+
+ dur = max_t(u64, now.now - started_at, 1);
+ usage = clamp_t(u32,
+ DIV64_U64_ROUND_UP(usage_us * WEIGHT_ONE, dur),
+ 1, WEIGHT_ONE);
+
+ iocg->usage_idx = uidx;
+ iocg->usages[uidx] = usage;