ffi 1.9.21 → 1.9.22
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of ffi might be problematic. Click here for more details.
- checksums.yaml +5 -5
- checksums.yaml.gz.sig +3 -0
- data.tar.gz.sig +0 -0
- data/.gitignore +22 -0
- data/.gitmodules +3 -0
- data/.travis.yml +52 -0
- data/.yardopts +5 -0
- data/Gemfile +15 -0
- data/{spec/ffi/LICENSE.SPECS → LICENSE.SPECS} +1 -1
- data/README.md +1 -1
- data/Rakefile +28 -3
- data/appveyor.yml +22 -0
- data/ext/ffi_c/Call.c +1 -22
- data/ext/ffi_c/Call.h +0 -9
- data/ext/ffi_c/Closure.c +54 -0
- data/ext/ffi_c/{ClosurePool.h → Closure.h} +13 -23
- data/ext/ffi_c/Function.c +16 -25
- data/ext/ffi_c/Function.h +1 -2
- data/ext/ffi_c/FunctionInfo.c +0 -4
- data/ext/ffi_c/MethodHandle.c +33 -268
- data/ext/ffi_c/extconf.rb +3 -3
- data/ext/ffi_c/ffi.c +2 -2
- data/ext/ffi_c/libffi.bsd.mk +3 -3
- data/ext/ffi_c/libffi.darwin.mk +1 -1
- data/ext/ffi_c/libffi.gnu.mk +1 -1
- data/ext/ffi_c/libffi.mk +2 -2
- data/ext/ffi_c/libffi.vc.mk +1 -1
- data/ext/ffi_c/libffi.vc64.mk +1 -1
- data/ext/ffi_c/libffi/.appveyor.yml +48 -0
- data/ext/ffi_c/libffi/.gitignore +36 -0
- data/ext/ffi_c/libffi/.travis.yml +30 -0
- data/ext/ffi_c/libffi/.travis/install.sh +14 -0
- data/ext/ffi_c/libffi/Makefile.am +5 -3
- data/ext/ffi_c/libffi/acinclude.m4 +6 -0
- data/ext/ffi_c/libffi/autogen.sh +1 -1
- data/ext/ffi_c/libffi/config.guess +1466 -0
- data/ext/ffi_c/libffi/config.sub +1836 -0
- data/ext/ffi_c/libffi/configure.ac +2 -2
- data/ext/ffi_c/libffi/configure.host +15 -3
- data/ext/ffi_c/libffi/generate-darwin-source-and-headers.py +11 -15
- data/ext/ffi_c/libffi/include/ffi.h.in +6 -1
- data/ext/ffi_c/libffi/libffi.xcodeproj/project.pbxproj +465 -59
- data/ext/ffi_c/libffi/src/aarch64/ffi.c +33 -10
- data/ext/ffi_c/libffi/src/aarch64/sysv.S +2 -2
- data/ext/ffi_c/libffi/src/arm/ffi.c +12 -1
- data/ext/ffi_c/libffi/src/arm/sysv.S +1 -1
- data/ext/ffi_c/libffi/src/closures.c +143 -97
- data/ext/ffi_c/libffi/src/ia64/unix.S +2 -0
- data/ext/ffi_c/libffi/src/mips/ffi.c +8 -0
- data/ext/ffi_c/libffi/src/mips/ffitarget.h +1 -1
- data/ext/ffi_c/libffi/src/mips/n32.S +2 -0
- data/ext/ffi_c/libffi/src/powerpc/aix.S +239 -1
- data/ext/ffi_c/libffi/src/powerpc/aix_closure.S +250 -3
- data/ext/ffi_c/libffi/src/powerpc/ffi_darwin.c +86 -5
- data/ext/ffi_c/libffi/src/powerpc/ffitarget.h +3 -0
- data/ext/ffi_c/libffi/src/x86/ffi.c +3 -1
- data/ext/ffi_c/libffi/src/x86/ffi64.c +26 -5
- data/ext/ffi_c/libffi/src/x86/sysv.S +2 -2
- data/ext/ffi_c/libffi/src/x86/unix64.S +1 -1
- data/ext/ffi_c/libffi/src/x86/win64.S +1 -1
- data/ext/ffi_c/libffi/testsuite/Makefile.am +2 -1
- data/ext/ffi_c/libffi/testsuite/lib/libffi.exp +2 -1
- data/ext/ffi_c/libffi/testsuite/libffi.call/cls_3float.c +95 -0
- data/ffi.gemspec +14 -1
- data/lib/ffi/library.rb +1 -1
- data/lib/ffi/version.rb +1 -1
- data/samples/getlogin.rb +8 -0
- data/samples/getpid.rb +8 -0
- data/samples/gettimeofday.rb +18 -0
- data/samples/hello.rb +7 -0
- data/samples/inotify.rb +60 -0
- data/samples/pty.rb +76 -0
- data/samples/qsort.rb +21 -0
- data/samples/sample_helper.rb +6 -0
- metadata +59 -81
- metadata.gz.sig +0 -0
- data/ext/ffi_c/ClosurePool.c +0 -283
- data/gen/Rakefile +0 -30
- data/libtest/Benchmark.c +0 -52
- data/libtest/BoolTest.c +0 -34
- data/libtest/BufferTest.c +0 -31
- data/libtest/ClosureTest.c +0 -205
- data/libtest/EnumTest.c +0 -51
- data/libtest/FunctionTest.c +0 -70
- data/libtest/GNUmakefile +0 -149
- data/libtest/GlobalVariable.c +0 -62
- data/libtest/LastErrorTest.c +0 -21
- data/libtest/NumberTest.c +0 -132
- data/libtest/PointerTest.c +0 -63
- data/libtest/ReferenceTest.c +0 -23
- data/libtest/StringTest.c +0 -34
- data/libtest/StructTest.c +0 -243
- data/libtest/UnionTest.c +0 -43
- data/libtest/VariadicTest.c +0 -99
- data/spec/ffi/async_callback_spec.rb +0 -35
- data/spec/ffi/bitmask_spec.rb +0 -575
- data/spec/ffi/bool_spec.rb +0 -32
- data/spec/ffi/buffer_spec.rb +0 -279
- data/spec/ffi/callback_spec.rb +0 -773
- data/spec/ffi/custom_param_type.rb +0 -37
- data/spec/ffi/custom_type_spec.rb +0 -74
- data/spec/ffi/dup_spec.rb +0 -52
- data/spec/ffi/enum_spec.rb +0 -423
- data/spec/ffi/errno_spec.rb +0 -20
- data/spec/ffi/ffi_spec.rb +0 -28
- data/spec/ffi/fixtures/Benchmark.c +0 -52
- data/spec/ffi/fixtures/BitmaskTest.c +0 -51
- data/spec/ffi/fixtures/BoolTest.c +0 -34
- data/spec/ffi/fixtures/BufferTest.c +0 -31
- data/spec/ffi/fixtures/ClosureTest.c +0 -205
- data/spec/ffi/fixtures/EnumTest.c +0 -51
- data/spec/ffi/fixtures/FunctionTest.c +0 -142
- data/spec/ffi/fixtures/GNUmakefile +0 -149
- data/spec/ffi/fixtures/GlobalVariable.c +0 -62
- data/spec/ffi/fixtures/LastErrorTest.c +0 -21
- data/spec/ffi/fixtures/NumberTest.c +0 -132
- data/spec/ffi/fixtures/PipeHelper.h +0 -21
- data/spec/ffi/fixtures/PipeHelperPosix.c +0 -41
- data/spec/ffi/fixtures/PipeHelperWindows.c +0 -72
- data/spec/ffi/fixtures/PointerTest.c +0 -63
- data/spec/ffi/fixtures/ReferenceTest.c +0 -23
- data/spec/ffi/fixtures/StringTest.c +0 -34
- data/spec/ffi/fixtures/StructTest.c +0 -243
- data/spec/ffi/fixtures/UnionTest.c +0 -43
- data/spec/ffi/fixtures/VariadicTest.c +0 -99
- data/spec/ffi/fixtures/classes.rb +0 -438
- data/spec/ffi/function_spec.rb +0 -97
- data/spec/ffi/io_spec.rb +0 -16
- data/spec/ffi/library_spec.rb +0 -286
- data/spec/ffi/long_double.rb +0 -30
- data/spec/ffi/managed_struct_spec.rb +0 -68
- data/spec/ffi/memorypointer_spec.rb +0 -78
- data/spec/ffi/number_spec.rb +0 -247
- data/spec/ffi/platform_spec.rb +0 -114
- data/spec/ffi/pointer_spec.rb +0 -285
- data/spec/ffi/rbx/attach_function_spec.rb +0 -34
- data/spec/ffi/rbx/memory_pointer_spec.rb +0 -198
- data/spec/ffi/rbx/spec_helper.rb +0 -6
- data/spec/ffi/rbx/struct_spec.rb +0 -18
- data/spec/ffi/spec_helper.rb +0 -93
- data/spec/ffi/string_spec.rb +0 -118
- data/spec/ffi/strptr_spec.rb +0 -50
- data/spec/ffi/struct_by_ref_spec.rb +0 -43
- data/spec/ffi/struct_callback_spec.rb +0 -69
- data/spec/ffi/struct_initialize_spec.rb +0 -35
- data/spec/ffi/struct_packed_spec.rb +0 -50
- data/spec/ffi/struct_spec.rb +0 -882
- data/spec/ffi/typedef_spec.rb +0 -91
- data/spec/ffi/union_spec.rb +0 -67
- data/spec/ffi/variadic_spec.rb +0 -132
- data/spec/spec.opts +0 -4
@@ -1,34 +0,0 @@
|
|
1
|
-
#
|
2
|
-
# This file is part of ruby-ffi.
|
3
|
-
# For licensing, see LICENSE.SPECS
|
4
|
-
#
|
5
|
-
|
6
|
-
require File.expand_path(File.join(File.dirname(__FILE__), "spec_helper"))
|
7
|
-
|
8
|
-
unless FFI::Platform.windows?
|
9
|
-
class Timeval < FFI::Struct
|
10
|
-
layout :tv_sec, :ulong, 0, :tv_usec, :ulong, 4
|
11
|
-
end
|
12
|
-
|
13
|
-
module LibC
|
14
|
-
extend FFI::Library
|
15
|
-
ffi_lib FFI::Library::LIBC
|
16
|
-
|
17
|
-
attach_function :gettimeofday, [:pointer, :pointer], :int
|
18
|
-
end
|
19
|
-
|
20
|
-
describe FFI::Library, "#attach_function" do
|
21
|
-
it "correctly returns a value for gettimeofday" do
|
22
|
-
t = Timeval.new
|
23
|
-
time = LibC.gettimeofday(t.pointer, nil)
|
24
|
-
expect(time).to be_kind_of(Integer)
|
25
|
-
end
|
26
|
-
|
27
|
-
it "correctly populates a struct for gettimeofday" do
|
28
|
-
t = Timeval.new
|
29
|
-
LibC.gettimeofday(t.pointer, nil)
|
30
|
-
expect(t[:tv_sec]).to be_kind_of(Numeric)
|
31
|
-
expect(t[:tv_usec]).to be_kind_of(Numeric)
|
32
|
-
end
|
33
|
-
end
|
34
|
-
end
|
@@ -1,198 +0,0 @@
|
|
1
|
-
# coding: utf-8
|
2
|
-
#
|
3
|
-
# This file is part of ruby-ffi.
|
4
|
-
# For licensing, see LICENSE.SPECS
|
5
|
-
#
|
6
|
-
|
7
|
-
require File.expand_path(File.join(File.dirname(__FILE__), "spec_helper"))
|
8
|
-
|
9
|
-
module CTest
|
10
|
-
extend FFI::Library
|
11
|
-
ffi_lib FFI::Library::LIBC
|
12
|
-
|
13
|
-
attach_function :strcat, [:pointer, :pointer], :pointer
|
14
|
-
end
|
15
|
-
|
16
|
-
describe "MemoryPointer" do
|
17
|
-
it "makes a pointer from a string" do
|
18
|
-
m = FFI::MemoryPointer.from_string("FFI is Awesome")
|
19
|
-
expect(m.total).to eq(15)
|
20
|
-
expect(m.type_size).to eq(1)
|
21
|
-
end
|
22
|
-
|
23
|
-
it "does not make a pointer from non-strings" do
|
24
|
-
expect { FFI::MemoryPointer.from_string(nil) }.to raise_error(TypeError)
|
25
|
-
end
|
26
|
-
|
27
|
-
it "makes a pointer from a string with multibyte characters" do
|
28
|
-
m = FFI::MemoryPointer.from_string("ぱんだ")
|
29
|
-
expect(m.total).to eq(10)
|
30
|
-
expect(m.type_size).to eq(1)
|
31
|
-
end
|
32
|
-
|
33
|
-
it "reads back a string" do
|
34
|
-
m = FFI::MemoryPointer.from_string("FFI is Awesome")
|
35
|
-
expect(m.read_string).to eq("FFI is Awesome")
|
36
|
-
end
|
37
|
-
|
38
|
-
it "reads back an empty string" do
|
39
|
-
expect(FFI::Pointer::NULL.read_string(0)).to eq('')
|
40
|
-
end
|
41
|
-
|
42
|
-
it "makes a pointer for a certain number of bytes" do
|
43
|
-
m = FFI::MemoryPointer.new(8)
|
44
|
-
m.write_array_of_int([1,2])
|
45
|
-
expect(m.read_array_of_int(2)).to eq([1,2])
|
46
|
-
end
|
47
|
-
|
48
|
-
it "allows access to an element of the pointer (as an array)" do
|
49
|
-
m = FFI::MemoryPointer.new(:int, 2)
|
50
|
-
m.write_array_of_int([1,2])
|
51
|
-
expect(m[0].read_int).to eq(1)
|
52
|
-
expect(m[1].read_int).to eq(2)
|
53
|
-
end
|
54
|
-
|
55
|
-
it "allows writing as an int" do
|
56
|
-
m = FFI::MemoryPointer.new(:int)
|
57
|
-
m.write_int(1)
|
58
|
-
expect(m.read_int).to eq(1)
|
59
|
-
expect(m.read :int).to eq(1)
|
60
|
-
expect(m.read FFI::Type::INT).to eq(1)
|
61
|
-
end
|
62
|
-
|
63
|
-
it "allows writing as a sized int" do
|
64
|
-
m = FFI::MemoryPointer.new(:uint32)
|
65
|
-
m.write_uint32(1)
|
66
|
-
expect(m.read_uint32).to eq(1)
|
67
|
-
expect(m.read :uint32).to eq(1)
|
68
|
-
expect(m.read FFI::Type::UINT32).to eq(1)
|
69
|
-
|
70
|
-
m = FFI::MemoryPointer.new(:uint32)
|
71
|
-
m.write :uint32, 1
|
72
|
-
expect(m.read :uint32).to eq(1)
|
73
|
-
|
74
|
-
m = FFI::MemoryPointer.new(:int64)
|
75
|
-
m.write_int64(1)
|
76
|
-
expect(m.read_int64).to eq(1)
|
77
|
-
expect(m.read :int64).to eq(1)
|
78
|
-
expect(m.read FFI::Type::INT64).to eq(1)
|
79
|
-
|
80
|
-
m = FFI::MemoryPointer.new(:int64)
|
81
|
-
m.write :int64, 1
|
82
|
-
expect(m.read :int64).to eq(1)
|
83
|
-
end
|
84
|
-
|
85
|
-
it "allows writing as a long" do
|
86
|
-
m = FFI::MemoryPointer.new(:long)
|
87
|
-
m.write_long(10)
|
88
|
-
expect(m.read_long).to eq(10)
|
89
|
-
expect(m.read :long).to eq(10)
|
90
|
-
expect(m.read FFI::Type::LONG).to eq(10)
|
91
|
-
|
92
|
-
m.write :long, 10
|
93
|
-
expect(m.read :long).to eq(10)
|
94
|
-
end
|
95
|
-
|
96
|
-
it "allows writing as a size_t" do
|
97
|
-
m = FFI::MemoryPointer.new(:size_t)
|
98
|
-
m.write(:size_t, 10)
|
99
|
-
expect(m.read :size_t).to eq(10)
|
100
|
-
end
|
101
|
-
|
102
|
-
it "allows writing as a bool" do
|
103
|
-
m = FFI::MemoryPointer.new(:bool)
|
104
|
-
m.write(:bool, true)
|
105
|
-
expect(m.read :bool).to eq(true)
|
106
|
-
expect(m.read FFI::Type::BOOL).to eq(true)
|
107
|
-
|
108
|
-
m.write(:bool, false)
|
109
|
-
expect(m.read :bool).to eq(false)
|
110
|
-
expect(m.read FFI::Type::BOOL).to eq(false)
|
111
|
-
end
|
112
|
-
|
113
|
-
it "allows writing a custom typedef" do
|
114
|
-
FFI.typedef :uint, :fubar_t
|
115
|
-
FFI.typedef :size_t, :fubar2_t
|
116
|
-
|
117
|
-
m = FFI::MemoryPointer.new(:fubar_t)
|
118
|
-
m.write(:fubar_t, 10)
|
119
|
-
expect(m.read :fubar_t).to eq(10)
|
120
|
-
|
121
|
-
m = FFI::MemoryPointer.new(:fubar2_t)
|
122
|
-
m.write(:fubar2_t, 10)
|
123
|
-
expect(m.read :fubar2_t).to eq(10)
|
124
|
-
end
|
125
|
-
|
126
|
-
it "raises an error if you try to read an undefined type" do
|
127
|
-
m = FFI::MemoryPointer.new(:long)
|
128
|
-
expect { m.read(:undefined_type) }.to raise_error(ArgumentError)
|
129
|
-
end
|
130
|
-
|
131
|
-
it "raises an error if you try putting a long into a pointer of size 1" do
|
132
|
-
m = FFI::MemoryPointer.new(1)
|
133
|
-
expect { m.write_long(10) }.to raise_error
|
134
|
-
end
|
135
|
-
|
136
|
-
it "raises an error if you try putting an int into a pointer of size 1" do
|
137
|
-
m = FFI::MemoryPointer.new(1)
|
138
|
-
expect { m.write_int(10) }.to raise_error
|
139
|
-
end
|
140
|
-
# it "does not raise IndexError for opaque pointers" do
|
141
|
-
# m = FFI::MemoryPointer.new(8)
|
142
|
-
# p2 = FFI::MemoryPointer.new(1024)
|
143
|
-
# m.write_long(p2.address)
|
144
|
-
# p = m.read_pointer
|
145
|
-
# lambda { p.write_int(10) }.should_not raise_error
|
146
|
-
# end
|
147
|
-
|
148
|
-
it "makes a pointer for a certain type" do
|
149
|
-
m = FFI::MemoryPointer.new(:int)
|
150
|
-
m.write_int(10)
|
151
|
-
expect(m.read_int).to eq(10)
|
152
|
-
end
|
153
|
-
|
154
|
-
it "makes a memory pointer for a number of a certain type" do
|
155
|
-
m = FFI::MemoryPointer.new(:int, 2)
|
156
|
-
m.write_array_of_int([1,2])
|
157
|
-
expect(m.read_array_of_int(2)).to eq([1,2])
|
158
|
-
end
|
159
|
-
|
160
|
-
it "makes a pointer for an object responding to #size" do
|
161
|
-
m = FFI::MemoryPointer.new(Struct.new(:size).new(8))
|
162
|
-
m.write_array_of_int([1,2])
|
163
|
-
expect(m.read_array_of_int(2)).to eq([1,2])
|
164
|
-
end
|
165
|
-
|
166
|
-
it "makes a pointer for a number of an object responding to #size" do
|
167
|
-
m = FFI::MemoryPointer.new(Struct.new(:size).new(4), 2)
|
168
|
-
m.write_array_of_int([1,2])
|
169
|
-
expect(m.read_array_of_int(2)).to eq([1,2])
|
170
|
-
end
|
171
|
-
|
172
|
-
it "MemoryPointer#address returns correct value" do
|
173
|
-
m = FFI::MemoryPointer.new(:long_long)
|
174
|
-
magic = 0x12345678
|
175
|
-
m.write_long(magic)
|
176
|
-
expect(m.read_pointer.address).to eq(magic)
|
177
|
-
end
|
178
|
-
|
179
|
-
it "MemoryPointer#null? returns true for zero value" do
|
180
|
-
m = FFI::MemoryPointer.new(:long_long)
|
181
|
-
m.write_long(0)
|
182
|
-
expect(m.read_pointer.null?).to be true
|
183
|
-
end
|
184
|
-
|
185
|
-
it "MemoryPointer#null? returns false for non-zero value" do
|
186
|
-
m = FFI::MemoryPointer.new(:long_long)
|
187
|
-
m.write_long(0x12345678)
|
188
|
-
expect(m.read_pointer.null?).to be false
|
189
|
-
end
|
190
|
-
|
191
|
-
it "initialize with block should execute block" do
|
192
|
-
block_executed = false
|
193
|
-
FFI::MemoryPointer.new(:pointer) do |ptr|
|
194
|
-
block_executed = true
|
195
|
-
end
|
196
|
-
expect(block_executed).to be true
|
197
|
-
end
|
198
|
-
end
|
data/spec/ffi/rbx/spec_helper.rb
DELETED
data/spec/ffi/rbx/struct_spec.rb
DELETED
@@ -1,18 +0,0 @@
|
|
1
|
-
#
|
2
|
-
# This file is part of ruby-ffi.
|
3
|
-
# For licensing, see LICENSE.SPECS
|
4
|
-
#
|
5
|
-
|
6
|
-
require File.expand_path(File.join(File.dirname(__FILE__), "spec_helper"))
|
7
|
-
|
8
|
-
class Timeval < FFI::Struct
|
9
|
-
layout :tv_sec, :ulong, 0, :tv_usec, :ulong, 4
|
10
|
-
end
|
11
|
-
|
12
|
-
describe FFI::Struct do
|
13
|
-
it "allows setting fields" do
|
14
|
-
t = Timeval.new
|
15
|
-
t[:tv_sec] = 12
|
16
|
-
expect(t[:tv_sec]).to eq(12)
|
17
|
-
end
|
18
|
-
end
|
data/spec/ffi/spec_helper.rb
DELETED
@@ -1,93 +0,0 @@
|
|
1
|
-
#
|
2
|
-
# This file is part of ruby-ffi.
|
3
|
-
# For licensing, see LICENSE.SPECS
|
4
|
-
#
|
5
|
-
|
6
|
-
require 'rbconfig'
|
7
|
-
require 'fileutils'
|
8
|
-
require 'ffi'
|
9
|
-
|
10
|
-
RSpec.configure do |c|
|
11
|
-
c.filter_run_excluding :broken => true
|
12
|
-
end
|
13
|
-
|
14
|
-
CPU = case RbConfig::CONFIG['host_cpu'].downcase
|
15
|
-
when /i[3456]86/
|
16
|
-
# Darwin always reports i686, even when running in 64bit mode
|
17
|
-
if RbConfig::CONFIG['host_os'] =~ /darwin/ && 0xfee1deadbeef.is_a?(Fixnum)
|
18
|
-
"x86_64"
|
19
|
-
else
|
20
|
-
"i386"
|
21
|
-
end
|
22
|
-
|
23
|
-
when /amd64|x86_64/
|
24
|
-
"x86_64"
|
25
|
-
|
26
|
-
when /ppc64|powerpc64/
|
27
|
-
"powerpc64"
|
28
|
-
|
29
|
-
when /ppc|powerpc/
|
30
|
-
"powerpc"
|
31
|
-
|
32
|
-
when /^arm/
|
33
|
-
"arm"
|
34
|
-
|
35
|
-
else
|
36
|
-
RbConfig::CONFIG['host_cpu']
|
37
|
-
end
|
38
|
-
|
39
|
-
OS = case RbConfig::CONFIG['host_os'].downcase
|
40
|
-
when /linux/
|
41
|
-
"linux"
|
42
|
-
when /darwin/
|
43
|
-
"darwin"
|
44
|
-
when /freebsd/
|
45
|
-
"freebsd"
|
46
|
-
when /openbsd/
|
47
|
-
"openbsd"
|
48
|
-
when /sunos|solaris/
|
49
|
-
"solaris"
|
50
|
-
when /mswin|mingw/
|
51
|
-
"win32"
|
52
|
-
else
|
53
|
-
RbConfig::CONFIG['host_os'].downcase
|
54
|
-
end
|
55
|
-
|
56
|
-
def compile_library(path, lib)
|
57
|
-
|
58
|
-
dir = File.expand_path(path, File.dirname(__FILE__))
|
59
|
-
lib = "#{dir}/#{lib}"
|
60
|
-
if !File.exist?(lib)
|
61
|
-
output = nil
|
62
|
-
FileUtils.cd(dir) do
|
63
|
-
output = system(*%{#{system('which gmake >/dev/null') && 'gmake' || 'make'} CPU=#{CPU} OS=#{OS} }.tap{|x| puts x.inspect})
|
64
|
-
end
|
65
|
-
|
66
|
-
if $?.exitstatus != 0
|
67
|
-
puts "ERROR:\n#{output}"
|
68
|
-
raise "Unable to compile \"#{lib}\""
|
69
|
-
end
|
70
|
-
end
|
71
|
-
|
72
|
-
lib
|
73
|
-
end
|
74
|
-
|
75
|
-
require "ffi"
|
76
|
-
|
77
|
-
module TestLibrary
|
78
|
-
PATH = compile_library("fixtures", "libtest.#{FFI::Platform::LIBSUFFIX}")
|
79
|
-
|
80
|
-
def self.force_gc
|
81
|
-
if RUBY_PLATFORM =~ /java/
|
82
|
-
java.lang.System.gc
|
83
|
-
elsif defined?(RUBY_ENGINE) && RUBY_ENGINE == 'rbx'
|
84
|
-
GC.run(true)
|
85
|
-
else
|
86
|
-
GC.start
|
87
|
-
end
|
88
|
-
end
|
89
|
-
end
|
90
|
-
module LibTest
|
91
|
-
extend FFI::Library
|
92
|
-
ffi_lib TestLibrary::PATH
|
93
|
-
end
|
data/spec/ffi/string_spec.rb
DELETED
@@ -1,118 +0,0 @@
|
|
1
|
-
#
|
2
|
-
# This file is part of ruby-ffi.
|
3
|
-
# For licensing, see LICENSE.SPECS
|
4
|
-
#
|
5
|
-
|
6
|
-
require File.expand_path(File.join(File.dirname(__FILE__), "spec_helper"))
|
7
|
-
describe "String tests" do
|
8
|
-
include FFI
|
9
|
-
module StrLibTest
|
10
|
-
extend FFI::Library
|
11
|
-
ffi_lib TestLibrary::PATH
|
12
|
-
attach_function :ptr_ret_pointer, [ :pointer, :int], :string
|
13
|
-
attach_function :string_equals, [ :string, :string ], :int
|
14
|
-
attach_function :string_dummy, [ :string ], :void
|
15
|
-
attach_function :string_null, [ ], :string
|
16
|
-
end
|
17
|
-
|
18
|
-
it "MemoryPointer#get_string returns a tainted string" do
|
19
|
-
mp = FFI::MemoryPointer.new 1024
|
20
|
-
mp.put_string(0, "test\0")
|
21
|
-
str = mp.get_string(0)
|
22
|
-
expect(str.tainted?).to be true
|
23
|
-
end
|
24
|
-
|
25
|
-
it "String returned by a method is tainted" do
|
26
|
-
mp = FFI::MemoryPointer.new :pointer
|
27
|
-
sp = FFI::MemoryPointer.new 1024
|
28
|
-
sp.put_string(0, "test")
|
29
|
-
mp.put_pointer(0, sp)
|
30
|
-
str = StrLibTest.ptr_ret_pointer(mp, 0)
|
31
|
-
expect(str).to eq("test")
|
32
|
-
expect(str).to be_tainted
|
33
|
-
end
|
34
|
-
|
35
|
-
it "Poison null byte raises error" do
|
36
|
-
s = "123\0abc"
|
37
|
-
expect { StrLibTest.string_equals(s, s) }.to raise_error
|
38
|
-
end
|
39
|
-
|
40
|
-
it "Tainted String parameter should throw a SecurityError" do
|
41
|
-
$SAFE = 1
|
42
|
-
str = "test"
|
43
|
-
str.taint
|
44
|
-
begin
|
45
|
-
expect(LibTest.string_equals(str, str)).to be false
|
46
|
-
rescue SecurityError
|
47
|
-
end
|
48
|
-
end if false
|
49
|
-
it "casts nil as NULL pointer" do
|
50
|
-
expect(StrLibTest.string_dummy(nil)).to be_nil
|
51
|
-
end
|
52
|
-
|
53
|
-
it "return nil for NULL char*" do
|
54
|
-
expect(StrLibTest.string_null).to be_nil
|
55
|
-
end
|
56
|
-
|
57
|
-
it "reads an array of strings until encountering a NULL pointer" do
|
58
|
-
strings = ["foo", "bar", "baz", "testing", "ffi"]
|
59
|
-
ptrary = FFI::MemoryPointer.new(:pointer, 6)
|
60
|
-
ary = strings.inject([]) do |a, str|
|
61
|
-
f = FFI::MemoryPointer.new(1024)
|
62
|
-
f.put_string(0, str)
|
63
|
-
a << f
|
64
|
-
end
|
65
|
-
ary.insert(3, nil)
|
66
|
-
ptrary.write_array_of_pointer(ary)
|
67
|
-
expect(ptrary.get_array_of_string(0)).to eq(["foo", "bar", "baz"])
|
68
|
-
end
|
69
|
-
|
70
|
-
it "reads an array of strings of the size specified, substituting nil when a pointer is NULL" do
|
71
|
-
strings = ["foo", "bar", "baz", "testing", "ffi"]
|
72
|
-
ptrary = FFI::MemoryPointer.new(:pointer, 6)
|
73
|
-
ary = strings.inject([]) do |a, str|
|
74
|
-
f = FFI::MemoryPointer.new(1024)
|
75
|
-
f.put_string(0, str)
|
76
|
-
a << f
|
77
|
-
end
|
78
|
-
ary.insert(2, nil)
|
79
|
-
ptrary.write_array_of_pointer(ary)
|
80
|
-
expect(ptrary.get_array_of_string(0, 4)).to eq(["foo", "bar", nil, "baz"])
|
81
|
-
end
|
82
|
-
|
83
|
-
it "reads an array of strings, taking a memory offset parameter" do
|
84
|
-
strings = ["foo", "bar", "baz", "testing", "ffi"]
|
85
|
-
ptrary = FFI::MemoryPointer.new(:pointer, 5)
|
86
|
-
ary = strings.inject([]) do |a, str|
|
87
|
-
f = FFI::MemoryPointer.new(1024)
|
88
|
-
f.put_string(0, str)
|
89
|
-
a << f
|
90
|
-
end
|
91
|
-
ptrary.write_array_of_pointer(ary)
|
92
|
-
expect(ptrary.get_array_of_string(2 * FFI.type_size(:pointer), 3)).to eq(["baz", "testing", "ffi"])
|
93
|
-
end
|
94
|
-
|
95
|
-
it "raises an IndexError when trying to read an array of strings out of bounds" do
|
96
|
-
strings = ["foo", "bar", "baz", "testing", "ffi"]
|
97
|
-
ptrary = FFI::MemoryPointer.new(:pointer, 5)
|
98
|
-
ary = strings.inject([]) do |a, str|
|
99
|
-
f = FFI::MemoryPointer.new(1024)
|
100
|
-
f.put_string(0, str)
|
101
|
-
a << f
|
102
|
-
end
|
103
|
-
ptrary.write_array_of_pointer(ary)
|
104
|
-
expect { ptrary.get_array_of_string(0, 6) }.to raise_error
|
105
|
-
end
|
106
|
-
|
107
|
-
it "raises an IndexError when trying to read an array of strings using a negative offset" do
|
108
|
-
strings = ["foo", "bar", "baz", "testing", "ffi"]
|
109
|
-
ptrary = FFI::MemoryPointer.new(:pointer, 5)
|
110
|
-
ary = strings.inject([]) do |a, str|
|
111
|
-
f = FFI::MemoryPointer.new(1024)
|
112
|
-
f.put_string(0, str)
|
113
|
-
a << f
|
114
|
-
end
|
115
|
-
ptrary.write_array_of_pointer(ary)
|
116
|
-
expect { ptrary.get_array_of_string(-1) }.to raise_error
|
117
|
-
end
|
118
|
-
end
|