Class: EvalHook::HookHandler
- Inherits:
-
Object
- Object
- EvalHook::HookHandler
- Includes:
- RedirectHelper
- Defined in:
- lib/evalhook.rb,
lib/evalhook/multi_hook_handler.rb
Direct Known Subclasses
Defined Under Namespace
Classes: HookedCallValue
Instance Attribute Summary collapse
-
#base_namespace ⇒ Object
Returns the value of attribute base_namespace.
Instance Method Summary collapse
-
#dispose ⇒ Object
Disposes all code packets created on this context.
- #evalhook(*args) ⇒ Object
- #evalhook_i(code, b_ = nil, name = "(eval)", line = 1) ⇒ Object
-
#handle_cdecl(*args) ⇒ Object
Overwrite to handle the assignment/creation of constants.
- #handle_colon2(context, name) ⇒ Object
-
#handle_colon3(*args) ⇒ Object
Overwrite to handle the evaluation o colon3 nodes (access to global namespace).
-
#handle_const(name) ⇒ Object
Overwrite to handle const read access.
-
#handle_gasgn(*args) ⇒ Object
Overwrite to handle the assignment/creation of global variables.
-
#handle_gvar(global_id) ⇒ Object
Overwrite to handle global variable read access.
-
#handle_method(klass, recv, method_name) ⇒ Object
Overwrite to handle the method calls.
-
#handle_xstr(*args) ⇒ Object
Overwrite to handle the evaluation o xstr nodes (execution of shell commands).
-
#hooked_cdecl(klass, const_id, value) ⇒ Object
:nodoc:.
-
#hooked_colon2(context, name) ⇒ Object
:nodoc:.
-
#hooked_const(name) ⇒ Object
:nodoc:.
-
#hooked_gasgn(global_id, value) ⇒ Object
:nodoc:.
-
#hooked_gvar(global_id) ⇒ Object
:nodoc:.
-
#hooked_method(receiver, mname, klass = nil) ⇒ Object
:nodoc:.
-
#hooked_variable_method(receiver, mname, _binding) ⇒ Object
:nodoc:.
-
#hooked_xstr(str) ⇒ Object
:nodoc:.
-
#initialize ⇒ HookHandler
constructor
A new instance of HookHandler.
-
#internal_eval(b_, original_args) ⇒ Object
used internally.
-
#packet(code) ⇒ Object
Creates a packet of preprocessed ruby code to run it later , useful to execute the same code repeatedly and avoid heavy preprocessing of ruby code all the times.
- #partialruby_context ⇒ Object
- #private_method_check(recv, mname) ⇒ Object
Methods included from RedirectHelper
#const_value, #global_value, #redirect_cdecl, #redirect_gasgn, #redirect_method
Constructor Details
#initialize ⇒ HookHandler
Returns a new instance of HookHandler.
62 63 64 65 |
# File 'lib/evalhook.rb', line 62 def initialize super self.base_namespace = Object end |
Instance Attribute Details
#base_namespace ⇒ Object
Returns the value of attribute base_namespace.
60 61 62 |
# File 'lib/evalhook.rb', line 60 def base_namespace @base_namespace end |
Instance Method Details
#dispose ⇒ Object
Disposes all code packets created on this context
295 296 297 298 299 |
# File 'lib/evalhook.rb', line 295 def dispose if @all_packets @all_packets.each(&:dispose) end end |
#evalhook(*args) ⇒ Object
312 313 314 |
# File 'lib/evalhook.rb', line 312 def evalhook(*args) evalhook_i(*args) end |
#evalhook_i(code, b_ = nil, name = "(eval)", line = 1) ⇒ Object
263 264 265 |
# File 'lib/evalhook.rb', line 263 def evalhook_i(code, b_ = nil, name = "(eval)", line = 1) packet(code).run(b_,name,line) end |
#handle_cdecl(*args) ⇒ Object
Overwrite to handle the assignment/creation of constants. By default do nothing but assign the variable. See examples
226 227 228 |
# File 'lib/evalhook.rb', line 226 def handle_cdecl(*args) nil end |
#handle_colon2(context, name) ⇒ Object
250 251 252 |
# File 'lib/evalhook.rb', line 250 def handle_colon2(context,name) nil end |
#handle_colon3(*args) ⇒ Object
Overwrite to handle the evaluation o colon3 nodes (access to global namespace)
231 232 233 |
# File 'lib/evalhook.rb', line 231 def handle_colon3(*args) nil end |
#handle_const(name) ⇒ Object
Overwrite to handle const read access
246 247 248 |
# File 'lib/evalhook.rb', line 246 def handle_const(name) nil end |
#handle_gasgn(*args) ⇒ Object
Overwrite to handle the assignment/creation of global variables. By default do nothing but assign the variable. See examples
221 222 223 |
# File 'lib/evalhook.rb', line 221 def handle_gasgn(*args) nil end |
#handle_gvar(global_id) ⇒ Object
Overwrite to handle global variable read access
255 256 257 |
# File 'lib/evalhook.rb', line 255 def handle_gvar(global_id) nil end |
#handle_method(klass, recv, method_name) ⇒ Object
Overwrite to handle the method calls. By default do nothing and the methods are called normally
241 242 243 |
# File 'lib/evalhook.rb', line 241 def handle_method(klass,recv,method_name) nil end |
#handle_xstr(*args) ⇒ Object
Overwrite to handle the evaluation o xstr nodes (execution of shell commands)
236 237 238 |
# File 'lib/evalhook.rb', line 236 def handle_xstr(*args) nil end |
#hooked_cdecl(klass, const_id, value) ⇒ Object
:nodoc:
116 117 118 119 120 121 122 123 124 125 126 |
# File 'lib/evalhook.rb', line 116 def hooked_cdecl(klass, const_id, value) #:nodoc: ret = handle_cdecl( klass, const_id, value ) if ret then klass = ret.klass const_id = ret.const_id value = ret.value end klass.const_set(const_id, value) end |
#hooked_colon2(context, name) ⇒ Object
:nodoc:
107 108 109 110 111 112 113 114 |
# File 'lib/evalhook.rb', line 107 def hooked_colon2(context,name) #:nodoc: ret = handle_colon2(context, name) if ret ret.value else context.const_get(name) end end |
#hooked_const(name) ⇒ Object
:nodoc:
98 99 100 101 102 103 104 105 |
# File 'lib/evalhook.rb', line 98 def hooked_const(name) #:nodoc: ret = handle_const(name) if ret ret.value else Object.const_get(name) end end |
#hooked_gasgn(global_id, value) ⇒ Object
:nodoc:
128 129 130 131 132 133 134 135 136 |
# File 'lib/evalhook.rb', line 128 def hooked_gasgn(global_id, value) #:nodoc: ret = handle_gasgn(global_id, value) if ret then global_id = ret.global_id value = ret.value end eval("#{global_id} = value") end |
#hooked_gvar(global_id) ⇒ Object
:nodoc:
89 90 91 92 93 94 95 96 |
# File 'lib/evalhook.rb', line 89 def hooked_gvar(global_id) #:nodoc: ret = handle_gvar(global_id) if ret ret.value else eval(global_id.to_s) end end |
#hooked_method(receiver, mname, klass = nil) ⇒ Object
:nodoc:
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 |
# File 'lib/evalhook.rb', line 147 def hooked_method(receiver, mname, klass = nil) #:nodoc: m = nil is_method_missing = false unless klass m = begin receiver.method(mname) rescue is_method_missing = true receiver.public_method(:method_missing) end klass = m.owner else m = klass.instance_method(mname).bind(receiver) end ret = handle_method(klass, receiver, mname ) if ret.kind_of? RedirectHelper::MethodRedirect klass = ret.klass mname = ret.method_name receiver = ret.recv begin m = ret.klass.instance_method(ret.method_name).bind(ret.recv) rescue m = ret.recv.method(ret.method_name) end end if is_method_missing orig_m = m m = lambda{|*x| orig_m.call(mname,*x) } end m end |
#hooked_variable_method(receiver, mname, _binding) ⇒ Object
:nodoc:
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 215 216 217 218 |
# File 'lib/evalhook.rb', line 184 def hooked_variable_method(receiver, mname, _binding) #:nodoc: local_vars = _binding.eval("local_variables").map(&:to_s) if local_vars.include? mname.to_s HookedCallValue.new( _binding.eval(mname.to_s) ) else is_method_missing = false m = begin receiver.method(mname) rescue is_method_missing = true receiver.method(:method_missing) end klass = m.owner ret = handle_method(klass, receiver, mname ) if ret.kind_of? RedirectHelper::MethodRedirect klass = ret.klass mname = ret.method_name receiver = ret.recv begin m = ret.klass.instance_method(ret.method_name).bind(ret.recv) rescue m = ret.recv.method(ret.method_name) end end if is_method_missing orig_m = m m = lambda{|*x| orig_m.call(mname,*x) } end m end end |
#hooked_xstr(str) ⇒ Object
:nodoc:
259 260 261 |
# File 'lib/evalhook.rb', line 259 def hooked_xstr(str) #:nodoc: runstr = handle_xstr(str) || str end |
#internal_eval(b_, original_args) ⇒ Object
used internally
306 307 308 309 |
# File 'lib/evalhook.rb', line 306 def internal_eval(b_, original_args) raise ArgumentError if original_args.size == 0 evalhook_i(original_args[0], original_args[1] || b_, original_args[2] || "(eval)", original_args[3] || 0) end |
#packet(code) ⇒ Object
Creates a packet of preprocessed ruby code to run it later , useful to execute the same code repeatedly and avoid heavy preprocessing of ruby code all the times.
See EvalHook::Packet for more information
Example:
hook_handler = HookHandler.new
pack = hook_handler.packet('print "hello world\n"')
10.times do
pack.run
end
pack.dispose
284 285 286 287 288 289 290 291 292 |
# File 'lib/evalhook.rb', line 284 def packet(code) @global_variable_name = nil partialruby_packet = partialruby_context.packet(code) @all_packets ||= [] newpacket = EvalHook::Packet.new(partialruby_packet, @global_variable_name) @all_packets << newpacket newpacket end |
#partialruby_context ⇒ Object
67 68 69 70 71 72 73 74 75 76 77 78 79 |
# File 'lib/evalhook.rb', line 67 def partialruby_context unless @partialruby_context @partialruby_context = PartialRuby::Context.new @partialruby_context.pre_process do |tree| @global_variable_name = "$hook_handler_" + rand(10000000000).to_s eval("#{@global_variable_name} = self") EvalHook::TreeProcessor.new(self, @global_variable_name).process(tree) end end @partialruby_context end |
#private_method_check(recv, mname) ⇒ Object
317 318 319 320 321 322 323 324 325 326 327 328 |
# File 'lib/evalhook.rb', line 317 def private_method_check(recv, mname) begin recv.public_method(mname) rescue NameError begin recv.public_method(:method_missing) rescue NameError raise NoMethodError end end recv end |