aboutsummaryrefslogtreecommitdiffstats
path: root/yardstick
diff options
context:
space:
mode:
authorKristian Hunt <kristian.hunt@gmail.com>2015-07-14 13:13:47 +0200
committerJörgen Karlsson <jorgen.w.karlsson@ericsson.com>2015-08-13 13:23:55 +0000
commiteca1e81cac34d7569fa5dcb15e5df10a6583559b (patch)
treeb33491e7192b1f8a6d8293927fba6dae34d0b7d4 /yardstick
parentce671dba3dafe0d7d80d4a7eea1f9395bc4d6d7d (diff)
Add perf scenario and sample
Supports using perf software event counters. No hardware events are currently supported. It is possible to add some load to the system using the load parameter, otherwise the system will sleep while the measurements are collected. It is possible to configure SLA for any event measured. Change-Id: Ic413d940093aadd10dc32888ea416aa94316a6fe JIRA: YARDSTICK-51 Signed-off-by: Kristian Hunt <kristian.hunt@gmail.com>
Diffstat (limited to 'yardstick')
-rw-r--r--yardstick/benchmark/scenarios/compute/perf.py140
-rw-r--r--yardstick/benchmark/scenarios/compute/perf_benchmark.bash68
2 files changed, 208 insertions, 0 deletions
diff --git a/yardstick/benchmark/scenarios/compute/perf.py b/yardstick/benchmark/scenarios/compute/perf.py
new file mode 100644
index 000000000..62b4297e3
--- /dev/null
+++ b/yardstick/benchmark/scenarios/compute/perf.py
@@ -0,0 +1,140 @@
+##############################################################################
+# Copyright (c) 2015 Ericsson AB and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+import pkg_resources
+import logging
+import json
+
+import yardstick.ssh as ssh
+from yardstick.benchmark.scenarios import base
+
+LOG = logging.getLogger(__name__)
+LOG.setLevel(logging.DEBUG)
+
+
+class Perf(base.Scenario):
+ """Execute perf benchmark in a host
+
+ Parameters
+ events - perf tool software, hardware or tracepoint events
+ type: [str]
+ unit: na
+ default: ['task-clock']
+ load - simulate load on the host by doing IO operations
+ type: bool
+ unit: na
+ default: false
+
+ For more info about perf and perf events see https://perf.wiki.kernel.org
+ """
+
+ __scenario_type__ = "Perf"
+
+ TARGET_SCRIPT = 'perf_benchmark.bash'
+
+ def __init__(self, context):
+ self.context = context
+ self.setup_done = False
+
+ def setup(self):
+ """scenario setup"""
+ self.target_script = pkg_resources.resource_filename(
+ 'yardstick.benchmark.scenarios.compute', Perf.TARGET_SCRIPT)
+ user = self.context.get('user', 'ubuntu')
+ host = self.context.get('host', None)
+ key_filename = self.context.get('key_filename', '~/.ssh/id_rsa')
+
+ LOG.debug("user:%s, host:%s", user, host)
+ self.client = ssh.SSH(user, host, key_filename=key_filename)
+ self.client.wait(timeout=600)
+
+ # copy script to host
+ self.client.run("cat > ~/perf_benchmark.sh",
+ stdin=open(self.target_script, "rb"))
+
+ self.setup_done = True
+
+ def run(self, args):
+ """execute the benchmark"""
+
+ if not self.setup_done:
+ self.setup()
+
+ options = args['options']
+ events = options.get('events', ['task-clock'])
+
+ events_string = ""
+ for event in events:
+ events_string += event + " "
+
+ # if run by a duration runner
+ duration_time = self.context.get("duration", None)
+ # if run by an arithmetic runner
+ arithmetic_time = options.get("duration", None)
+ if duration_time:
+ duration = duration_time
+ elif arithmetic_time:
+ duration = arithmetic_time
+ else:
+ duration = 30
+
+ if 'load' in options:
+ load = "dd if=/dev/urandom of=/dev/null"
+ else:
+ load = "sleep %d" % duration
+
+ cmd = "sudo bash perf_benchmark.sh '%s' %d %s" \
+ % (load, duration, events_string)
+
+ LOG.debug("Executing command: %s", cmd)
+ status, stdout, stderr = self.client.execute(cmd)
+
+ if status:
+ raise RuntimeError(stdout)
+
+ output = json.loads(stdout)
+
+ if "sla" in args:
+ metric = args['sla']['metric']
+ exp_val = args['sla']['expected_value']
+ smaller_than_exp = 'smaller_than_expected' in args['sla']
+
+ if metric not in output:
+ assert False, "Metric (%s) not found." % metric
+ else:
+ if smaller_than_exp:
+ assert output[metric] < exp_val, "%s %d >= %d (sla)" \
+ % (metric, output[metric], exp_val)
+ else:
+ assert output[metric] >= exp_val, "%s %d < %d (sla)" \
+ % (metric, output[metric], exp_val)
+ return output
+
+
+def _test():
+ """internal test function"""
+ key_filename = pkg_resources.resource_filename('yardstick.resources',
+ 'files/yardstick_key')
+ ctx = {'host': '172.16.0.137',
+ 'user': 'ubuntu',
+ 'key_filename': key_filename
+ }
+
+ logger = logging.getLogger('yardstick')
+ logger.setLevel(logging.DEBUG)
+
+ p = Perf(ctx)
+
+ options = {'load': True}
+ args = {'options': options}
+
+ result = p.run(args)
+ print result
+
+if __name__ == '__main__':
+ _test()
diff --git a/yardstick/benchmark/scenarios/compute/perf_benchmark.bash b/yardstick/benchmark/scenarios/compute/perf_benchmark.bash
new file mode 100644
index 000000000..5ae107a52
--- /dev/null
+++ b/yardstick/benchmark/scenarios/compute/perf_benchmark.bash
@@ -0,0 +1,68 @@
+#!/bin/sh
+
+##############################################################################
+# Copyright (c) 2015 Ericsson AB and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+
+set -e
+
+# Commandline arguments
+PAYLOAD_OP=$1
+shift
+DURATION=$1
+shift
+EVENTS=("$@")
+OUTPUT_FILE=/tmp/perfout.txt
+
+# run perf test
+run_perf()
+{
+ COMMA_SEP_E=$( IFS=$','; echo "${EVENTS[*]}" )
+
+ if [[ $PAYLOAD_OP == dd* ]]
+ then
+ sudo perf stat -o $OUTPUT_FILE -e ${COMMA_SEP_E[@]} $PAYLOAD_OP &
+ sleep $DURATION
+ sudo killall -q -u root dd
+ else
+ sudo perf stat -o $OUTPUT_FILE -e ${COMMA_SEP_E[@]} $PAYLOAD_OP
+ fi
+}
+
+# write the result to stdout in json format
+output_json()
+{
+ EVENTS+=('time')
+
+ last_pos=$(( ${#EVENTS[*]} - 1 ))
+ last=${EVENTS[$last_pos]}
+
+ echo -n {
+ for EVENT in ${EVENTS[@]}
+ do
+ value=$(cat $OUTPUT_FILE | grep $EVENT | awk 'match($0,/[0-9]+|[0-9]+\.[0-9]*/, a) { print a[0]}')
+
+ if [[ $EVENT != $last ]]
+ then
+ echo -n \"$EVENT\": $value,
+ else
+ echo -n \"$EVENT\": $value
+ fi
+ done
+ echo }
+}
+
+# main entry
+main()
+{
+ run_perf > /dev/null 2>&1
+ sleep 1
+ output_json
+}
+
+main