-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathREADME
214 lines (151 loc) · 4.03 KB
/
README
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
= rallhook - An ruby absolute method hooker
This package contains rallhook, a ruby C extension to intercept ruby methods calls at interpreter level in a transparent way from ruby itself.
== Installation
=== Prerequisites
* ruby-cymbol >= 0.1.0 (found at http://github.com/tario/ruby-cymbol)
* ruby debug info ( apt-get install libruby1.8-dbg or libruby1.9-dbg on debian based systems)
* ruby development package ( apt-get install ruby1.8-dev or ruby1.9-dev on debian based systems)
* objdump
=== Installation
* run in your system
sudo gem install rallhook
OR
* Download the last version of the gem from http://github.com/tario/ruby-cpp/downloads
* Install the gem with the following;
sudo gem install rallhook-X.X.X.gem
== Usage
=== Basic Example
test.rb:
require "rubygems"
require "rallhook"
include RallHook
class MethodHandler < HookHandler
def handle_method (klass,self_,m, method_id)
# print to the standar output details about the method called
print "method call #{m}:#{method_id} over #{self_}:#{self_.class} \n"
nil # do nothing
end
end
MethodHandler.hook do
# all ruby calls in this block are intercepted by hook_recv::call
[1,2,3].each do |x|
print x,"\n"
end
end
standard output:
method call each:4001 over 123:Array
method call print:7697 over main:Object
method call write:7649 over #<IO:0x7fb15e54fad0>:IO
method call to_s:3137 over 1:Fixnum
1method call write:7649 over #<IO:0x7fb15e54fad0>:IO
method call print:7697 over main:Object
method call write:7649 over #<IO:0x7fb15e54fad0>:IO
method call to_s:3137 over 2:Fixnum
2method call write:7649 over #<IO:0x7fb15e54fad0>:IO
method call print:7697 over main:Object
method call write:7649 over #<IO:0x7fb15e54fad0>:IO
method call to_s:3137 over 3:Fixnum
3method call write:7649 over #<IO:0x7fb15e54fad0>:IO
=== Redirecting calls
require "rubygems"
require "rallhook"
include RallHook
class MethodHandler < HookHandler
include RallHook::Helper
def handle_method (klass,recv,m,method_id)
if m == :foo
# redirects the calls of method foo to method bar on the same object
return redirect_call(klass,recv, :bar)
end
if m == :bar
# redirects the calls of method bar to method bar on the method_handler
return redirect_call(self.class,self, :bar)
end
nil # do nothing
end
def bar
print "bar in MethodHandler\n"
end
end
class X
def foo
print "foo in X\n"
end
def bar
print "bar in X\n"
end
end
print "WITHOUT HOOK:\n"
x = X.new
x.foo
x.bar
print "WITH HOOK:\n"
MethodHandler.hook do
# all ruby calls in this block are intercepted by hook_recv::call
x = X.new
x.foo # redirected to X#bar
x.bar # redirected to MethodHandler#bar
end
=== Wrap Calls
require "rubygems"
require "rallhook"
include RallHook
class MethodHandler < HookHandler
include RallHook::Helper
class FooMethodWrapper < MethodWrapper
def call(*x)
# call with reyield if block_given
if block_given?
original_call(*x) do |*a|
yield(*a)
end
# add "�bar?"
yield("bar?")
else
original_call(*x)
end
end
end
def handle_method (klass,recv,m,method_id)
if m == :each
return FooMethodWrapper.redirect_handler(klass,recv,m,method_id)
end
nil # do nothing
end
end
print "calling Array#each without hook\n"
[1,2,3,4].each do |x|
print x.inspect, " "
end
print "\n"
print "calling Array#each WITH hook\n"
MethodHandler.hook do
# 1 2 3 4 "bar?"
[1,2,3,4].each do |x|
print x.inspect," "
end
print "\n"
end
=== Method Instrospection new features example
source1.rb
class X
def foo
end
end
source2.rb
class Y < X
def foo
end
end
main.rb
require "rallhook"
require "source1.rb"
require "source2.rb"
x = X.new
y = Y.new
print x.method(:foo).body.file,"\n" # source1.rb
print y.method(:foo).body.file,"\n" # source2.rb
print y.method(X,:foo).body.file,"\n" # source1.rb
print y.method(Y,:foo).body.file,"\n" # source2.rb
== Copying
Copyright (c) 2010 Dario Seminara, released under the GPL License (see LICENSE)