From 018b6f45483941e70df37661986bae39b0c90849 Mon Sep 17 00:00:00 2001 From: Anita Zhang Date: Wed, 21 Oct 2020 01:52:53 -0700 Subject: [PATCH 1/3] oomd: use ERRNO_IS_NOT_SUPPORTED and ERRNO_IS_PRIVILEGE --- src/oom/test-oomd-util.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/oom/test-oomd-util.c b/src/oom/test-oomd-util.c index 38cae9e034..5e7c187154 100644 --- a/src/oom/test-oomd-util.c +++ b/src/oom/test-oomd-util.c @@ -57,7 +57,7 @@ static void test_oomd_cgroup_kill(void) { /* If we don't have permissions to set xattrs we're likely in a userns or missing capabilities */ r = cg_set_xattr(SYSTEMD_CGROUP_CONTROLLER, cgroup, "user.oomd_test", "test", 4, 0); - if (IN_SET(r, -EPERM, -ENOTSUP)) + if (ERRNO_IS_PRIVILEGE(r) || ERRNO_IS_NOT_SUPPORTED(r)) return (void) log_tests_skipped("Cannot set user xattrs"); /* Do this twice to also check the increment behavior on the xattrs */ From e4ff80404a71746864d29c0a3dc019a309277e53 Mon Sep 17 00:00:00 2001 From: Anita Zhang Date: Fri, 14 Aug 2020 01:20:43 -0700 Subject: [PATCH 2/3] test: add basic memory pressure extended test for oomd Simple test to generate a lot of pressure in one unit and assert that systemd-oomd kills the right one. --- test/TEST-56-OOMD/Makefile | 1 + test/TEST-56-OOMD/test.sh | 48 ++++++++++++++++++ test/test-functions | 1 + test/units/testsuite-56-slowgrowth.sh | 34 +++++++++++++ test/units/testsuite-56.service | 7 +++ test/units/testsuite-56.sh | 70 +++++++++++++++++++++++++++ 6 files changed, 161 insertions(+) create mode 120000 test/TEST-56-OOMD/Makefile create mode 100755 test/TEST-56-OOMD/test.sh create mode 100755 test/units/testsuite-56-slowgrowth.sh create mode 100644 test/units/testsuite-56.service create mode 100755 test/units/testsuite-56.sh diff --git a/test/TEST-56-OOMD/Makefile b/test/TEST-56-OOMD/Makefile new file mode 120000 index 0000000000..e9f93b1104 --- /dev/null +++ b/test/TEST-56-OOMD/Makefile @@ -0,0 +1 @@ +../TEST-01-BASIC/Makefile \ No newline at end of file diff --git a/test/TEST-56-OOMD/test.sh b/test/TEST-56-OOMD/test.sh new file mode 100755 index 0000000000..55b0d1dafd --- /dev/null +++ b/test/TEST-56-OOMD/test.sh @@ -0,0 +1,48 @@ +#!/usr/bin/env bash +set -e +TEST_DESCRIPTION="systemd-oomd Memory Pressure Test" + +. $TEST_BASE_DIR/test-functions + +check_result_nspawn() { + local ret=1 + local journald_report="" + local pids="" + [[ -e $1/testok ]] && ret=0 + if [[ -e $1/skipped ]]; then + echo "TEST-56-OOMD was skipped:" + cat $1/skipped + ret=0 + fi + [[ -f $1/failed ]] && cp -a $1/failed $TESTDIR + save_journal $1/var/log/journal + [[ -f $TESTDIR/failed ]] && cat $TESTDIR/failed + echo $JOURNAL_LIST + test -s $TESTDIR/failed && ret=$(($ret+1)) + [ -n "$TIMED_OUT" ] && ret=$(($ret+1)) + check_asan_reports "$1" || ret=$(($ret+1)) + _umount_dir $initdir + return $ret +} + +check_result_qemu() { + local ret=1 + mount_initdir + [[ -e $initdir/testok ]] && ret=0 + if [[ -e $initdir/skipped ]]; then + echo "TEST-56-OOMD was skipped:" + cat $initdir/skipped + ret=0 + fi + [[ -f $initdir/failed ]] && cp -a $initdir/failed $TESTDIR + save_journal $initdir/var/log/journal + check_asan_reports "$initdir" || ret=$(($ret+1)) + _umount_dir $initdir + [[ -f $TESTDIR/failed ]] && cat $TESTDIR/failed + echo $JOURNAL_LIST + test -s $TESTDIR/failed && ret=$(($ret+1)) + [ -n "$TIMED_OUT" ] && ret=$(($ret+1)) + return $ret +} + +do_test "$@" 56 diff --git a/test/test-functions b/test/test-functions index 9893864bcd..a2cb28c380 100644 --- a/test/test-functions +++ b/test/test-functions @@ -65,6 +65,7 @@ BASICTOOLS=( echo env false + getconf getent getfacl grep diff --git a/test/units/testsuite-56-slowgrowth.sh b/test/units/testsuite-56-slowgrowth.sh new file mode 100755 index 0000000000..ff5a747348 --- /dev/null +++ b/test/units/testsuite-56-slowgrowth.sh @@ -0,0 +1,34 @@ +#!/usr/bin/env bash +set -eu -o pipefail + +PAGE_SIZE=$(getconf PAGE_SIZE) +BLOAT_ITERATION_TARGET=$(( 100 << 20 )) # 100 MB +BLOAT_HOLDER=() +PID="$$" + +function bloat { + local set_size=$(cat "/proc/$PID/statm" | cut -d " " -f2) + local mem_usage=$(( "$set_size" * "$PAGE_SIZE" )) + local target_mem_size=$(( "$mem_usage" + "$1" )) + + BLOAT_HOLDER=() + while [[ "$mem_usage" -lt "$target_mem_size" ]]; do + echo "target $target_mem_size" + echo "mem usage $mem_usage" + BLOAT_HOLDER+=( $(printf "%0.sg" {1..1000000}) ) + set_size=$(cat "/proc/$PID/statm" | cut -d " " -f2) + mem_usage=$(( "$set_size" * "$PAGE_SIZE" )) + done +} + +function run { + local arr=() + + while [[ true ]]; do + bloat "$BLOAT_ITERATION_TARGET" + arr+=( "$BLOAT_HOLDER" ) + sleep 1 + done +} + +run diff --git a/test/units/testsuite-56.service b/test/units/testsuite-56.service new file mode 100644 index 0000000000..b53b0905db --- /dev/null +++ b/test/units/testsuite-56.service @@ -0,0 +1,7 @@ +[Unit] +Description=TESTSUITE-56-OOMD + +[Service] +ExecStartPre=rm -f /failed /skipped /testok +ExecStart=/usr/lib/systemd/tests/testdata/units/%N.sh +Type=oneshot diff --git a/test/units/testsuite-56.sh b/test/units/testsuite-56.sh new file mode 100755 index 0000000000..5be6658972 --- /dev/null +++ b/test/units/testsuite-56.sh @@ -0,0 +1,70 @@ +#!/usr/bin/env bash +set -ex +set -o pipefail + +systemd-analyze log-level debug +systemd-analyze log-target console + +# Loose checks to ensure the environment has the necessary features for systemd-oomd +[[ "$( awk '/SwapTotal/ { print $2 }' /proc/meminfo )" != "0" ]] || echo "no swap" >> /skipped +[[ -e /proc/pressure ]] || echo "no PSI" >> /skipped +cgroup_type=$(stat -fc %T /sys/fs/cgroup/) +if [[ "$cgroup_type" != *"cgroup2"* ]] && [[ "$cgroup_type" != *"0x63677270"* ]]; then + echo "no cgroup2" >> /skipped +fi +[[ -e /skipped ]] && exit 0 || true + +cat > /etc/systemd/system/testworkload.slice < /etc/systemd/system/testbloat.service < /etc/systemd/system/testchill.service < /testok + +exit 0 From 532855bead422499e6e5f85b6ebf3af28e652022 Mon Sep 17 00:00:00 2001 From: Anita Zhang Date: Thu, 22 Oct 2020 02:03:20 -0700 Subject: [PATCH 3/3] oomd: make start up swap check more robust --- src/oom/oomd.c | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/src/oom/oomd.c b/src/oom/oomd.c index 2c0031aeac..203395c1e7 100644 --- a/src/oom/oomd.c +++ b/src/oom/oomd.c @@ -117,6 +117,8 @@ static int parse_argv(int argc, char *argv[]) { static int run(int argc, char *argv[]) { _cleanup_(notify_on_cleanup) const char *notify_msg = NULL; _cleanup_(manager_freep) Manager *m = NULL; + _cleanup_free_ char *swap = NULL; + unsigned long long s = 0; int r; log_setup_service(); @@ -131,8 +133,17 @@ static int run(int argc, char *argv[]) { /* Do some basic requirement checks for running systemd-oomd. It's not exhaustive as some of the other * requirements do not have a reliable means to check for in code. */ - if (access("/proc/swaps", F_OK) < 0) - return log_error_errno(errno, "Swap not enabled: %m"); + + /* SwapTotal is always available in /proc/meminfo and defaults to 0, even on swap-disabled kernels. */ + r = get_proc_field("/proc/meminfo", "SwapTotal", WHITESPACE, &swap); + if (r < 0) + return log_error_errno(r, "Failed to get SwapTotal from /proc/meminfo: %m"); + + r = safe_atollu(swap, &s); + if (r < 0) + return log_error_errno(r, "Failed to parse SwapTotal from /proc/meminfo: %s: %m", swap); + if (s == 0) + return log_error_errno(SYNTHETIC_ERRNO(EOPNOTSUPP), "Requires swap to operate"); if (!is_pressure_supported()) return log_error_errno(SYNTHETIC_ERRNO(EOPNOTSUPP), "Pressure Stall Information (PSI) is not supported");