mirror of
https://github.com/systemd/systemd
synced 2024-09-16 06:43:18 +00:00
Merge pull request #18444 from anitazha/proprename
oom: parse properties with 1/10000 precision instead of 1/100
This commit is contained in:
commit
3d0112878f
|
@ -272,7 +272,7 @@ All cgroup/resource control settings are available for transient units
|
||||||
✓ IPAddressDeny=
|
✓ IPAddressDeny=
|
||||||
✓ ManagedOOMSwap=
|
✓ ManagedOOMSwap=
|
||||||
✓ ManagedOOMMemoryPressure=
|
✓ ManagedOOMMemoryPressure=
|
||||||
✓ ManagedOOMMemoryPressureLimitPercent=
|
✓ ManagedOOMMemoryPressureLimit=
|
||||||
```
|
```
|
||||||
|
|
||||||
## Process Killing Settings
|
## Process Killing Settings
|
||||||
|
|
|
@ -59,10 +59,10 @@
|
||||||
</varlistentry>
|
</varlistentry>
|
||||||
|
|
||||||
<varlistentry>
|
<varlistentry>
|
||||||
<term><varname>DefaultMemoryPressureLimitPercent=</varname></term>
|
<term><varname>DefaultMemoryPressureLimit=</varname></term>
|
||||||
|
|
||||||
<listitem><para>Sets the limit for memory pressure on the unit's cgroup before <command>systemd-oomd</command>
|
<listitem><para>Sets the limit for memory pressure on the unit's cgroup before <command>systemd-oomd</command>
|
||||||
will take action. A unit can override this value with <varname>ManagedOOMMemoryPressureLimitPercent=</varname>.
|
will take action. A unit can override this value with <varname>ManagedOOMMemoryPressureLimit=</varname>.
|
||||||
The memory pressure for this property represents the fraction of time in a 10 second window in which all tasks
|
The memory pressure for this property represents the fraction of time in a 10 second window in which all tasks
|
||||||
in the cgroup were delayed. For each monitored cgroup, if the memory pressure on that cgroup exceeds the
|
in the cgroup were delayed. For each monitored cgroup, if the memory pressure on that cgroup exceeds the
|
||||||
limit set for longer than the duration set by <varname>DefaultMemoryPressureDurationSec=</varname>,
|
limit set for longer than the duration set by <varname>DefaultMemoryPressureDurationSec=</varname>,
|
||||||
|
@ -78,7 +78,7 @@
|
||||||
|
|
||||||
<listitem><para>Sets the amount of time a unit's cgroup needs to have exceeded memory pressure limits before
|
<listitem><para>Sets the amount of time a unit's cgroup needs to have exceeded memory pressure limits before
|
||||||
<command>systemd-oomd</command> will take action. Memory pressure limits are defined by
|
<command>systemd-oomd</command> will take action. Memory pressure limits are defined by
|
||||||
<varname>DefaultMemoryPressureLimitPercent=</varname> and <varname>ManagedOOMMemoryPressureLimitPercent=</varname>.
|
<varname>DefaultMemoryPressureLimit=</varname> and <varname>ManagedOOMMemoryPressureLimit=</varname>.
|
||||||
Defaults to 30 seconds when this property is unset or set to 0.</para></listitem>
|
Defaults to 30 seconds when this property is unset or set to 0.</para></listitem>
|
||||||
</varlistentry>
|
</varlistentry>
|
||||||
|
|
||||||
|
|
|
@ -2449,7 +2449,7 @@ node /org/freedesktop/systemd1/unit/avahi_2ddaemon_2eservice {
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressure = '...';
|
readonly s ManagedOOMMemoryPressure = '...';
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressureLimitPercent = '...';
|
readonly u ManagedOOMMemoryPressureLimitPermyriad = ...;
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||||
readonly as Environment = ['...', ...];
|
readonly as Environment = ['...', ...];
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||||
|
@ -2972,7 +2972,7 @@ node /org/freedesktop/systemd1/unit/avahi_2ddaemon_2eservice {
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressure is not documented!-->
|
<!--property ManagedOOMMemoryPressure is not documented!-->
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressureLimitPercent is not documented!-->
|
<!--property ManagedOOMMemoryPressureLimitPermyriad is not documented!-->
|
||||||
|
|
||||||
<!--property EnvironmentFiles is not documented!-->
|
<!--property EnvironmentFiles is not documented!-->
|
||||||
|
|
||||||
|
@ -3536,7 +3536,7 @@ node /org/freedesktop/systemd1/unit/avahi_2ddaemon_2eservice {
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPercent"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPermyriad"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="Environment"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="Environment"/>
|
||||||
|
|
||||||
|
@ -4203,7 +4203,7 @@ node /org/freedesktop/systemd1/unit/avahi_2ddaemon_2esocket {
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressure = '...';
|
readonly s ManagedOOMMemoryPressure = '...';
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressureLimitPercent = '...';
|
readonly u ManagedOOMMemoryPressureLimitPermyriad = ...;
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||||
readonly as Environment = ['...', ...];
|
readonly as Environment = ['...', ...];
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||||
|
@ -4754,7 +4754,7 @@ node /org/freedesktop/systemd1/unit/avahi_2ddaemon_2esocket {
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressure is not documented!-->
|
<!--property ManagedOOMMemoryPressure is not documented!-->
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressureLimitPercent is not documented!-->
|
<!--property ManagedOOMMemoryPressureLimitPermyriad is not documented!-->
|
||||||
|
|
||||||
<!--property EnvironmentFiles is not documented!-->
|
<!--property EnvironmentFiles is not documented!-->
|
||||||
|
|
||||||
|
@ -5316,7 +5316,7 @@ node /org/freedesktop/systemd1/unit/avahi_2ddaemon_2esocket {
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPercent"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPermyriad"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="Environment"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="Environment"/>
|
||||||
|
|
||||||
|
@ -5896,7 +5896,7 @@ node /org/freedesktop/systemd1/unit/home_2emount {
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressure = '...';
|
readonly s ManagedOOMMemoryPressure = '...';
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressureLimitPercent = '...';
|
readonly u ManagedOOMMemoryPressureLimitPermyriad = ...;
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||||
readonly as Environment = ['...', ...];
|
readonly as Environment = ['...', ...];
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||||
|
@ -6375,7 +6375,7 @@ node /org/freedesktop/systemd1/unit/home_2emount {
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressure is not documented!-->
|
<!--property ManagedOOMMemoryPressure is not documented!-->
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressureLimitPercent is not documented!-->
|
<!--property ManagedOOMMemoryPressureLimitPermyriad is not documented!-->
|
||||||
|
|
||||||
<!--property EnvironmentFiles is not documented!-->
|
<!--property EnvironmentFiles is not documented!-->
|
||||||
|
|
||||||
|
@ -6855,7 +6855,7 @@ node /org/freedesktop/systemd1/unit/home_2emount {
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPercent"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPermyriad"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="Environment"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="Environment"/>
|
||||||
|
|
||||||
|
@ -7556,7 +7556,7 @@ node /org/freedesktop/systemd1/unit/dev_2dsda3_2eswap {
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressure = '...';
|
readonly s ManagedOOMMemoryPressure = '...';
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressureLimitPercent = '...';
|
readonly u ManagedOOMMemoryPressureLimitPermyriad = ...;
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||||
readonly as Environment = ['...', ...];
|
readonly as Environment = ['...', ...];
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||||
|
@ -8021,7 +8021,7 @@ node /org/freedesktop/systemd1/unit/dev_2dsda3_2eswap {
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressure is not documented!-->
|
<!--property ManagedOOMMemoryPressure is not documented!-->
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressureLimitPercent is not documented!-->
|
<!--property ManagedOOMMemoryPressureLimitPermyriad is not documented!-->
|
||||||
|
|
||||||
<!--property EnvironmentFiles is not documented!-->
|
<!--property EnvironmentFiles is not documented!-->
|
||||||
|
|
||||||
|
@ -8487,7 +8487,7 @@ node /org/freedesktop/systemd1/unit/dev_2dsda3_2eswap {
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPercent"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPermyriad"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="Environment"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="Environment"/>
|
||||||
|
|
||||||
|
@ -9041,7 +9041,7 @@ node /org/freedesktop/systemd1/unit/system_2eslice {
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressure = '...';
|
readonly s ManagedOOMMemoryPressure = '...';
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressureLimitPercent = '...';
|
readonly u ManagedOOMMemoryPressureLimitPermyriad = ...;
|
||||||
};
|
};
|
||||||
interface org.freedesktop.DBus.Peer { ... };
|
interface org.freedesktop.DBus.Peer { ... };
|
||||||
interface org.freedesktop.DBus.Introspectable { ... };
|
interface org.freedesktop.DBus.Introspectable { ... };
|
||||||
|
@ -9176,7 +9176,7 @@ node /org/freedesktop/systemd1/unit/system_2eslice {
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressure is not documented!-->
|
<!--property ManagedOOMMemoryPressure is not documented!-->
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressureLimitPercent is not documented!-->
|
<!--property ManagedOOMMemoryPressureLimitPermyriad is not documented!-->
|
||||||
|
|
||||||
<!--Autogenerated cross-references for systemd.directives, do not edit-->
|
<!--Autogenerated cross-references for systemd.directives, do not edit-->
|
||||||
|
|
||||||
|
@ -9316,7 +9316,7 @@ node /org/freedesktop/systemd1/unit/system_2eslice {
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPercent"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPermyriad"/>
|
||||||
|
|
||||||
<!--End of Autogenerated section-->
|
<!--End of Autogenerated section-->
|
||||||
|
|
||||||
|
@ -9476,7 +9476,7 @@ node /org/freedesktop/systemd1/unit/session_2d1_2escope {
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressure = '...';
|
readonly s ManagedOOMMemoryPressure = '...';
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("false")
|
||||||
readonly s ManagedOOMMemoryPressureLimitPercent = '...';
|
readonly u ManagedOOMMemoryPressureLimitPermyriad = ...;
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||||
readonly s KillMode = '...';
|
readonly s KillMode = '...';
|
||||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||||
|
@ -9627,7 +9627,7 @@ node /org/freedesktop/systemd1/unit/session_2d1_2escope {
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressure is not documented!-->
|
<!--property ManagedOOMMemoryPressure is not documented!-->
|
||||||
|
|
||||||
<!--property ManagedOOMMemoryPressureLimitPercent is not documented!-->
|
<!--property ManagedOOMMemoryPressureLimitPermyriad is not documented!-->
|
||||||
|
|
||||||
<!--property KillMode is not documented!-->
|
<!--property KillMode is not documented!-->
|
||||||
|
|
||||||
|
@ -9793,7 +9793,7 @@ node /org/freedesktop/systemd1/unit/session_2d1_2escope {
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressure"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPercent"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="ManagedOOMMemoryPressureLimitPermyriad"/>
|
||||||
|
|
||||||
<variablelist class="dbus-property" generated="True" extra-ref="KillMode"/>
|
<variablelist class="dbus-property" generated="True" extra-ref="KillMode"/>
|
||||||
|
|
||||||
|
|
|
@ -901,7 +901,7 @@ DeviceAllow=/dev/loop-control
|
||||||
</varlistentry>
|
</varlistentry>
|
||||||
|
|
||||||
<varlistentry>
|
<varlistentry>
|
||||||
<term><varname>ManagedOOMMemoryPressureLimitPercent=</varname></term>
|
<term><varname>ManagedOOMMemoryPressureLimit=</varname></term>
|
||||||
|
|
||||||
<listitem>
|
<listitem>
|
||||||
<para>Overrides the default memory pressure limit set by
|
<para>Overrides the default memory pressure limit set by
|
||||||
|
|
|
@ -627,11 +627,11 @@ int parse_fractional_part_u(const char **p, size_t digits, unsigned *res) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int parse_percent_unbounded(const char *p) {
|
static int parse_parts_value_whole(const char *p, const char *symbol) {
|
||||||
const char *pc, *n;
|
const char *pc, *n;
|
||||||
int r, v;
|
int r, v;
|
||||||
|
|
||||||
pc = endswith(p, "%");
|
pc = endswith(p, symbol);
|
||||||
if (!pc)
|
if (!pc)
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
|
|
||||||
|
@ -645,6 +645,74 @@ int parse_percent_unbounded(const char *p) {
|
||||||
return v;
|
return v;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int parse_parts_value_with_tenths_place(const char *p, const char *symbol) {
|
||||||
|
const char *pc, *dot, *n;
|
||||||
|
int r, q, v;
|
||||||
|
|
||||||
|
pc = endswith(p, symbol);
|
||||||
|
if (!pc)
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
dot = memchr(p, '.', pc - p);
|
||||||
|
if (dot) {
|
||||||
|
if (dot + 2 != pc)
|
||||||
|
return -EINVAL;
|
||||||
|
if (dot[1] < '0' || dot[1] > '9')
|
||||||
|
return -EINVAL;
|
||||||
|
q = dot[1] - '0';
|
||||||
|
n = strndupa(p, dot - p);
|
||||||
|
} else {
|
||||||
|
q = 0;
|
||||||
|
n = strndupa(p, pc - p);
|
||||||
|
}
|
||||||
|
r = safe_atoi(n, &v);
|
||||||
|
if (r < 0)
|
||||||
|
return r;
|
||||||
|
if (v < 0)
|
||||||
|
return -ERANGE;
|
||||||
|
if (v > (INT_MAX - q) / 10)
|
||||||
|
return -ERANGE;
|
||||||
|
|
||||||
|
v = v * 10 + q;
|
||||||
|
return v;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int parse_parts_value_with_hundredths_place(const char *p, const char *symbol) {
|
||||||
|
const char *pc, *dot, *n;
|
||||||
|
int r, q, v;
|
||||||
|
|
||||||
|
pc = endswith(p, symbol);
|
||||||
|
if (!pc)
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
dot = memchr(p, '.', pc - p);
|
||||||
|
if (dot) {
|
||||||
|
if (dot + 3 != pc)
|
||||||
|
return -EINVAL;
|
||||||
|
if (dot[1] < '0' || dot[1] > '9' || dot[2] < '0' || dot[2] > '9')
|
||||||
|
return -EINVAL;
|
||||||
|
q = (dot[1] - '0') * 10 + (dot[2] - '0');
|
||||||
|
n = strndupa(p, dot - p);
|
||||||
|
} else {
|
||||||
|
q = 0;
|
||||||
|
n = strndupa(p, pc - p);
|
||||||
|
}
|
||||||
|
r = safe_atoi(n, &v);
|
||||||
|
if (r < 0)
|
||||||
|
return r;
|
||||||
|
if (v < 0)
|
||||||
|
return -ERANGE;
|
||||||
|
if (v > (INT_MAX - q) / 100)
|
||||||
|
return -ERANGE;
|
||||||
|
|
||||||
|
v = v * 100 + q;
|
||||||
|
return v;
|
||||||
|
}
|
||||||
|
|
||||||
|
int parse_percent_unbounded(const char *p) {
|
||||||
|
return parse_parts_value_whole(p, "%");
|
||||||
|
}
|
||||||
|
|
||||||
int parse_percent(const char *p) {
|
int parse_percent(const char *p) {
|
||||||
int v;
|
int v;
|
||||||
|
|
||||||
|
@ -656,46 +724,13 @@ int parse_percent(const char *p) {
|
||||||
}
|
}
|
||||||
|
|
||||||
int parse_permille_unbounded(const char *p) {
|
int parse_permille_unbounded(const char *p) {
|
||||||
const char *pc, *pm, *dot, *n;
|
const char *pm;
|
||||||
int r, q, v;
|
|
||||||
|
|
||||||
pm = endswith(p, "‰");
|
pm = endswith(p, "‰");
|
||||||
if (pm) {
|
if (pm)
|
||||||
n = strndupa(p, pm - p);
|
return parse_parts_value_whole(p, "‰");
|
||||||
r = safe_atoi(n, &v);
|
|
||||||
if (r < 0)
|
|
||||||
return r;
|
|
||||||
if (v < 0)
|
|
||||||
return -ERANGE;
|
|
||||||
} else {
|
|
||||||
pc = endswith(p, "%");
|
|
||||||
if (!pc)
|
|
||||||
return -EINVAL;
|
|
||||||
|
|
||||||
dot = memchr(p, '.', pc - p);
|
return parse_parts_value_with_tenths_place(p, "%");
|
||||||
if (dot) {
|
|
||||||
if (dot + 2 != pc)
|
|
||||||
return -EINVAL;
|
|
||||||
if (dot[1] < '0' || dot[1] > '9')
|
|
||||||
return -EINVAL;
|
|
||||||
q = dot[1] - '0';
|
|
||||||
n = strndupa(p, dot - p);
|
|
||||||
} else {
|
|
||||||
q = 0;
|
|
||||||
n = strndupa(p, pc - p);
|
|
||||||
}
|
|
||||||
r = safe_atoi(n, &v);
|
|
||||||
if (r < 0)
|
|
||||||
return r;
|
|
||||||
if (v < 0)
|
|
||||||
return -ERANGE;
|
|
||||||
if (v > (INT_MAX - q) / 10)
|
|
||||||
return -ERANGE;
|
|
||||||
|
|
||||||
v = v * 10 + q;
|
|
||||||
}
|
|
||||||
|
|
||||||
return v;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int parse_permille(const char *p) {
|
int parse_permille(const char *p) {
|
||||||
|
@ -708,6 +743,30 @@ int parse_permille(const char *p) {
|
||||||
return v;
|
return v;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int parse_permyriad_unbounded(const char *p) {
|
||||||
|
const char *pm;
|
||||||
|
|
||||||
|
pm = endswith(p, "‱");
|
||||||
|
if (pm)
|
||||||
|
return parse_parts_value_whole(p, "‱");
|
||||||
|
|
||||||
|
pm = endswith(p, "‰");
|
||||||
|
if (pm)
|
||||||
|
return parse_parts_value_with_tenths_place(p, "‰");
|
||||||
|
|
||||||
|
return parse_parts_value_with_hundredths_place(p, "%");
|
||||||
|
}
|
||||||
|
|
||||||
|
int parse_permyriad(const char *p) {
|
||||||
|
int v;
|
||||||
|
|
||||||
|
v = parse_permyriad_unbounded(p);
|
||||||
|
if (v > 10000)
|
||||||
|
return -ERANGE;
|
||||||
|
|
||||||
|
return v;
|
||||||
|
}
|
||||||
|
|
||||||
int parse_nice(const char *p, int *ret) {
|
int parse_nice(const char *p, int *ret) {
|
||||||
int n, r;
|
int n, r;
|
||||||
|
|
||||||
|
|
|
@ -133,6 +133,9 @@ int parse_percent(const char *p);
|
||||||
int parse_permille_unbounded(const char *p);
|
int parse_permille_unbounded(const char *p);
|
||||||
int parse_permille(const char *p);
|
int parse_permille(const char *p);
|
||||||
|
|
||||||
|
int parse_permyriad_unbounded(const char *p);
|
||||||
|
int parse_permyriad(const char *p);
|
||||||
|
|
||||||
int parse_nice(const char *p, int *ret);
|
int parse_nice(const char *p, int *ret);
|
||||||
|
|
||||||
int parse_ip_port(const char *s, uint16_t *ret);
|
int parse_ip_port(const char *s, uint16_t *ret);
|
||||||
|
|
|
@ -417,7 +417,7 @@ void cgroup_context_dump(Unit *u, FILE* f, const char *prefix) {
|
||||||
"%sDelegate: %s\n"
|
"%sDelegate: %s\n"
|
||||||
"%sManagedOOMSwap: %s\n"
|
"%sManagedOOMSwap: %s\n"
|
||||||
"%sManagedOOMMemoryPressure: %s\n"
|
"%sManagedOOMMemoryPressure: %s\n"
|
||||||
"%sManagedOOMMemoryPressureLimitPercent: %d%%\n",
|
"%sManagedOOMMemoryPressureLimit: %" PRIu32 ".%02" PRIu32 "%%\n",
|
||||||
prefix, yes_no(c->cpu_accounting),
|
prefix, yes_no(c->cpu_accounting),
|
||||||
prefix, yes_no(c->io_accounting),
|
prefix, yes_no(c->io_accounting),
|
||||||
prefix, yes_no(c->blockio_accounting),
|
prefix, yes_no(c->blockio_accounting),
|
||||||
|
@ -450,7 +450,7 @@ void cgroup_context_dump(Unit *u, FILE* f, const char *prefix) {
|
||||||
prefix, yes_no(c->delegate),
|
prefix, yes_no(c->delegate),
|
||||||
prefix, managed_oom_mode_to_string(c->moom_swap),
|
prefix, managed_oom_mode_to_string(c->moom_swap),
|
||||||
prefix, managed_oom_mode_to_string(c->moom_mem_pressure),
|
prefix, managed_oom_mode_to_string(c->moom_mem_pressure),
|
||||||
prefix, c->moom_mem_pressure_limit);
|
prefix, c->moom_mem_pressure_limit_permyriad / 100, c->moom_mem_pressure_limit_permyriad % 100);
|
||||||
|
|
||||||
if (c->delegate) {
|
if (c->delegate) {
|
||||||
_cleanup_free_ char *t = NULL;
|
_cleanup_free_ char *t = NULL;
|
||||||
|
|
|
@ -163,7 +163,7 @@ struct CGroupContext {
|
||||||
/* Settings for systemd-oomd */
|
/* Settings for systemd-oomd */
|
||||||
ManagedOOMMode moom_swap;
|
ManagedOOMMode moom_swap;
|
||||||
ManagedOOMMode moom_mem_pressure;
|
ManagedOOMMode moom_mem_pressure;
|
||||||
int moom_mem_pressure_limit;
|
uint32_t moom_mem_pressure_limit_permyriad;
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Used when querying IP accounting data */
|
/* Used when querying IP accounting data */
|
||||||
|
|
|
@ -83,7 +83,7 @@ static int build_managed_oom_json_array_element(Unit *u, const char *property, J
|
||||||
JSON_BUILD_PAIR("mode", JSON_BUILD_STRING(mode)),
|
JSON_BUILD_PAIR("mode", JSON_BUILD_STRING(mode)),
|
||||||
JSON_BUILD_PAIR("path", JSON_BUILD_STRING(u->cgroup_path)),
|
JSON_BUILD_PAIR("path", JSON_BUILD_STRING(u->cgroup_path)),
|
||||||
JSON_BUILD_PAIR("property", JSON_BUILD_STRING(property)),
|
JSON_BUILD_PAIR("property", JSON_BUILD_STRING(property)),
|
||||||
JSON_BUILD_PAIR_CONDITION(use_limit, "limit", JSON_BUILD_UNSIGNED(c->moom_mem_pressure_limit))));
|
JSON_BUILD_PAIR_CONDITION(use_limit, "limit", JSON_BUILD_UNSIGNED(c->moom_mem_pressure_limit_permyriad))));
|
||||||
}
|
}
|
||||||
|
|
||||||
int manager_varlink_send_managed_oom_update(Unit *u) {
|
int manager_varlink_send_managed_oom_update(Unit *u) {
|
||||||
|
|
|
@ -394,7 +394,7 @@ const sd_bus_vtable bus_cgroup_vtable[] = {
|
||||||
SD_BUS_PROPERTY("DisableControllers", "as", property_get_cgroup_mask, offsetof(CGroupContext, disable_controllers), 0),
|
SD_BUS_PROPERTY("DisableControllers", "as", property_get_cgroup_mask, offsetof(CGroupContext, disable_controllers), 0),
|
||||||
SD_BUS_PROPERTY("ManagedOOMSwap", "s", property_get_managed_oom_mode, offsetof(CGroupContext, moom_swap), 0),
|
SD_BUS_PROPERTY("ManagedOOMSwap", "s", property_get_managed_oom_mode, offsetof(CGroupContext, moom_swap), 0),
|
||||||
SD_BUS_PROPERTY("ManagedOOMMemoryPressure", "s", property_get_managed_oom_mode, offsetof(CGroupContext, moom_mem_pressure), 0),
|
SD_BUS_PROPERTY("ManagedOOMMemoryPressure", "s", property_get_managed_oom_mode, offsetof(CGroupContext, moom_mem_pressure), 0),
|
||||||
SD_BUS_PROPERTY("ManagedOOMMemoryPressureLimitPercent", "s", bus_property_get_percent, offsetof(CGroupContext, moom_mem_pressure_limit), 0),
|
SD_BUS_PROPERTY("ManagedOOMMemoryPressureLimitPermyriad", "u", NULL, offsetof(CGroupContext, moom_mem_pressure_limit_permyriad), 0),
|
||||||
SD_BUS_VTABLE_END
|
SD_BUS_VTABLE_END
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -1696,14 +1696,24 @@ int bus_cgroup_set_property(
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (streq(name, "ManagedOOMMemoryPressureLimitPercent")) {
|
if (streq(name, "ManagedOOMMemoryPressureLimitPermyriad")) {
|
||||||
|
uint32_t v;
|
||||||
|
|
||||||
if (!UNIT_VTABLE(u)->can_set_managed_oom)
|
if (!UNIT_VTABLE(u)->can_set_managed_oom)
|
||||||
return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Cannot set %s for this unit type", name);
|
return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Cannot set %s for this unit type", name);
|
||||||
|
|
||||||
r = bus_set_transient_percent(u, name, &c->moom_mem_pressure_limit, message, flags, error);
|
r = sd_bus_message_read(message, "u", &v);
|
||||||
if (r < 0)
|
if (r < 0)
|
||||||
return r;
|
return r;
|
||||||
|
|
||||||
|
if (v > 10000)
|
||||||
|
return -ERANGE;
|
||||||
|
|
||||||
|
if (!UNIT_WRITE_FLAGS_NOOP(flags)) {
|
||||||
|
c->moom_mem_pressure_limit_permyriad = v;
|
||||||
|
unit_write_settingf(u, flags, name, "ManagedOOMMemoryPressureLimit=%" PRIu32 ".%02" PRIu32 "%%", v / 100, v % 100);
|
||||||
|
}
|
||||||
|
|
||||||
if (c->moom_mem_pressure == MANAGED_OOM_KILL)
|
if (c->moom_mem_pressure == MANAGED_OOM_KILL)
|
||||||
(void) manager_varlink_send_managed_oom_update(u);
|
(void) manager_varlink_send_managed_oom_update(u);
|
||||||
|
|
||||||
|
|
|
@ -93,35 +93,6 @@ int bus_set_transient_bool(
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
int bus_set_transient_percent(
|
|
||||||
Unit *u,
|
|
||||||
const char *name,
|
|
||||||
int *p,
|
|
||||||
sd_bus_message *message,
|
|
||||||
UnitWriteFlags flags,
|
|
||||||
sd_bus_error *error) {
|
|
||||||
|
|
||||||
const char *v;
|
|
||||||
int r;
|
|
||||||
|
|
||||||
assert(p);
|
|
||||||
|
|
||||||
r = sd_bus_message_read(message, "s", &v);
|
|
||||||
if (r < 0)
|
|
||||||
return r;
|
|
||||||
|
|
||||||
r = parse_percent(v);
|
|
||||||
if (r < 0)
|
|
||||||
return r;
|
|
||||||
|
|
||||||
if (!UNIT_WRITE_FLAGS_NOOP(flags)) {
|
|
||||||
*p = r;
|
|
||||||
unit_write_settingf(u, flags, name, "%s=%d%%", name, r);
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
int bus_set_transient_usec_internal(
|
int bus_set_transient_usec_internal(
|
||||||
Unit *u,
|
Unit *u,
|
||||||
const char *name,
|
const char *name,
|
||||||
|
|
|
@ -241,7 +241,6 @@ int bus_set_transient_user_relaxed(Unit *u, const char *name, char **p, sd_bus_m
|
||||||
int bus_set_transient_path(Unit *u, const char *name, char **p, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error);
|
int bus_set_transient_path(Unit *u, const char *name, char **p, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error);
|
||||||
int bus_set_transient_string(Unit *u, const char *name, char **p, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error);
|
int bus_set_transient_string(Unit *u, const char *name, char **p, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error);
|
||||||
int bus_set_transient_bool(Unit *u, const char *name, bool *p, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error);
|
int bus_set_transient_bool(Unit *u, const char *name, bool *p, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error);
|
||||||
int bus_set_transient_percent(Unit *u, const char *name, int *p, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error);
|
|
||||||
int bus_set_transient_usec_internal(Unit *u, const char *name, usec_t *p, bool fix_0, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error);
|
int bus_set_transient_usec_internal(Unit *u, const char *name, usec_t *p, bool fix_0, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error);
|
||||||
static inline int bus_set_transient_usec(Unit *u, const char *name, usec_t *p, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error) {
|
static inline int bus_set_transient_usec(Unit *u, const char *name, usec_t *p, sd_bus_message *message, UnitWriteFlags flags, sd_bus_error *error) {
|
||||||
return bus_set_transient_usec_internal(u, name, p, false, message, flags, error);
|
return bus_set_transient_usec_internal(u, name, p, false, message, flags, error);
|
||||||
|
|
|
@ -229,7 +229,7 @@ $1.IPIngressFilterPath, config_parse_ip_filter_bpf_progs,
|
||||||
$1.IPEgressFilterPath, config_parse_ip_filter_bpf_progs, 0, offsetof($1, cgroup_context.ip_filters_egress)
|
$1.IPEgressFilterPath, config_parse_ip_filter_bpf_progs, 0, offsetof($1, cgroup_context.ip_filters_egress)
|
||||||
$1.ManagedOOMSwap, config_parse_managed_oom_mode, 0, offsetof($1, cgroup_context.moom_swap)
|
$1.ManagedOOMSwap, config_parse_managed_oom_mode, 0, offsetof($1, cgroup_context.moom_swap)
|
||||||
$1.ManagedOOMMemoryPressure, config_parse_managed_oom_mode, 0, offsetof($1, cgroup_context.moom_mem_pressure)
|
$1.ManagedOOMMemoryPressure, config_parse_managed_oom_mode, 0, offsetof($1, cgroup_context.moom_mem_pressure)
|
||||||
$1.ManagedOOMMemoryPressureLimitPercent, config_parse_managed_oom_mem_pressure_limit, 0, offsetof($1, cgroup_context.moom_mem_pressure_limit)
|
$1.ManagedOOMMemoryPressureLimit, config_parse_managed_oom_mem_pressure_limit, 0, offsetof($1, cgroup_context.moom_mem_pressure_limit_permyriad)
|
||||||
$1.NetClass, config_parse_warn_compat, DISABLED_LEGACY, 0'
|
$1.NetClass, config_parse_warn_compat, DISABLED_LEGACY, 0'
|
||||||
)m4_dnl
|
)m4_dnl
|
||||||
Unit.Description, config_parse_unit_string_printf, 0, offsetof(Unit, description)
|
Unit.Description, config_parse_unit_string_printf, 0, offsetof(Unit, description)
|
||||||
|
|
|
@ -3875,7 +3875,7 @@ int config_parse_managed_oom_mem_pressure_limit(
|
||||||
const char *rvalue,
|
const char *rvalue,
|
||||||
void *data,
|
void *data,
|
||||||
void *userdata) {
|
void *userdata) {
|
||||||
int *limit = data;
|
uint32_t *limit = data;
|
||||||
UnitType t;
|
UnitType t;
|
||||||
int r;
|
int r;
|
||||||
|
|
||||||
|
@ -3890,9 +3890,9 @@ int config_parse_managed_oom_mem_pressure_limit(
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
r = parse_percent(rvalue);
|
r = parse_permyriad(rvalue);
|
||||||
if (r < 0) {
|
if (r < 0) {
|
||||||
log_syntax(unit, LOG_WARNING, filename, line, r, "Failed to parse limit percent value, ignoring: %s", rvalue);
|
log_syntax(unit, LOG_WARNING, filename, line, r, "Failed to parse memory pressure limit value, ignoring: %s", rvalue);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -100,10 +100,10 @@ static int process_managed_oom_reply(
|
||||||
limit = m->default_mem_pressure_limit;
|
limit = m->default_mem_pressure_limit;
|
||||||
|
|
||||||
if (streq(reply.property, "ManagedOOMMemoryPressure")) {
|
if (streq(reply.property, "ManagedOOMMemoryPressure")) {
|
||||||
if (reply.limit > 100)
|
if (reply.limit > 10000)
|
||||||
continue;
|
continue;
|
||||||
else if (reply.limit != 0) {
|
else if (reply.limit != 0) {
|
||||||
ret = store_loadavg_fixed_point((unsigned long) reply.limit, 0, &limit);
|
ret = store_loadavg_fixed_point((unsigned long) reply.limit / 100, (unsigned long) reply.limit % 100, &limit);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -478,8 +478,8 @@ static int manager_connect_bus(Manager *m) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int manager_start(Manager *m, bool dry_run, int swap_used_limit, int mem_pressure_limit, usec_t mem_pressure_usec) {
|
int manager_start(Manager *m, bool dry_run, int swap_used_limit, int mem_pressure_limit_permyriad, usec_t mem_pressure_usec) {
|
||||||
unsigned long l;
|
unsigned long l, f;
|
||||||
int r;
|
int r;
|
||||||
|
|
||||||
assert(m);
|
assert(m);
|
||||||
|
@ -489,8 +489,16 @@ int manager_start(Manager *m, bool dry_run, int swap_used_limit, int mem_pressur
|
||||||
m->swap_used_limit = swap_used_limit != -1 ? swap_used_limit : DEFAULT_SWAP_USED_LIMIT;
|
m->swap_used_limit = swap_used_limit != -1 ? swap_used_limit : DEFAULT_SWAP_USED_LIMIT;
|
||||||
assert(m->swap_used_limit <= 100);
|
assert(m->swap_used_limit <= 100);
|
||||||
|
|
||||||
l = mem_pressure_limit != -1 ? mem_pressure_limit : DEFAULT_MEM_PRESSURE_LIMIT;
|
if (mem_pressure_limit_permyriad != -1) {
|
||||||
r = store_loadavg_fixed_point(l, 0, &m->default_mem_pressure_limit);
|
assert(mem_pressure_limit_permyriad <= 10000);
|
||||||
|
|
||||||
|
l = mem_pressure_limit_permyriad / 100;
|
||||||
|
f = mem_pressure_limit_permyriad % 100;
|
||||||
|
} else {
|
||||||
|
l = DEFAULT_MEM_PRESSURE_LIMIT_PERCENT;
|
||||||
|
f = 0;
|
||||||
|
}
|
||||||
|
r = store_loadavg_fixed_point(l, f, &m->default_mem_pressure_limit);
|
||||||
if (r < 0)
|
if (r < 0)
|
||||||
return r;
|
return r;
|
||||||
|
|
||||||
|
@ -530,12 +538,12 @@ int manager_get_dump_string(Manager *m, char **ret) {
|
||||||
fprintf(f,
|
fprintf(f,
|
||||||
"Dry Run: %s\n"
|
"Dry Run: %s\n"
|
||||||
"Swap Used Limit: %u%%\n"
|
"Swap Used Limit: %u%%\n"
|
||||||
"Default Memory Pressure Limit: %lu%%\n"
|
"Default Memory Pressure Limit: %lu.%02lu%%\n"
|
||||||
"Default Memory Pressure Duration: %s\n"
|
"Default Memory Pressure Duration: %s\n"
|
||||||
"System Context:\n",
|
"System Context:\n",
|
||||||
yes_no(m->dry_run),
|
yes_no(m->dry_run),
|
||||||
m->swap_used_limit,
|
m->swap_used_limit,
|
||||||
LOAD_INT(m->default_mem_pressure_limit),
|
LOAD_INT(m->default_mem_pressure_limit), LOAD_FRAC(m->default_mem_pressure_limit),
|
||||||
format_timespan(buf, sizeof(buf), m->default_mem_pressure_duration_usec, USEC_PER_SEC));
|
format_timespan(buf, sizeof(buf), m->default_mem_pressure_duration_usec, USEC_PER_SEC));
|
||||||
oomd_dump_system_context(&m->system_context, f, "\t");
|
oomd_dump_system_context(&m->system_context, f, "\t");
|
||||||
|
|
||||||
|
|
|
@ -17,7 +17,7 @@
|
||||||
* Generally 60 or higher might be acceptable for something like system.slice with no memory.high set; processes in
|
* Generally 60 or higher might be acceptable for something like system.slice with no memory.high set; processes in
|
||||||
* system.slice are assumed to be less latency sensitive. */
|
* system.slice are assumed to be less latency sensitive. */
|
||||||
#define DEFAULT_MEM_PRESSURE_DURATION_USEC (30 * USEC_PER_SEC)
|
#define DEFAULT_MEM_PRESSURE_DURATION_USEC (30 * USEC_PER_SEC)
|
||||||
#define DEFAULT_MEM_PRESSURE_LIMIT 60
|
#define DEFAULT_MEM_PRESSURE_LIMIT_PERCENT 60
|
||||||
#define DEFAULT_SWAP_USED_LIMIT 90
|
#define DEFAULT_SWAP_USED_LIMIT 90
|
||||||
|
|
||||||
#define RECLAIM_DURATION_USEC (30 * USEC_PER_SEC)
|
#define RECLAIM_DURATION_USEC (30 * USEC_PER_SEC)
|
||||||
|
@ -56,7 +56,7 @@ DEFINE_TRIVIAL_CLEANUP_FUNC(Manager*, manager_free);
|
||||||
|
|
||||||
int manager_new(Manager **ret);
|
int manager_new(Manager **ret);
|
||||||
|
|
||||||
int manager_start(Manager *m, bool dry_run, int swap_used_limit, int mem_pressure_limit, usec_t mem_pressure_usec);
|
int manager_start(Manager *m, bool dry_run, int swap_used_limit, int mem_pressure_limit_permyriad, usec_t mem_pressure_usec);
|
||||||
|
|
||||||
int manager_get_dump_string(Manager *m, char **ret);
|
int manager_get_dump_string(Manager *m, char **ret);
|
||||||
|
|
||||||
|
|
|
@ -415,11 +415,11 @@ void oomd_dump_memory_pressure_cgroup_context(const OomdCGroupContext *ctx, FILE
|
||||||
|
|
||||||
fprintf(f,
|
fprintf(f,
|
||||||
"%sPath: %s\n"
|
"%sPath: %s\n"
|
||||||
"%s\tMemory Pressure Limit: %lu%%\n"
|
"%s\tMemory Pressure Limit: %lu.%02lu%%\n"
|
||||||
"%s\tPressure: Avg10: %lu.%02lu Avg60: %lu.%02lu Avg300: %lu.%02lu Total: %s\n"
|
"%s\tPressure: Avg10: %lu.%02lu Avg60: %lu.%02lu Avg300: %lu.%02lu Total: %s\n"
|
||||||
"%s\tCurrent Memory Usage: %s\n",
|
"%s\tCurrent Memory Usage: %s\n",
|
||||||
strempty(prefix), ctx->path,
|
strempty(prefix), ctx->path,
|
||||||
strempty(prefix), LOAD_INT(ctx->mem_pressure_limit),
|
strempty(prefix), LOAD_INT(ctx->mem_pressure_limit), LOAD_FRAC(ctx->mem_pressure_limit),
|
||||||
strempty(prefix),
|
strempty(prefix),
|
||||||
LOAD_INT(ctx->memory_pressure.avg10), LOAD_FRAC(ctx->memory_pressure.avg10),
|
LOAD_INT(ctx->memory_pressure.avg10), LOAD_FRAC(ctx->memory_pressure.avg10),
|
||||||
LOAD_INT(ctx->memory_pressure.avg60), LOAD_FRAC(ctx->memory_pressure.avg60),
|
LOAD_INT(ctx->memory_pressure.avg60), LOAD_FRAC(ctx->memory_pressure.avg60),
|
||||||
|
|
|
@ -18,14 +18,14 @@
|
||||||
|
|
||||||
static bool arg_dry_run = false;
|
static bool arg_dry_run = false;
|
||||||
static int arg_swap_used_limit = -1;
|
static int arg_swap_used_limit = -1;
|
||||||
static int arg_mem_pressure_limit = -1;
|
static int arg_mem_pressure_limit_permyriad = -1;
|
||||||
static usec_t arg_mem_pressure_usec = 0;
|
static usec_t arg_mem_pressure_usec = 0;
|
||||||
|
|
||||||
static int parse_config(void) {
|
static int parse_config(void) {
|
||||||
static const ConfigTableItem items[] = {
|
static const ConfigTableItem items[] = {
|
||||||
{ "OOM", "SwapUsedLimitPercent", config_parse_percent, 0, &arg_swap_used_limit },
|
{ "OOM", "SwapUsedLimitPercent", config_parse_percent, 0, &arg_swap_used_limit },
|
||||||
{ "OOM", "DefaultMemoryPressureLimitPercent", config_parse_percent, 0, &arg_mem_pressure_limit },
|
{ "OOM", "DefaultMemoryPressureLimit", config_parse_permyriad, 0, &arg_mem_pressure_limit_permyriad },
|
||||||
{ "OOM", "DefaultMemoryPressureDurationSec", config_parse_sec, 0, &arg_mem_pressure_usec },
|
{ "OOM", "DefaultMemoryPressureDurationSec", config_parse_sec, 0, &arg_mem_pressure_usec },
|
||||||
{}
|
{}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -159,7 +159,7 @@ static int run(int argc, char *argv[]) {
|
||||||
if (r < 0)
|
if (r < 0)
|
||||||
return log_error_errno(r, "Failed to create manager: %m");
|
return log_error_errno(r, "Failed to create manager: %m");
|
||||||
|
|
||||||
r = manager_start(m, arg_dry_run, arg_swap_used_limit, arg_mem_pressure_limit, arg_mem_pressure_usec);
|
r = manager_start(m, arg_dry_run, arg_swap_used_limit, arg_mem_pressure_limit_permyriad, arg_mem_pressure_usec);
|
||||||
if (r < 0)
|
if (r < 0)
|
||||||
return log_error_errno(r, "Failed to start up daemon: %m");
|
return log_error_errno(r, "Failed to start up daemon: %m");
|
||||||
|
|
||||||
|
|
|
@ -13,5 +13,5 @@
|
||||||
|
|
||||||
[OOM]
|
[OOM]
|
||||||
#SwapUsedLimitPercent=90%
|
#SwapUsedLimitPercent=90%
|
||||||
#DefaultMemoryPressureLimitPercent=60%
|
#DefaultMemoryPressureLimit=60%
|
||||||
#DefaultMemoryPressureDurationSec=30s
|
#DefaultMemoryPressureDurationSec=30s
|
||||||
|
|
|
@ -55,23 +55,6 @@ int bus_property_get_id128(
|
||||||
return sd_bus_message_append_array(reply, 'y', id->bytes, 16);
|
return sd_bus_message_append_array(reply, 'y', id->bytes, 16);
|
||||||
}
|
}
|
||||||
|
|
||||||
int bus_property_get_percent(
|
|
||||||
sd_bus *bus,
|
|
||||||
const char *path,
|
|
||||||
const char *interface,
|
|
||||||
const char *property,
|
|
||||||
sd_bus_message *reply,
|
|
||||||
void *userdata,
|
|
||||||
sd_bus_error *error) {
|
|
||||||
|
|
||||||
char pstr[DECIMAL_STR_MAX(int) + 2];
|
|
||||||
int p = *(int*) userdata;
|
|
||||||
|
|
||||||
xsprintf(pstr, "%d%%", p);
|
|
||||||
|
|
||||||
return sd_bus_message_append_basic(reply, 's', pstr);
|
|
||||||
}
|
|
||||||
|
|
||||||
#if __SIZEOF_SIZE_T__ != 8
|
#if __SIZEOF_SIZE_T__ != 8
|
||||||
int bus_property_get_size(
|
int bus_property_get_size(
|
||||||
sd_bus *bus,
|
sd_bus *bus,
|
||||||
|
|
|
@ -8,7 +8,6 @@
|
||||||
int bus_property_get_bool(sd_bus *bus, const char *path, const char *interface, const char *property, sd_bus_message *reply, void *userdata, sd_bus_error *error);
|
int bus_property_get_bool(sd_bus *bus, const char *path, const char *interface, const char *property, sd_bus_message *reply, void *userdata, sd_bus_error *error);
|
||||||
int bus_property_set_bool(sd_bus *bus, const char *path, const char *interface, const char *property, sd_bus_message *value, void *userdata, sd_bus_error *error);
|
int bus_property_set_bool(sd_bus *bus, const char *path, const char *interface, const char *property, sd_bus_message *value, void *userdata, sd_bus_error *error);
|
||||||
int bus_property_get_id128(sd_bus *bus, const char *path, const char *interface, const char *property, sd_bus_message *reply, void *userdata, sd_bus_error *error);
|
int bus_property_get_id128(sd_bus *bus, const char *path, const char *interface, const char *property, sd_bus_message *reply, void *userdata, sd_bus_error *error);
|
||||||
int bus_property_get_percent(sd_bus *bus, const char *path, const char *interface, const char *property, sd_bus_message *reply, void *userdata, sd_bus_error *error);
|
|
||||||
|
|
||||||
#define bus_property_get_usec ((sd_bus_property_get_t) NULL)
|
#define bus_property_get_usec ((sd_bus_property_get_t) NULL)
|
||||||
#define bus_property_set_usec ((sd_bus_property_set_t) NULL)
|
#define bus_property_set_usec ((sd_bus_property_set_t) NULL)
|
||||||
|
|
|
@ -435,10 +435,25 @@ static int bus_append_cgroup_property(sd_bus_message *m, const char *field, cons
|
||||||
if (STR_IN_SET(field, "DevicePolicy",
|
if (STR_IN_SET(field, "DevicePolicy",
|
||||||
"Slice",
|
"Slice",
|
||||||
"ManagedOOMSwap",
|
"ManagedOOMSwap",
|
||||||
"ManagedOOMMemoryPressure",
|
"ManagedOOMMemoryPressure"))
|
||||||
"ManagedOOMMemoryPressureLimitPercent"))
|
|
||||||
return bus_append_string(m, field, eq);
|
return bus_append_string(m, field, eq);
|
||||||
|
|
||||||
|
if (STR_IN_SET(field, "ManagedOOMMemoryPressureLimit")) {
|
||||||
|
char *n;
|
||||||
|
|
||||||
|
r = parse_permyriad(eq);
|
||||||
|
if (r < 0)
|
||||||
|
return log_error_errno(r, "Failed to parse %s value: %s", field, eq);
|
||||||
|
|
||||||
|
n = strjoina(field, "Permyriad");
|
||||||
|
|
||||||
|
r = sd_bus_message_append(m, "(sv)", n, "u", (uint32_t) r);
|
||||||
|
if (r < 0)
|
||||||
|
return bus_log_create_error(r);
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
if (STR_IN_SET(field, "CPUAccounting",
|
if (STR_IN_SET(field, "CPUAccounting",
|
||||||
"MemoryAccounting",
|
"MemoryAccounting",
|
||||||
"IOAccounting",
|
"IOAccounting",
|
||||||
|
|
|
@ -1356,3 +1356,4 @@ int config_parse_hwaddrs(
|
||||||
}
|
}
|
||||||
|
|
||||||
DEFINE_CONFIG_PARSE(config_parse_percent, parse_percent, "Failed to parse percent value");
|
DEFINE_CONFIG_PARSE(config_parse_percent, parse_percent, "Failed to parse percent value");
|
||||||
|
DEFINE_CONFIG_PARSE(config_parse_permyriad, parse_permyriad, "Failed to parse permyriad value");
|
||||||
|
|
|
@ -150,6 +150,7 @@ CONFIG_PARSER_PROTOTYPE(config_parse_vlanprotocol);
|
||||||
CONFIG_PARSER_PROTOTYPE(config_parse_hwaddr);
|
CONFIG_PARSER_PROTOTYPE(config_parse_hwaddr);
|
||||||
CONFIG_PARSER_PROTOTYPE(config_parse_hwaddrs);
|
CONFIG_PARSER_PROTOTYPE(config_parse_hwaddrs);
|
||||||
CONFIG_PARSER_PROTOTYPE(config_parse_percent);
|
CONFIG_PARSER_PROTOTYPE(config_parse_percent);
|
||||||
|
CONFIG_PARSER_PROTOTYPE(config_parse_permyriad);
|
||||||
|
|
||||||
typedef enum Disabled {
|
typedef enum Disabled {
|
||||||
DISABLED_CONFIGURATION,
|
DISABLED_CONFIGURATION,
|
||||||
|
|
|
@ -790,6 +790,72 @@ static void test_parse_permille_unbounded(void) {
|
||||||
assert_se(parse_permille_unbounded("429496729.6%") == -ERANGE);
|
assert_se(parse_permille_unbounded("429496729.6%") == -ERANGE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void test_parse_permyriad(void) {
|
||||||
|
assert_se(parse_permyriad("") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("foo") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("0") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("50") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("100") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("-1") == -EINVAL);
|
||||||
|
|
||||||
|
assert_se(parse_permyriad("0‱") == 0);
|
||||||
|
assert_se(parse_permyriad("555‱") == 555);
|
||||||
|
assert_se(parse_permyriad("1000‱") == 1000);
|
||||||
|
assert_se(parse_permyriad("-7‱") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad("10007‱") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad("‱") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("‱‱") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("‱1") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("1‱‱") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("3.2‱") == -EINVAL);
|
||||||
|
|
||||||
|
assert_se(parse_permyriad("0‰") == 0);
|
||||||
|
assert_se(parse_permyriad("555.5‰") == 5555);
|
||||||
|
assert_se(parse_permyriad("1000.0‰") == 10000);
|
||||||
|
assert_se(parse_permyriad("-7‰") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad("1007‰") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad("‰") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("‰‰") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("‰1") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("1‰‰") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("3.22‰") == -EINVAL);
|
||||||
|
|
||||||
|
assert_se(parse_permyriad("0%") == 0);
|
||||||
|
assert_se(parse_permyriad("55%") == 5500);
|
||||||
|
assert_se(parse_permyriad("55.53%") == 5553);
|
||||||
|
assert_se(parse_permyriad("100%") == 10000);
|
||||||
|
assert_se(parse_permyriad("-7%") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad("107%") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad("%") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("%%") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("%1") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("1%%") == -EINVAL);
|
||||||
|
assert_se(parse_permyriad("3.212%") == -EINVAL);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void test_parse_permyriad_unbounded(void) {
|
||||||
|
assert_se(parse_permyriad_unbounded("1001‱") == 1001);
|
||||||
|
assert_se(parse_permyriad_unbounded("4000‱") == 4000);
|
||||||
|
assert_se(parse_permyriad_unbounded("2147483647‱") == 2147483647);
|
||||||
|
assert_se(parse_permyriad_unbounded("2147483648‱") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad_unbounded("4294967295‱") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad_unbounded("4294967296‱") == -ERANGE);
|
||||||
|
|
||||||
|
assert_se(parse_permyriad_unbounded("101‰") == 1010);
|
||||||
|
assert_se(parse_permyriad_unbounded("400‰") == 4000);
|
||||||
|
assert_se(parse_permyriad_unbounded("214748364.7‰") == 2147483647);
|
||||||
|
assert_se(parse_permyriad_unbounded("214748364.8‰") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad_unbounded("429496729.5‰") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad_unbounded("429496729.6‰") == -ERANGE);
|
||||||
|
|
||||||
|
assert_se(parse_permyriad_unbounded("99%") == 9900);
|
||||||
|
assert_se(parse_permyriad_unbounded("40%") == 4000);
|
||||||
|
assert_se(parse_permyriad_unbounded("21474836.47%") == 2147483647);
|
||||||
|
assert_se(parse_permyriad_unbounded("21474836.48%") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad_unbounded("42949672.95%") == -ERANGE);
|
||||||
|
assert_se(parse_permyriad_unbounded("42949672.96%") == -ERANGE);
|
||||||
|
}
|
||||||
|
|
||||||
static void test_parse_nice(void) {
|
static void test_parse_nice(void) {
|
||||||
int n;
|
int n;
|
||||||
|
|
||||||
|
@ -987,6 +1053,8 @@ int main(int argc, char *argv[]) {
|
||||||
test_parse_percent_unbounded();
|
test_parse_percent_unbounded();
|
||||||
test_parse_permille();
|
test_parse_permille();
|
||||||
test_parse_permille_unbounded();
|
test_parse_permille_unbounded();
|
||||||
|
test_parse_permyriad();
|
||||||
|
test_parse_permyriad_unbounded();
|
||||||
test_parse_nice();
|
test_parse_nice();
|
||||||
test_parse_dev();
|
test_parse_dev();
|
||||||
test_parse_errno();
|
test_parse_errno();
|
||||||
|
|
|
@ -7,4 +7,4 @@ MemoryAccounting=true
|
||||||
IOAccounting=true
|
IOAccounting=true
|
||||||
TasksAccounting=true
|
TasksAccounting=true
|
||||||
ManagedOOMMemoryPressure=kill
|
ManagedOOMMemoryPressure=kill
|
||||||
ManagedOOMMemoryPressureLimitPercent=1%
|
ManagedOOMMemoryPressureLimit=1%
|
||||||
|
|
|
@ -20,7 +20,7 @@ systemctl start testsuite-56-testbloat.service
|
||||||
|
|
||||||
# Verify systemd-oomd is monitoring the expected units
|
# Verify systemd-oomd is monitoring the expected units
|
||||||
oomctl | grep "/testsuite-56-workload.slice"
|
oomctl | grep "/testsuite-56-workload.slice"
|
||||||
oomctl | grep "1%"
|
oomctl | grep "1.00%"
|
||||||
oomctl | grep "Default Memory Pressure Duration: 5s"
|
oomctl | grep "Default Memory Pressure Duration: 5s"
|
||||||
|
|
||||||
# systemd-oomd watches for elevated pressure for 30 seconds before acting.
|
# systemd-oomd watches for elevated pressure for 30 seconds before acting.
|
||||||
|
|
Loading…
Reference in a new issue