ffi-extra 0.0.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/lib/ffi/extra.rb +131 -0
- metadata +64 -0
data/lib/ffi/extra.rb
ADDED
@@ -0,0 +1,131 @@
|
|
1
|
+
#--
|
2
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
3
|
+
# Version 2, December 2004
|
4
|
+
#
|
5
|
+
# Copyleft meh. [http://meh.paranoid.pk | meh@paranoici.org]
|
6
|
+
#
|
7
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
8
|
+
# TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
9
|
+
#
|
10
|
+
# 0. You just DO WHAT THE FUCK YOU WANT TO.
|
11
|
+
#++
|
12
|
+
|
13
|
+
class Integer
|
14
|
+
def to_ffi
|
15
|
+
self
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
class String
|
20
|
+
def to_ffi
|
21
|
+
self
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
class NilClass
|
26
|
+
def to_ffi
|
27
|
+
self
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
module FFI
|
32
|
+
def self.type_size (type)
|
33
|
+
type = FFI.find_type(type) if type.is_a?(Symbol)
|
34
|
+
|
35
|
+
if type.is_a?(Class) && type.ancestors.member?(FFI::Struct) || type.ancestors.member?(FFI::ManagedStruct) || type.ancestors.member?(Type::Builtin)
|
36
|
+
type.size
|
37
|
+
elsif type.respond_to? :from_native
|
38
|
+
type.native_type.size
|
39
|
+
else
|
40
|
+
raise ArgumentError, 'you have to pass a Struct, a Builtin type or a Symbol'
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
module Library
|
45
|
+
def ffi_lib_add (*names)
|
46
|
+
ffi_lib *((begin
|
47
|
+
ffi_libraries
|
48
|
+
rescue Exception
|
49
|
+
[]
|
50
|
+
end).map {|lib|
|
51
|
+
lib.name
|
52
|
+
} + names).compact.uniq.reject {|lib|
|
53
|
+
lib == '[current process]'
|
54
|
+
}
|
55
|
+
end
|
56
|
+
|
57
|
+
def has_function? (sym, libraries=nil)
|
58
|
+
libraries ||= ffi_libraries
|
59
|
+
|
60
|
+
libraries.any? {|lib|
|
61
|
+
if lib.is_a?(DynamicLibrary)
|
62
|
+
lib
|
63
|
+
else
|
64
|
+
DynamicLibrary.new(lib, 0)
|
65
|
+
end.find_function(sym.to_s) rescue nil
|
66
|
+
}
|
67
|
+
end
|
68
|
+
|
69
|
+
def attach_function! (*args, &block)
|
70
|
+
begin
|
71
|
+
attach_function(*args, &block)
|
72
|
+
rescue Exception => e
|
73
|
+
false
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
class Type::Builtin
|
79
|
+
def name
|
80
|
+
inspect[/:(\w+) /][1 .. -2]
|
81
|
+
end
|
82
|
+
end
|
83
|
+
|
84
|
+
class Pointer
|
85
|
+
def typecast (type)
|
86
|
+
if type.is_a?(Symbol)
|
87
|
+
if respond_to? "read_#{type}"
|
88
|
+
return send "read_#{type}"
|
89
|
+
else
|
90
|
+
type = FFI.find_type(type)
|
91
|
+
end
|
92
|
+
end
|
93
|
+
|
94
|
+
if type.is_a?(Class) && type.ancestors.member?(FFI::Struct) && !type.ancestors.member?(FFI::ManagedStruct)
|
95
|
+
type.new(self)
|
96
|
+
elsif type.is_a?(Type::Builtin)
|
97
|
+
send "read_#{type.name.downcase}"
|
98
|
+
elsif type.respond_to? :from_native
|
99
|
+
type.from_native(typecast(type.native_type), nil)
|
100
|
+
else
|
101
|
+
raise ArgumentError, 'you have to pass a Struct, a Builtin type or a Symbol'
|
102
|
+
end
|
103
|
+
end
|
104
|
+
|
105
|
+
def read_array_of (type, number)
|
106
|
+
if type.is_a?(Symbol)
|
107
|
+
if respond_to? "read_array_of_#{type}"
|
108
|
+
return send "read_array_of_#{type}"
|
109
|
+
else
|
110
|
+
type = FFI.find_type(type)
|
111
|
+
end
|
112
|
+
end
|
113
|
+
|
114
|
+
type = type.native_type if type.respond_to? :native_type
|
115
|
+
|
116
|
+
if type.is_a?(Class) && type.ancestors.member?(FFI::Struct) || type.is_a?(FFI::ManagedStruct)
|
117
|
+
read_array_of_pointer(number).map {|pointer|
|
118
|
+
type.new(pointer)
|
119
|
+
}
|
120
|
+
else
|
121
|
+
begin
|
122
|
+
send "read_array_of_#{type.name.downcase}", number
|
123
|
+
rescue
|
124
|
+
raise ArgumentError, "#{type.name} is not supported"
|
125
|
+
end
|
126
|
+
end
|
127
|
+
end
|
128
|
+
end
|
129
|
+
|
130
|
+
find_type(:size_t) rescue typedef(:ulong, :size_t)
|
131
|
+
end
|
metadata
ADDED
@@ -0,0 +1,64 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: ffi-extra
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
prerelease:
|
5
|
+
version: 0.0.1
|
6
|
+
platform: ruby
|
7
|
+
authors:
|
8
|
+
- meh.
|
9
|
+
autorequire:
|
10
|
+
bindir: bin
|
11
|
+
cert_chain: []
|
12
|
+
|
13
|
+
date: 2011-09-06 00:00:00 Z
|
14
|
+
dependencies:
|
15
|
+
- !ruby/object:Gem::Dependency
|
16
|
+
name: ffi
|
17
|
+
prerelease: false
|
18
|
+
requirement: &id001 !ruby/object:Gem::Requirement
|
19
|
+
none: false
|
20
|
+
requirements:
|
21
|
+
- - ">="
|
22
|
+
- !ruby/object:Gem::Version
|
23
|
+
version: "0"
|
24
|
+
type: :runtime
|
25
|
+
version_requirements: *id001
|
26
|
+
description:
|
27
|
+
email: meh@paranoici.org
|
28
|
+
executables: []
|
29
|
+
|
30
|
+
extensions: []
|
31
|
+
|
32
|
+
extra_rdoc_files: []
|
33
|
+
|
34
|
+
files:
|
35
|
+
- lib/ffi/extra.rb
|
36
|
+
homepage: http://github.com/meh/ruby-ffi-extra
|
37
|
+
licenses: []
|
38
|
+
|
39
|
+
post_install_message:
|
40
|
+
rdoc_options: []
|
41
|
+
|
42
|
+
require_paths:
|
43
|
+
- lib
|
44
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
45
|
+
none: false
|
46
|
+
requirements:
|
47
|
+
- - ">="
|
48
|
+
- !ruby/object:Gem::Version
|
49
|
+
version: "0"
|
50
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
51
|
+
none: false
|
52
|
+
requirements:
|
53
|
+
- - ">="
|
54
|
+
- !ruby/object:Gem::Version
|
55
|
+
version: "0"
|
56
|
+
requirements: []
|
57
|
+
|
58
|
+
rubyforge_project:
|
59
|
+
rubygems_version: 1.8.5
|
60
|
+
signing_key:
|
61
|
+
specification_version: 3
|
62
|
+
summary: Some extra methods for FFI
|
63
|
+
test_files: []
|
64
|
+
|