MOKSHA-2026-0088: Int64 Overflow in bytes_per_interval via VIF.qos_algorithm_params

Advisory IDMOKSHA-2026-0088
Semantic IDVQP-4
Published2026-04-24
CVSS 3.12.3 Low
CVSS 3.1 VectorAV:N/AC:L/PR:L/UI:N/S:U/C:N/I:L/A:N
CVSS 4.05.3 Medium
CVSS 4.0 VectorAV:N/AC:L/AT:N/PR:L/UI:N/VC:N/VI:L/VA:N/SC:N/SI:N/SA:N
XAPI ObjectVIF
XAPI Fieldqos_algorithm_params:kbps, qos_algorithm_params:timeslice_us
Entry Rolevm-admin
ResearcherJakob Wolffhechel, Moksha

Affected Products

VendorProductVersions
Citrix / Cloud Software GroupXenServer / Citrix Hypervisorall versions (shared XAPI codebase)
VatesXCP-ng8.3.0

Summary

A vm-admin in XAPI-based hypervisors (XenServer, XCP-ng) can set VIF.qos_algorithm_params:kbps and timeslice_us to values that cause Int64 overflow in the bytes_per_interval computation at device.ml:835-845. OCaml silently wraps on integer overflow, producing unexpected rate values. xenopsd's subsequent bounds check (0 < bytes_per_interval < 0xffffffff) catches most overflow results and silently drops the rate. In edge cases where the wrapped value falls within the valid range, the applied rate bears no relation to the configured kbps value. The VIF.qos_algorithm_params field has zero map_keys_roles entries.

Vulnerability Description

VIF.qos_algorithm_params is a Map(String, String) field defined at datamodel.ml:1666-1681 via the qos function with zero map_keys_roles entries and _R_VM_ADMIN as the class default write role.

The overflow occurs in the rate computation at device.ml:835-848:

let bytes_per_interval =
  ((kbytes_per_s ^* 1024L) ^* timeslice_us) ^/ 1000000L

Where ^* is Int64.mul and ^/ is Int64.div. OCaml's Int64.mul performs modular arithmetic on overflow - it silently wraps without raising an exception.

The data flow:

  1. vm-admin sets kbps=9223372036854775 and timeslice_us=1000000
  2. XAPI parses via Int64.of_string at xapi_xenops.ml:795 - no range check
  3. Rate tuple (9223372036854775L, 1000000L) forwarded to xenopsd
  4. xenopsd computes: (9223372036854775 * 1024 * 1000000) / 1000000
  5. The intermediate multiplication 9223372036854775 * 1024 overflows Int64
  6. The wrapped result is divided by 1000000
  7. If the final value is in (0, 0xffffffff), it is applied as the rate
  8. If outside that range, xenopsd silently drops it (observability gap)

In most overflow cases, xenopsd's bounds check rejects the result. The concern is the architectural pattern: user-controlled values flow into arithmetic operations without overflow guards, and OCaml's silent wrapping makes the behavior unpredictable.

Root Causes

  1. Missing overflow protection. The bytes_per_interval computation uses Int64.mul without checking for overflow. OCaml silently wraps on overflow.

  2. Missing write-time validation. XAPI accepts any Int64-parseable string for kbps without range checking. Values near Int64 bounds are stored without error.

  3. Missing RBAC protection. VIF.qos_algorithm_params has zero map_keys_roles entries. All keys are writable by vm-admin.

  4. set_qos_algorithm_params RBAC bypass. The set_qos_algorithm_params method replaces the entire map and bypasses map_keys_roles per-key checks.

Affected Systems

Directly Affected

Indirectly Affected

Exploitation Scenarios

Scenario Impact Pre-conditions Status
Overflow producing valid rate VIF rate-limited at unexpected value, unrelated to configured kbps vm-admin, VIF with ratelimit QoS Source-traced
Overflow producing out-of-range Rate silently dropped, VIF operates without rate limit vm-admin, VIF with ratelimit QoS Live-tested (rejection confirmed)
Observability gap XAPI DB shows configured kbps, xenstore has different or no rate vm-admin Live-tested

Chaining Analysis

Detection

Remediation

Short-Term Mitigations

Long-Term Fix

Add overflow-safe arithmetic. Check for overflow before the Int64.mul operations in device.ml:848. Reject values where the multiplication would overflow.

Add write-time range validation. Validate kbps at XAPI write time: enforce 0 < kbps <= 100000000 (100 Gbps maximum). Reject values that would cause overflow in the rate computation.

Return error on rejection. When xenopsd rejects a rate value, propagate an error to XAPI rather than silently dropping the rate.

Upstream patches exist. They are held privately pending coordinated disclosure.

Disclosure

Disclosure:

References

Credits

Discovered and reported by Jakob Wolffhechel, Moksha.

Jakob Wolffhechel · Moksha · Copenhagen
jakob@wolffhechel.dk · +45 3170 7337
Published 2026-04-24 08:00 CEST · cna.moksha.dk · shittrix.moksha.dk