90 lines
2.6 KiB
Python
Executable File
90 lines
2.6 KiB
Python
Executable File
#!/usr/bin/python2
|
|
|
|
"""
|
|
python-libpfm4 provides python bindings to the libpfm4
|
|
library and the perf_event kernel subsystem. This
|
|
script builds on them to provide a *stat like interface
|
|
to CPU performance counters.
|
|
|
|
Run as: ./cpistat -c cpulist -e eventlist
|
|
|
|
Depends on libpfm4: http://perfmon2.sf.net/
|
|
|
|
git://perfmon2.git.sourceforge.net/gitroot/perfmon2/libpfm4
|
|
"""
|
|
|
|
from __future__ import absolute_import
|
|
from __future__ import division
|
|
from __future__ import print_function
|
|
|
|
import sys, os, optparse, time, struct, perfmon
|
|
from six.moves import range
|
|
|
|
if __name__ == '__main__':
|
|
parser = optparse.OptionParser()
|
|
parser.add_option('-e', '--events', help='Events to use',
|
|
action='store', dest='events')
|
|
parser.add_option('-c', '--cpulist', help='CPUs to monitor',
|
|
action='store', dest='cpulist')
|
|
parser.set_defaults(events='PERF_COUNT_HW_CPU_CYCLES,' +
|
|
'PERF_COUNT_HW_INSTRUCTIONS')
|
|
(options, args) = parser.parse_args()
|
|
|
|
show_per_cpu = False
|
|
if not options.cpulist:
|
|
ncpus = os.sysconf('SC_NPROCESSORS_ONLN')
|
|
cpus = list(range(0, ncpus))
|
|
else:
|
|
cpus = options.cpulist.split(',')
|
|
cpus = [ int(c) for c in cpus ]
|
|
show_per_cpu = True
|
|
|
|
if options.events:
|
|
events = options.events.split(',')
|
|
else:
|
|
raise ValueError('You need to specify events to monitor')
|
|
|
|
s = perfmon.SystemWideSession(cpus, events)
|
|
|
|
s.start()
|
|
# Measuring loop
|
|
interval = 1
|
|
iters = -1
|
|
infinite = True
|
|
if len(args) == 2:
|
|
interval = int(args[0])
|
|
iters = int(args[1])
|
|
infinite = False
|
|
|
|
delta = {}
|
|
last = {}
|
|
sum = {}
|
|
for e in events:
|
|
delta[e] = {}
|
|
last[e] = {}
|
|
sum[e] = {}
|
|
for c in cpus:
|
|
delta[e][c] = 0
|
|
last[e][c] = 0
|
|
|
|
while infinite or iters:
|
|
for i in range(0, len(events)):
|
|
e = events[i]
|
|
sum[e] = 0
|
|
for c in cpus:
|
|
count = struct.unpack('L', s.read(c, i))[0]
|
|
delta[e][c] = count - last[e][c]
|
|
last[e][c] = count
|
|
if show_per_cpu:
|
|
print('''CPU%d: %s\t%lu''' % (c, e, delta[e][c]))
|
|
sum[e] += delta[e][c]
|
|
|
|
cycles = sum['PERF_COUNT_HW_CPU_CYCLES']
|
|
instructions = sum['PERF_COUNT_HW_INSTRUCTIONS']
|
|
CPI = cycles * 1.0/instructions
|
|
print('cycles: %12lu, instructions: %12lu, CPI: %2.4f'
|
|
% (cycles, instructions, CPI))
|
|
sys.stdout.flush()
|
|
time.sleep(interval)
|
|
iters = iters - 1
|