1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
|
#!/usr/bin/python
# ===-- IStatsSum.py ------------------------------------------------------===##
#
# The KLEE Symbolic Virtual Machine
#
# This file is distributed under the University of Illinois Open Source
# License. See LICENSE.TXT for details.
#
# ===----------------------------------------------------------------------===##
from __future__ import division
import sys, os
def getSummary(input):
inputs = [[None,iter(open(input))]]
def getLine(elt):
la,i = elt
if la is None:
try:
ln = i.next()
except StopIteration:
ln = None
except:
raise ValueError("unexpected IO error")
return ln
else:
elt[0] = None
return la
def getLines():
return map(getLine,inputs)
def putback(ln,elt):
assert elt[0] is None
elt[0] = ln
events = None
# read header (up to ob=)
while 1:
lns = getLines()
ln = lns[0]
if ln.startswith('ob='):
break
else:
if ln.startswith('positions:'):
if ln!='positions: instr line\n':
raise ValueError("unexpected 'positions' directive")
elif ln.startswith('events:'):
events = ln[len('events: '):].strip().split(' ')
if events is None:
raise ValueError('missing events directive')
boolTypes = set(['Icov','Iuncov'])
numEvents = len(events)
eventTypes = [e in boolTypes for e in events]
def readCalls():
results = {}
for elt in inputs:
while 1:
ln = getLine(elt)
if ln is not None and (ln.startswith('cfl=') or ln.startswith('cfn=')):
if ln.startswith('cfl='):
cfl = ln
cfn = getLine(elt)
if not cfn.startswith('cfn='):
raise ValueError("unexpected cfl directive without function")
else:
cfl = None
cfn = ln
target = getLine(elt)
if not target.startswith('calls='):
raise ValueError("unexpected cfn directive with calls")
stat = map(int,getLine(elt).strip().split(' '))
key = target
existing = results.get(target)
if existing is None:
results[key] = [cfl,cfn,target,stat]
else:
if existing[0]!=cfl or existing[1]!=cfn:
raise ValueError("multiple call descriptions for a single target")
existing[3] = mergeStats([existing[3],stat])
else:
putback(ln, elt)
break
return results
summed = [0]*len(events)
# read statistics
while 1:
lns = getLines()
ln = lns[0]
if ln is None:
break
elif ln.startswith('fn') or ln.startswith('fl'):
pass
elif ln.strip():
# an actual statistic
data = [map(int,ln.strip().split(' ')) for ln in lns][0]
summed = map(lambda a,b: a+b, data[2:], summed)
# read any associated calls
for cfl,cfn,calls,stat in readCalls().values():
pass
return events,summed
def main(args):
from optparse import OptionParser
op = OptionParser("usage: %prog [options] file")
opts,args = op.parse_args()
total = {}
for i in args:
events,summed = getSummary(i)
for e,s in zip(events,summed):
total[e] = total.get(e,[0,0])
total[e][0] += s
total[e][1] += 1
print '-- %s --'%(i,)
items = zip(events,summed)
items.sort()
for e,s in items:
print '%s: %s'%(e,s)
print '-- totals --'
items = total.items()
table = []
for e,(s,N) in items:
table.append((str(e),str(s),str(N),str(s//N)))
w = map(lambda l: max(map(len,l)), zip(*table))
for (a,b,c,d) in table:
print '%-*s: %*s (in %*s files, avg: %*s)'%(w[0],a,w[1],b,w[2],c,w[3],d)
if __name__=='__main__':
main(sys.argv)
|