ruby-prof 0.18.0-x64-mingw32 → 1.1.0-x64-mingw32

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.
Files changed (119) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGES +32 -0
  3. data/LICENSE +2 -2
  4. data/README.rdoc +1 -483
  5. data/Rakefile +3 -6
  6. data/bin/ruby-prof +65 -30
  7. data/ext/ruby_prof/extconf.rb +6 -38
  8. data/ext/ruby_prof/rp_allocation.c +279 -0
  9. data/ext/ruby_prof/rp_allocation.h +31 -0
  10. data/ext/ruby_prof/rp_call_info.c +129 -283
  11. data/ext/ruby_prof/rp_call_info.h +16 -34
  12. data/ext/ruby_prof/rp_measure_allocations.c +25 -49
  13. data/ext/ruby_prof/rp_measure_memory.c +21 -56
  14. data/ext/ruby_prof/rp_measure_process_time.c +35 -39
  15. data/ext/ruby_prof/rp_measure_wall_time.c +36 -19
  16. data/ext/ruby_prof/rp_measurement.c +230 -0
  17. data/ext/ruby_prof/rp_measurement.h +50 -0
  18. data/ext/ruby_prof/rp_method.c +389 -389
  19. data/ext/ruby_prof/rp_method.h +34 -39
  20. data/ext/ruby_prof/rp_profile.c +895 -0
  21. data/ext/ruby_prof/rp_profile.h +37 -0
  22. data/ext/ruby_prof/rp_stack.c +103 -80
  23. data/ext/ruby_prof/rp_stack.h +5 -12
  24. data/ext/ruby_prof/rp_thread.c +143 -83
  25. data/ext/ruby_prof/rp_thread.h +15 -6
  26. data/ext/ruby_prof/ruby_prof.c +11 -757
  27. data/ext/ruby_prof/ruby_prof.h +4 -47
  28. data/ext/ruby_prof/vc/ruby_prof.vcxproj +10 -8
  29. data/lib/{2.6.3 → 2.6.5}/ruby_prof.so +0 -0
  30. data/lib/ruby-prof.rb +2 -18
  31. data/lib/ruby-prof/assets/call_stack_printer.html.erb +713 -0
  32. data/lib/ruby-prof/assets/call_stack_printer.png +0 -0
  33. data/lib/ruby-prof/assets/graph_printer.html.erb +356 -0
  34. data/lib/ruby-prof/call_info.rb +35 -93
  35. data/lib/ruby-prof/call_info_visitor.rb +19 -21
  36. data/lib/ruby-prof/compatibility.rb +37 -107
  37. data/lib/ruby-prof/exclude_common_methods.rb +198 -0
  38. data/lib/ruby-prof/measurement.rb +14 -0
  39. data/lib/ruby-prof/method_info.rb +52 -83
  40. data/lib/ruby-prof/printers/abstract_printer.rb +73 -50
  41. data/lib/ruby-prof/printers/call_info_printer.rb +13 -3
  42. data/lib/ruby-prof/printers/call_stack_printer.rb +62 -145
  43. data/lib/ruby-prof/printers/call_tree_printer.rb +20 -12
  44. data/lib/ruby-prof/printers/dot_printer.rb +5 -5
  45. data/lib/ruby-prof/printers/flat_printer.rb +6 -24
  46. data/lib/ruby-prof/printers/graph_html_printer.rb +6 -192
  47. data/lib/ruby-prof/printers/graph_printer.rb +13 -15
  48. data/lib/ruby-prof/printers/multi_printer.rb +66 -23
  49. data/lib/ruby-prof/profile.rb +10 -3
  50. data/lib/ruby-prof/rack.rb +0 -3
  51. data/lib/ruby-prof/thread.rb +12 -12
  52. data/lib/ruby-prof/version.rb +1 -1
  53. data/ruby-prof.gemspec +2 -2
  54. data/test/abstract_printer_test.rb +0 -27
  55. data/test/alias_test.rb +129 -0
  56. data/test/basic_test.rb +41 -40
  57. data/test/call_info_visitor_test.rb +3 -3
  58. data/test/dynamic_method_test.rb +0 -2
  59. data/test/fiber_test.rb +11 -17
  60. data/test/gc_test.rb +96 -0
  61. data/test/line_number_test.rb +120 -39
  62. data/test/marshal_test.rb +119 -0
  63. data/test/measure_allocations.rb +30 -0
  64. data/test/measure_allocations_test.rb +371 -12
  65. data/test/measure_allocations_trace_test.rb +385 -0
  66. data/test/measure_memory_trace_test.rb +756 -0
  67. data/test/measure_process_time_test.rb +821 -33
  68. data/test/measure_times.rb +54 -0
  69. data/test/measure_wall_time_test.rb +349 -145
  70. data/test/multi_printer_test.rb +1 -34
  71. data/test/parser_timings.rb +24 -0
  72. data/test/pause_resume_test.rb +5 -5
  73. data/test/prime.rb +2 -0
  74. data/test/printer_call_stack_test.rb +28 -0
  75. data/test/printer_call_tree_test.rb +31 -0
  76. data/test/printer_flat_test.rb +68 -0
  77. data/test/printer_graph_html_test.rb +60 -0
  78. data/test/printer_graph_test.rb +41 -0
  79. data/test/printers_test.rb +32 -166
  80. data/test/printing_recursive_graph_test.rb +26 -72
  81. data/test/recursive_test.rb +72 -77
  82. data/test/stack_printer_test.rb +2 -15
  83. data/test/start_stop_test.rb +22 -25
  84. data/test/test_helper.rb +5 -248
  85. data/test/thread_test.rb +11 -54
  86. data/test/unique_call_path_test.rb +16 -28
  87. data/test/yarv_test.rb +1 -0
  88. metadata +28 -36
  89. data/examples/flat.txt +0 -50
  90. data/examples/graph.dot +0 -84
  91. data/examples/graph.html +0 -823
  92. data/examples/graph.txt +0 -139
  93. data/examples/multi.flat.txt +0 -23
  94. data/examples/multi.graph.html +0 -760
  95. data/examples/multi.grind.dat +0 -114
  96. data/examples/multi.stack.html +0 -547
  97. data/examples/stack.html +0 -547
  98. data/ext/ruby_prof/rp_measure.c +0 -40
  99. data/ext/ruby_prof/rp_measure.h +0 -45
  100. data/ext/ruby_prof/rp_measure_cpu_time.c +0 -136
  101. data/ext/ruby_prof/rp_measure_gc_runs.c +0 -73
  102. data/ext/ruby_prof/rp_measure_gc_time.c +0 -60
  103. data/lib/ruby-prof/aggregate_call_info.rb +0 -76
  104. data/lib/ruby-prof/assets/call_stack_printer.css.html +0 -117
  105. data/lib/ruby-prof/assets/call_stack_printer.js.html +0 -385
  106. data/lib/ruby-prof/printers/flat_printer_with_line_numbers.rb +0 -83
  107. data/lib/ruby-prof/profile/exclude_common_methods.rb +0 -207
  108. data/lib/ruby-prof/profile/legacy_method_elimination.rb +0 -50
  109. data/test/aggregate_test.rb +0 -136
  110. data/test/block_test.rb +0 -74
  111. data/test/call_info_test.rb +0 -78
  112. data/test/issue137_test.rb +0 -63
  113. data/test/measure_cpu_time_test.rb +0 -212
  114. data/test/measure_gc_runs_test.rb +0 -32
  115. data/test/measure_gc_time_test.rb +0 -36
  116. data/test/measure_memory_test.rb +0 -33
  117. data/test/method_elimination_test.rb +0 -84
  118. data/test/module_test.rb +0 -45
  119. data/test/stack_test.rb +0 -138
@@ -1,207 +0,0 @@
1
- require 'set'
2
-
3
- module RubyProf
4
- class Profile
5
- class ExcludeCommonMethods
6
- ENUMERABLE_NAMES = Enumerable.instance_methods(false)
7
-
8
- def self.apply!(profile)
9
- new(profile).apply!
10
- end
11
-
12
- def initialize(profile)
13
- @profile = profile
14
- end
15
-
16
- def apply!
17
- ##
18
- # Kernel Methods
19
- ##
20
-
21
- exclude_methods Kernel, [
22
- :dup,
23
- :initialize_dup,
24
- :tap,
25
- :send,
26
- :public_send,
27
- ]
28
-
29
- ##
30
- # Fundamental Types
31
- ##
32
-
33
- exclude_methods BasicObject, :"!="
34
- exclude_methods Method, :"[]"
35
- exclude_methods Module, :new
36
- exclude_methods Class, :new
37
- exclude_methods Proc, :call, :yield
38
- exclude_methods Range, :each
39
- exclude_methods Integer, :times
40
-
41
- ##
42
- # Value Types
43
- ##
44
-
45
- exclude_methods String, [
46
- :sub,
47
- :sub!,
48
- :gsub,
49
- :gsub!,
50
- ]
51
-
52
- ##
53
- # Emumerables
54
- ##
55
-
56
- exclude_enumerable Enumerable
57
- exclude_enumerable Enumerator
58
-
59
- ##
60
- # Collections
61
- ##
62
-
63
- exclude_enumerable Array, [
64
- :each_index,
65
- :map!,
66
- :select!,
67
- :reject!,
68
- :collect!,
69
- :sort!,
70
- :sort_by!,
71
- :index,
72
- :delete_if,
73
- :keep_if,
74
- :drop_while,
75
- :uniq,
76
- :uniq!,
77
- :"==",
78
- :eql?,
79
- :hash,
80
- :to_json,
81
- :as_json,
82
- :encode_json,
83
- ]
84
-
85
- exclude_enumerable Hash, [
86
- :dup,
87
- :initialize_dup,
88
- :fetch,
89
- :"[]",
90
- :"[]=",
91
- :each_key,
92
- :each_value,
93
- :each_pair,
94
- :map!,
95
- :select!,
96
- :reject!,
97
- :collect!,
98
- :delete_if,
99
- :keep_if,
100
- :slice,
101
- :slice!,
102
- :except,
103
- :except!,
104
- :"==",
105
- :eql?,
106
- :hash,
107
- :to_json,
108
- :as_json,
109
- :encode_json,
110
- ]
111
-
112
- exclude_enumerable Set, [
113
- :map!,
114
- :select!,
115
- :reject!,
116
- :collect!,
117
- :classify,
118
- :delete_if,
119
- :keep_if,
120
- :divide,
121
- :"==",
122
- :eql?,
123
- :hash,
124
- :to_json,
125
- :as_json,
126
- :encode_json,
127
- ]
128
-
129
- ##
130
- # Garbage Collection
131
- ##
132
-
133
- exclude_singleton_methods GC, [
134
- :start
135
- ]
136
-
137
- ##
138
- # Unicorn
139
- ##
140
-
141
- if defined?(Unicorn)
142
- exclude_methods Unicorn::HttpServer, :process_client
143
- end
144
-
145
- if defined?(Unicorn::OobGC)
146
- exclude_methods Unicorn::OobGC, :process_client
147
- end
148
-
149
- ##
150
- # New Relic
151
- ##
152
-
153
- if defined?(NewRelic::Agent)
154
- if defined?(NewRelic::Agent::Instrumentation::MiddlewareTracing)
155
- exclude_methods NewRelic::Agent::Instrumentation::MiddlewareTracing, [
156
- :call
157
- ]
158
- end
159
-
160
- if defined?(NewRelic::Agent::MethodTracerHelpers)
161
- exclude_methods NewRelic::Agent::MethodTracerHelpers, [
162
- :trace_execution_scoped,
163
- :log_errors,
164
- ]
165
-
166
- exclude_singleton_methods NewRelic::Agent::MethodTracerHelpers, [
167
- :trace_execution_scoped,
168
- :log_errors,
169
- ]
170
- end
171
-
172
- if defined?(NewRelic::Agent::MethodTracer)
173
- exclude_methods NewRelic::Agent::MethodTracer, [
174
- :trace_execution_scoped,
175
- :trace_execution_unscoped,
176
- ]
177
- end
178
- end
179
-
180
- ##
181
- # Miscellaneous Methods
182
- ##
183
-
184
- if defined?(Mustache)
185
- exclude_methods Mustache::Context, [
186
- :fetch
187
- ]
188
- end
189
- end
190
-
191
- private
192
-
193
- def exclude_methods(mod, *method_or_methods)
194
- @profile.exclude_methods!(mod, method_or_methods)
195
- end
196
-
197
- def exclude_singleton_methods(mod, *method_or_methods)
198
- @profile.exclude_singleton_methods!(mod, method_or_methods)
199
- end
200
-
201
- def exclude_enumerable(mod, *method_or_methods)
202
- exclude_methods(mod, [:each, *method_or_methods])
203
- exclude_methods(mod, ENUMERABLE_NAMES)
204
- end
205
- end
206
- end
207
- end
@@ -1,50 +0,0 @@
1
- module RubyProf
2
- class Profile
3
- module LegacyMethodElimination
4
- # eliminate some calls from the graph by merging the information into callers.
5
- # matchers can be a list of strings or regular expressions or the name of a file containing regexps.
6
- def eliminate_methods!(matchers)
7
- RubyProf.deprecation_warning(
8
- "Method 'eliminate_methods!' is deprecated",
9
- "Please call 'exclude_methods!' before starting the profile run instead."
10
- )
11
- matchers = read_regexps_from_file(matchers) if matchers.is_a?(String)
12
- eliminated = []
13
- threads.each do |thread|
14
- matchers.each{ |matcher| eliminated.concat(eliminate_methods(thread.methods, matcher)) }
15
- end
16
- eliminated
17
- end
18
-
19
- private
20
-
21
- # read regexps from file
22
- def read_regexps_from_file(file_name)
23
- matchers = []
24
- File.open(file_name).each_line do |l|
25
- next if (l =~ /^(#.*|\s*)$/) # emtpy lines and lines starting with #
26
- matchers << Regexp.new(l.strip)
27
- end
28
- matchers
29
- end
30
-
31
- # eliminate methods matching matcher
32
- def eliminate_methods(methods, matcher)
33
- eliminated = []
34
- i = 0
35
- while i < methods.size
36
- method_info = methods[i]
37
- method_name = method_info.full_name
38
- if matcher === method_name
39
- raise "can't eliminate root method" if method_info.root?
40
- eliminated << methods.delete_at(i)
41
- method_info.eliminate!
42
- else
43
- i += 1
44
- end
45
- end
46
- eliminated
47
- end
48
- end
49
- end
50
- end
@@ -1,136 +0,0 @@
1
- #!/usr/bin/env ruby
2
- # encoding: UTF-8
3
-
4
- require File.expand_path('../test_helper', __FILE__)
5
-
6
- # Test data
7
- # A B C
8
- # | | |
9
- # Z A A
10
- # | |
11
- # Z Z
12
-
13
- class AggClass
14
- def z
15
- sleep 1
16
- end
17
-
18
- def a
19
- z
20
- end
21
-
22
- def b
23
- a
24
- end
25
-
26
- def c
27
- a
28
- end
29
- end
30
-
31
- class AggregateTest < TestCase
32
- def setup
33
- # Need to use wall time for this test due to the sleep calls
34
- RubyProf::measure_mode = RubyProf::WALL_TIME
35
- end
36
-
37
- def test_all_call_infos_are_not_recursive
38
- c1 = AggClass.new
39
- result = RubyProf.profile do
40
- c1.a
41
- c1.b
42
- c1.c
43
- end
44
- methods = result.threads.first.methods.sort.reverse
45
- methods.each do |m|
46
- m.call_infos.each do |ci|
47
- assert(!ci.recursive?)
48
- end
49
- end
50
- end
51
-
52
- def test_call_infos
53
- c1 = AggClass.new
54
- result = RubyProf.profile do
55
- c1.a
56
- c1.b
57
- c1.c
58
- end
59
-
60
- methods = result.threads.first.methods.sort.reverse
61
- method = methods.find {|meth| meth.full_name == 'AggClass#z'}
62
-
63
- # Check AggClass#z
64
- assert_equal('AggClass#z', method.full_name)
65
- assert_equal(3, method.called)
66
- assert_in_delta(3, method.total_time, 0.05)
67
- assert_in_delta(0, method.wait_time, 0.05)
68
- assert_in_delta(0, method.self_time, 0.05)
69
- assert_in_delta(3, method.children_time, 0.05)
70
- assert_equal(3, method.call_infos.length)
71
-
72
- call_info = method.call_infos[0]
73
- assert_equal('AggregateTest#test_call_infos->AggClass#a->AggClass#z', call_info.call_sequence)
74
- assert_equal(1, call_info.children.length)
75
-
76
- call_info = method.call_infos[1]
77
- assert_equal('AggregateTest#test_call_infos->AggClass#b->AggClass#a->AggClass#z', call_info.call_sequence)
78
- assert_equal(1, call_info.children.length)
79
-
80
- call_info = method.call_infos[2]
81
- assert_equal('AggregateTest#test_call_infos->AggClass#c->AggClass#a->AggClass#z', call_info.call_sequence)
82
- assert_equal(1, call_info.children.length)
83
- end
84
-
85
- def test_aggregates_parents
86
- c1 = AggClass.new
87
- result = RubyProf.profile do
88
- c1.a
89
- c1.b
90
- c1.c
91
- end
92
-
93
- methods = result.threads.first.methods.sort.reverse
94
- method = methods.find {|meth| meth.full_name == 'AggClass#z'}
95
-
96
- # Check AggClass#z
97
- assert_equal('AggClass#z', method.full_name)
98
-
99
- call_infos = method.aggregate_parents
100
- assert_equal(1, call_infos.length)
101
-
102
- call_info = call_infos.first
103
- assert_equal('AggClass#a', call_info.parent.target.full_name)
104
- assert_in_delta(3, call_info.total_time, 0.05)
105
- assert_in_delta(0, call_info.wait_time, 0.05)
106
- assert_in_delta(0, call_info.self_time, 0.05)
107
- assert_in_delta(3, call_info.children_time, 0.05)
108
- assert_equal(3, call_info.called)
109
- end
110
-
111
- def test_aggregates_children
112
- c1 = AggClass.new
113
- result = RubyProf.profile do
114
- c1.a
115
- c1.b
116
- c1.c
117
- end
118
-
119
- methods = result.threads.first.methods.sort.reverse
120
- method = methods.find {|meth| meth.full_name == 'AggClass#a'}
121
-
122
- # Check AggClass#a
123
- assert_equal('AggClass#a', method.full_name)
124
-
125
- call_infos = method.aggregate_children
126
- assert_equal(1, call_infos.length)
127
-
128
- call_info = call_infos.first
129
- assert_equal('AggClass#z', call_info.target.full_name)
130
- assert_in_delta(3, call_info.total_time, 0.05)
131
- assert_in_delta(0, call_info.wait_time, 0.05)
132
- assert_in_delta(0, call_info.self_time, 0.05)
133
- assert_in_delta(3, call_info.children_time, 0.05)
134
- assert_equal(3, call_info.called)
135
- end
136
- end
data/test/block_test.rb DELETED
@@ -1,74 +0,0 @@
1
- #!/usr/bin/env ruby
2
- # encoding: UTF-8
3
-
4
- require File.expand_path("../test_helper", __FILE__)
5
-
6
- class BlockMethodTest < TestCase
7
- def setup
8
- # Need to use wall time for this test due to the sleep calls
9
- RubyProf::measure_mode = RubyProf::WALL_TIME
10
- end
11
-
12
- def test_block
13
- result = RubyProf.profile do
14
- 1.times { RubyProf::C1.new.hello }
15
- end
16
-
17
- # Methods called
18
- # Kernel#sleep
19
- # <Class::BasicObject>#allocate
20
- # #{RubyProf.parent_object}#inizialize
21
- # RubyProf::C1#hello
22
- # Class#new
23
- # Integer#times
24
- # BlockMethodTest#test_block
25
-
26
- methods = result.threads.first.methods.sort.reverse
27
- assert_equal(RubyProf.ruby_2? ? 6 : 7, methods.length)
28
-
29
- # Check times
30
- assert_equal("BlockMethodTest#test_block", methods[0].full_name)
31
- assert_in_delta(0.2, methods[0].total_time, 0.02)
32
- assert_in_delta(0.0, methods[0].wait_time, 0.02)
33
- assert_in_delta(0.0, methods[0].self_time, 0.02)
34
-
35
- assert_equal("Integer#times", methods[1].full_name)
36
- assert_in_delta(0.2, methods[1].total_time, 0.02)
37
- assert_in_delta(0.0, methods[1].wait_time, 0.02)
38
- assert_in_delta(0.0, methods[1].self_time, 0.02)
39
-
40
- assert_equal("RubyProf::C1#hello", methods[2].full_name)
41
- assert_in_delta(0.2, methods[2].total_time, 0.02)
42
- assert_in_delta(0.0, methods[2].wait_time, 0.02)
43
- assert_in_delta(0.0, methods[2].self_time, 0.02)
44
-
45
- assert_equal("Kernel#sleep", methods[3].full_name)
46
- assert_in_delta(0.2, methods[3].total_time, 0.01)
47
- assert_in_delta(0.0, methods[3].wait_time, 0.01)
48
- assert_in_delta(0.2, methods[3].self_time, 0.01)
49
-
50
- assert_equal("Class#new", methods[4].full_name)
51
- assert_in_delta(0.0, methods[4].total_time, 0.01)
52
- assert_in_delta(0.0, methods[4].wait_time, 0.01)
53
- assert_in_delta(0.0, methods[4].self_time, 0.01)
54
-
55
- # the timing difference between #initialize and #allocate is so small
56
- # that we cannot rely on #initialize appearing first.
57
- # so switch them, if necessary
58
- if methods[5].full_name =~ /#allocate/
59
- methods[5], methods[6] = methods[6], methods[5]
60
- end
61
-
62
- assert_equal("#{RubyProf.parent_object}#initialize", methods[5].full_name)
63
- assert_in_delta(0.0, methods[5].total_time, 0.01)
64
- assert_in_delta(0.0, methods[5].wait_time, 0.01)
65
- assert_in_delta(0.0, methods[5].self_time, 0.01)
66
-
67
- unless RubyProf.ruby_2?
68
- assert_equal("<Class::#{RubyProf.parent_object}>#allocate", methods[6].full_name)
69
- assert_in_delta(0.0, methods[6].total_time, 0.01)
70
- assert_in_delta(0.0, methods[6].wait_time, 0.01)
71
- assert_in_delta(0.0, methods[6].self_time, 0.01)
72
- end
73
- end
74
- end