rdp-ruby-prof 0.7.4

Sign up to get free protection for your applications and to get access to all the features.
Files changed (64) hide show
  1. data/CHANGES +202 -0
  2. data/LICENSE +23 -0
  3. data/README +445 -0
  4. data/Rakefile +123 -0
  5. data/bin/ruby-prof +207 -0
  6. data/examples/flat.txt +55 -0
  7. data/examples/graph.html +823 -0
  8. data/examples/graph.txt +170 -0
  9. data/ext/#ruby_prof.c# +1679 -0
  10. data/ext/Makefile +180 -0
  11. data/ext/extconf.rb +40 -0
  12. data/ext/measure_allocations.h +58 -0
  13. data/ext/measure_cpu_time.h +152 -0
  14. data/ext/measure_gc_runs.h +76 -0
  15. data/ext/measure_gc_time.h +57 -0
  16. data/ext/measure_memory.h +101 -0
  17. data/ext/measure_process_time.h +52 -0
  18. data/ext/measure_wall_time.h +53 -0
  19. data/ext/mingw/Rakefile +23 -0
  20. data/ext/mingw/build.rake +38 -0
  21. data/ext/ruby_prof.c +1707 -0
  22. data/ext/ruby_prof.e +19984 -0
  23. data/ext/ruby_prof.h +188 -0
  24. data/ext/vc/ruby_prof.sln +20 -0
  25. data/ext/vc/ruby_prof.vcproj +241 -0
  26. data/ext/version.h +4 -0
  27. data/lib/ruby-prof.rb +48 -0
  28. data/lib/ruby-prof/abstract_printer.rb +41 -0
  29. data/lib/ruby-prof/aggregate_call_info.rb +62 -0
  30. data/lib/ruby-prof/call_info.rb +47 -0
  31. data/lib/ruby-prof/call_tree_printer.rb +84 -0
  32. data/lib/ruby-prof/flat_printer.rb +79 -0
  33. data/lib/ruby-prof/graph_html_printer.rb +256 -0
  34. data/lib/ruby-prof/graph_html_printer.rb.orig +256 -0
  35. data/lib/ruby-prof/graph_html_printer.rb.rej +34 -0
  36. data/lib/ruby-prof/graph_printer.rb +164 -0
  37. data/lib/ruby-prof/graph_printer.rb.orig +164 -0
  38. data/lib/ruby-prof/method_info.rb +111 -0
  39. data/lib/ruby-prof/task.rb +146 -0
  40. data/lib/ruby-prof/test.rb +148 -0
  41. data/lib/unprof.rb +8 -0
  42. data/rails/environment/profile.rb +24 -0
  43. data/rails/example/example_test.rb +9 -0
  44. data/rails/profile_test_helper.rb +21 -0
  45. data/test/aggregate_test.rb +121 -0
  46. data/test/basic_test.rb +283 -0
  47. data/test/duplicate_names_test.rb +32 -0
  48. data/test/exceptions_test.rb +15 -0
  49. data/test/exclude_threads_test.rb +54 -0
  50. data/test/line_number_test.rb +73 -0
  51. data/test/measurement_test.rb +121 -0
  52. data/test/module_test.rb +54 -0
  53. data/test/no_method_class_test.rb +13 -0
  54. data/test/prime.rb +58 -0
  55. data/test/prime_test.rb +13 -0
  56. data/test/printers_test.rb +71 -0
  57. data/test/recursive_test.rb +254 -0
  58. data/test/singleton_test.rb +37 -0
  59. data/test/stack_test.rb +138 -0
  60. data/test/start_stop_test.rb +95 -0
  61. data/test/test_suite.rb +23 -0
  62. data/test/thread_test.rb +159 -0
  63. data/test/unique_call_path_test.rb +206 -0
  64. metadata +124 -0
@@ -0,0 +1,32 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'test/unit'
4
+ require 'ruby-prof'
5
+
6
+ class DuplicateNames < Test::Unit::TestCase
7
+ def test_names
8
+ result = RubyProf::profile do
9
+ str = %{module Foo; class Bar; def foo; end end end}
10
+
11
+ eval str
12
+ Foo::Bar.new.foo
13
+ DuplicateNames.class_eval {remove_const :Foo}
14
+
15
+ eval str
16
+ Foo::Bar.new.foo
17
+ DuplicateNames.class_eval {remove_const :Foo}
18
+
19
+ eval str
20
+ Foo::Bar.new.foo
21
+ end
22
+
23
+ # There should be 3 foo methods
24
+ methods = result.threads.values.first.sort.reverse
25
+
26
+ methods = methods.select do |method|
27
+ method.full_name == 'DuplicateNames::Foo::Bar#foo'
28
+ end
29
+
30
+ assert_equal(3, methods.length)
31
+ end
32
+ end
@@ -0,0 +1,15 @@
1
+ #!/usr/bin/env ruby
2
+ require 'test/unit'
3
+ require 'ruby-prof'
4
+
5
+ class ExceptionsTest < Test::Unit::TestCase
6
+ def test_profile
7
+ result = begin
8
+ RubyProf.profile do
9
+ raise(RuntimeError, 'Test error')
10
+ end
11
+ rescue => e
12
+ end
13
+ assert_not_nil(result)
14
+ end
15
+ end
@@ -0,0 +1,54 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'test/unit'
4
+ require 'ruby-prof'
5
+
6
+
7
+ # -- Tests ----
8
+ class ExcludeThreadsTest < Test::Unit::TestCase
9
+ def test_exclude_threads
10
+
11
+ def thread1_proc
12
+ sleep(0.5)
13
+ sleep(2)
14
+ end
15
+
16
+ def thread2_proc
17
+ sleep(0.5)
18
+ sleep(2)
19
+ end
20
+
21
+ thread1 = Thread.new do
22
+ thread1_proc
23
+ end
24
+
25
+ thread2 = Thread.new do
26
+ thread2_proc
27
+ end
28
+
29
+ RubyProf::exclude_threads = [ thread2 ]
30
+
31
+ RubyProf.start
32
+
33
+ thread1.join
34
+ thread2.join
35
+
36
+ result = RubyProf.stop
37
+
38
+ RubyProf::exclude_threads = nil
39
+
40
+ assert_equal(2, result.threads.length)
41
+
42
+ output = Array.new
43
+ result.threads.each do | thread_id, methods |
44
+ methods.each do | m |
45
+ if m.full_name.index("ExcludeThreadsTest#thread") == 0
46
+ output.push(m.full_name)
47
+ end
48
+ end
49
+ end
50
+
51
+ assert_equal(1, output.length)
52
+ assert_equal("ExcludeThreadsTest#thread1_proc", output[0])
53
+ end
54
+ end
@@ -0,0 +1,73 @@
1
+ #!/usr/bin/env ruby
2
+ require 'test/unit'
3
+ require 'ruby-prof'
4
+ require 'prime'
5
+
6
+ class LineNumbers
7
+ def method1
8
+ a = 3
9
+ end
10
+
11
+ def method2
12
+ a = 3
13
+ method1
14
+ end
15
+
16
+ def method3
17
+ sleep(1)
18
+ end
19
+ end
20
+
21
+ # -- Tests ----
22
+ class LineNumbersTest < Test::Unit::TestCase
23
+ def test_function_line_no
24
+ numbers = LineNumbers.new
25
+
26
+ result = RubyProf.profile do
27
+ numbers.method2
28
+ end
29
+
30
+ methods = result.threads.values.first.sort.reverse
31
+ assert_equal(3, methods.length)
32
+
33
+ method = methods[0]
34
+ assert_equal('LineNumbersTest#test_function_line_no', method.full_name)
35
+ assert_equal(27, method.line)
36
+
37
+ method = methods[1]
38
+ assert_equal('LineNumbers#method2', method.full_name)
39
+ assert_equal(11, method.line)
40
+
41
+ method = methods[2]
42
+ assert_equal('LineNumbers#method1', method.full_name)
43
+ assert_equal(7, method.line)
44
+ end
45
+
46
+ def test_c_function
47
+ numbers = LineNumbers.new
48
+
49
+ result = RubyProf.profile do
50
+ numbers.method3
51
+ end
52
+
53
+ methods = result.threads.values.first.sort_by {|method| method.full_name}
54
+ assert_equal(3, methods.length)
55
+
56
+ # Methods:
57
+ # LineNumbers#method3
58
+ # LineNumbersTest#test_c_function
59
+ # Kernel#sleep
60
+
61
+ method = methods[0]
62
+ assert_equal('Kernel#sleep', method.full_name)
63
+ assert_equal(0, method.line)
64
+
65
+ method = methods[1]
66
+ assert_equal('LineNumbers#method3', method.full_name)
67
+ assert_equal(16, method.line)
68
+
69
+ method = methods[2]
70
+ assert_equal('LineNumbersTest#test_c_function', method.full_name)
71
+ assert_equal(50, method.line)
72
+ end
73
+ end
@@ -0,0 +1,121 @@
1
+ #!/usr/bin/env ruby
2
+ require 'test/unit'
3
+ require 'ruby-prof'
4
+
5
+ class MeasurementTest < Test::Unit::TestCase
6
+ def setup
7
+ GC.enable_stats if GC.respond_to?(:enable_stats)
8
+ end
9
+
10
+ def teardown
11
+ GC.disable_stats if GC.respond_to?(:disable_stats)
12
+ end
13
+
14
+ def test_process_time_mode
15
+ RubyProf::measure_mode = RubyProf::PROCESS_TIME
16
+ assert_equal(RubyProf::PROCESS_TIME, RubyProf::measure_mode)
17
+ end
18
+
19
+ def test_process_time
20
+ t = RubyProf.measure_process_time
21
+ assert_kind_of(Float, t)
22
+
23
+ u = RubyProf.measure_process_time
24
+ assert(u >= t, [t, u].inspect)
25
+ end
26
+
27
+ def test_wall_time_mode
28
+ RubyProf::measure_mode = RubyProf::WALL_TIME
29
+ assert_equal(RubyProf::WALL_TIME, RubyProf::measure_mode)
30
+ end
31
+
32
+ def test_wall_time
33
+ t = RubyProf.measure_wall_time
34
+ assert_kind_of Float, t
35
+
36
+ u = RubyProf.measure_wall_time
37
+ assert u >= t, [t, u].inspect
38
+ end
39
+
40
+ if RubyProf::CPU_TIME
41
+ def test_cpu_time_mode
42
+ RubyProf::measure_mode = RubyProf::CPU_TIME
43
+ assert_equal(RubyProf::CPU_TIME, RubyProf::measure_mode)
44
+ end
45
+
46
+ def test_cpu_time
47
+ RubyProf.cpu_frequency = 2.33e9
48
+
49
+ t = RubyProf.measure_cpu_time
50
+ assert_kind_of Float, t
51
+
52
+ u = RubyProf.measure_cpu_time
53
+ assert u > t, [t, u].inspect
54
+ end
55
+ end
56
+
57
+ if RubyProf::ALLOCATIONS
58
+ def test_allocations_mode
59
+ RubyProf::measure_mode = RubyProf::ALLOCATIONS
60
+ assert_equal(RubyProf::ALLOCATIONS, RubyProf::measure_mode)
61
+ end
62
+
63
+ def test_allocations
64
+ t = RubyProf.measure_allocations
65
+ assert_kind_of Integer, t
66
+
67
+ u = RubyProf.measure_allocations
68
+ assert u > t, [t, u].inspect
69
+ end
70
+ end
71
+
72
+ if RubyProf::MEMORY
73
+ def test_memory_mode
74
+ RubyProf::measure_mode = RubyProf::MEMORY
75
+ assert_equal(RubyProf::MEMORY, RubyProf::measure_mode)
76
+ end
77
+
78
+ def test_memory
79
+ t = RubyProf.measure_memory
80
+ assert_kind_of Integer, t
81
+
82
+ u = RubyProf.measure_memory
83
+ assert(u >= t, [t, u].inspect)
84
+
85
+ result = RubyProf.profile {Array.new}
86
+ total = result.threads.values.first.methods.inject(0) { |sum, m| sum + m.total_time }
87
+
88
+ assert(total > 0, 'Should measure more than zero kilobytes of memory usage')
89
+ assert_not_equal(0, total % 1, 'Should not truncate fractional kilobyte measurements')
90
+ end
91
+ end
92
+
93
+ if RubyProf::GC_RUNS
94
+ def test_gc_runs_mode
95
+ RubyProf::measure_mode = RubyProf::GC_RUNS
96
+ assert_equal(RubyProf::GC_RUNS, RubyProf::measure_mode)
97
+ end
98
+
99
+ def test_gc_runs
100
+ t = RubyProf.measure_gc_runs
101
+ assert_kind_of Integer, t
102
+
103
+ GC.start
104
+
105
+ u = RubyProf.measure_gc_runs
106
+ assert u > t, [t, u].inspect
107
+ end
108
+ end
109
+
110
+ if RubyProf::GC_TIME
111
+ def test_gc_time
112
+ t = RubyProf.measure_gc_time
113
+ assert_kind_of Integer, t
114
+
115
+ GC.start
116
+
117
+ u = RubyProf.measure_gc_time
118
+ assert u > t, [t, u].inspect
119
+ end
120
+ end
121
+ end
@@ -0,0 +1,54 @@
1
+ #!/usr/bin/env ruby
2
+ require 'test/unit'
3
+ require 'ruby-prof'
4
+
5
+ # Need to use wall time for this test due to the sleep calls
6
+ RubyProf::measure_mode = RubyProf::WALL_TIME
7
+
8
+ module Foo
9
+ def Foo::hello
10
+ sleep(0.5)
11
+ end
12
+ end
13
+
14
+ module Bar
15
+ def Bar::hello
16
+ sleep(0.5)
17
+ Foo::hello
18
+ end
19
+
20
+ def hello
21
+ sleep(0.5)
22
+ Bar::hello
23
+ end
24
+ end
25
+
26
+ include Bar
27
+
28
+ class ModuleTest < Test::Unit::TestCase
29
+ def test_nested_modules
30
+ result = RubyProf.profile do
31
+ hello
32
+ end
33
+
34
+ methods = result.threads.values.first.sort.reverse
35
+
36
+ # Length should be 5
37
+ assert_equal(5, methods.length)
38
+
39
+ method = methods[0]
40
+ assert_equal('ModuleTest#test_nested_modules', method.full_name)
41
+
42
+ method = methods[1]
43
+ assert_equal('Bar#hello', method.full_name)
44
+
45
+ method = methods[2]
46
+ assert_equal('Kernel#sleep', method.full_name)
47
+
48
+ method = methods[3]
49
+ assert_equal('<Module::Bar>#hello', method.full_name)
50
+
51
+ method = methods[4]
52
+ assert_equal('<Module::Foo>#hello', method.full_name)
53
+ end
54
+ end
@@ -0,0 +1,13 @@
1
+ #!/usr/bin/env ruby
2
+ require 'ruby-prof'
3
+
4
+ # Make sure this works with no class or method
5
+ result = RubyProf.profile do
6
+ sleep 1
7
+ end
8
+
9
+ methods = result.threads.values.first
10
+ global_method = methods.sort_by {|method| method.full_name}.first
11
+ if global_method.full_name != 'Global#[No method]'
12
+ raise(RuntimeError, "Wrong method name. Expected: Global#[No method]. Actual: #{global_method.full_name}")
13
+ end
@@ -0,0 +1,58 @@
1
+ # A silly little test program that finds prime numbers. It
2
+ # is intentionally badly designed to show off the use
3
+ # of ruby-prof.
4
+ #
5
+ # Source from http://people.cs.uchicago.edu/~bomb154/154/maclabs/profilers-lab/
6
+
7
+ def make_random_array(length, maxnum)
8
+ result = Array.new(length)
9
+ result.each_index do |i|
10
+ result[i] = rand(maxnum)
11
+ end
12
+
13
+ result
14
+ end
15
+
16
+ def is_prime(x)
17
+ y = 2
18
+ y.upto(x-1) do |i|
19
+ return false if (x % i) == 0
20
+ end
21
+ true
22
+ end
23
+
24
+ def find_primes(arr)
25
+ result = arr.select do |value|
26
+ is_prime(value)
27
+ end
28
+ result
29
+ end
30
+
31
+ def find_largest(primes)
32
+ largest = primes.first
33
+
34
+ # Intentionally use upto for example purposes
35
+ # (upto is also called from is_prime)
36
+ 0.upto(primes.length-1) do |i|
37
+ sleep(0.02)
38
+ prime = primes[i]
39
+ if prime > largest
40
+ largest = prime
41
+ end
42
+ end
43
+ largest
44
+ end
45
+
46
+ def run_primes
47
+ length = 10
48
+ maxnum = 10000
49
+
50
+ # Create random numbers
51
+ random_array = make_random_array(length, maxnum)
52
+
53
+ # Find the primes
54
+ primes = find_primes(random_array)
55
+
56
+ # Find the largest primes
57
+ largest = find_largest(primes)
58
+ end
@@ -0,0 +1,13 @@
1
+ #!/usr/bin/env ruby
2
+ require 'test/unit'
3
+ require 'ruby-prof'
4
+ require 'prime'
5
+
6
+ # -- Tests ----
7
+ class PrimeTest< Test::Unit::TestCase
8
+ def test_consistency
9
+ result = RubyProf.profile do
10
+ run_primes
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,71 @@
1
+ #!/usr/bin/env ruby
2
+ require 'test/unit'
3
+ require 'ruby-prof'
4
+ require 'prime'
5
+
6
+ # -- Tests ----
7
+ class PrintersTest < Test::Unit::TestCase
8
+ def setup
9
+ RubyProf::measure_mode = RubyProf::PROCESS_TIME
10
+ @result = RubyProf.profile do
11
+ run_primes
12
+ end
13
+ end
14
+
15
+ def test_printers
16
+ printer = RubyProf::FlatPrinter.new(@result)
17
+ printer.print(STDOUT)
18
+
19
+ printer = RubyProf::GraphHtmlPrinter.new(@result)
20
+ printer.print
21
+
22
+ printer = RubyProf::GraphPrinter.new(@result)
23
+ printer.print
24
+
25
+ printer = RubyProf::CallTreePrinter.new(@result)
26
+ printer.print(STDOUT)
27
+
28
+ # we should get here
29
+ assert(true)
30
+ end
31
+
32
+ def test_flat_string
33
+ output = ''
34
+
35
+ printer = RubyProf::FlatPrinter.new(@result)
36
+ assert_nothing_raised { printer.print(output) }
37
+
38
+ assert_match(/Thread ID: -?\d+/i, output)
39
+ assert_match(/Total: \d+\.\d+/i, output)
40
+ assert_match(/Object#run_primes/i, output)
41
+ end
42
+
43
+ def test_graph_html_string
44
+ output = ''
45
+ printer = RubyProf::GraphHtmlPrinter.new(@result)
46
+ assert_nothing_raised { printer.print(output) }
47
+
48
+ assert_match( /DTD HTML 4\.01/i, output )
49
+ assert_match( %r{<th>Total Time</th>}i, output )
50
+ assert_match( /Object#run_primes/i, output )
51
+ end
52
+
53
+ def test_graph_string
54
+ output = ''
55
+ printer = RubyProf::GraphPrinter.new(@result)
56
+ assert_nothing_raised { printer.print(output) }
57
+
58
+ assert_match( /Thread ID: -?\d+/i, output )
59
+ assert_match( /Total Time: \d+\.\d+/i, output )
60
+ assert_match( /Object#run_primes/i, output )
61
+ end
62
+
63
+ def test_call_tree_string
64
+ output = ''
65
+ printer = RubyProf::CallTreePrinter.new(@result)
66
+ assert_nothing_raised { printer.print(output) }
67
+
68
+ assert_match(/fn=Object::find_primes/i, output)
69
+ assert_match(/events: process_time/i, output)
70
+ end
71
+ end