tduehr-ragweed 0.1.7 → 0.1.7.1

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.
data/History.txt CHANGED
@@ -1,3 +1,8 @@
1
+ == 0.1.7.1 / 2009-08-03
2
+
3
+ * added Rasm::Subl to avoid conflict in Bblock with Kernel#sub
4
+ * setup for call tramolines in osx
5
+
1
6
  == 0.1.7 / 2009-08-03
2
7
 
3
8
  * bug fixes (Wraposx#RegionInfo should now fully work)
data/Rakefile CHANGED
@@ -23,10 +23,12 @@ PROJ.ignore_file = '.gitignore'
23
23
  PROJ.authors = 'tduehr, tqbf, struct'
24
24
  PROJ.email = 'td@matasano.com'
25
25
  PROJ.description = 'General debugging tool written in Ruby for OSX/Win32/Linux'
26
+ PROJ.summary = 'Scriptable debugger'
27
+ PROJ.exclude << %w(old$)
26
28
  PROJ.url = 'http://github.com/tduehr/ragweed/tree/master'
27
29
  PROJ.version = Ragweed::VERSION
28
- # PROJ.rubyforge.name = 'ragweed'
29
-
30
+ PROJ.rdoc.opts << "--inline-source"
31
+ PROJ.rdoc.opts << "--line-numbers"
30
32
  PROJ.spec.opts << '--color'
31
33
 
32
34
  # EOF
@@ -2,7 +2,7 @@
2
2
 
3
3
  ## Simple example of attaching to a process and letting it run
4
4
 
5
- require 'pp'
5
+ require 'rubygems' # Yah I know its bad
6
6
  require 'ragweed'
7
7
 
8
8
  pid = Ragweed::Debuggertux.find_by_regex(/gcalctool/)
@@ -35,14 +35,14 @@ class Ragweed::Debugger32
35
35
  @orig = process.read8(@addr)
36
36
  if(@orig != INT3)
37
37
  process.write8(@addr, INT3)
38
- Wrap32::flush_instruction_cache(@bp.process.handle)
38
+ Ragweed::Wrap32::flush_instruction_cache(@bp.process.handle)
39
39
  end
40
40
  end
41
41
 
42
42
  def uninstall
43
43
  if(@orig != INT3)
44
44
  process.write8(@addr, @orig)
45
- Wrap32::flush_instruction_cache(@bp.process.handle)
45
+ Ragweed::Wrap32::flush_instruction_cache(@bp.process.handle)
46
46
  end
47
47
  end
48
48
 
@@ -57,7 +57,7 @@ class Ragweed::Debugger32
57
57
  # on the image name of the process.
58
58
  # d = Debugger.find_by_regex /notepad/i
59
59
  def self.find_by_regex(rx)
60
- Wrap32::all_processes do |p|
60
+ Ragweed::Wrap32::all_processes do |p|
61
61
  if p.szExeFile =~ rx
62
62
  return self.new(p.th32ProcessID)
63
63
  end
@@ -69,12 +69,12 @@ class Ragweed::Debugger32
69
69
  # pass this either a PID or a Process object.
70
70
  def initialize(p)
71
71
  # grab debug privilege at least once.
72
- @@token ||= Wrap32::ProcessToken.new.grant("seDebugPrivilege")
72
+ @@token ||= Ragweed::Wrap32::ProcessToken.new.grant("seDebugPrivilege")
73
73
 
74
74
  p = Process.new(p) if p.kind_of? Numeric
75
75
  @p = p
76
76
  @steppers = []
77
- @handled = Wrap32::ContinueCodes::UNHANDLED
77
+ @handled = Ragweed::Wrap32::ContinueCodes::UNHANDLED
78
78
  @first = true
79
79
  @attached = false
80
80
 
@@ -107,8 +107,8 @@ class Ragweed::Debugger32
107
107
  # for an example of how to use this.
108
108
  def step(tid, callable)
109
109
  if @steppers.empty?
110
- Wrap32::open_thread(tid) do |h|
111
- ctx = Wrap32::ThreadContext.get(h)
110
+ Ragweed::Wrap32::open_thread(tid) do |h|
111
+ ctx = Ragweed::Wrap32::ThreadContext.get(h)
112
112
  ctx.single_step(true)
113
113
  ctx.set(h)
114
114
  end
@@ -122,8 +122,8 @@ class Ragweed::Debugger32
122
122
  def unstep(tid, callable)
123
123
  @steppers = @steppers.reject {|x| x == callable}
124
124
  if @steppers.empty?
125
- Wrap32::open_thread(tid) do |h|
126
- ctx = Wrap32::ThreadContext.get(h)
125
+ Ragweed::Wrap32::open_thread(tid) do |h|
126
+ ctx = Ragweed::Wrap32::ThreadContext.get(h)
127
127
  ctx.single_step(false)
128
128
  ctx.set(h)
129
129
  end
@@ -137,7 +137,7 @@ class Ragweed::Debugger32
137
137
  else
138
138
  tid = tid_or_event
139
139
  end
140
- Wrap32::open_thread(tid) {|h| Wrap32::ThreadContext.get(h)}
140
+ Ragweed::Wrap32::open_thread(tid) {|h| Ragweed::Wrap32::ThreadContext.get(h)}
141
141
  end
142
142
 
143
143
  # set a breakpoint given an address, which can also be a string in the form
@@ -218,7 +218,7 @@ class Ragweed::Debugger32
218
218
  end))
219
219
 
220
220
  # put execution back where it's supposed to be...
221
- Wrap32::open_thread(ev.tid) do |h|
221
+ Ragweed::Wrap32::open_thread(ev.tid) do |h|
222
222
  ctx = context(ev)
223
223
  ctx.eip = eip # eip was ev.exception_address
224
224
  ctx.set(h)
@@ -226,13 +226,13 @@ class Ragweed::Debugger32
226
226
  end
227
227
 
228
228
  # tell the target to stop handling this event
229
- @handled = Wrap32::ContinueCodes::CONTINUE
229
+ @handled = Ragweed::Wrap32::ContinueCodes::CONTINUE
230
230
  end
231
231
 
232
232
  # handle a single-step event
233
233
  def on_single_step(ev)
234
234
  ctx = context(ev)
235
- Wrap32::open_thread(ev.tid) do |h|
235
+ Ragweed::Wrap32::open_thread(ev.tid) do |h|
236
236
  # re-enable the trap flag before our handler, which may
237
237
  # choose to disable it.
238
238
  ctx.single_step(true)
@@ -241,7 +241,7 @@ class Ragweed::Debugger32
241
241
 
242
242
  @steppers.each {|s| s.call(ev, ctx)}
243
243
 
244
- @handled = Wrap32::ContinueCodes::CONTINUE
244
+ @handled = Ragweed::Wrap32::ContinueCodes::CONTINUE
245
245
  end
246
246
 
247
247
  # this is sort of insane but most of my programs are just
@@ -259,54 +259,54 @@ class Ragweed::Debugger32
259
259
  def wait
260
260
  self.attach() if not @attached
261
261
 
262
- ev = Wrap32::wait_for_debug_event
262
+ ev = Ragweed::Wrap32::wait_for_debug_event
263
263
  return if not ev
264
264
  case ev.code
265
- when Wrap32::DebugCodes::CREATE_PROCESS
265
+ when Ragweed::Wrap32::DebugCodes::CREATE_PROCESS
266
266
  try(:on_create_process, ev)
267
- when Wrap32::DebugCodes::CREATE_THREAD
267
+ when Ragweed::Wrap32::DebugCodes::CREATE_THREAD
268
268
  try(:on_create_thread, ev)
269
- when Wrap32::DebugCodes::EXIT_PROCESS
269
+ when Ragweed::Wrap32::DebugCodes::EXIT_PROCESS
270
270
  try(:on_exit_process, ev)
271
- when Wrap32::DebugCodes::EXIT_THREAD
271
+ when Ragweed::Wrap32::DebugCodes::EXIT_THREAD
272
272
  try(:on_exit_thread, ev)
273
- when Wrap32::DebugCodes::LOAD_DLL
273
+ when Ragweed::Wrap32::DebugCodes::LOAD_DLL
274
274
  try(:on_load_dll, ev)
275
- when Wrap32::DebugCodes::OUTPUT_DEBUG_STRING
275
+ when Ragweed::Wrap32::DebugCodes::OUTPUT_DEBUG_STRING
276
276
  try(:on_output_debug_string, ev)
277
- when Wrap32::DebugCodes::RIP
277
+ when Ragweed::Wrap32::DebugCodes::RIP
278
278
  try(:on_rip, ev)
279
- when Wrap32::DebugCodes::UNLOAD_DLL
279
+ when Ragweed::Wrap32::DebugCodes::UNLOAD_DLL
280
280
  try(:on_unload_dll, ev)
281
- when Wrap32::DebugCodes::EXCEPTION
281
+ when Ragweed::Wrap32::DebugCodes::EXCEPTION
282
282
  case ev.exception_code
283
- when Wrap32::ExceptionCodes::ACCESS_VIOLATION
283
+ when Ragweed::Wrap32::ExceptionCodes::ACCESS_VIOLATION
284
284
  try(:on_access_violation, ev)
285
- when Wrap32::ExceptionCodes::BREAKPOINT
285
+ when Ragweed::Wrap32::ExceptionCodes::BREAKPOINT
286
286
  try(:on_breakpoint, ev)
287
- when Wrap32::ExceptionCodes::ALIGNMENT
287
+ when Ragweed::Wrap32::ExceptionCodes::ALIGNMENT
288
288
  try(:on_alignment, ev)
289
- when Wrap32::ExceptionCodes::SINGLE_STEP
289
+ when Ragweed::Wrap32::ExceptionCodes::SINGLE_STEP
290
290
  try(:on_single_step, ev)
291
- when Wrap32::ExceptionCodes::BOUNDS
291
+ when Ragweed::Wrap32::ExceptionCodes::BOUNDS
292
292
  try(:on_bounds, ev)
293
- when Wrap32::ExceptionCodes::DIVIDE_BY_ZERO
293
+ when Ragweed::Wrap32::ExceptionCodes::DIVIDE_BY_ZERO
294
294
  try(:on_divide_by_zero, ev)
295
- when Wrap32::ExceptionCodes::INT_OVERFLOW
295
+ when Ragweed::Wrap32::ExceptionCodes::INT_OVERFLOW
296
296
  try(:on_int_overflow, ev)
297
- when Wrap32::ExceptionCodes::INVALID_HANDLE
297
+ when Ragweed::Wrap32::ExceptionCodes::INVALID_HANDLE
298
298
  try(:on_invalid_handle, ev)
299
- when Wrap32::ExceptionCodes::PRIV_INSTRUCTION
299
+ when Ragweed::Wrap32::ExceptionCodes::PRIV_INSTRUCTION
300
300
  try(:on_priv_instruction, ev)
301
- when Wrap32::ExceptionCodes::STACK_OVERFLOW
301
+ when Ragweed::Wrap32::ExceptionCodes::STACK_OVERFLOW
302
302
  try(:on_stack_overflow, ev)
303
- when Wrap32::ExceptionCodes::INVALID_DISPOSITION
303
+ when Ragweed::Wrap32::ExceptionCodes::INVALID_DISPOSITION
304
304
  try(:on_invalid_disposition, ev)
305
305
  end
306
306
  end
307
307
 
308
- Wrap32::continue_debug_event(ev.pid, ev.tid, @handled)
309
- @handled = Wrap32::ContinueCodes::UNHANDLED
308
+ Ragweed::Wrap32::continue_debug_event(ev.pid, ev.tid, @handled)
309
+ @handled = Ragweed::Wrap32::ContinueCodes::UNHANDLED
310
310
  end
311
311
 
312
312
  # debug loop.
@@ -319,8 +319,8 @@ class Ragweed::Debugger32
319
319
  # this is called implicitly by Debugger#wait.
320
320
  # Attaches to the child process for debugging
321
321
  def attach
322
- Wrap32::debug_active_process(@p.pid)
323
- Wrap32::debug_set_process_kill_on_exit
322
+ Ragweed::Wrap32::debug_active_process(@p.pid)
323
+ Ragweed::Wrap32::debug_set_process_kill_on_exit
324
324
  @attached = true
325
325
  @breakpoints.each do |k, v|
326
326
  v.install
@@ -329,7 +329,7 @@ class Ragweed::Debugger32
329
329
 
330
330
  # let go of the target.
331
331
  def release
332
- Wrap32::debug_active_process_stop(@p.pid)
332
+ Ragweed::Wrap32::debug_active_process_stop(@p.pid)
333
333
  @attached = false
334
334
  @breakpoints.each do |k, v|
335
335
  v.uninstall
@@ -346,6 +346,16 @@ class Ragweed::Debuggerosx
346
346
  Ragweed::Wraposx::task_threads(@task)
347
347
  end
348
348
 
349
+ # decrement our tasks suspend count
350
+ def resume_task
351
+ Ragweed::Wraposx::task_resume(@task)
352
+ end
353
+
354
+ # increment our tasks suspend count
355
+ def suspend_task
356
+ Ragweed::Wraposx::task_suspend(@task)
357
+ end
358
+
349
359
  # returns a Ragweed::Wraposx::ThreadContext object containing the register states
350
360
  # thread: thread to get the register state of
351
361
  def get_registers(thread=nil)
@@ -396,10 +406,8 @@ class Ragweed::Debuggerosx
396
406
 
397
407
  # Extended and Top info flavors are included in case Apple re implements them
398
408
  when :extended
399
- warn "VM Region Extended Info not implemented by Apple. Returning RegionBasicInfo"
400
409
  return Ragweed::Wraposx::RegionExtendedInfo.get(@task, addr)
401
410
  when :top
402
- warn "VM Region Top Info not implemented be Apple. Returning RegionBasicInfo"
403
411
  return Ragweed::Wraposx::RegionTopInfo.get(@task, addr)
404
412
  else
405
413
  warn "Unknown flavor requested. Returning RegionBasicInfo."
@@ -13,7 +13,7 @@ module Ragweed; end
13
13
  ## debugger and define your own on_whatever events. If you handle an event
14
14
  ## that Debuggertux already handles, call "super", too.
15
15
  class Ragweed::Debuggertux
16
- include Ragweed
16
+ # include Ragweed
17
17
 
18
18
  attr_reader :pid
19
19
  attr_reader :status
@@ -99,16 +99,16 @@ class Ragweed::Debuggertux
99
99
 
100
100
  ## This is crude!
101
101
  def self.find_by_regex(rx)
102
- a = Dir.entries("/proc/")
103
- a.delete_if do |x| x == '.' end
104
- a.delete_if do |x| x == '..' end
105
- a.delete_if do |x| x =~ /[a-z]/ end
106
- a.each do |x|
107
- f = File.read("/proc/#{x}/cmdline")
108
- if f =~ rx
109
- return x
110
- end
111
- end
102
+ a = Dir.entries("/proc/")
103
+ a.delete_if do |x| x == '.'; end
104
+ a.delete_if do |x| x == '..'; end
105
+ a.delete_if do |x| x =~ /[a-z]/; end
106
+ a.each do |x|
107
+ f = File.read("/proc/#{x}/cmdline")
108
+ if f =~ rx
109
+ return x
110
+ end
111
+ end
112
112
  end
113
113
 
114
114
  def install_bps
@@ -128,24 +128,24 @@ class Ragweed::Debuggertux
128
128
  ## Attach calls install_bps so dont forget to call breakpoint_set
129
129
  ## BEFORE attach or explicitly call install_bps
130
130
  def attach(opts=@opts)
131
- Wraptux::ptrace(Ragweed::Wraptux::Ptrace::ATTACH, @pid, 0, 0)
131
+ Ragweed::Wraptux::ptrace(Ragweed::Wraptux::Ptrace::ATTACH, @pid, 0, 0)
132
132
  @attached = true
133
133
  self.install_bps if (opts[:install] and not @installed)
134
134
  end
135
135
 
136
136
  def continue
137
137
  on_continue
138
- Wraptux::ptrace(Ragweed::Wraptux::Ptrace::CONTINUE, @pid, 0, 0)
138
+ Ragweed::Wraptux::ptrace(Ragweed::Wraptux::Ptrace::CONTINUE, @pid, 0, 0)
139
139
  end
140
140
 
141
141
  def detach
142
142
  on_detach
143
- Wraptux::ptrace(Ragweed::Wraptux::Ptrace::DETACH, @pid, 0, 0)
143
+ Ragweed::Wraptux::ptrace(Ragweed::Wraptux::Ptrace::DETACH, @pid, 0, 0)
144
144
  end
145
145
 
146
146
  def stepp
147
147
  on_stepp
148
- ret = Wraptux::ptrace(Ragweed::Wraptux::Ptrace::STEP, @pid, 1, 0)
148
+ ret = Ragweed::Wraptux::ptrace(Ragweed::Wraptux::Ptrace::STEP, @pid, 1, 0)
149
149
  end
150
150
 
151
151
  ## Adds a breakpoint to be installed
@@ -205,7 +205,7 @@ class Ragweed::Debuggertux
205
205
  ## originally stored with it. If its a different signal,
206
206
  ## then process it accordingly and move on
207
207
  def wait(opts = 0)
208
- r = Wraptux::waitpid(@pid,opts)
208
+ r = Ragweed::Wraptux::waitpid(@pid,opts)
209
209
  status = r[1]
210
210
  wstatus = status & 0x7f
211
211
  signal = status >> 8
@@ -218,13 +218,13 @@ class Ragweed::Debuggertux
218
218
  when wstatus != 0x7f ##WIFSIGNALED
219
219
  @exited = false
220
220
  self.on_signal
221
- when signal == Wraptux::Signal::SIGINT
221
+ when signal == Ragweed::Wraptux::Signal::SIGINT
222
222
  self.continue
223
- when signal == Wraptux::Signal::SIGSEGV
223
+ when signal == Ragweed::Wraptux::Signal::SIGSEGV
224
224
  self.on_segv
225
- when signal == Wraptux::Signal::SIGILL
225
+ when signal == Ragweed::Wraptux::Signal::SIGILL
226
226
  self.on_illegalinst
227
- when signal == Wraptux::Signal::SIGTRAP
227
+ when signal == Ragweed::Wraptux::Signal::SIGTRAP
228
228
  ## Check if EIP matches a breakpoint we have set
229
229
  r = self.get_registers
230
230
  eip = r[:eip]
@@ -236,9 +236,9 @@ class Ragweed::Debuggertux
236
236
  puts "We got a SIGTRAP but not at our breakpoint... continuing"
237
237
  end
238
238
  self.continue
239
- when signal == Wraptux::Signal::SIGCONT
239
+ when signal == Ragweed::Wraptux::Signal::SIGCONT
240
240
  self.continue
241
- when signal == Wraptux::Signal::SIGSTOP
241
+ when signal == Ragweed::Wraptux::Signal::SIGSTOP
242
242
  self.continue
243
243
  else
244
244
  raise "Add more signal handlers (##{signal})"
@@ -249,23 +249,23 @@ class Ragweed::Debuggertux
249
249
  ## Return an array of thread PIDs
250
250
  def self.threads(pid)
251
251
  a = Dir.entries("/proc/#{pid}/task/")
252
- a.delete_if do |x| x == '.' end
253
- a.delete_if do |x| x == '..' end
252
+ a.delete_if { |x| x == '.' }
253
+ a.delete_if { |x| x == '..' }
254
254
  end
255
255
 
256
256
  ## Gets the registers for the given process
257
257
  def get_registers
258
- size = Wraptux::SIZEOFLONG * 17
258
+ size = Ragweed::Wraptux::SIZEOFLONG * 17
259
259
  regs = Array.new(size)
260
260
  regs = regs.to_ptr
261
261
  regs.struct!('LLLLLLLLLLLLLLLLL', :ebx,:ecx,:edx,:esi,:edi,:ebp,:eax,:xds,:xes,:xfs,:xgs,:orig_eax,:eip,:xcs,:eflags,:esp,:xss)
262
- Wraptux::ptrace(Ragweed::Wraptux::Ptrace::GETREGS, @pid, 0, regs.to_i)
262
+ Ragweed::Wraptux::ptrace(Ragweed::Wraptux::Ptrace::GETREGS, @pid, 0, regs.to_i)
263
263
  return regs
264
264
  end
265
265
 
266
266
  ## Sets registers for the given process
267
267
  def set_registers(r)
268
- Wraptux::ptrace(Ragweed::Wraptux::Ptrace::SETREGS, @pid, 0, r.to_i)
268
+ Ragweed::Wraptux::ptrace(Ragweed::Wraptux::Ptrace::SETREGS, @pid, 0, r.to_i)
269
269
  end
270
270
 
271
271
  ## Here we need to do something about the bp
@@ -284,14 +284,14 @@ class Ragweed::Debuggertux
284
284
  set_registers(r)
285
285
  stepp
286
286
  ## ptrace peektext returns -1 upon reinstallation of bp without calling
287
- ## waitpid() if that occurs the breakpoint cannot be reinstalled
288
- Wraptux::waitpid(@pid, 0)
287
+ ## waitpid() if that occurs the breakpoint cannot be reinstalled
288
+ Ragweed::Wraptux::waitpid(@pid, 0)
289
289
  @breakpoints[eip].first.install
290
290
  end
291
291
  end
292
292
 
293
293
  def print_regs
294
- regs = self.get_registers
294
+ regs = self.get_registers
295
295
  puts "eip %08x" % regs[:eip]
296
296
  puts "edi %08x" % regs[:esi]
297
297
  puts "edi %08x" % regs[:edi]
@@ -332,15 +332,15 @@ class Ragweed::Debuggertux
332
332
  end
333
333
 
334
334
  def on_stepp
335
- #puts "single stepping"
335
+ #puts "single stepping"
336
336
  end
337
337
 
338
338
  def on_segv
339
- print_regs
339
+ print_regs
340
340
  exit
341
341
  end
342
342
 
343
343
  def default_opts(opts)
344
- @opts = @opts.merge(opts)
344
+ @opts = @opts.merge(opts)
345
345
  end
346
346
  end
@@ -0,0 +1,68 @@
1
+ module Ragweed; end
2
+ module Ragweed::Rasm
3
+ # Ruby inline assembler.
4
+ class Bblock
5
+ # Don't call this directly; use Bblock#make
6
+ def initialize
7
+ @insns = Ragweed::Rasm::Subprogram.new
8
+ end
9
+
10
+ # Wrap the methods of Rasm::Subprogram we care about:
11
+
12
+ # Assemble the instructions, which also calculates appropriate
13
+ # jump labels.
14
+ def assemble; @insns.assemble; end
15
+
16
+ # Disassemble the block (after it's been assembled) into
17
+ # Frasm objects.
18
+ def disassemble; @insns.disassemble; end
19
+
20
+ # Generate a human-readable assembly listing.
21
+ def listing; @insns.dump_disassembly; end
22
+
23
+ # Append more instructions to a previously created block;
24
+ # see Bblock#make
25
+ def add(&block)
26
+ instance_eval(&block)
27
+ end
28
+
29
+ # Takes a block argument, containing (mostly) assembly
30
+ # instructions, as interpreted by Rasm. For example:
31
+ #
32
+ # Bblock.make {
33
+ # push ebp
34
+ # mov ebp, esp
35
+ # push ebx
36
+ # xor ebx, ebx
37
+ # addl esp, 4
38
+ # pop ebp
39
+ # ret
40
+ # }
41
+ #
42
+ # Each of those instructions is in fact the name of a class
43
+ # in Rasm, lowercased; Bblock has a method_missing that catches
44
+ # and instantiates them.
45
+ #
46
+ # Your block can contain arbitrary Ruby, but remember that it
47
+ # runs in the scope of an anonymous class and so cannot directly
48
+ # reference instance variables.
49
+ def self.make(&block)
50
+ c = Bblock.new
51
+ c.instance_eval(&block)
52
+ c
53
+ end
54
+
55
+ def method_missing(meth, *args)
56
+ k = Ragweed::Rasm.const_get(meth.to_s.capitalize)
57
+
58
+ # If it's a class, it's an assembly opcode; otherwise,
59
+ # it's a register or operand.
60
+ if k.class == Class
61
+ @insns << (k = k.new(*args))
62
+ else
63
+ k
64
+ end
65
+ k
66
+ end
67
+ end
68
+ end
@@ -174,7 +174,7 @@ module Ragweed::Rasm
174
174
  # labels. Produces raw instruction stream.
175
175
  def assemble
176
176
  patches = {}
177
- buf = Sbuf.new
177
+ buf = Ragweed::Sbuf.new
178
178
 
179
179
  each do |i|
180
180
  if i.kind_of? Instruction
@@ -248,7 +248,7 @@ module Ragweed::Rasm
248
248
  def coerce(v)
249
249
  if v
250
250
  v = v.derive
251
- v = v.to_i if v.kind_of? Ptr
251
+ v = v.to_i if v.kind_of? Ragweed::Ptr
252
252
  if v.kind_of? Array
253
253
  v = v[0].clone
254
254
  v.indir = true
@@ -263,7 +263,7 @@ module Ragweed::Rasm
263
263
 
264
264
  # Never called directly (see subclasses below)
265
265
  def initialize(x=nil, y=nil)
266
- @buf = Sbuf.new
266
+ @buf = Ragweed::Sbuf.new
267
267
  self.src = y
268
268
  self.dst = x
269
269
  @loc = nil
@@ -472,6 +472,27 @@ module Ragweed::Rasm
472
472
  super
473
473
  end
474
474
  end
475
+
476
+ ## ------------------------------------------------------------------------
477
+
478
+ # Push the registers onto the stack
479
+ # not valid for 64bit mode
480
+ class Pushad < Instruction
481
+ def to_s
482
+ add(0x60)
483
+ super
484
+ end
485
+ end
486
+
487
+ ## ------------------------------------------------------------------------
488
+
489
+ # Pop the registers off the stack
490
+ class Popad < Instruction
491
+ def to_s
492
+ add(0x61)
493
+ super
494
+ end
495
+ end
475
496
 
476
497
  ## ------------------------------------------------------------------------
477
498
 
@@ -599,6 +620,7 @@ module Ragweed::Rasm
599
620
  @x = Ebp.clone
600
621
  end
601
622
  end
623
+ Subl = Sub
602
624
 
603
625
  ## ------------------------------------------------------------------------
604
626
 
@@ -1019,10 +1041,11 @@ module Ragweed::Rasm
1019
1041
  class Pushf < Instruction
1020
1042
  # 9c pushfd
1021
1043
 
1022
- def initialize; end
1044
+ # def initialize; end
1023
1045
  def to_s
1024
1046
  raise(TooMan, "too many arguments") if @src or @dst
1025
1047
  add(0x9c)
1048
+ super
1026
1049
  end
1027
1050
  end
1028
1051
 
@@ -1031,15 +1054,25 @@ module Ragweed::Rasm
1031
1054
  class Popf < Instruction
1032
1055
  # 9d popfd
1033
1056
 
1034
- def initialize; end
1057
+ # def initialize; end
1035
1058
  def to_s
1036
1059
  raise(TooMan, "too many arguments") if @src or @dst
1037
1060
  add(0x9d)
1061
+ super
1038
1062
  end
1039
1063
  end
1040
1064
 
1041
1065
  ## ------------------------------------------------------------------------
1042
1066
 
1067
+ class Iret < Instruction
1068
+ def to_s
1069
+ add(0xcf)
1070
+ super
1071
+ end
1072
+ end
1073
+
1074
+ ## ------------------------------------------------------------------------
1075
+
1043
1076
  # INT 3, mostly, but will do INT X
1044
1077
  class Int < Instruction
1045
1078
  ## cc int 3
data/lib/ragweed/rasm.rb CHANGED
@@ -5,7 +5,7 @@ module Ragweed; end
5
5
  module Ragweed::Rasm
6
6
 
7
7
  # :stopdoc:
8
- VERSION = '0.1.7'
8
+ VERSION = '0.1.7.1'
9
9
  LIBPATH = ::File.expand_path(::File.dirname(__FILE__)) + ::File::SEPARATOR
10
10
  PATH = ::File.dirname(LIBPATH) + ::File::SEPARATOR
11
11
  # :startdoc:
data/lib/ragweed/sbuf.rb CHANGED
@@ -138,7 +138,7 @@ class Ragweed::Sbuf
138
138
  def eof?; @position >= length; end
139
139
  def clear!; @content = "" and reset; end
140
140
  def remainder(n = position); @content[n..-1] || ""; end
141
- def remainder_as_buffer(t=Sbuf); t.new(:content => remainder); end
141
+ def remainder_as_buffer(t=Ragweed::Sbuf); t.new(:content => remainder); end
142
142
 
143
143
  def self.szl64; 8; end
144
144
  def self.szb64; 8; end
@@ -57,9 +57,9 @@ class Ragweed::Trampoline
57
57
  s = @shim.assemble
58
58
  base.write(s)
59
59
 
60
- th = Wrap32::create_remote_thread(@p.handle, base, argm)
61
- Wrap32::wait_for_single_object(th) if @wait
62
- Wrap32::close_handle(th)
60
+ th = Ragweed::Wrap32::create_remote_thread(@p.handle, base, argm)
61
+ Ragweed::Wrap32::wait_for_single_object(th) if @wait
62
+ Ragweed::Wrap32::close_handle(th)
63
63
  ret = @p.read32(cur)
64
64
  if ret == 0xDEADBEEF
65
65
  ret = nil
@@ -91,12 +91,12 @@ class Trevil
91
91
  "WaitForSingleObject"].
92
92
  map {|x| @p.get_proc("kernel32!#{x}").to_i}.
93
93
  pack("LLLLL")
94
- state = [Wrap32::get_current_process_id, @ev1.handle, @ev2.handle].
94
+ state = [Ragweed::Wrap32::get_current_process_id, @ev1.handle, @ev2.handle].
95
95
  pack("LLL")
96
96
 
97
97
  data.write(swch + state)
98
98
  base.write(event_pair_stub(:debug => false).assemble)
99
- Wrap32::create_remote_thread(@p.handle, base, data)
99
+ Ragweed::Wrap32::create_remote_thread(@p.handle, base, data)
100
100
  @ev1.wait
101
101
  @ev2
102
102
  end