summaryrefslogtreecommitdiff
diff options
authorRod Smith <rod.smith@canonical.com>2016-02-16 16:12:18 +0000
committerSylvain Pineau <>2016-02-16 16:12:18 +0000
commit34892edfb76f5a3fa7e1f5c111672981612e4c68 (patch)
tree021cb766ef742f5b09600145a52ea6a32dda79eb
parent71b6376abe48daa5daaa7ab5ba0293c5167d7540 (diff)
parent0e61f29f29a7526c2a6d450f175e82c2a3b1c6b2 (diff)
"automatic merge of lp:~rodsmith/checkbox/new-memory-test/ by tarmac [r=bladernr,sylvain-pineau][bug=][author=rodsmith]"
-rwxr-xr-xbin/memory_stress_ng157
-rw-r--r--jobs/memory.txt.in14
2 files changed, 171 insertions, 0 deletions
diff --git a/bin/memory_stress_ng b/bin/memory_stress_ng
new file mode 100755
index 00000000..e33cccf4
--- /dev/null
+++ b/bin/memory_stress_ng
@@ -0,0 +1,157 @@
+#!/bin/bash
+
+# Script to perform memory stress tests
+#
+# Copyright (c) 2016 Canonical Ltd.
+#
+# Authors
+# Rod Smith <rod.smith@canonical.com>
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License version 3,
+# as published by the Free Software Foundation.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+#
+# The purpose of this script is to run memory stress tests using the
+# stress-ng program. It also happens to impose a heavy CPU load, but
+# that's a side effect of the memory stressors, not their purpose.
+#
+# Usage:
+# memory_stress_ng [ --base-time <time> ] [ --time-per-gig <time> ]
+#
+# Parameters:
+# --base-time is the time in seconds to run each stressor. (The default
+# is 300 seconds, or five minutes.)
+# --time-per-gig is extra time given to SOME stressors, measured in a
+# seconds per GiB way. (The default is 10 seconds per GiB.)
+#
+# There are a total of 23 constant-run-time stressors and 6 variable-
+# run-time stressors. Given the defaults, this works out to a total
+# expected default run time of 8700 seconds (145 minutes) plus 60 seconds
+# per GiB of RAM -- so a system with 16 GiB should take 161 minutes; one
+# with 32 GiB should take 177 minutes, and so on, using the default
+# values.
+
+
+get_params() {
+ base_time=300
+ time_per_gig=10
+ while [ $# -gt 0 ] ; do
+ case $1 in
+ --base-time) base_time="$2"
+ shift
+ ;;
+ --time-per-gig) time_per_gig="$2"
+ shift
+ ;;
+ *) echo "Usage: $0 [ --base-time <time> ] [ --time-per-gig <time> ]"
+ exit 1
+ ;;
+ esac
+ shift
+ done
+ local extra_time=$(($time_per_gig * $total_mem_in_GiB))
+ variable_time=$(($base_time + $extra_time ))
+} # get_params()
+
+
+# Run an individual stressor
+# Input:
+# $1 = stressor name (e.g., malloc, brk)
+# $2 = run time
+# Output:
+# had_error -- sets to "1" if an error occurred
+run_stressor() {
+ local runtime="$2"
+ # Add 50% to runtime; will forcefully terminate if stress-ng
+ # fails to return in that time.
+ end_time=$((runtime*15/10))
+ echo "Running stress-ng $1 stressor for $2 seconds...."
+ # Use "timeout" command to launch stress-ng, to catch it should it go into la-la land
+ timeout -s 9 $end_time stress-ng --aggressive --verify --timeout $runtime --$1 0
+ return_code="$?"
+ echo "return_code is $return_code"
+ if [ "$return_code" != "0" ] ; then
+ had_error=1
+ echo "*****************************************************************"
+ if [ $return_code = "137" ] ; then
+ echo "** stress-ng memory test timed out and was forcefully terminated!"
+ else
+ echo "** Error $return_code reported on stressor $stressor!)"
+ fi
+ echo "*****************************************************************"
+ had_error=1
+ fi
+} # run_stressor()
+
+
+#
+# Main program body....
+#
+
+swap_space=`cat /proc/meminfo | grep -i SwapTotal | tr -s " " | cut -f 2 -d " "`
+if [ -z $swap_space ] || [ $swap_space = "0" ] ; then
+ echo "Swap space unavailable! Please activate swap space and re-run this test!"
+ exit 1
+fi
+
+# Total memory in KiB....
+total_mem_in_KiB=`cat /proc/meminfo | grep MemTotal | tr -s " " | cut -f 2 -d " "`
+total_mem_in_GiB=$((($total_mem_in_KiB/1048576)+1))
+echo "Total memory is $total_mem_in_GiB GiB"
+
+get_params "$@"
+echo "Constant run time is $base_time seconds per stressor"
+echo "Variable run time is $variable_time seconds per stressor"
+
+had_error=0
+
+# NOTE: Specify stressors in two arrays rather than rely on stress-ng's
+# --class memory,vm option for two reasons:
+# 1. We want to run some stressors (those that exhaust all memory)
+# for longer than others, so we need to specify different run
+# times for different stressors.
+# 2. stress-ng is constantly being updated with new tests. We don't
+# want to run one set of tests on SUT 1 and a larger set of tests
+# on SUT 2 if we happen to have updated stress-ng for some unrelated
+# reason (like a bug fix); thus, we specify tests individually.
+
+# Constant-run-time stressors -- run them for the same length of time on all
+# systems....
+crt_stressors=("bsearch" "context" "hsearch" "lockbus" "lsearch" "matrix" \
+ "memcpy" "null" "pipe" "qsort" "stack" "str" "stream" \
+ "tsearch" "vm-rw" "wcs" "zero" "mlock" "mmapfork" "mmapmany" \
+ "mremap" "shm-sysv" "vm-splice")
+crt_runtime=$((${#crt_stressors[@]}*$base_time))
+
+# Variable-run-time stressors -- run them longer on systems with more RAM....
+vrt_stressors=("malloc" "mincore" "vm" "bigheap" "brk" "mmap")
+vrt_runtime=$((${#vrt_stressors[@]}*$variable_time))
+
+total_runtime=$((($crt_runtime + $vrt_runtime) / 60))
+echo "Estimated total run time is $total_runtime minutes"
+echo ""
+
+for stressor in ${crt_stressors[@]}; do
+ run_stressor $stressor $base_time
+done
+
+for stressor in ${vrt_stressors[@]}; do
+ run_stressor $stressor $variable_time
+done
+
+echo "*******************************************************************"
+if [ $had_error = "0" ] ; then
+ echo "** stress-ng memory test passed!"
+else
+ echo "** stress-ng memory test failed; most recent error was $return_code"
+fi
+echo "*******************************************************************"
+exit $result
diff --git a/jobs/memory.txt.in b/jobs/memory.txt.in
index a6d6b424..6be50a30 100644
--- a/jobs/memory.txt.in
+++ b/jobs/memory.txt.in
@@ -22,3 +22,17 @@ _description:
should have suitably large swap files for the amount of RAM they have
installed.
+plugin: shell
+category_id: 2013.com.canonical.plainbox::memory
+id: memory/memory_stress_ng
+estimated_duration: 11000.0
+user: root
+requires:
+ package.name == 'stress-ng'
+command: memory_stress_ng
+_description:
+ Test to perform some basic stress and exercise of system memory via the
+ stress_ng tool. This test also includes an over-commit function to force
+ swapping to disk, thus SUTs should have suitably large swap files for the
+ amount of RAM they have installed.
+