blob: 033e8825fa3003190f6cb3d59f9c8e504c33b7b5 [file] [log] [blame]
#
# sysstat.py - rteval measurment module collecting system statistics
# using the sysstat utility
#
# Copyright 2013 David Sommerseth <davids@redhat.com>
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# 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, write to the Free Software Foundation, Inc.,
# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
#
# For the avoidance of doubt the "preferred form" of this code is one which
# is in an open unpatent encumbered format. Where cryptographic key signing
# forms part of the process of creating an executable the information
# including keys needed to generate an equivalently functional executable
# are deemed to be part of the source code.
#
import os, sys, libxml2, tempfile, time, subprocess, base64, bz2, textwrap
from rteval.Log import Log
from rteval.modules import rtevalModulePrototype
class sysstat(rtevalModulePrototype):
def __init__(self, config, logger=None):
rtevalModulePrototype.__init__(self, 'measurement', 'sysstat', logger)
self.__cfg = config
self.__started = False
self.__logentry = 0
self.__bin_sadc = "/usr/lib64/sa/sadc" # FIXME: Do dynamically
self.__datadir = os.path.join(self.__cfg.reportdir, 'sysstat')
self.__datafile = os.path.join(self.__datadir, "sysstat.dat")
def _WorkloadSetup(self):
# Nothing to do here for sysstat
pass
def _WorkloadBuild(self):
# Nothing to build
self._setReady()
def _WorkloadPrepare(self):
os.mkdir(self.__datadir)
def _WorkloadTask(self):
# This workload will actually not run any process, but
# it will update the data files each time rteval checks
# if this workload is alive.
#
# Just add a single notification that rteval started
if self.__logentry == 0:
cmd = [self.__bin_sadc, "-S", "XALL", "-C", "rteval started", self.__datafile]
subprocess.call(cmd)
self.__logentry += 1
def WorkloadAlive(self):
# Here the sysstat tool will be called, which will update
# the file containing the system information
cmd = [self.__bin_sadc, "-S", "XALL", "1", "1", self.__datafile]
subprocess.call(cmd)
self.__logentry += 1
return True
def _WorkloadCleanup(self):
# Add 'rteval stopped' comment line
cmd = [self.__bin_sadc, "-S", "XALL", "-C", "rteval stopped", self.__datafile]
subprocess.call(cmd)
self.__logentry += 1
self._setFinished()
def MakeReport(self):
rep_n = libxml2.newNode('sysstat')
rep_n.newProp('command_line', '(sysstat specifics)')
rep_n.newProp('num_entries', str(self.__logentry))
fp = open(self.__datafile, "rb")
compr = bz2.BZ2Compressor(9)
cmpr = compr.compress(fp.read())
data = base64.b64encode(cmpr + compr.flush())
data_n = rep_n.newTextChild(None, 'data', "\n"+"\n".join(textwrap.wrap(data,75))+"\n")
data_n.newProp('contents', 'sysstat/sar binary data')
data_n.newProp('encoding','base64')
data_n.newProp('compression','bz2')
fp.close()
del cmpr
del compr
# Return the report
return rep_n
def ModuleInfo():
# sysstat features - run in parallel with outher measurement modules with loads
return {"parallel": True,
"loads": True}
def ModuleParameters():
return {} # No arguments available
def create(params, logger):
return sysstat(params, logger)
if __name__ == '__main__':
from rteval.rtevalConfig import rtevalConfig
l = Log()
l.SetLogVerbosity(Log.INFO|Log.DEBUG|Log.ERR|Log.WARN)
cfg = rtevalConfig({}, logger=l)
prms = {}
modprms = ModuleParameters()
for c, p in modprms.items():
prms[c] = p['default']
cfg.AppendConfig('MeasurementModuleTemplate', prms)
cfg_ct = cfg.GetSection('MeasurementModuleTemplate')
cfg_ct.reportdir = "."
runtime = 10
c = sysstat(cfg_ct, l)
c._WorkloadSetup()
c._WorkloadPrepare()
c._WorkloadTask()
print "Running for approx %i seconds" % runtime
while runtime > 0:
c.WorkloadAlive()
time.sleep(1)
runtime -= 1
c._WorkloadCleanup()
rep_n = c.MakeReport()
xml = libxml2.newDoc('1.0')
xml.setRootElement(rep_n)
xml.saveFormatFileEnc('-','UTF-8',1)