diff options
Diffstat (limited to 'tools/perf/scripts/python')
-rw-r--r-- | tools/perf/scripts/python/bin/export-to-postgresql-report | 15 | ||||
-rw-r--r-- | tools/perf/scripts/python/export-to-postgresql.py | 66 |
2 files changed, 75 insertions, 6 deletions
diff --git a/tools/perf/scripts/python/bin/export-to-postgresql-report b/tools/perf/scripts/python/bin/export-to-postgresql-report index a8fdd15f85bf..cd335b6e2a01 100644 --- a/tools/perf/scripts/python/bin/export-to-postgresql-report +++ b/tools/perf/scripts/python/bin/export-to-postgresql-report | |||
@@ -1,6 +1,6 @@ | |||
1 | #!/bin/bash | 1 | #!/bin/bash |
2 | # description: export perf data to a postgresql database | 2 | # description: export perf data to a postgresql database |
3 | # args: [database name] [columns] | 3 | # args: [database name] [columns] [calls] |
4 | n_args=0 | 4 | n_args=0 |
5 | for i in "$@" | 5 | for i in "$@" |
6 | do | 6 | do |
@@ -9,11 +9,16 @@ do | |||
9 | fi | 9 | fi |
10 | n_args=$(( $n_args + 1 )) | 10 | n_args=$(( $n_args + 1 )) |
11 | done | 11 | done |
12 | if [ "$n_args" -gt 2 ] ; then | 12 | if [ "$n_args" -gt 3 ] ; then |
13 | echo "usage: export-to-postgresql-report [database name] [columns]" | 13 | echo "usage: export-to-postgresql-report [database name] [columns] [calls]" |
14 | exit | 14 | exit |
15 | fi | 15 | fi |
16 | if [ "$n_args" -gt 1 ] ; then | 16 | if [ "$n_args" -gt 2 ] ; then |
17 | dbname=$1 | ||
18 | columns=$2 | ||
19 | calls=$3 | ||
20 | shift 3 | ||
21 | elif [ "$n_args" -gt 1 ] ; then | ||
17 | dbname=$1 | 22 | dbname=$1 |
18 | columns=$2 | 23 | columns=$2 |
19 | shift 2 | 24 | shift 2 |
@@ -21,4 +26,4 @@ elif [ "$n_args" -gt 0 ] ; then | |||
21 | dbname=$1 | 26 | dbname=$1 |
22 | shift | 27 | shift |
23 | fi | 28 | fi |
24 | perf script $@ -s "$PERF_EXEC_PATH"/scripts/python/export-to-postgresql.py $dbname $columns | 29 | perf script $@ -s "$PERF_EXEC_PATH"/scripts/python/export-to-postgresql.py $dbname $columns $calls |
diff --git a/tools/perf/scripts/python/export-to-postgresql.py b/tools/perf/scripts/python/export-to-postgresql.py index bb79aecccf58..4cdafd880074 100644 --- a/tools/perf/scripts/python/export-to-postgresql.py +++ b/tools/perf/scripts/python/export-to-postgresql.py | |||
@@ -40,10 +40,12 @@ sys.path.append(os.environ['PERF_EXEC_PATH'] + \ | |||
40 | #from Core import * | 40 | #from Core import * |
41 | 41 | ||
42 | perf_db_export_mode = True | 42 | perf_db_export_mode = True |
43 | perf_db_export_calls = False | ||
43 | 44 | ||
44 | def usage(): | 45 | def usage(): |
45 | print >> sys.stderr, "Usage is: export-to-postgresql.py <database name> [<columns>]" | 46 | print >> sys.stderr, "Usage is: export-to-postgresql.py <database name> [<columns>] [<calls>]" |
46 | print >> sys.stderr, "where: columns 'all' or 'branches'" | 47 | print >> sys.stderr, "where: columns 'all' or 'branches'" |
48 | print >> sys.stderr, " calls 'calls' => create calls table" | ||
47 | raise Exception("Too few arguments") | 49 | raise Exception("Too few arguments") |
48 | 50 | ||
49 | if (len(sys.argv) < 2): | 51 | if (len(sys.argv) < 2): |
@@ -61,6 +63,12 @@ if columns not in ("all", "branches"): | |||
61 | 63 | ||
62 | branches = (columns == "branches") | 64 | branches = (columns == "branches") |
63 | 65 | ||
66 | if (len(sys.argv) >= 4): | ||
67 | if (sys.argv[3] == "calls"): | ||
68 | perf_db_export_calls = True | ||
69 | else: | ||
70 | usage() | ||
71 | |||
64 | output_dir_name = os.getcwd() + "/" + dbname + "-perf-data" | 72 | output_dir_name = os.getcwd() + "/" + dbname + "-perf-data" |
65 | os.mkdir(output_dir_name) | 73 | os.mkdir(output_dir_name) |
66 | 74 | ||
@@ -170,6 +178,25 @@ else: | |||
170 | 'branch_type integer,' | 178 | 'branch_type integer,' |
171 | 'in_tx boolean)') | 179 | 'in_tx boolean)') |
172 | 180 | ||
181 | if perf_db_export_calls: | ||
182 | do_query(query, 'CREATE TABLE call_paths (' | ||
183 | 'id bigint NOT NULL,' | ||
184 | 'parent_id bigint,' | ||
185 | 'symbol_id bigint,' | ||
186 | 'ip bigint)') | ||
187 | do_query(query, 'CREATE TABLE calls (' | ||
188 | 'id bigint NOT NULL,' | ||
189 | 'thread_id bigint,' | ||
190 | 'comm_id bigint,' | ||
191 | 'call_path_id bigint,' | ||
192 | 'call_time bigint,' | ||
193 | 'return_time bigint,' | ||
194 | 'branch_count bigint,' | ||
195 | 'call_id bigint,' | ||
196 | 'return_id bigint,' | ||
197 | 'parent_call_path_id bigint,' | ||
198 | 'flags integer)') | ||
199 | |||
173 | do_query(query, 'CREATE VIEW samples_view AS ' | 200 | do_query(query, 'CREATE VIEW samples_view AS ' |
174 | 'SELECT ' | 201 | 'SELECT ' |
175 | 'id,' | 202 | 'id,' |
@@ -246,6 +273,9 @@ dso_file = open_output_file("dso_table.bin") | |||
246 | symbol_file = open_output_file("symbol_table.bin") | 273 | symbol_file = open_output_file("symbol_table.bin") |
247 | branch_type_file = open_output_file("branch_type_table.bin") | 274 | branch_type_file = open_output_file("branch_type_table.bin") |
248 | sample_file = open_output_file("sample_table.bin") | 275 | sample_file = open_output_file("sample_table.bin") |
276 | if perf_db_export_calls: | ||
277 | call_path_file = open_output_file("call_path_table.bin") | ||
278 | call_file = open_output_file("call_table.bin") | ||
249 | 279 | ||
250 | def trace_begin(): | 280 | def trace_begin(): |
251 | print datetime.datetime.today(), "Writing to intermediate files..." | 281 | print datetime.datetime.today(), "Writing to intermediate files..." |
@@ -256,6 +286,9 @@ def trace_begin(): | |||
256 | comm_table(0, "unknown") | 286 | comm_table(0, "unknown") |
257 | dso_table(0, 0, "unknown", "unknown", "") | 287 | dso_table(0, 0, "unknown", "unknown", "") |
258 | symbol_table(0, 0, 0, 0, 0, "unknown") | 288 | symbol_table(0, 0, 0, 0, 0, "unknown") |
289 | sample_table(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0) | ||
290 | if perf_db_export_calls: | ||
291 | call_path_table(0, 0, 0, 0) | ||
259 | 292 | ||
260 | unhandled_count = 0 | 293 | unhandled_count = 0 |
261 | 294 | ||
@@ -270,6 +303,9 @@ def trace_end(): | |||
270 | copy_output_file(symbol_file, "symbols") | 303 | copy_output_file(symbol_file, "symbols") |
271 | copy_output_file(branch_type_file, "branch_types") | 304 | copy_output_file(branch_type_file, "branch_types") |
272 | copy_output_file(sample_file, "samples") | 305 | copy_output_file(sample_file, "samples") |
306 | if perf_db_export_calls: | ||
307 | copy_output_file(call_path_file, "call_paths") | ||
308 | copy_output_file(call_file, "calls") | ||
273 | 309 | ||
274 | print datetime.datetime.today(), "Removing intermediate files..." | 310 | print datetime.datetime.today(), "Removing intermediate files..." |
275 | remove_output_file(evsel_file) | 311 | remove_output_file(evsel_file) |
@@ -281,6 +317,9 @@ def trace_end(): | |||
281 | remove_output_file(symbol_file) | 317 | remove_output_file(symbol_file) |
282 | remove_output_file(branch_type_file) | 318 | remove_output_file(branch_type_file) |
283 | remove_output_file(sample_file) | 319 | remove_output_file(sample_file) |
320 | if perf_db_export_calls: | ||
321 | remove_output_file(call_path_file) | ||
322 | remove_output_file(call_file) | ||
284 | os.rmdir(output_dir_name) | 323 | os.rmdir(output_dir_name) |
285 | print datetime.datetime.today(), "Adding primary keys" | 324 | print datetime.datetime.today(), "Adding primary keys" |
286 | do_query(query, 'ALTER TABLE selected_events ADD PRIMARY KEY (id)') | 325 | do_query(query, 'ALTER TABLE selected_events ADD PRIMARY KEY (id)') |
@@ -292,6 +331,9 @@ def trace_end(): | |||
292 | do_query(query, 'ALTER TABLE symbols ADD PRIMARY KEY (id)') | 331 | do_query(query, 'ALTER TABLE symbols ADD PRIMARY KEY (id)') |
293 | do_query(query, 'ALTER TABLE branch_types ADD PRIMARY KEY (id)') | 332 | do_query(query, 'ALTER TABLE branch_types ADD PRIMARY KEY (id)') |
294 | do_query(query, 'ALTER TABLE samples ADD PRIMARY KEY (id)') | 333 | do_query(query, 'ALTER TABLE samples ADD PRIMARY KEY (id)') |
334 | if perf_db_export_calls: | ||
335 | do_query(query, 'ALTER TABLE call_paths ADD PRIMARY KEY (id)') | ||
336 | do_query(query, 'ALTER TABLE calls ADD PRIMARY KEY (id)') | ||
295 | 337 | ||
296 | print datetime.datetime.today(), "Adding foreign keys" | 338 | print datetime.datetime.today(), "Adding foreign keys" |
297 | do_query(query, 'ALTER TABLE threads ' | 339 | do_query(query, 'ALTER TABLE threads ' |
@@ -313,6 +355,18 @@ def trace_end(): | |||
313 | 'ADD CONSTRAINT symbolfk FOREIGN KEY (symbol_id) REFERENCES symbols (id),' | 355 | 'ADD CONSTRAINT symbolfk FOREIGN KEY (symbol_id) REFERENCES symbols (id),' |
314 | 'ADD CONSTRAINT todsofk FOREIGN KEY (to_dso_id) REFERENCES dsos (id),' | 356 | 'ADD CONSTRAINT todsofk FOREIGN KEY (to_dso_id) REFERENCES dsos (id),' |
315 | 'ADD CONSTRAINT tosymbolfk FOREIGN KEY (to_symbol_id) REFERENCES symbols (id)') | 357 | 'ADD CONSTRAINT tosymbolfk FOREIGN KEY (to_symbol_id) REFERENCES symbols (id)') |
358 | if perf_db_export_calls: | ||
359 | do_query(query, 'ALTER TABLE call_paths ' | ||
360 | 'ADD CONSTRAINT parentfk FOREIGN KEY (parent_id) REFERENCES call_paths (id),' | ||
361 | 'ADD CONSTRAINT symbolfk FOREIGN KEY (symbol_id) REFERENCES symbols (id)') | ||
362 | do_query(query, 'ALTER TABLE calls ' | ||
363 | 'ADD CONSTRAINT threadfk FOREIGN KEY (thread_id) REFERENCES threads (id),' | ||
364 | 'ADD CONSTRAINT commfk FOREIGN KEY (comm_id) REFERENCES comms (id),' | ||
365 | 'ADD CONSTRAINT call_pathfk FOREIGN KEY (call_path_id) REFERENCES call_paths (id),' | ||
366 | 'ADD CONSTRAINT callfk FOREIGN KEY (call_id) REFERENCES samples (id),' | ||
367 | 'ADD CONSTRAINT returnfk FOREIGN KEY (return_id) REFERENCES samples (id),' | ||
368 | 'ADD CONSTRAINT parent_call_pathfk FOREIGN KEY (parent_call_path_id) REFERENCES call_paths (id)') | ||
369 | do_query(query, 'CREATE INDEX pcpid_idx ON calls (parent_call_path_id)') | ||
316 | 370 | ||
317 | if (unhandled_count): | 371 | if (unhandled_count): |
318 | print datetime.datetime.today(), "Warning: ", unhandled_count, " unhandled events" | 372 | print datetime.datetime.today(), "Warning: ", unhandled_count, " unhandled events" |
@@ -378,3 +432,13 @@ def sample_table(sample_id, evsel_id, machine_id, thread_id, comm_id, dso_id, sy | |||
378 | else: | 432 | else: |
379 | value = struct.pack("!hiqiqiqiqiqiqiqiqiqiqiiiqiqiqiqiqiqiqiqiiiB", 21, 8, sample_id, 8, evsel_id, 8, machine_id, 8, thread_id, 8, comm_id, 8, dso_id, 8, symbol_id, 8, sym_offset, 8, ip, 8, time, 4, cpu, 8, to_dso_id, 8, to_symbol_id, 8, to_sym_offset, 8, to_ip, 8, period, 8, weight, 8, transaction, 8, data_src, 4, branch_type, 1, in_tx) | 433 | value = struct.pack("!hiqiqiqiqiqiqiqiqiqiqiiiqiqiqiqiqiqiqiqiiiB", 21, 8, sample_id, 8, evsel_id, 8, machine_id, 8, thread_id, 8, comm_id, 8, dso_id, 8, symbol_id, 8, sym_offset, 8, ip, 8, time, 4, cpu, 8, to_dso_id, 8, to_symbol_id, 8, to_sym_offset, 8, to_ip, 8, period, 8, weight, 8, transaction, 8, data_src, 4, branch_type, 1, in_tx) |
380 | sample_file.write(value) | 434 | sample_file.write(value) |
435 | |||
436 | def call_path_table(cp_id, parent_id, symbol_id, ip, *x): | ||
437 | fmt = "!hiqiqiqiq" | ||
438 | value = struct.pack(fmt, 4, 8, cp_id, 8, parent_id, 8, symbol_id, 8, ip) | ||
439 | call_path_file.write(value) | ||
440 | |||
441 | def call_return_table(cr_id, thread_id, comm_id, call_path_id, call_time, return_time, branch_count, call_id, return_id, parent_call_path_id, flags, *x): | ||
442 | fmt = "!hiqiqiqiqiqiqiqiqiqiqii" | ||
443 | value = struct.pack(fmt, 11, 8, cr_id, 8, thread_id, 8, comm_id, 8, call_path_id, 8, call_time, 8, return_time, 8, branch_count, 8, call_id, 8, return_id, 8, parent_call_path_id, 4, flags) | ||
444 | call_file.write(value) | ||