gir_ffi 0.2.2 → 0.2.3
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 +6 -0
- data/lib/ffi-glib.rb +1 -0
- data/lib/ffi-glib/array.rb +49 -10
- data/lib/ffi-glib/hash_table.rb +19 -5
- data/lib/ffi-glib/list.rb +4 -1
- data/lib/ffi-glib/list_methods.rb +8 -1
- data/lib/ffi-glib/s_list.rb +4 -1
- data/lib/ffi-glib/strv.rb +31 -0
- data/lib/ffi-gobject.rb +2 -35
- data/lib/ffi-gobject/base.rb +38 -0
- data/lib/ffi-gobject/object.rb +28 -30
- data/lib/ffi-gobject/value.rb +72 -56
- data/lib/ffi-gobject_introspection/i_struct_info.rb +11 -1
- data/lib/ffi-gobject_introspection/lib.rb +3 -1
- data/lib/gir_ffi/arg_helper.rb +2 -19
- data/lib/gir_ffi/builder/argument.rb +239 -305
- data/lib/gir_ffi/builder/argument/base.rb +12 -9
- data/lib/gir_ffi/builder/argument/in_base.rb +2 -6
- data/lib/gir_ffi/builder/argument/in_out_base.rb +2 -5
- data/lib/gir_ffi/builder/argument/out_base.rb +0 -11
- data/lib/gir_ffi/builder/field.rb +55 -0
- data/lib/gir_ffi/builder/function.rb +7 -7
- data/lib/gir_ffi/builder/module.rb +5 -7
- data/lib/gir_ffi/builder/type/object.rb +0 -33
- data/lib/gir_ffi/builder/type/registered_type.rb +0 -16
- data/lib/gir_ffi/builder/type/struct_based.rb +3 -3
- data/lib/gir_ffi/builder/type/unintrospectable.rb +1 -1
- data/lib/gir_ffi/builder/type/with_layout.rb +26 -58
- data/lib/gir_ffi/builder/type/with_methods.rb +9 -11
- data/lib/gir_ffi/class_base.rb +24 -6
- data/lib/gir_ffi/ffi_ext/pointer.rb +15 -0
- data/lib/gir_ffi/in_pointer.rb +10 -5
- data/lib/gir_ffi/info_ext/i_field_info.rb +15 -0
- data/lib/gir_ffi/info_ext/i_type_info.rb +26 -0
- data/lib/gir_ffi/method_stubber.rb +18 -0
- data/lib/gir_ffi/type_map.rb +1 -0
- data/lib/gir_ffi/variable_name_generator.rb +2 -0
- data/lib/gir_ffi/version.rb +1 -1
- data/test/builder_test.rb +6 -5
- data/test/ffi-glib/array_test.rb +40 -5
- data/test/ffi-glib/hash_table_test.rb +27 -3
- data/test/ffi-glib/list_test.rb +23 -0
- data/test/ffi-glib/strv_test.rb +41 -0
- data/test/ffi-gobject/gobject_test.rb +26 -22
- data/test/ffi-gobject/value_test.rb +26 -1
- data/test/ffi-gobject_introspection/lib_test.rb +10 -0
- data/test/gir_ffi_test_helper.rb +1 -1
- data/test/integration/derived_classes_test.rb +31 -0
- data/test/integration/generated_gimarshallingtests_test.rb +29 -15
- data/test/integration/generated_gio_test.rb +5 -6
- data/test/integration/generated_regress_test.rb +11 -7
- data/test/integration/method_lookup_test.rb +32 -0
- data/test/interface_type_builder_test.rb +1 -1
- data/test/test_helper.rb +38 -0
- data/test/unit/argument_builder_test.rb +16 -4
- data/test/unit/class_base_test.rb +48 -0
- data/test/unit/function_builder_test.rb +144 -4
- data/test/unit/hash_table_element_type_provider_test.rb +16 -0
- data/test/unit/i_field_info_test.rb +39 -0
- data/test/unit/i_type_info_test.rb +23 -0
- data/test/unit/list_element_type_provider_test.rb +13 -0
- data/test/unit/module_builder_test.rb +1 -1
- data/test/unit/object_type_builder_test.rb +0 -17
- data/test/unit/struct_builder_test.rb +27 -39
- metadata +118 -60
- data/lib/gir_ffi/builder/argument/hash_table_base.rb +0 -20
- data/lib/gir_ffi/builder/argument/list_base.rb +0 -16
- data/test/class_base_test.rb +0 -10
- data/test/function_definition_builder_test.rb +0 -130
@@ -1,3 +1,5 @@
|
|
1
|
+
require 'gir_ffi/method_stubber'
|
2
|
+
|
1
3
|
module GirFFI
|
2
4
|
module Builder
|
3
5
|
module Type
|
@@ -15,6 +17,10 @@ module GirFFI
|
|
15
17
|
attach_and_define_method method, go, build_class
|
16
18
|
end
|
17
19
|
|
20
|
+
def has_instance_method method
|
21
|
+
!!instance_method_introspection_data(method)
|
22
|
+
end
|
23
|
+
|
18
24
|
private
|
19
25
|
|
20
26
|
def meta_class
|
@@ -28,7 +34,7 @@ module GirFFI
|
|
28
34
|
|
29
35
|
def instance_method_introspection_data method
|
30
36
|
data = method_introspection_data method
|
31
|
-
return
|
37
|
+
return data if data && data.method?
|
32
38
|
end
|
33
39
|
|
34
40
|
def function_definition_builder go
|
@@ -43,24 +49,16 @@ module GirFFI
|
|
43
49
|
return false if go.nil?
|
44
50
|
Builder.attach_ffi_function lib, go
|
45
51
|
modul.class_eval { remove_method method }
|
46
|
-
|
52
|
+
build_class.class_eval function_definition(go)
|
47
53
|
true
|
48
54
|
end
|
49
55
|
|
50
56
|
def stub_methods
|
51
57
|
info.get_methods.each do |minfo|
|
52
|
-
@klass.class_eval
|
58
|
+
@klass.class_eval MethodStubber.new(minfo).method_stub
|
53
59
|
end
|
54
60
|
end
|
55
61
|
|
56
|
-
def method_stub symbol, is_instance_method
|
57
|
-
"
|
58
|
-
def #{is_instance_method ? '' : 'self.'}#{symbol} *args, &block
|
59
|
-
setup_and_call :#{symbol}, *args, &block
|
60
|
-
end
|
61
|
-
"
|
62
|
-
end
|
63
|
-
|
64
62
|
def pretty_print_methods
|
65
63
|
info.get_methods.map do |minfo|
|
66
64
|
function_definition_builder(minfo).pretty_print.indent + "\n"
|
data/lib/gir_ffi/class_base.rb
CHANGED
@@ -1,4 +1,6 @@
|
|
1
1
|
require 'forwardable'
|
2
|
+
require 'gir_ffi/ffi_ext/pointer'
|
3
|
+
|
2
4
|
module GirFFI
|
3
5
|
# Base class for all generated classes. Contains code for dealing with
|
4
6
|
# the generated Struct classes.
|
@@ -20,16 +22,28 @@ module GirFFI
|
|
20
22
|
end
|
21
23
|
|
22
24
|
def setup_and_call method, *arguments, &block
|
23
|
-
|
25
|
+
result = self.class.ancestors.any? do |klass|
|
26
|
+
klass.respond_to?(:_setup_instance_method) &&
|
27
|
+
klass._setup_instance_method(method.to_s)
|
28
|
+
end
|
29
|
+
|
30
|
+
unless result
|
24
31
|
raise RuntimeError, "Unable to set up instance method #{method} in #{self}"
|
25
32
|
end
|
33
|
+
|
26
34
|
self.send method, *arguments, &block
|
27
35
|
end
|
28
36
|
|
29
37
|
def self.setup_and_call method, *arguments, &block
|
30
|
-
|
38
|
+
result = self.ancestors.any? do |klass|
|
39
|
+
klass.respond_to?(:_setup_method) &&
|
40
|
+
klass._setup_method(method.to_s)
|
41
|
+
end
|
42
|
+
|
43
|
+
unless result
|
31
44
|
raise RuntimeError, "Unable to set up method #{method} in #{self}"
|
32
45
|
end
|
46
|
+
|
33
47
|
self.send method, *arguments, &block
|
34
48
|
end
|
35
49
|
|
@@ -67,10 +81,7 @@ module GirFFI
|
|
67
81
|
|
68
82
|
def wrap ptr
|
69
83
|
return nil if ptr.nil? or ptr.null?
|
70
|
-
|
71
|
-
ptr = ptr.to_ptr
|
72
|
-
end
|
73
|
-
_real_new ptr
|
84
|
+
_real_new ptr.to_ptr
|
74
85
|
end
|
75
86
|
|
76
87
|
# TODO: Only makes sense for :objects.
|
@@ -81,6 +92,13 @@ module GirFFI
|
|
81
92
|
def allocate
|
82
93
|
_real_new
|
83
94
|
end
|
95
|
+
|
96
|
+
# Pass-through casting method. This may become a type checking
|
97
|
+
# method. It is overridden by GValue to implement wrapping of plain
|
98
|
+
# Ruby objects.
|
99
|
+
def from val
|
100
|
+
val
|
101
|
+
end
|
84
102
|
end
|
85
103
|
end
|
86
104
|
end
|
data/lib/gir_ffi/in_pointer.rb
CHANGED
@@ -8,11 +8,7 @@ module GirFFI
|
|
8
8
|
return from_utf8_array ary if type == :utf8
|
9
9
|
return from_interface_pointer_array ary if type == :interface_pointer
|
10
10
|
|
11
|
-
|
12
|
-
block = ArgHelper.allocate_array_of_type ffi_type, ary.length
|
13
|
-
block.send "put_array_of_#{ffi_type}", 0, ary
|
14
|
-
|
15
|
-
self.new block
|
11
|
+
return from_basic_type_array type, ary
|
16
12
|
end
|
17
13
|
|
18
14
|
def self.from type, val
|
@@ -48,6 +44,15 @@ module GirFFI
|
|
48
44
|
ptr = AllocationHelper.safe_malloc(len + 1).write_string(str).put_char(len, 0)
|
49
45
|
self.new ptr
|
50
46
|
end
|
47
|
+
|
48
|
+
def from_basic_type_array type, ary
|
49
|
+
ffi_type = TypeMap.map_basic_type type
|
50
|
+
block = ArgHelper.allocate_array_of_type ffi_type, ary.length
|
51
|
+
block.send "put_array_of_#{ffi_type}", 0, ary
|
52
|
+
|
53
|
+
self.new block
|
54
|
+
end
|
55
|
+
|
51
56
|
end
|
52
57
|
end
|
53
58
|
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
require 'gir_ffi/info_ext/i_type_info'
|
2
|
+
|
3
|
+
module GirFFI
|
4
|
+
module InfoExt
|
5
|
+
module IFieldInfo
|
6
|
+
def layout_specification
|
7
|
+
[ name.to_sym,
|
8
|
+
field_type.layout_specification_type,
|
9
|
+
offset ]
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
GObjectIntrospection::IFieldInfo.send :include, GirFFI::InfoExt::IFieldInfo
|
@@ -0,0 +1,26 @@
|
|
1
|
+
require 'gir_ffi/builder_helper'
|
2
|
+
|
3
|
+
module GirFFI
|
4
|
+
module InfoExt
|
5
|
+
module ITypeInfo
|
6
|
+
include BuilderHelper
|
7
|
+
|
8
|
+
def layout_specification_type
|
9
|
+
ffitype = GirFFI::Builder.itypeinfo_to_ffitype self
|
10
|
+
case ffitype
|
11
|
+
when Class
|
12
|
+
ffitype.const_get :Struct
|
13
|
+
when :bool
|
14
|
+
:int
|
15
|
+
when :array
|
16
|
+
subtype = param_type(0).layout_specification_type
|
17
|
+
[subtype, array_fixed_size]
|
18
|
+
else
|
19
|
+
ffitype
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
GObjectIntrospection::ITypeInfo.send :include, GirFFI::InfoExt::ITypeInfo
|
@@ -0,0 +1,18 @@
|
|
1
|
+
module GirFFI
|
2
|
+
# Generates method stubs that will replace themselves with the real
|
3
|
+
# method upon being called.
|
4
|
+
class MethodStubber
|
5
|
+
def initialize method_info
|
6
|
+
@info = method_info
|
7
|
+
end
|
8
|
+
|
9
|
+
def method_stub
|
10
|
+
symbol = @info.name
|
11
|
+
"
|
12
|
+
def #{@info.method? ? '' : 'self.'}#{symbol} *args, &block
|
13
|
+
setup_and_call :#{symbol}, *args, &block
|
14
|
+
end
|
15
|
+
"
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
data/lib/gir_ffi/type_map.rb
CHANGED
data/lib/gir_ffi/version.rb
CHANGED
data/test/builder_test.rb
CHANGED
@@ -64,7 +64,7 @@ class BuilderTest < MiniTest::Spec
|
|
64
64
|
end
|
65
65
|
|
66
66
|
should "create a Gtk::Window#to_ptr method" do
|
67
|
-
assert Gtk::Window.
|
67
|
+
assert Gtk::Window.public_method_defined? :to_ptr
|
68
68
|
end
|
69
69
|
|
70
70
|
after do
|
@@ -126,7 +126,7 @@ class BuilderTest < MiniTest::Spec
|
|
126
126
|
end
|
127
127
|
|
128
128
|
GirFFI::Builder.send :attach_ffi_function, libmod, @go
|
129
|
-
|
129
|
+
assert_defines_singleton_method libmod, :gtk_main
|
130
130
|
end
|
131
131
|
end
|
132
132
|
|
@@ -269,9 +269,10 @@ class BuilderTest < MiniTest::Spec
|
|
269
269
|
GirFFI::Builder.build_module 'Regress'
|
270
270
|
end
|
271
271
|
|
272
|
-
should "
|
273
|
-
|
274
|
-
|
272
|
+
should "autocreate singleton methods" do
|
273
|
+
refute_defines_singleton_method Regress, :test_uint
|
274
|
+
Regress.test_uint 31
|
275
|
+
assert_defines_singleton_method Regress, :test_uint
|
275
276
|
end
|
276
277
|
|
277
278
|
should "autocreate the TestObj class" do
|
data/test/ffi-glib/array_test.rb
CHANGED
@@ -32,12 +32,22 @@ describe GLib::Array do
|
|
32
32
|
|
33
33
|
assert_equal [1, 2, 3], a
|
34
34
|
end
|
35
|
+
end
|
36
|
+
|
37
|
+
describe "::wrap" do
|
38
|
+
it "wraps a pointer, taking the element type as the first argument" do
|
39
|
+
arr = GLib::Array.new :gint32
|
40
|
+
arr.append_vals [1, 2, 3]
|
41
|
+
arr2 = GLib::Array.wrap :gint32, arr.to_ptr
|
42
|
+
assert_equal arr.to_a, arr2.to_a
|
43
|
+
end
|
35
44
|
|
36
|
-
it "
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
45
|
+
it "raises an error if the element sizes don't match" do
|
46
|
+
arr = GLib::Array.new :gint32
|
47
|
+
arr.append_vals [1, 2, 3]
|
48
|
+
assert_raises RuntimeError do
|
49
|
+
GLib::Array.wrap :gint8, arr.to_ptr
|
50
|
+
end
|
41
51
|
end
|
42
52
|
end
|
43
53
|
|
@@ -50,5 +60,30 @@ describe GLib::Array do
|
|
50
60
|
arr.append_vals [1, 2, 3]
|
51
61
|
assert_equal [1, 2, 3], arr.to_a
|
52
62
|
end
|
63
|
+
|
64
|
+
describe "::from" do
|
65
|
+
it "creates a GArray from a Ruby array" do
|
66
|
+
arr = GLib::Array.from :gint32, [3, 2, 1]
|
67
|
+
assert_equal [3, 2, 1], arr.to_a
|
68
|
+
end
|
69
|
+
|
70
|
+
it "return its argument if given a GArray" do
|
71
|
+
arr = GLib::Array.new :gint32
|
72
|
+
arr.append_vals [3, 2, 1]
|
73
|
+
arr2 = GLib::Array.from :foo, arr
|
74
|
+
assert_equal arr, arr2
|
75
|
+
end
|
76
|
+
|
77
|
+
it "wraps its argument if given a pointer" do
|
78
|
+
arr = GLib::Array.new :gint32
|
79
|
+
arr.append_vals [3, 2, 1]
|
80
|
+
pointer = arr.to_ptr
|
81
|
+
assert_instance_of FFI::Pointer, pointer
|
82
|
+
arr2 = GLib::Array.from :gint32, pointer
|
83
|
+
assert_instance_of GLib::Array, arr2
|
84
|
+
refute_equal arr, arr2
|
85
|
+
assert_equal arr.to_a, arr2.to_a
|
86
|
+
end
|
87
|
+
end
|
53
88
|
end
|
54
89
|
|
@@ -9,16 +9,40 @@ describe GLib::HashTable do
|
|
9
9
|
|
10
10
|
describe "::from_hash" do
|
11
11
|
it "creates a GHashTable from a Ruby array" do
|
12
|
-
hsh = GLib::HashTable.from_hash :utf8, :gint32,
|
12
|
+
hsh = GLib::HashTable.from_hash [:utf8, :gint32],
|
13
13
|
{"foo" => 23, "bar" => 32}
|
14
14
|
assert_equal({"foo" => 23, "bar" => 32}, hsh.to_hash)
|
15
15
|
end
|
16
16
|
|
17
17
|
it "return its argument if given a GHashTable" do
|
18
|
-
hsh = GLib::HashTable.from_hash :utf8, :gint32, {"foo" => 23, "bar" => 32}
|
19
|
-
hsh2 = GLib::HashTable.from_hash :utf8, :gint32, hsh
|
18
|
+
hsh = GLib::HashTable.from_hash [:utf8, :gint32], {"foo" => 23, "bar" => 32}
|
19
|
+
hsh2 = GLib::HashTable.from_hash [:utf8, :gint32], hsh
|
20
20
|
assert_equal hsh, hsh2
|
21
21
|
end
|
22
22
|
end
|
23
|
+
|
24
|
+
describe "::from" do
|
25
|
+
it "creates a GHashTable from a Ruby array" do
|
26
|
+
hsh = GLib::HashTable.from [:utf8, :gint32],
|
27
|
+
{"foo" => 23, "bar" => 32}
|
28
|
+
assert_equal({"foo" => 23, "bar" => 32}, hsh.to_hash)
|
29
|
+
end
|
30
|
+
|
31
|
+
it "return its argument if given a GHashTable" do
|
32
|
+
hsh = GLib::HashTable.from [:utf8, :gint32], {"foo" => 23, "bar" => 32}
|
33
|
+
hsh2 = GLib::HashTable.from [:utf8, :gint32], hsh
|
34
|
+
assert_equal hsh, hsh2
|
35
|
+
end
|
36
|
+
|
37
|
+
it "wraps its argument if given a pointer" do
|
38
|
+
hsh = GLib::HashTable.from [:utf8, :gint32], {"foo" => 23, "bar" => 32}
|
39
|
+
pointer = hsh.to_ptr
|
40
|
+
assert_instance_of FFI::Pointer, pointer
|
41
|
+
hsh2 = GLib::HashTable.from [:utf8, :gint32], pointer
|
42
|
+
assert_instance_of GLib::HashTable, hsh2
|
43
|
+
refute_equal hsh, hsh2
|
44
|
+
assert_equal hsh.to_hash, hsh2.to_hash
|
45
|
+
end
|
46
|
+
end
|
23
47
|
end
|
24
48
|
|
data/test/ffi-glib/list_test.rb
CHANGED
@@ -43,4 +43,27 @@ describe GLib::List do
|
|
43
43
|
assert_equal lst, lst2
|
44
44
|
end
|
45
45
|
end
|
46
|
+
|
47
|
+
describe "::from" do
|
48
|
+
it "creates a GList from a Ruby array" do
|
49
|
+
lst = GLib::List.from :gint32, [3, 2, 1]
|
50
|
+
assert_equal [3, 2, 1], lst.to_a
|
51
|
+
end
|
52
|
+
|
53
|
+
it "return its argument if given a GList" do
|
54
|
+
lst = GLib::List.from :gint32, [3, 2, 1]
|
55
|
+
lst2 = GLib::List.from :gint32, lst
|
56
|
+
assert_equal lst, lst2
|
57
|
+
end
|
58
|
+
|
59
|
+
it "wraps its argument if given a pointer" do
|
60
|
+
lst = GLib::List.from :gint32, [3, 2, 1]
|
61
|
+
pointer = lst.to_ptr
|
62
|
+
assert_instance_of FFI::Pointer, pointer
|
63
|
+
lst2 = GLib::List.from :gint32, pointer
|
64
|
+
assert_instance_of GLib::List, lst2
|
65
|
+
refute_equal lst, lst2
|
66
|
+
assert_equal lst.to_a, lst2.to_a
|
67
|
+
end
|
68
|
+
end
|
46
69
|
end
|
@@ -0,0 +1,41 @@
|
|
1
|
+
require File.expand_path('../gir_ffi_test_helper.rb', File.dirname(__FILE__))
|
2
|
+
|
3
|
+
require 'ffi-glib/strv'
|
4
|
+
|
5
|
+
describe GLib::Strv do
|
6
|
+
it "wraps a pointer" do
|
7
|
+
strv = GLib::Strv.new :some_pointer
|
8
|
+
assert_equal :some_pointer, strv.to_ptr
|
9
|
+
end
|
10
|
+
|
11
|
+
describe "::wrap" do
|
12
|
+
it "takes a pointer and returns a GLib::Strv wrapping it" do
|
13
|
+
strv = GLib::Strv.wrap :some_pointer
|
14
|
+
assert_instance_of GLib::Strv, strv
|
15
|
+
assert_equal :some_pointer, strv.to_ptr
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
describe "#each" do
|
20
|
+
it "yields each string element" do
|
21
|
+
ptr = GirFFI::InPointer.from_array :utf8, ["one", "two", "three"]
|
22
|
+
strv = GLib::Strv.new ptr
|
23
|
+
arr = []
|
24
|
+
strv.each do |str|
|
25
|
+
arr << str
|
26
|
+
end
|
27
|
+
assert_equal ["one", "two", "three"], arr
|
28
|
+
end
|
29
|
+
|
30
|
+
it "yields zero times for a Strv wrapping a null pointer" do
|
31
|
+
strv = GLib::Strv.new FFI::Pointer.new(0)
|
32
|
+
strv.each do |str|
|
33
|
+
flunk
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
it "includes Enumerable" do
|
39
|
+
GLib::Strv.must_include Enumerable
|
40
|
+
end
|
41
|
+
end
|