mirror of https://gitee.com/openkylin/libvirt.git
cgroups: Redefine what "unlimited" means wrt memory limits
Since kernel 3.12 (commit 34ff8dc08956098563989d8599840b130be81252 in linux-stable.git in particular) the value for 'unlimited' in cgroup memory limits changed from LLONG_MAX to ULLONG_MAX. Due to rather unfortunate choice of our VIR_DOMAIN_MEMORY_PARAM_UNLIMITED constant (which we transfer as an unsigned long long in Kibibytes), we ended up with the situation described below (applies to x86_64): - 2^64-1 (ULLONG_MAX) -- "unlimited" in kernel = 3.12 - 2^63-1 (LLONG_MAX) -- "unlimited" in kernel < 3.12 - 2^63-1024 -- our PARAM_UNLIMITED scaled to Bytes - 2^53-1 -- our PARAM_UNLIMITED unscaled (in Kibibytes) This means that when any number within (2^63-1, 2^64-1] is read from memory cgroup, we are transferring that number instead of "unlimited". Unfortunately, changing VIR_DOMAIN_MEMORY_PARAM_UNLIMITED would break ABI compatibility and thus we have to resort to a different solution. With this patch every value greater than PARAM_UNLIMITED means "unlimited". Even though this may seem misleading, we are already in such unclear situation when running 3.12 kernel with memory limits set to 2^63. One example showing most of the problems at once (with kernel 3.12.2): # virsh memtune asdf --hard-limit 9007199254740991 --swap-hard-limit -1 # echo 12345678901234567890 >\ /sys/fs/cgroup/memory/machine/asdf.libvirt-qemu/memory.soft_limit_in_bytes # virsh memtune asdf hard_limit : 18014398509481983 soft_limit : 12056327051986884 swap_hard_limit: 18014398509481983 Signed-off-by: Martin Kletzander <mkletzan@redhat.com>
This commit is contained in:
parent
586b0ed818
commit
231656bbeb
|
@ -1957,12 +1957,19 @@ int
|
||||||
virCgroupGetMemoryHardLimit(virCgroupPtr group, unsigned long long *kb)
|
virCgroupGetMemoryHardLimit(virCgroupPtr group, unsigned long long *kb)
|
||||||
{
|
{
|
||||||
long long unsigned int limit_in_bytes;
|
long long unsigned int limit_in_bytes;
|
||||||
int ret;
|
int ret = -1;
|
||||||
ret = virCgroupGetValueU64(group,
|
|
||||||
VIR_CGROUP_CONTROLLER_MEMORY,
|
if (virCgroupGetValueU64(group,
|
||||||
"memory.limit_in_bytes", &limit_in_bytes);
|
VIR_CGROUP_CONTROLLER_MEMORY,
|
||||||
if (ret == 0)
|
"memory.limit_in_bytes", &limit_in_bytes) < 0)
|
||||||
*kb = limit_in_bytes >> 10;
|
goto cleanup;
|
||||||
|
|
||||||
|
*kb = limit_in_bytes >> 10;
|
||||||
|
if (*kb > VIR_DOMAIN_MEMORY_PARAM_UNLIMITED)
|
||||||
|
*kb = VIR_DOMAIN_MEMORY_PARAM_UNLIMITED;
|
||||||
|
|
||||||
|
ret = 0;
|
||||||
|
cleanup:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2012,12 +2019,19 @@ int
|
||||||
virCgroupGetMemorySoftLimit(virCgroupPtr group, unsigned long long *kb)
|
virCgroupGetMemorySoftLimit(virCgroupPtr group, unsigned long long *kb)
|
||||||
{
|
{
|
||||||
long long unsigned int limit_in_bytes;
|
long long unsigned int limit_in_bytes;
|
||||||
int ret;
|
int ret = -1;
|
||||||
ret = virCgroupGetValueU64(group,
|
|
||||||
VIR_CGROUP_CONTROLLER_MEMORY,
|
if (virCgroupGetValueU64(group,
|
||||||
"memory.soft_limit_in_bytes", &limit_in_bytes);
|
VIR_CGROUP_CONTROLLER_MEMORY,
|
||||||
if (ret == 0)
|
"memory.soft_limit_in_bytes", &limit_in_bytes) < 0)
|
||||||
*kb = limit_in_bytes >> 10;
|
goto cleanup;
|
||||||
|
|
||||||
|
*kb = limit_in_bytes >> 10;
|
||||||
|
if (*kb > VIR_DOMAIN_MEMORY_PARAM_UNLIMITED)
|
||||||
|
*kb = VIR_DOMAIN_MEMORY_PARAM_UNLIMITED;
|
||||||
|
|
||||||
|
ret = 0;
|
||||||
|
cleanup:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2067,12 +2081,19 @@ int
|
||||||
virCgroupGetMemSwapHardLimit(virCgroupPtr group, unsigned long long *kb)
|
virCgroupGetMemSwapHardLimit(virCgroupPtr group, unsigned long long *kb)
|
||||||
{
|
{
|
||||||
long long unsigned int limit_in_bytes;
|
long long unsigned int limit_in_bytes;
|
||||||
int ret;
|
int ret = -1;
|
||||||
ret = virCgroupGetValueU64(group,
|
|
||||||
VIR_CGROUP_CONTROLLER_MEMORY,
|
if (virCgroupGetValueU64(group,
|
||||||
"memory.memsw.limit_in_bytes", &limit_in_bytes);
|
VIR_CGROUP_CONTROLLER_MEMORY,
|
||||||
if (ret == 0)
|
"memory.memsw.limit_in_bytes", &limit_in_bytes) < 0)
|
||||||
*kb = limit_in_bytes >> 10;
|
goto cleanup;
|
||||||
|
|
||||||
|
*kb = limit_in_bytes >> 10;
|
||||||
|
if (*kb > VIR_DOMAIN_MEMORY_PARAM_UNLIMITED)
|
||||||
|
*kb = VIR_DOMAIN_MEMORY_PARAM_UNLIMITED;
|
||||||
|
|
||||||
|
ret = 0;
|
||||||
|
cleanup:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue