ruby-prof 1.7.2 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/{CHANGES → CHANGELOG.md} +112 -178
- data/README.md +5 -5
- data/bin/ruby-prof +1 -4
- data/docs/advanced-usage.md +132 -0
- data/docs/alternatives.md +98 -0
- data/docs/architecture.md +122 -0
- data/docs/best-practices.md +27 -0
- data/docs/getting-started.md +130 -0
- data/docs/history.md +11 -0
- data/docs/index.md +45 -0
- data/docs/profiling-rails.md +64 -0
- data/docs/public/examples/example.rb +33 -0
- data/docs/public/examples/generate_reports.rb +92 -0
- data/docs/public/examples/reports/call_info.txt +27 -0
- data/docs/public/examples/reports/call_stack.html +835 -0
- data/docs/public/examples/reports/callgrind.out +150 -0
- data/docs/public/examples/reports/flame_graph.html +408 -0
- data/docs/public/examples/reports/flat.txt +45 -0
- data/docs/public/examples/reports/graph.dot +129 -0
- data/docs/public/examples/reports/graph.html +1319 -0
- data/docs/public/examples/reports/graph.txt +100 -0
- data/docs/public/examples/reports/graphviz_viewer.html +1 -0
- data/docs/public/images/call_stack.png +0 -0
- data/docs/public/images/class_diagram.png +0 -0
- data/docs/public/images/dot_printer.png +0 -0
- data/docs/public/images/flame_graph.png +0 -0
- data/docs/public/images/flat.png +0 -0
- data/docs/public/images/graph.png +0 -0
- data/docs/public/images/graph_html.png +0 -0
- data/docs/public/images/ruby-prof-logo.svg +1 -0
- data/docs/reports.md +150 -0
- data/docs/stylesheets/extra.css +80 -0
- data/ext/ruby_prof/rp_allocation.c +0 -15
- data/ext/ruby_prof/rp_allocation.h +29 -33
- data/ext/ruby_prof/rp_call_tree.c +3 -0
- data/ext/ruby_prof/rp_call_tree.h +1 -4
- data/ext/ruby_prof/rp_call_trees.h +1 -4
- data/ext/ruby_prof/rp_measurement.c +0 -5
- data/ext/ruby_prof/rp_measurement.h +49 -53
- data/ext/ruby_prof/rp_method.c +3 -0
- data/ext/ruby_prof/rp_method.h +1 -4
- data/ext/ruby_prof/rp_profile.c +1 -1
- data/ext/ruby_prof/rp_profile.h +1 -5
- data/ext/ruby_prof/rp_stack.h +50 -53
- data/ext/ruby_prof/rp_thread.h +1 -4
- data/ext/ruby_prof/ruby_prof.h +1 -4
- data/ext/ruby_prof/vc/ruby_prof.vcxproj +7 -8
- data/lib/ruby-prof/assets/call_stack_printer.html.erb +746 -711
- data/lib/ruby-prof/assets/flame_graph_printer.html.erb +412 -0
- data/lib/ruby-prof/assets/graph_printer.html.erb +355 -355
- data/lib/ruby-prof/call_tree.rb +57 -57
- data/lib/ruby-prof/call_tree_visitor.rb +36 -36
- data/lib/ruby-prof/measurement.rb +17 -17
- data/lib/ruby-prof/printers/abstract_printer.rb +19 -33
- data/lib/ruby-prof/printers/call_info_printer.rb +53 -53
- data/lib/ruby-prof/printers/call_stack_printer.rb +168 -180
- data/lib/ruby-prof/printers/call_tree_printer.rb +132 -145
- data/lib/ruby-prof/printers/dot_printer.rb +177 -132
- data/lib/ruby-prof/printers/flame_graph_printer.rb +79 -0
- data/lib/ruby-prof/printers/flat_printer.rb +52 -52
- data/lib/ruby-prof/printers/graph_html_printer.rb +62 -63
- data/lib/ruby-prof/printers/graph_printer.rb +112 -113
- data/lib/ruby-prof/printers/multi_printer.rb +134 -127
- data/lib/ruby-prof/profile.rb +13 -0
- data/lib/ruby-prof/rack.rb +114 -105
- data/lib/ruby-prof/task.rb +147 -147
- data/lib/ruby-prof/thread.rb +20 -20
- data/lib/ruby-prof/version.rb +1 -1
- data/lib/ruby-prof.rb +50 -52
- data/lib/unprof.rb +10 -10
- data/ruby-prof.gemspec +5 -5
- data/test/abstract_printer_test.rb +25 -27
- data/test/alias_test.rb +203 -117
- data/test/call_tree_builder.rb +126 -126
- data/test/call_tree_visitor_test.rb +27 -27
- data/test/call_trees_test.rb +66 -66
- data/test/duplicate_names_test.rb +32 -32
- data/test/dynamic_method_test.rb +50 -50
- data/test/exceptions_test.rb +24 -24
- data/test/exclude_threads_test.rb +48 -48
- data/test/fiber_test.rb +72 -72
- data/test/inverse_call_tree_test.rb +174 -174
- data/test/line_number_test.rb +138 -1
- data/test/marshal_test.rb +144 -145
- data/test/measure_allocations.rb +26 -26
- data/test/measure_allocations_test.rb +340 -1
- data/test/measure_process_time_test.rb +3098 -3142
- data/test/measure_times.rb +56 -56
- data/test/measure_wall_time_test.rb +511 -372
- data/test/measurement_test.rb +82 -82
- data/test/merge_test.rb +48 -48
- data/test/multi_printer_test.rb +52 -66
- data/test/no_method_class_test.rb +15 -15
- data/test/pause_resume_test.rb +171 -171
- data/test/prime.rb +54 -54
- data/test/prime_script.rb +5 -5
- data/test/printer_call_stack_test.rb +28 -27
- data/test/printer_call_tree_test.rb +30 -30
- data/test/printer_flame_graph_test.rb +82 -0
- data/test/printer_flat_test.rb +99 -99
- data/test/printer_graph_html_test.rb +62 -59
- data/test/printer_graph_test.rb +42 -40
- data/test/printers_test.rb +28 -44
- data/test/printing_recursive_graph_test.rb +81 -81
- data/test/profile_test.rb +101 -101
- data/test/rack_test.rb +103 -93
- data/test/recursive_test.rb +139 -139
- data/test/scheduler.rb +4 -0
- data/test/singleton_test.rb +39 -38
- data/test/stack_printer_test.rb +61 -61
- data/test/start_stop_test.rb +106 -106
- data/test/test_helper.rb +4 -0
- data/test/thread_test.rb +29 -29
- data/test/unique_call_path_test.rb +123 -123
- data/test/yarv_test.rb +56 -56
- metadata +53 -11
- data/ext/ruby_prof/rp_measure_memory.c +0 -46
- data/lib/ruby-prof/compatibility.rb +0 -113
- data/test/compatibility_test.rb +0 -49
- data/test/measure_memory_test.rb +0 -1193
data/lib/ruby-prof/call_tree.rb
CHANGED
|
@@ -1,57 +1,57 @@
|
|
|
1
|
-
# encoding: utf-8
|
|
2
|
-
|
|
3
|
-
module RubyProf
|
|
4
|
-
# The CallTree class is used to track the relationships between methods. It is a helper class used by
|
|
5
|
-
# RubyProf::MethodInfo to keep track of which methods called a given method and which methods a given
|
|
6
|
-
# method called. Each CallTree has a parent and target method. You cannot create a CallTree object directly,
|
|
7
|
-
# they are generated while running a profile.
|
|
8
|
-
class CallTree
|
|
9
|
-
# The number of times the parent method called the target method
|
|
10
|
-
def called
|
|
11
|
-
self.measurement.called
|
|
12
|
-
end
|
|
13
|
-
|
|
14
|
-
# The total time resulting from the parent method calling the target method
|
|
15
|
-
def total_time
|
|
16
|
-
self.measurement.total_time
|
|
17
|
-
end
|
|
18
|
-
|
|
19
|
-
# The self time (of the parent) resulting from the parent method calling the target method
|
|
20
|
-
def self_time
|
|
21
|
-
self.measurement.self_time
|
|
22
|
-
end
|
|
23
|
-
|
|
24
|
-
# The wait time (of the parent) resulting from the parent method calling the target method
|
|
25
|
-
def wait_time
|
|
26
|
-
self.measurement.wait_time
|
|
27
|
-
end
|
|
28
|
-
|
|
29
|
-
# The time spent in child methods resulting from the parent method calling the target method
|
|
30
|
-
def children_time
|
|
31
|
-
self.total_time - self.self_time - self.wait_time
|
|
32
|
-
end
|
|
33
|
-
|
|
34
|
-
# Compares two CallTree instances. The comparison is based on the CallTree#parent, CallTree#target,
|
|
35
|
-
# and total time.
|
|
36
|
-
def <=>(other)
|
|
37
|
-
if self.target == other.target && self.parent == other.parent
|
|
38
|
-
0
|
|
39
|
-
elsif self.total_time < other.total_time
|
|
40
|
-
-1
|
|
41
|
-
elsif self.total_time > other.total_time
|
|
42
|
-
1
|
|
43
|
-
else
|
|
44
|
-
self.target.full_name <=> other.target.full_name
|
|
45
|
-
end
|
|
46
|
-
end
|
|
47
|
-
|
|
48
|
-
# :nodoc:
|
|
49
|
-
def to_s
|
|
50
|
-
"<#{self.class.name} - #{self.target.full_name}>"
|
|
51
|
-
end
|
|
52
|
-
|
|
53
|
-
def inspect
|
|
54
|
-
self.to_s
|
|
55
|
-
end
|
|
56
|
-
end
|
|
57
|
-
end
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
|
|
3
|
+
module RubyProf
|
|
4
|
+
# The CallTree class is used to track the relationships between methods. It is a helper class used by
|
|
5
|
+
# RubyProf::MethodInfo to keep track of which methods called a given method and which methods a given
|
|
6
|
+
# method called. Each CallTree has a parent and target method. You cannot create a CallTree object directly,
|
|
7
|
+
# they are generated while running a profile.
|
|
8
|
+
class CallTree
|
|
9
|
+
# The number of times the parent method called the target method
|
|
10
|
+
def called
|
|
11
|
+
self.measurement.called
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
# The total time resulting from the parent method calling the target method
|
|
15
|
+
def total_time
|
|
16
|
+
self.measurement.total_time
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
# The self time (of the parent) resulting from the parent method calling the target method
|
|
20
|
+
def self_time
|
|
21
|
+
self.measurement.self_time
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
# The wait time (of the parent) resulting from the parent method calling the target method
|
|
25
|
+
def wait_time
|
|
26
|
+
self.measurement.wait_time
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
# The time spent in child methods resulting from the parent method calling the target method
|
|
30
|
+
def children_time
|
|
31
|
+
self.total_time - self.self_time - self.wait_time
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
# Compares two CallTree instances. The comparison is based on the CallTree#parent, CallTree#target,
|
|
35
|
+
# and total time.
|
|
36
|
+
def <=>(other)
|
|
37
|
+
if self.target == other.target && self.parent == other.parent
|
|
38
|
+
0
|
|
39
|
+
elsif self.total_time < other.total_time
|
|
40
|
+
-1
|
|
41
|
+
elsif self.total_time > other.total_time
|
|
42
|
+
1
|
|
43
|
+
else
|
|
44
|
+
self.target.full_name <=> other.target.full_name
|
|
45
|
+
end
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
# :nodoc:
|
|
49
|
+
def to_s
|
|
50
|
+
"<#{self.class.name} - #{self.target.full_name}>"
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
def inspect
|
|
54
|
+
self.to_s
|
|
55
|
+
end
|
|
56
|
+
end
|
|
57
|
+
end
|
|
@@ -1,36 +1,36 @@
|
|
|
1
|
-
module RubyProf
|
|
2
|
-
# The call info visitor class does a depth-first traversal across a
|
|
3
|
-
# list of call infos. At each call_tree node, the visitor executes
|
|
4
|
-
# the block provided in the #visit method. The block is passed two
|
|
5
|
-
# parameters, the event and the call_tree instance. Event will be
|
|
6
|
-
# either :enter or :exit.
|
|
7
|
-
#
|
|
8
|
-
# visitor = RubyProf::CallTreeVisitor.new(result.threads.first.call_tree)
|
|
9
|
-
#
|
|
10
|
-
# method_names = Array.new
|
|
11
|
-
#
|
|
12
|
-
# visitor.visit do |call_tree, event|
|
|
13
|
-
# method_names << call_tree.target.full_name if event == :enter
|
|
14
|
-
# end
|
|
15
|
-
#
|
|
16
|
-
# puts method_names
|
|
17
|
-
class CallTreeVisitor
|
|
18
|
-
def initialize(call_tree)
|
|
19
|
-
@call_tree = call_tree
|
|
20
|
-
end
|
|
21
|
-
|
|
22
|
-
def visit(&block)
|
|
23
|
-
visit_call_tree(@call_tree, &block)
|
|
24
|
-
end
|
|
25
|
-
|
|
26
|
-
private
|
|
27
|
-
|
|
28
|
-
def visit_call_tree(call_tree, &block)
|
|
29
|
-
yield call_tree, :enter
|
|
30
|
-
call_tree.children.each do |child|
|
|
31
|
-
visit_call_tree(child, &block)
|
|
32
|
-
end
|
|
33
|
-
yield call_tree, :exit
|
|
34
|
-
end
|
|
35
|
-
end
|
|
36
|
-
end
|
|
1
|
+
module RubyProf
|
|
2
|
+
# The call info visitor class does a depth-first traversal across a
|
|
3
|
+
# list of call infos. At each call_tree node, the visitor executes
|
|
4
|
+
# the block provided in the #visit method. The block is passed two
|
|
5
|
+
# parameters, the event and the call_tree instance. Event will be
|
|
6
|
+
# either :enter or :exit.
|
|
7
|
+
#
|
|
8
|
+
# visitor = RubyProf::CallTreeVisitor.new(result.threads.first.call_tree)
|
|
9
|
+
#
|
|
10
|
+
# method_names = Array.new
|
|
11
|
+
#
|
|
12
|
+
# visitor.visit do |call_tree, event|
|
|
13
|
+
# method_names << call_tree.target.full_name if event == :enter
|
|
14
|
+
# end
|
|
15
|
+
#
|
|
16
|
+
# puts method_names
|
|
17
|
+
class CallTreeVisitor
|
|
18
|
+
def initialize(call_tree)
|
|
19
|
+
@call_tree = call_tree
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
def visit(&block)
|
|
23
|
+
visit_call_tree(@call_tree, &block)
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
private
|
|
27
|
+
|
|
28
|
+
def visit_call_tree(call_tree, &block)
|
|
29
|
+
yield call_tree, :enter
|
|
30
|
+
call_tree.children.each do |child|
|
|
31
|
+
visit_call_tree(child, &block)
|
|
32
|
+
end
|
|
33
|
+
yield call_tree, :exit
|
|
34
|
+
end
|
|
35
|
+
end
|
|
36
|
+
end
|
|
@@ -1,17 +1,17 @@
|
|
|
1
|
-
module RubyProf
|
|
2
|
-
# The Measurement class is a helper class used by RubyProf::MethodInfo to store information about the method.
|
|
3
|
-
# You cannot create a CallTree object directly, they are generated while running a profile.
|
|
4
|
-
class Measurement
|
|
5
|
-
def children_time
|
|
6
|
-
self.total_time - self.self_time - self.wait_time
|
|
7
|
-
end
|
|
8
|
-
|
|
9
|
-
def to_s
|
|
10
|
-
"c: #{called}, tt: #{total_time}, st: #{self_time}"
|
|
11
|
-
end
|
|
12
|
-
|
|
13
|
-
def inspect
|
|
14
|
-
super + "(#{self.to_s})"
|
|
15
|
-
end
|
|
16
|
-
end
|
|
17
|
-
end
|
|
1
|
+
module RubyProf
|
|
2
|
+
# The Measurement class is a helper class used by RubyProf::MethodInfo to store information about the method.
|
|
3
|
+
# You cannot create a CallTree object directly, they are generated while running a profile.
|
|
4
|
+
class Measurement
|
|
5
|
+
def children_time
|
|
6
|
+
self.total_time - self.self_time - self.wait_time
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
def to_s
|
|
10
|
+
"c: #{called}, tt: #{total_time}, st: #{self_time}"
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
def inspect
|
|
14
|
+
super + "(#{self.to_s})"
|
|
15
|
+
end
|
|
16
|
+
end
|
|
17
|
+
end
|
|
@@ -17,60 +17,46 @@ module RubyProf
|
|
|
17
17
|
@output = nil
|
|
18
18
|
end
|
|
19
19
|
|
|
20
|
-
|
|
21
|
-
def min_percent
|
|
22
|
-
@options[:min_percent] || 0
|
|
23
|
-
end
|
|
24
|
-
|
|
25
|
-
# Returns the max_percent of time a method can take to be included in a profiling report
|
|
26
|
-
def max_percent
|
|
27
|
-
@options[:max_percent] || 100
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
# Returns the method to filter methods by (when using min_percent and max_percent)
|
|
31
|
-
def filter_by
|
|
32
|
-
@options[:filter_by] || :self_time
|
|
33
|
-
end
|
|
20
|
+
attr_reader :min_percent, :max_percent, :filter_by, :sort_method
|
|
34
21
|
|
|
35
22
|
# Returns the time format used to show when a profile was run
|
|
36
23
|
def time_format
|
|
37
24
|
'%A, %B %-d at %l:%M:%S %p (%Z)'
|
|
38
25
|
end
|
|
39
26
|
|
|
40
|
-
# Returns how profile data should be sorted
|
|
41
|
-
def sort_method
|
|
42
|
-
@options[:sort_method]
|
|
43
|
-
end
|
|
44
|
-
|
|
45
27
|
# Prints a report to the provided output.
|
|
46
28
|
#
|
|
47
29
|
# output - Any IO object, including STDOUT or a file.
|
|
48
30
|
# The default value is STDOUT.
|
|
49
31
|
#
|
|
50
|
-
#
|
|
51
|
-
#
|
|
52
|
-
#
|
|
53
|
-
# :min_percent - Number 0 to 100 that specifies the minimum
|
|
32
|
+
# Keyword arguments:
|
|
33
|
+
# min_percent - Number 0 to 100 that specifies the minimum
|
|
54
34
|
# %self (the methods self time divided by the
|
|
55
35
|
# overall total time) that a method must take
|
|
56
36
|
# for it to be printed out in the report.
|
|
57
37
|
# Default value is 0.
|
|
58
38
|
#
|
|
59
|
-
#
|
|
39
|
+
# max_percent - Number 0 to 100 that specifies the maximum
|
|
40
|
+
# %self for methods to include.
|
|
41
|
+
# Default value is 100.
|
|
42
|
+
#
|
|
43
|
+
# filter_by - Which time metric to use when applying
|
|
44
|
+
# min_percent and max_percent filters.
|
|
45
|
+
# Default value is :self_time.
|
|
46
|
+
#
|
|
47
|
+
# sort_method - Specifies method used for sorting method infos.
|
|
60
48
|
# Available values are :total_time, :self_time,
|
|
61
|
-
# :wait_time, :children_time
|
|
62
|
-
# Default value
|
|
63
|
-
def print(output = STDOUT,
|
|
49
|
+
# :wait_time, :children_time.
|
|
50
|
+
# Default value depends on the printer.
|
|
51
|
+
def print(output = STDOUT, min_percent: 0, max_percent: 100, filter_by: :self_time, sort_method: nil, **)
|
|
64
52
|
@output = output
|
|
65
|
-
|
|
53
|
+
@min_percent = min_percent
|
|
54
|
+
@max_percent = max_percent
|
|
55
|
+
@filter_by = filter_by
|
|
56
|
+
@sort_method = sort_method
|
|
66
57
|
print_threads
|
|
67
58
|
end
|
|
68
59
|
|
|
69
|
-
# :nodoc:
|
|
70
|
-
def setup_options(options = {})
|
|
71
|
-
@options = options
|
|
72
|
-
end
|
|
73
|
-
|
|
74
60
|
def method_location(method)
|
|
75
61
|
if method.source_file
|
|
76
62
|
"#{method.source_file}:#{method.line}"
|
|
@@ -1,53 +1,53 @@
|
|
|
1
|
-
# encoding: utf-8
|
|
2
|
-
|
|
3
|
-
module RubyProf
|
|
4
|
-
# Prints out the call graph based on CallTree instances. This
|
|
5
|
-
# is mainly for debugging purposes as it provides access into
|
|
6
|
-
# into RubyProf's internals.
|
|
7
|
-
#
|
|
8
|
-
# To use the printer:
|
|
9
|
-
#
|
|
10
|
-
# result = RubyProf.profile do
|
|
11
|
-
# [code to profile]
|
|
12
|
-
# end
|
|
13
|
-
#
|
|
14
|
-
# printer = RubyProf::CallInfoPrinter.new(result)
|
|
15
|
-
# printer.print(STDOUT)
|
|
16
|
-
class CallInfoPrinter < AbstractPrinter
|
|
17
|
-
TIME_WIDTH = 0
|
|
18
|
-
|
|
19
|
-
private
|
|
20
|
-
|
|
21
|
-
def print_header(thread)
|
|
22
|
-
@output << "----------------------------------------------------\n"
|
|
23
|
-
@output << "Thread ID: #{thread.id}\n"
|
|
24
|
-
@output << "Fiber ID: #{thread.fiber_id}\n"
|
|
25
|
-
@output << "Total Time: #{thread.total_time}\n"
|
|
26
|
-
@output << "Sort by: #{sort_method}\n"
|
|
27
|
-
@output << "\n"
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
def print_methods(thread)
|
|
31
|
-
visitor = CallTreeVisitor.new(thread.call_tree)
|
|
32
|
-
|
|
33
|
-
visitor.visit do |call_tree, event|
|
|
34
|
-
if event == :enter
|
|
35
|
-
@output << " " * call_tree.depth
|
|
36
|
-
@output << call_tree.target.full_name
|
|
37
|
-
@output << " ("
|
|
38
|
-
@output << "tt:#{sprintf("%#{TIME_WIDTH}.2f", call_tree.total_time)}, "
|
|
39
|
-
@output << "st:#{sprintf("%#{TIME_WIDTH}.2f", call_tree.self_time)}, "
|
|
40
|
-
@output << "wt:#{sprintf("%#{TIME_WIDTH}.2f", call_tree.wait_time)}, "
|
|
41
|
-
@output << "ct:#{sprintf("%#{TIME_WIDTH}.2f", call_tree.children_time)}, "
|
|
42
|
-
@output << "call:#{call_tree.called}, "
|
|
43
|
-
@output << ")"
|
|
44
|
-
@output << "\n"
|
|
45
|
-
end
|
|
46
|
-
end
|
|
47
|
-
end
|
|
48
|
-
|
|
49
|
-
def print_footer(thread)
|
|
50
|
-
@output << "\n" << "\n"
|
|
51
|
-
end
|
|
52
|
-
end
|
|
53
|
-
end
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
|
|
3
|
+
module RubyProf
|
|
4
|
+
# Prints out the call graph based on CallTree instances. This
|
|
5
|
+
# is mainly for debugging purposes as it provides access into
|
|
6
|
+
# into RubyProf's internals.
|
|
7
|
+
#
|
|
8
|
+
# To use the printer:
|
|
9
|
+
#
|
|
10
|
+
# result = RubyProf.profile do
|
|
11
|
+
# [code to profile]
|
|
12
|
+
# end
|
|
13
|
+
#
|
|
14
|
+
# printer = RubyProf::CallInfoPrinter.new(result)
|
|
15
|
+
# printer.print(STDOUT)
|
|
16
|
+
class CallInfoPrinter < AbstractPrinter
|
|
17
|
+
TIME_WIDTH = 0
|
|
18
|
+
|
|
19
|
+
private
|
|
20
|
+
|
|
21
|
+
def print_header(thread)
|
|
22
|
+
@output << "----------------------------------------------------\n"
|
|
23
|
+
@output << "Thread ID: #{thread.id}\n"
|
|
24
|
+
@output << "Fiber ID: #{thread.fiber_id}\n"
|
|
25
|
+
@output << "Total Time: #{thread.total_time}\n"
|
|
26
|
+
@output << "Sort by: #{sort_method}\n"
|
|
27
|
+
@output << "\n"
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
def print_methods(thread)
|
|
31
|
+
visitor = CallTreeVisitor.new(thread.call_tree)
|
|
32
|
+
|
|
33
|
+
visitor.visit do |call_tree, event|
|
|
34
|
+
if event == :enter
|
|
35
|
+
@output << " " * call_tree.depth
|
|
36
|
+
@output << call_tree.target.full_name
|
|
37
|
+
@output << " ("
|
|
38
|
+
@output << "tt:#{sprintf("%#{TIME_WIDTH}.2f", call_tree.total_time)}, "
|
|
39
|
+
@output << "st:#{sprintf("%#{TIME_WIDTH}.2f", call_tree.self_time)}, "
|
|
40
|
+
@output << "wt:#{sprintf("%#{TIME_WIDTH}.2f", call_tree.wait_time)}, "
|
|
41
|
+
@output << "ct:#{sprintf("%#{TIME_WIDTH}.2f", call_tree.children_time)}, "
|
|
42
|
+
@output << "call:#{call_tree.called}, "
|
|
43
|
+
@output << ")"
|
|
44
|
+
@output << "\n"
|
|
45
|
+
end
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
def print_footer(thread)
|
|
50
|
+
@output << "\n" << "\n"
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
end
|