Skip to content
Merged
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions .github/workflows/integration_tests_validation.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -92,9 +92,9 @@ jobs:
run: sudo add-apt-repository -y ppa:criu/ppa
- name: Install requirements
run: sudo env PATH=$PATH just ci-prepare
- name: Install runc 1.3.1
- name: Install runc 1.3.2
run: |
wget -q https://github.com/opencontainers/runc/releases/download/v1.3.1/runc.amd64
wget -q https://github.com/opencontainers/runc/releases/download/v1.3.2/runc.amd64
sudo mv runc.amd64 /usr/bin/runc
sudo chmod 755 /usr/bin/runc
- name: Build
Expand Down
24 changes: 22 additions & 2 deletions crates/libcgroups/src/systemd/cpu.rs
Original file line number Diff line number Diff line change
Expand Up @@ -86,12 +86,32 @@ impl Cpu {
}
}

// Convert CPU shares (cgroup v1) into CPU weight (cgroup v2).
// cgroup v1 shares span [2, 262_144] with a default of 1_024.
// cgroup v2 weight spans [1, 10_000] with a default of 100.
// A shares value of 0 keeps the field unset.
// The quadratic fit matches runc's mapping and preserves the defaults.
pub fn convert_shares_to_cgroup2(shares: u64) -> u64 {
if shares == 0 {
return 0;
}

1 + ((shares.saturating_sub(2)) * 9999) / 262142
const MIN_SHARES: u64 = 2;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Having comments would make it even easier to understand.

const MAX_SHARES: u64 = 262_144;
const MAX_WEIGHT: u64 = 10_000;

if shares <= MIN_SHARES {
return 1;
}

if shares >= MAX_SHARES {
return MAX_WEIGHT;
}

let log_shares = (shares as f64).log2();
let exponent = (log_shares * log_shares + 125.0 * log_shares) / 612.0 - 7.0 / 34.0;

(10f64.powf(exponent)).ceil() as u64
}

#[cfg(test)]
Expand Down Expand Up @@ -120,7 +140,7 @@ mod tests {

let cpu_weight = &properties[CPU_WEIGHT];
let val = recast!(cpu_weight, Variant)?;
assert_eq!(val, Variant::U64(840));
assert_eq!(val, Variant::U64(1204));

Ok(())
}
Expand Down
2 changes: 1 addition & 1 deletion crates/libcgroups/src/systemd/unified.rs
Original file line number Diff line number Diff line change
Expand Up @@ -178,7 +178,7 @@ mod tests {
.collect();

let mut expected: HashMap<&str, Variant> = HashMap::new();
expected.insert(cpu::CPU_WEIGHT, Variant::U64(840));
expected.insert(cpu::CPU_WEIGHT, Variant::U64(1204));
expected.insert(cpuset::ALLOWED_CPUS, Variant::ArrayU64(vec![15u64]));
expected.insert(cpuset::ALLOWED_NODES, Variant::ArrayU64(vec![15u64]));
expected.insert(memory::MEMORY_MIN, Variant::U64(100000u64));
Expand Down
25 changes: 22 additions & 3 deletions crates/libcgroups/src/v2/cpu.rs
Original file line number Diff line number Diff line change
Expand Up @@ -133,13 +133,32 @@ impl Cpu {
Ok(())
}

// Convert CPU shares (cgroup v1) into CPU weight (cgroup v2).
// cgroup v1 shares span [2, 262_144] with a default of 1_024.
// cgroup v2 weight spans [1, 10_000] with a default of 100.
// A shares value of 0 keeps the field unset.
// The quadratic fit mirrors runc's mapping to keep extrema and defaults.
fn convert_shares_to_cgroup2(shares: u64) -> u64 {
if shares == 0 {
return 0;
}

let weight = 1 + ((shares.saturating_sub(2)) * 9999) / 262142;
weight.min(MAX_CPU_WEIGHT)
const MIN_SHARES: u64 = 2;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Having comments would make it even easier to understand.

const MAX_SHARES: u64 = 262_144;

if shares <= MIN_SHARES {
return 1;
}

if shares >= MAX_SHARES {
return MAX_CPU_WEIGHT;
}

let log_shares = (shares as f64).log2();
let exponent = (log_shares * log_shares + 125.0 * log_shares) / 612.0 - 7.0 / 34.0;
let weight = (10f64.powf(exponent)).ceil() as u64;

weight.clamp(1, MAX_CPU_WEIGHT)
}

fn is_realtime_requested(cpu: &LinuxCpu) -> bool {
Expand Down Expand Up @@ -190,7 +209,7 @@ mod tests {
// assert
let content = fs::read_to_string(weight)
.unwrap_or_else(|_| panic!("read {CGROUP_CPU_WEIGHT} file content"));
assert_eq!(content, 840.to_string());
assert_eq!(content, 1204.to_string());
}

#[test]
Expand Down
2 changes: 1 addition & 1 deletion tests/contest/contest/src/tests/cgroups/cpu/v2.rs
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@ fn test_cpu_idle_default() -> TestResult {
/// Tests if a cpu weight that is in the valid range [1, 10000] is successfully set
fn test_cpu_weight_valid_set() -> TestResult {
let cpu_weight = 22_000u64;
let converted_cpu_weight = 840u64;
let converted_cpu_weight = 1204u64;
let cpu = test_result!(
LinuxCpuBuilder::default()
.shares(cpu_weight)
Expand Down
Loading