annotate contrib/header-tools/graph-header-logs @ 111:04ced10e8804

gcc 7
author kono
date Fri, 27 Oct 2017 22:46:09 +0900
parents
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
111
kono
parents:
diff changeset
1 #! /usr/bin/python2
kono
parents:
diff changeset
2 import os.path
kono
parents:
diff changeset
3 import sys
kono
parents:
diff changeset
4 import shlex
kono
parents:
diff changeset
5 import re
kono
parents:
diff changeset
6
kono
parents:
diff changeset
7 from headerutils import *
kono
parents:
diff changeset
8
kono
parents:
diff changeset
9 header_roots = { }
kono
parents:
diff changeset
10 extra_edges = list()
kono
parents:
diff changeset
11 verbose = False
kono
parents:
diff changeset
12 verbosity = 0
kono
parents:
diff changeset
13 nodes = list()
kono
parents:
diff changeset
14
kono
parents:
diff changeset
15 def unpretty (name):
kono
parents:
diff changeset
16 if name[-2:] == "_h":
kono
parents:
diff changeset
17 name = name[:-2] + ".h"
kono
parents:
diff changeset
18 return name.replace("_", "-")
kono
parents:
diff changeset
19
kono
parents:
diff changeset
20 def pretty_name (name):
kono
parents:
diff changeset
21 name = os.path.basename (name)
kono
parents:
diff changeset
22 return name.replace(".","_").replace("-","_").replace("/","_").replace("+","_");
kono
parents:
diff changeset
23
kono
parents:
diff changeset
24 depstring = ("In file included from", " from")
kono
parents:
diff changeset
25
kono
parents:
diff changeset
26 # indentation indicates nesting levels of included files
kono
parents:
diff changeset
27 ignore = [ "coretypes_h",
kono
parents:
diff changeset
28 "insn_modes_h",
kono
parents:
diff changeset
29 "signop_h",
kono
parents:
diff changeset
30 "wide_int_h",
kono
parents:
diff changeset
31 "wide_int_print_h",
kono
parents:
diff changeset
32 "insn_modes_inline_h",
kono
parents:
diff changeset
33 "machmode_h",
kono
parents:
diff changeset
34 "double_int_h",
kono
parents:
diff changeset
35 "real_h",
kono
parents:
diff changeset
36 "fixed_value_h",
kono
parents:
diff changeset
37 "hash_table_h",
kono
parents:
diff changeset
38 "statistics_h",
kono
parents:
diff changeset
39 "ggc_h",
kono
parents:
diff changeset
40 "vec_h",
kono
parents:
diff changeset
41 "hashtab_h",
kono
parents:
diff changeset
42 "inchash_h",
kono
parents:
diff changeset
43 "mem_stats_traits_h",
kono
parents:
diff changeset
44 "hash_map_traits_h",
kono
parents:
diff changeset
45 "mem_stats_h",
kono
parents:
diff changeset
46 "hash_map_h",
kono
parents:
diff changeset
47 "hash_set_h",
kono
parents:
diff changeset
48 "input_h",
kono
parents:
diff changeset
49 "line_map_h",
kono
parents:
diff changeset
50 "is_a_h",
kono
parents:
diff changeset
51 "system_h",
kono
parents:
diff changeset
52 "config_h" ]
kono
parents:
diff changeset
53
kono
parents:
diff changeset
54 def process_log_file (header, logfile):
kono
parents:
diff changeset
55 if header_roots.get (header) != None:
kono
parents:
diff changeset
56 print "Error: already processed log file: " + header + ".log"
kono
parents:
diff changeset
57 return
kono
parents:
diff changeset
58 hname = pretty_name (header)
kono
parents:
diff changeset
59 header_roots[hname] = { }
kono
parents:
diff changeset
60
kono
parents:
diff changeset
61 sline = list();
kono
parents:
diff changeset
62 incfrom = list()
kono
parents:
diff changeset
63 newinc = True
kono
parents:
diff changeset
64 for line in logfile:
kono
parents:
diff changeset
65 if len (line) > 21 and line[:21] in depstring:
kono
parents:
diff changeset
66 if newinc:
kono
parents:
diff changeset
67 incfrom = list()
kono
parents:
diff changeset
68 newinc = False
kono
parents:
diff changeset
69 fn = re.findall(ur".*/(.*?):", line)
kono
parents:
diff changeset
70 if len(fn) != 1:
kono
parents:
diff changeset
71 continue
kono
parents:
diff changeset
72 if fn[0][-2:] != ".h":
kono
parents:
diff changeset
73 continue
kono
parents:
diff changeset
74 n = pretty_name (fn[0])
kono
parents:
diff changeset
75 if n not in ignore:
kono
parents:
diff changeset
76 incfrom.append (n)
kono
parents:
diff changeset
77 continue
kono
parents:
diff changeset
78 newinc = True
kono
parents:
diff changeset
79 note = re.findall (ur"^.*note: (.*)", line)
kono
parents:
diff changeset
80 if len(note) > 0:
kono
parents:
diff changeset
81 sline.append (("note", note[0]))
kono
parents:
diff changeset
82 else:
kono
parents:
diff changeset
83 err_msg = re.findall (ur"^.*: error: (.*)", line)
kono
parents:
diff changeset
84 if len(err_msg) == 1:
kono
parents:
diff changeset
85 msg = err_msg[0]
kono
parents:
diff changeset
86 if (len (re.findall("error: forward declaration", line))) != 0:
kono
parents:
diff changeset
87 continue
kono
parents:
diff changeset
88 path = re.findall (ur"^(.*?):.*error: ", line)
kono
parents:
diff changeset
89 if len(path) != 1:
kono
parents:
diff changeset
90 continue
kono
parents:
diff changeset
91 if path[0][-2:] != ".h":
kono
parents:
diff changeset
92 continue
kono
parents:
diff changeset
93 fname = pretty_name (path[0])
kono
parents:
diff changeset
94 if fname in ignore or fname[0:3] == "gt_":
kono
parents:
diff changeset
95 continue
kono
parents:
diff changeset
96 sline.append (("error", msg, fname, incfrom))
kono
parents:
diff changeset
97
kono
parents:
diff changeset
98 print str(len(sline)) + " lines to process"
kono
parents:
diff changeset
99 lastline = "note"
kono
parents:
diff changeset
100 for line in sline:
kono
parents:
diff changeset
101 if line[0] != "note" and lastline[0] == "error":
kono
parents:
diff changeset
102 fname = lastline[2]
kono
parents:
diff changeset
103 msg = lastline[1]
kono
parents:
diff changeset
104 incfrom = lastline[3]
kono
parents:
diff changeset
105 string = ""
kono
parents:
diff changeset
106 ofname = fname
kono
parents:
diff changeset
107 if len(incfrom) != 0:
kono
parents:
diff changeset
108 for t in incfrom:
kono
parents:
diff changeset
109 string = string + t + " : "
kono
parents:
diff changeset
110 ee = (fname, t)
kono
parents:
diff changeset
111 if ee not in extra_edges:
kono
parents:
diff changeset
112 extra_edges.append (ee)
kono
parents:
diff changeset
113 fname = t
kono
parents:
diff changeset
114 print string
kono
parents:
diff changeset
115
kono
parents:
diff changeset
116 if hname not in nodes:
kono
parents:
diff changeset
117 nodes.append(hname)
kono
parents:
diff changeset
118 if fname not in nodes:
kono
parents:
diff changeset
119 nodes.append (ofname)
kono
parents:
diff changeset
120 for y in incfrom:
kono
parents:
diff changeset
121 if y not in nodes:
kono
parents:
diff changeset
122 nodes.append (y)
kono
parents:
diff changeset
123
kono
parents:
diff changeset
124
kono
parents:
diff changeset
125 if header_roots[hname].get(fname) == None:
kono
parents:
diff changeset
126 header_roots[hname][fname] = list()
kono
parents:
diff changeset
127 if msg not in header_roots[hname][fname]:
kono
parents:
diff changeset
128 print string + ofname + " : " +msg
kono
parents:
diff changeset
129 header_roots[hname][fname].append (msg)
kono
parents:
diff changeset
130 lastline = line;
kono
parents:
diff changeset
131
kono
parents:
diff changeset
132
kono
parents:
diff changeset
133 dotname = "graph.dot"
kono
parents:
diff changeset
134 graphname = "graph.png"
kono
parents:
diff changeset
135
kono
parents:
diff changeset
136
kono
parents:
diff changeset
137 def build_dot_file (file_list):
kono
parents:
diff changeset
138 output = open(dotname, "w")
kono
parents:
diff changeset
139 output.write ("digraph incweb {\n");
kono
parents:
diff changeset
140 for x in file_list:
kono
parents:
diff changeset
141 if os.path.exists (x) and x[-4:] == ".log":
kono
parents:
diff changeset
142 header = x[:-4]
kono
parents:
diff changeset
143 logfile = open(x).read().splitlines()
kono
parents:
diff changeset
144 process_log_file (header, logfile)
kono
parents:
diff changeset
145 elif os.path.exists (x + ".log"):
kono
parents:
diff changeset
146 logfile = open(x + ".log").read().splitlines()
kono
parents:
diff changeset
147 process_log_file (x, logfile)
kono
parents:
diff changeset
148
kono
parents:
diff changeset
149 for n in nodes:
kono
parents:
diff changeset
150 fn = unpretty(n)
kono
parents:
diff changeset
151 label = n + " [ label = \"" + fn + "\" ];"
kono
parents:
diff changeset
152 output.write (label + "\n")
kono
parents:
diff changeset
153 if os.path.exists (fn):
kono
parents:
diff changeset
154 h = open(fn).read().splitlines()
kono
parents:
diff changeset
155 for l in h:
kono
parents:
diff changeset
156 t = find_pound_include (l, True, False)
kono
parents:
diff changeset
157 if t != "":
kono
parents:
diff changeset
158 t = pretty_name (t)
kono
parents:
diff changeset
159 if t in ignore or t[-2:] != "_h":
kono
parents:
diff changeset
160 continue
kono
parents:
diff changeset
161 if t not in nodes:
kono
parents:
diff changeset
162 nodes.append (t)
kono
parents:
diff changeset
163 ee = (t, n)
kono
parents:
diff changeset
164 if ee not in extra_edges:
kono
parents:
diff changeset
165 extra_edges.append (ee)
kono
parents:
diff changeset
166
kono
parents:
diff changeset
167 depcount = list()
kono
parents:
diff changeset
168 for h in header_roots:
kono
parents:
diff changeset
169 for dep in header_roots[h]:
kono
parents:
diff changeset
170 label = " [ label = "+ str(len(header_roots[h][dep])) + " ];"
kono
parents:
diff changeset
171 string = h + " -> " + dep + label
kono
parents:
diff changeset
172 output.write (string + "\n");
kono
parents:
diff changeset
173 if verbose:
kono
parents:
diff changeset
174 depcount.append ((h, dep, len(header_roots[h][dep])))
kono
parents:
diff changeset
175
kono
parents:
diff changeset
176 for ee in extra_edges:
kono
parents:
diff changeset
177 string = ee[0] + " -> " + ee[1] + "[ color=red ];"
kono
parents:
diff changeset
178 output.write (string + "\n");
kono
parents:
diff changeset
179
kono
parents:
diff changeset
180
kono
parents:
diff changeset
181 if verbose:
kono
parents:
diff changeset
182 depcount.sort(key=lambda tup:tup[2])
kono
parents:
diff changeset
183 for x in depcount:
kono
parents:
diff changeset
184 print " ("+str(x[2])+ ") : " + x[0] + " -> " + x[1]
kono
parents:
diff changeset
185 if (x[2] <= verbosity):
kono
parents:
diff changeset
186 for l in header_roots[x[0]][x[1]]:
kono
parents:
diff changeset
187 print " " + l
kono
parents:
diff changeset
188
kono
parents:
diff changeset
189 output.write ("}\n");
kono
parents:
diff changeset
190
kono
parents:
diff changeset
191
kono
parents:
diff changeset
192 files = list()
kono
parents:
diff changeset
193 dohelp = False
kono
parents:
diff changeset
194 edge_thresh = 0
kono
parents:
diff changeset
195 for arg in sys.argv[1:]:
kono
parents:
diff changeset
196 if arg[0:2] == "-o":
kono
parents:
diff changeset
197 dotname = arg[2:]+".dot"
kono
parents:
diff changeset
198 graphname = arg[2:]+".png"
kono
parents:
diff changeset
199 elif arg[0:2] == "-h":
kono
parents:
diff changeset
200 dohelp = True
kono
parents:
diff changeset
201 elif arg[0:2] == "-v":
kono
parents:
diff changeset
202 verbose = True
kono
parents:
diff changeset
203 if len(arg) > 2:
kono
parents:
diff changeset
204 verbosity = int (arg[2:])
kono
parents:
diff changeset
205 if (verbosity == 9):
kono
parents:
diff changeset
206 verbosity = 9999
kono
parents:
diff changeset
207 elif arg[0:1] == "-":
kono
parents:
diff changeset
208 print "Unrecognized option " + arg
kono
parents:
diff changeset
209 dohelp = True
kono
parents:
diff changeset
210 else:
kono
parents:
diff changeset
211 files.append (arg)
kono
parents:
diff changeset
212
kono
parents:
diff changeset
213 if len(sys.argv) == 1:
kono
parents:
diff changeset
214 dohelp = True
kono
parents:
diff changeset
215
kono
parents:
diff changeset
216 if dohelp:
kono
parents:
diff changeset
217 print "Parses the log files from the reduce-headers tool to generate"
kono
parents:
diff changeset
218 print "dependency graphs for the include web for specified files."
kono
parents:
diff changeset
219 print "Usage: [-nnum] [-h] [-v[n]] [-ooutput] file1 [[file2] ... [filen]]"
kono
parents:
diff changeset
220 print " -ooutput : Specifies output to output.dot and output.png"
kono
parents:
diff changeset
221 print " Defaults to 'graph.dot and graph.png"
kono
parents:
diff changeset
222 print " -vn : verbose mode, shows the number of connections, and if n"
kono
parents:
diff changeset
223 print " is specified, show the messages if # < n. 9 is infinity"
kono
parents:
diff changeset
224 print " -h : help"
kono
parents:
diff changeset
225 else:
kono
parents:
diff changeset
226 print files
kono
parents:
diff changeset
227 build_dot_file (files)
kono
parents:
diff changeset
228 os.system ("dot -Tpng " + dotname + " -o" + graphname)
kono
parents:
diff changeset
229
kono
parents:
diff changeset
230