ragweed 0.1.7.3 → 0.2.0.pre1

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.
@@ -1,7 +1,11 @@
1
- %w[ostruct Win32API pp].each {|x| require x}
1
+ require 'ffi'
2
+ require 'ostruct'
3
+ require 'Win32API'
4
+ require 'pp'
2
5
 
3
6
  module Ragweed;end
4
7
  module Ragweed::Wrap32
8
+
5
9
  NULL = 0x0
6
10
 
7
11
  module PagePerms
@@ -68,32 +72,73 @@ module Ragweed::Wrap32
68
72
  ALLOCATE_BUFFER = 256
69
73
  end
70
74
 
71
- # Does 2 things:
72
- # 1. Parses a terse notation for Win32 functions: "module!function:args=return",
73
- # where "args" and "return" are in String#unpack notation.
74
- #
75
- # 2. Memoizes the Win32API lookup.
76
- #
77
- # Returns a callable object implementing the specified call.
78
-
79
- CALLS = Hash.new do |h, str|
80
- lib = proc = args = ret = nil
81
- lib, rest = str.split "!"
82
- proc, rest = rest.split ":"
83
- args, ret = rest.split("=") if rest
84
- ret ||= ""
85
- args ||= []
86
- raise "need proc" if not proc
87
- h[str] = Win32API.new(lib, proc, args, ret)
75
+ module Win
76
+ extend FFI::Library
77
+
78
+ ffi_lib 'kernel32', 'Advapi32'
79
+ ffi_convention :stdcall
80
+ attach_function 'OpenProcess', [ :long, :long, :long ], :long
81
+ attach_function 'OpenThread', [ :long, :long, :long ], :long
82
+ attach_function 'CloseHandle', [ :long ], :long
83
+ attach_function 'GetLastError', [ ], :long
84
+ attach_function 'FormatMessageA', [ :long, :pointer, :long, :long, :pointer, :long, :pointer ], :void
85
+ attach_function 'VirtualAllocEx', [ :long, :long, :long, :long, :long ], :long
86
+ attach_function 'VirtualFreeEx', [ :long, :long, :long, :long, ], :long
87
+ attach_function 'WriteProcessMemory', [ :long, :long, :pointer, :long, :long ], :long
88
+ attach_function 'ReadProcessMemory', [ :long, :long, :pointer, :long, :long ], :long
89
+ attach_function 'VirtualQueryEx', [ :long, :long, :pointer, :long ], :long
90
+ attach_function 'VirtualProtectEx', [ :long, :long, :long, :long, :pointer ], :void
91
+ attach_function 'GetCurrentProcessId', [], :long
92
+ attach_function 'GetProcessId', [ :long ], :long
93
+ attach_function 'GetCurrentThreadId', [], :long
94
+ attach_function 'GetModuleHandleA', [ :pointer ], :long
95
+ attach_function 'LoadLibraryA', [ :pointer ], :long
96
+ attach_function 'GetProcAddress', [ :long, :pointer], :long
97
+ attach_function 'WaitForSingleObject', [ :long, :long ], :long
98
+ attach_function 'Process32First', [ :long, :pointer ], :long
99
+ attach_function 'Process32Next', [ :long, :pointer ], :long
100
+ attach_function 'Module32First', [ :long, :pointer ], :long
101
+ attach_function 'Module32Next', [ :long, :pointer ], :long
102
+ attach_function 'CreateToolhelp32Snapshot', [ :long, :long ], :long
103
+ attach_function 'Thread32First', [ :long, :pointer ], :long
104
+ attach_function 'Thread32Next', [ :long, :pointer ], :long
105
+ attach_function 'SuspendThread', [ :long ], :long
106
+ attach_function 'ResumeThread', [ :long ], :long
107
+ attach_function 'CreateRemoteThread', [ :long, :long, :long, :long, :long, :long, :long ], :long
108
+ attach_function 'Sleep', [ :long ], :long
109
+ attach_function 'DuplicateHandle', [ :long, :long, :long, :pointer, :long, :long, :long ], :long
110
+ attach_function 'CreateFileA', [ :pointer, :long, :long, :pointer, :long, :long, :pointer ], :long
111
+ attach_function 'OpenEventA', [ :long, :long, :pointer ], :long
112
+ attach_function 'CreateEventA', [ :long, :long, :long, :pointer ], :long
113
+ attach_function 'SetEvent', [ :long ], :long
114
+ attach_function 'ResetEvent', [ :long ], :long
115
+ attach_function 'WriteFile', [ :long, :pointer, :long, :pointer, :pointer ], :long
116
+ attach_function 'ReadFile', [ :long, :pointer, :long, :pointer, :pointer ], :long
117
+ attach_function 'DeviceIoControl', [ :long, :long, :pointer, :long, :pointer, :long, :pointer, :pointer ], :long
118
+ attach_function 'GetOverlappedResult', [ :long, :pointer, :pointer, :long ], :long
119
+ attach_function 'WaitForMultipleObjects', [ :long, :pointer, :long, :long ], :long
120
+
121
+ ffi_lib 'ntdll'
122
+ ffi_convention :stdcall
123
+ attach_function 'NtQueryInformationProcess', [ :long, :long, :pointer, :long, :pointer ], :long
124
+
125
+ ffi_lib 'msvcrt'
126
+ ffi_convention :stdcall
127
+ attach_function 'malloc', [ :long ], :long
128
+ attach_function 'memcpy', [ :pointer, :pointer, :long ], :long
129
+
130
+ ## XXX This shouldnt be in psapi in win7, need to clean this up
131
+ ## XXX Also the unicode version should be supported, this is NOT complete
132
+ ffi_lib 'psapi'
133
+ ffi_convention :stdcall
134
+ attach_function 'GetMappedFileNameA', [ :long, :long, :pointer, :long ], :long
88
135
  end
89
136
 
90
- # --------------------------------------------------------------------------------------
91
-
92
137
  class << self
93
138
 
94
139
  # Get a process handle given a pid
95
140
  def open_process(pid)
96
- r = CALLS["kernel32!OpenProcess:LLL=L"].call(0x1F0FFF, 0, pid)
141
+ r = Win.OpenProcess(0x1F0FFF, 0, pid)
97
142
  raise WinX.new(:open_process) if r == 0
98
143
  return r
99
144
  end
@@ -101,7 +146,7 @@ module Ragweed::Wrap32
101
146
  # Get a thread handle given a tid; if a block is provided, the semantics are
102
147
  # as File#open with a block.
103
148
  def open_thread(tid, &block)
104
- h = CALLS["kernel32!OpenThread:LLL=L"].call(0x1F03FF, 0, tid)
149
+ h = Win.OpenThread(0x1F03FF, 0, tid)
105
150
  raise WinX.new(:open_thread) if h == 0
106
151
  if block_given?
107
152
  ret = yield h
@@ -114,34 +159,32 @@ module Ragweed::Wrap32
114
159
  # Close any Win32 handle. Reminder: Win32 handles are just integers, like file
115
160
  # descriptors in Posix.
116
161
  def close_handle(h)
117
- raise WinX.new(:close_handle) if CALLS["kernel32!CloseHandle:L"].call(h) != 0
162
+ raise WinX.new(:close_handle) if Win.CloseHandle(h) == 0
118
163
  end
119
164
 
120
165
  # Get the last error code (errno) (can't fail)
121
166
  def get_last_error
122
- CALLS["kernel32!GetLastError:=L"].call
167
+ Win.GetLastError()
123
168
  end
124
169
 
125
170
  # strerror(errno) (can't fail)
126
171
  def format_message(code=nil)
127
172
  code ||= get_last_error
128
- buf = "\x00" * 4096
129
- CALLS["kernel32!FormatMessageA:LPLLPLP"].
130
- call(4096, NULL, code, 0x00000400, buf, 4096, NULL)
131
- return buf.split("\x00")[0]
173
+ buf = FFI::MemoryPointer.from_string("\x00" * 4096)
174
+ Win.FormatMessageA(4096, nil, code, 0x00000400, buf, 4096, nil)
175
+ return buf.to_s.split("\x00")[0]
132
176
  end
133
177
 
134
178
  # Allocate memory in a remote process (or yourself, with handle -1)
135
179
  def virtual_alloc_ex(h, sz, addr=NULL, prot=0x40)
136
- r = CALLS["kernel32!VirtualAllocEx:LLLLL=L"].
137
- call(h, addr, sz, 0x1000, prot)
180
+ r = Win.VirtualAllocEx(h, addr, sz, 0x1000, prot)
138
181
  raise WinX.new(:virtual_alloc_ex) if r == 0
139
182
  return r
140
183
  end
141
184
 
142
185
  # Free memory in a remote process given the pointer returned from virtual_alloc_ex
143
186
  def virtual_free_ex(h, ptr, type=0x8000)
144
- r = CALLS["kernel32!VirtualFreeEx:LLLL=L"].call(h, ptr.to_i, 0, type)
187
+ r = Win.VirtualFreeEx(h, ptr.to_i, 0, type)
145
188
  raise WinX.new(:virtual_free_ex) if r == 0
146
189
  return r
147
190
  end
@@ -149,19 +192,27 @@ module Ragweed::Wrap32
149
192
  # Write a string into the memory of a remote process given its handle and an address
150
193
  def write_process_memory(h, dst, val)
151
194
  val = val.to_s if not val.kind_of? String
152
- r = CALLS["kernel32!WriteProcessMemory:LLPLL=L"].call(h, dst.to_i, val, val.size, NULL)
195
+ r = Win.WriteProcessMemory(h, dst.to_i, val, val.size, NULL)
153
196
  raise WinX.new(:write_process_memory) if r == 0
154
197
  return r
155
198
  end
156
199
 
157
200
  # Read from a remote process given an address and length, returning a string.
158
201
  def read_process_memory(h, ptr, len)
202
+ # val = FFI::MemoryPointer.from_string("\x00" * len)
159
203
  val = "\x00" * len
160
- r = CALLS["kernel32!ReadProcessMemory:LLPLL=L"].call(h, ptr.to_i, val, len, NULL)
204
+ r = Win.ReadProcessMemory(h, ptr.to_i, val, len, NULL)
161
205
  raise WinX.new(:read_process_memory) if r == 0
162
206
  return val ## don't handle short reads XXX
163
207
  end
164
208
 
209
+ def get_mapped_filename(h, lpv, size)
210
+ val = "\x00" * size
211
+ r = Win.GetMappedFileNameA(h, lpv.to_i, val, size)
212
+ raise WinX.new(:get_mapped_filename) if r == 0
213
+ return val
214
+ end
215
+
165
216
  def str2memory_basic_info(mbi)
166
217
  s = OpenStruct.new
167
218
  s.BaseAddress,
@@ -179,7 +230,7 @@ module Ragweed::Wrap32
179
230
  # flags.
180
231
  def virtual_query_ex(h, ptr)
181
232
  mbi = [0,0,0,0,0,0,0].pack("LLLLLLL")
182
- if CALLS["kernel32!VirtualQueryEx:LLPL=L"].call(h, ptr, mbi, mbi.size)
233
+ if Win.VirtualQueryEx(h, ptr, mbi, mbi.size)
183
234
  str2memory_basic_info(mbi)
184
235
  else
185
236
  nil
@@ -192,7 +243,7 @@ module Ragweed::Wrap32
192
243
  base = virtual_query_ex(h, addr).BaseAddress if size == 0
193
244
  base ||= addr
194
245
 
195
- if CALLS["kernel32!VirtualProtectEx:LLLLP=L"].call(h, base, size, prot, old)
246
+ if Win.VirtualProtectEx(h, base, size, prot, old)
196
247
  old.unpack("L").first
197
248
  else
198
249
  raise WinX.new(:virtual_protect_ex)
@@ -201,26 +252,31 @@ module Ragweed::Wrap32
201
252
 
202
253
  # getpid
203
254
  def get_current_process_id
204
- CALLS["kernel32!GetCurrentProcessId:=L"].call # can't realistically fail
255
+ Win.GetCurrentProcessId() # can't realistically fail
256
+ end
257
+
258
+ # get_processid
259
+ def get_process_id(h)
260
+ Win.GetProcessId(h)
205
261
  end
206
262
 
207
263
  # gettid
208
264
  def get_current_thread_id
209
- CALLS["kernel32!GetCurrentThreadId:=L"].call # can't realistically fail
265
+ Win.GetCurrentThreadId() # can't realistically fail
210
266
  end
211
267
 
212
268
  # Given a DLL name, get a handle to the DLL.
213
269
  def get_module_handle(name)
214
- name = name.to_utf16
215
- r = CALLS["kernel32!GetModuleHandleW:P=L"].call(name)
270
+ name = name
271
+ r = Win.GetModuleHandleA(name)
216
272
  raise WinX.new(:get_module_handle) if r == 0
217
273
  return r
218
274
  end
219
275
 
220
276
  # load a library explicitly from a dll
221
277
  def load_library(name)
222
- name = name.to_utf16
223
- r = CALLS["kernel32!LoadLibraryW:P=L"].call(name)
278
+ name = name
279
+ r = Win.LoadLibraryA(name)
224
280
  raise WinX.new(:load_library) if r == 0
225
281
  return r
226
282
  end
@@ -236,13 +292,13 @@ module Ragweed::Wrap32
236
292
  meth = y
237
293
  end
238
294
 
239
- r = CALLS["kernel32!GetProcAddress:LP=L"].call(h, meth)
295
+ r = Win.GetProcAddress(h, meth)
240
296
  return r # pass error through
241
297
  end
242
298
 
243
299
  # Select(2), for a single object handle.
244
300
  def wait_for_single_object(h)
245
- r = CALLS["kernel32!WaitForSingleObject:LL=L"].call(h, -1)
301
+ r = Win.WaitForSingleObject(h, -1)
246
302
  raise WinX.new(:wait_for_single_object) if r == -1
247
303
  end
248
304
 
@@ -265,12 +321,12 @@ module Ragweed::Wrap32
265
321
  # Use Toolhelp32 to enumerate all running processes on the box, returning
266
322
  # a struct with PIDs and executable names.
267
323
  def all_processes
268
- h = CALLS["kernel32!CreateToolhelp32Snapshot:LL=L"].call(0x2, 0)
324
+ h = Win.CreateToolhelp32Snapshot(0x2, 0)
269
325
  if h != -1
270
326
  pi = [(9*4)+2048,0,0,0,0,0,0,0,0,"\x00"*2048].pack("LLLLLLLLLa2048")
271
- if CALLS["kernel32!Process32First:LP=L"].call(h, pi) != 0
327
+ if Win.Process32First(h, pi) != 0
272
328
  yield str2process_info(pi)
273
- while CALLS["kernel32!Process32Next:LP=L"].call(h, pi) != 0
329
+ while Win.Process32Next(h, pi) != 0
274
330
  yield str2process_info(pi)
275
331
  end
276
332
  end
@@ -299,12 +355,12 @@ module Ragweed::Wrap32
299
355
  # Given a pid, enumerate the modules loaded into the process, returning base
300
356
  # addresses, memory ranges, and the module name.
301
357
  def list_modules(pid=0)
302
- h = CALLS["kernel32!CreateToolhelp32Snapshot:LL=L"].call(0x8, pid)
358
+ h = Win.CreateToolhelp32Snapshot(0x8, pid)
303
359
  if h != -1
304
360
  mi = [260+256+(8*4),0,0,0,0,0,0,0,"\x00"*256,"\x00"*260].pack("LLLLLLLLa256a260")
305
- if CALLS["kernel32!Module32First:LP=L"].call(h, mi) != 0
361
+ if Win.Module32First(h, mi) != 0
306
362
  yield str2module_info(mi)
307
- while CALLS["kernel32!Module32Next:LP=L"].call(h, mi) != 0
363
+ while Win.Module32Next(h, mi) != 0
308
364
  yield str2module_info(mi)
309
365
  end
310
366
  end
@@ -327,7 +383,7 @@ module Ragweed::Wrap32
327
383
  # interface is Ioctl-style; provide an ordinal and a buffer to pass results through.
328
384
  def nt_query_information_process(h, ord, buf)
329
385
  lenp = [0].pack("L")
330
- if CALLS["ntdll!NtQueryInformationProcess:LLPLP=L"].call(h, ord, buf, buf.size, lenp) == 0
386
+ if Win.NtQueryInformationProcess(h, ord, buf, buf.size, lenp) == 0
331
387
  len = lenp.unpack("L").first
332
388
  return buf[0..(len-1)]
333
389
  end
@@ -349,13 +405,13 @@ module Ragweed::Wrap32
349
405
  # List all the threads in a process given its pid, returning a struct containing
350
406
  # tids and run state. This is relatively expensive, because it uses Toolhelp32.
351
407
  def threads(pid)
352
- h = CALLS["kernel32!CreateToolhelp32Snapshot:LL=L"].call(0x4, pid)
408
+ h = Win.CreateToolhelp32Snapshot(0x4, pid)
353
409
  if h != -1
354
410
  mi = [(7*4),0,0,0,0,0,0].pack("LLLLLLL")
355
- if CALLS["kernel32!Thread32First:LP=L"].call(h, mi) != 0
411
+ if Win.Thread32First(h, mi) != 0
356
412
  ti = str2thread_info(mi)
357
413
  yield str2thread_info(mi) if ti.th32OwnerProcessID == pid
358
- while CALLS["kernel32!Thread32Next:LP=L"].call(h, mi) != 0
414
+ while Win.Thread32Next(h, mi) != 0
359
415
  ti = str2thread_info(mi)
360
416
  yield str2thread_info(mi) if ti.th32OwnerProcessID == pid
361
417
  end
@@ -367,7 +423,7 @@ module Ragweed::Wrap32
367
423
 
368
424
  # Suspend a thread given its handle.
369
425
  def suspend_thread(h)
370
- r = CALLS["kernel32!SuspendThread:L=L"].call(h)
426
+ r = Win.SuspendThread(h)
371
427
  raise WinX.new(:suspend_thread) if r == 0
372
428
  return r
373
429
  end
@@ -375,25 +431,25 @@ module Ragweed::Wrap32
375
431
  # Resume a suspended thread, returning nonzero if the thread was suspended,
376
432
  # and 0 if it was running.
377
433
  def resume_thread(h)
378
- CALLS["kernel32!ResumeThread:L=L"].call(h)
434
+ ResumeThread(h)
379
435
  end
380
436
 
381
437
  # Create a remote thread in the process, starting at the location
382
438
  # "start", with the threadproc argument "arg"
383
439
  def create_remote_thread(h, start, arg)
384
- r = CALLS["kernel32!CreateRemoteThread:LLLLLLL=L"].call(h, NULL, 0, start.to_i, arg.to_i, 0, 0)
440
+ r = Win.CreateRemoteThread(h, NULL, 0, start.to_i, arg.to_i, 0, 0)
385
441
  raise WinX.new(:create_remote_thread) if r == 0
386
442
  return r
387
443
  end
388
444
 
389
445
  def sleep(ms=0)
390
- CALLS["kernel32!Sleep:L=L"].call(ms)
446
+ Win.Sleep(ms)
391
447
  end
392
448
 
393
449
  # clone a handle out of another open process (or self, with -1)
394
450
  def duplicate_handle(ph, h)
395
451
  ret = "\x00\x00\x00\x00"
396
- r = CALLS["kernel32!DuplicateHandle:LLLPLLL=L"].call(ph, h, -1, ret, 0, 0, 0x2)
452
+ r = Win.DuplicateHandle(ph, h, -1, ret, 0, 0, 0x2)
397
453
  raise WinX.new(:duplicate_handle) if r == 0
398
454
  ret.to_l32
399
455
  end
@@ -404,29 +460,28 @@ module Ragweed::Wrap32
404
460
  opts[:access] ||= FileAccess::GENERIC_ALL
405
461
  opts[:flags] ||= 0
406
462
 
407
- r = CALLS["kernel32!CreateFile:PLLPLLP=L"].
408
- call(name, opts[:access], opts[:sharing], NULL, opts[:disposition], opts[:flags], NULL)
463
+ r = Win.CreateFileA(name, opts[:access], opts[:sharing], NULL, opts[:disposition], opts[:flags], NULL)
409
464
  raise WinX.new(:create_file) if r == -1
410
465
  return r
411
466
  end
412
467
 
413
468
  # i haven't made this work, but named handles are kind of silly anyways
414
469
  def open_event(name)
415
- r = CALLS["kernel32!OpenEvent:LLP=L"].call(0, 0, name)
470
+ r = Win.OpenEventA(0, 0, name)
416
471
  raise WinX.new(:open_event) if r == 0
417
472
  return r
418
473
  end
419
474
 
420
475
  # signal an event
421
476
  def set_event(h)
422
- r = CALLS["kernel32!SetEvent:L=L"].call(h)
477
+ r = Win.SetEvent(h)
423
478
  raise WinX.new(:set_event) if r == 0
424
479
  return r
425
480
  end
426
481
 
427
482
  # force-unsignal event (waiting on the event handle also does this)
428
483
  def reset_event(h)
429
- r = CALLS["kernel32!ResetEvent:L=L"].call(h)
484
+ r = Win.ResetEvent(h)
430
485
  raise WinX.new(:reset_event) if r == 0
431
486
  return r
432
487
  end
@@ -437,7 +492,7 @@ module Ragweed::Wrap32
437
492
  signalled = (1 if signalled) || 0
438
493
  name ||= 0
439
494
 
440
- r = CALLS["kernel32!CreateEvent:LLLP=L"].call(0, auto, signalled, name);
495
+ r = Win.CreateEventA(0, auto, signalled, name);
441
496
  raise WinX.new(:create_event) if r == 0
442
497
  return r
443
498
  end
@@ -450,7 +505,7 @@ module Ragweed::Wrap32
450
505
  end
451
506
 
452
507
  outw = "\x00" * 4
453
- r = CALLS["kernel32!WriteFile:LPLPP=L"].call(h, buf, buf.size, outw, opp)
508
+ r = Win.WriteFile(h, buf, buf.size, outw, opp)
454
509
  raise WinX.new(:write_file) if r == 0 and get_last_error != 997
455
510
  return buf, outw.unpack("L").first
456
511
  end
@@ -467,7 +522,7 @@ module Ragweed::Wrap32
467
522
  overlapped.target = buf if overlapped
468
523
  end
469
524
 
470
- r = CALLS["kernel32!ReadFile:LPLPP=L"].call(h, buf, count, outw, opp)
525
+ r = Win.ReadFile(h, buf, count, outw, opp)
471
526
  raise WinX.new(:read_file) if r == 0 and get_last_error != 997
472
527
  return buf, outw.unpack("L").first
473
528
  end
@@ -475,8 +530,7 @@ module Ragweed::Wrap32
475
530
  def device_io_control(h, code, inbuf, outbuf, overlapped=NULL)
476
531
  overlapped = overlapped.to_s if overlapped
477
532
  outw = "\x00" * 4
478
- r = CALLS["kernel32!DeviceIoControl:LLPLPLPP=L"].
479
- call(h, code, inbuf, inbuf.size, outbuf, outbuf.size, outw, overlapped)
533
+ r = Win.DeviceIoControl(h, code, inbuf, inbuf.size, outbuf, outbuf.size, outw, overlapped)
480
534
  raise WinX.new(:device_io_control) if r == 0 and get_last_error != 997
481
535
  return outw.unpack("L").first
482
536
  end
@@ -484,20 +538,21 @@ module Ragweed::Wrap32
484
538
  def get_overlapped_result(h, overlapped)
485
539
  overlapped = overlapped.to_s
486
540
  outw = "\x00" * 4
487
- r = CALLS["kernel32!GetOverlappedResult:LPPL=L"].call(h, overlapped, outw, 0)
541
+ r = Win.GetOverlappedResult(h, overlapped, outw, 0)
488
542
  raise WinX.new(:get_overlapped_result) if r == 0
489
543
  return outw.unpack("L").first
490
544
  end
491
545
 
492
546
  # just grab some local memory
547
+ # XXX same as FFI name ?
493
548
  def malloc(sz)
494
- r = CALLS["msvcrt!malloc:L=L"].call(sz)
549
+ r = Win.malloc(sz)
495
550
  raise WinX.new(:malloc) if r == 0
496
551
  return r
497
552
  end
498
553
 
499
554
  def memcpy(dst, src, size)
500
- CALLS["msvcrt!memcpy:PPL=L"].call(dst, src, size)
555
+ Win.memcpy(dst, src, size)
501
556
  end
502
557
 
503
558
  # Block wrapper for thread suspension
@@ -514,7 +569,7 @@ module Ragweed::Wrap32
514
569
 
515
570
  def wfmo(handles, ms=100)
516
571
  hp = handles.to_ptr
517
- r = CALLS["kernel32!WaitForMultipleObjects:LPLL=L"].call(handles.size, hp, 0, ms)
572
+ r = Win.WaitForMultipleObjects(handles.size, hp, 0, ms)
518
573
  raise WinX(:wait_for_multiple_objects) if r == 0xFFFFFFFF
519
574
  if r < handles.size
520
575
  return handles[r]
@@ -5,7 +5,7 @@ module Ragweed; end
5
5
  module Ragweed::Wrap32
6
6
 
7
7
  # :stopdoc:
8
- VERSION = '0.1.7.3'
8
+ VERSION = File.read(File.join(File.dirname(__FILE__),"..","..","VERSION"))
9
9
  LIBPATH = ::File.expand_path(::File.dirname(__FILE__)) + ::File::SEPARATOR
10
10
  PATH = ::File.dirname(LIBPATH) + ::File::SEPARATOR
11
11
  # :startdoc:
@@ -86,6 +86,7 @@ module Ragweed::Wraposx::Vm::Prot
86
86
  NONE = 0x0 #no rights
87
87
  ALL = 0x7 #all permissions
88
88
  end
89
+
89
90
  module Ragweed::Wraposx::Vm::Sm
90
91
  # share mode constants
91
92
  COW = 1
@@ -97,15 +98,6 @@ module Ragweed::Wraposx::Vm::Sm
97
98
  SHARED_ALIASED = 7
98
99
  end
99
100
 
100
- # this should be moved to an include for all wrappers
101
- module Ragweed::Wraposx::SizeOf
102
- INT = [1].pack("I_").size
103
- SHORT = [1].pack("S_").size
104
- LONG = [1].pack("L_").size
105
- DOUBLE = [1].pack("D").size
106
- FLOAT = [1].pack("F").size
107
- end
108
-
109
101
  module Ragweed::Wraposx::Dl
110
102
  RTLD_LAZY = 0x1
111
103
  RTLD_NOW = 0x2