ffi-compiler 0.0.3 → 0.1.0

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/README.md CHANGED
@@ -33,13 +33,13 @@ Example
33
33
  long
34
34
  example(void)
35
35
  {
36
- return 0xdeadbeef;
36
+ return 0xdeadbeef;
37
37
  }
38
38
 
39
39
  ###### ext/Rakefile
40
- require 'ffi-compiler/task'
40
+ require 'ffi-compiler/compile_task'
41
41
 
42
- FFI::Compiler::Task.new('example') do |c|
42
+ FFI::Compiler::CompileTask.new('example') do |c|
43
43
  c.have_header?('stdio.h', '/usr/local/include')
44
44
  c.have_func?('puts')
45
45
  c.have_library?('z')
data/ffi-compiler.gemspec CHANGED
@@ -1,6 +1,6 @@
1
1
  Gem::Specification.new do |s|
2
2
  s.name = 'ffi-compiler'
3
- s.version = '0.0.3'
3
+ s.version = '0.1.0'
4
4
  s.author = 'Wayne Meissner'
5
5
  s.email = 'wmeissner@gmail.com'
6
6
  s.homepage = 'http://wiki.github.com/ffi/ffi'
@@ -0,0 +1,216 @@
1
+ require 'rake'
2
+ require 'rake/tasklib'
3
+ require 'rake/clean'
4
+ require 'ffi'
5
+ require 'tmpdir'
6
+ require 'rbconfig'
7
+ require_relative 'platform'
8
+
9
+ module FFI
10
+ module Compiler
11
+ DEFAULT_CFLAGS = %w(-fexceptions -O -fno-omit-frame-pointer -fno-strict-aliasing)
12
+ DEFAULT_LDFLAGS = %w(-fexceptions)
13
+
14
+ class CompileTask < Rake::TaskLib
15
+ attr_reader :cflags, :cxxflags, :ldflags, :libs, :platform
16
+
17
+ def initialize(name)
18
+ @name = File.basename(name)
19
+ @ext_dir = File.dirname(name)
20
+ @defines = []
21
+ @include_paths = []
22
+ @library_paths = []
23
+ @libraries = []
24
+ @headers = []
25
+ @functions = []
26
+ @cflags = DEFAULT_CFLAGS.dup
27
+ @cxxflags = DEFAULT_CFLAGS.dup
28
+ @ldflags = DEFAULT_LDFLAGS.dup
29
+ @libs = []
30
+ @platform = Platform.system
31
+ @exports = []
32
+
33
+ yield self if block_given?
34
+ define_task!
35
+ end
36
+
37
+ def have_func?(func)
38
+ main = <<-C_FILE
39
+ extern void #{func}();
40
+ int main(int argc, char **argv) { #{func}(); return 0; }
41
+ C_FILE
42
+
43
+ if try_compile(main)
44
+ @functions << func
45
+ return true
46
+ end
47
+ false
48
+ end
49
+
50
+ def have_header?(header, *paths)
51
+ try_header(header, @include_paths) || try_header(header, paths)
52
+ end
53
+
54
+ def have_library?(libname, *paths)
55
+ try_library(libname, paths: @library_paths) || try_library(libname, paths: paths)
56
+ end
57
+
58
+ def have_library(lib, func = nil, headers = nil, &b)
59
+ try_library(lib, function: func, headers: headers, paths: @library_paths)
60
+ end
61
+
62
+ def find_library(lib, func, *paths)
63
+ try_library(lib, function: func, paths: @library_paths) || try_library(libname, function: func, paths: paths)
64
+ end
65
+
66
+ def export(rb_file)
67
+ @exports << { :rb_file => rb_file, :header => File.join(@ext_dir, File.basename(rb_file).sub(/\.rb$/, '.h')) }
68
+ end
69
+
70
+ private
71
+ def define_task!
72
+ pic_flags = %w(-fPIC)
73
+ so_flags = []
74
+
75
+ if @platform.mac?
76
+ pic_flags = []
77
+ so_flags << '-bundle'
78
+
79
+ elsif @platform.name =~ /linux/
80
+ so_flags << "-shared -Wl,-soname,#{lib_name}"
81
+
82
+ else
83
+ so_flags << '-shared'
84
+ end
85
+ so_flags = so_flags.join(' ')
86
+
87
+ out_dir = "#{@platform.arch}-#{@platform.os}"
88
+ if @ext_dir != '.'
89
+ out_dir = File.join(@ext_dir, out_dir)
90
+ end
91
+
92
+ directory(out_dir)
93
+ CLOBBER.include(out_dir)
94
+
95
+ lib_name = File.join(out_dir, Platform.system.map_library_name(@name))
96
+
97
+ iflags = @include_paths.uniq.map { |p| "-I#{p}" }
98
+ defines = @functions.uniq.map { |f| "-DHAVE_#{f.upcase}=1" }
99
+ defines << @headers.uniq.map { |h| "-DHAVE_#{h.upcase.sub(/\./, '_')}=1" }
100
+
101
+ cflags = (@cflags + pic_flags + iflags + defines).join(' ')
102
+ cxxflags = (@cxxflags + @cflags + pic_flags + iflags + defines).join(' ')
103
+ ld_flags = (@library_paths.map { |path| "-L#{path}" } + @ldflags).join(' ')
104
+ libs = (@libraries.map { |l| "-l#{l}" } + @libs).join(' ')
105
+
106
+ src_files = FileList["#{@ext_dir}/**/*.{c,cpp}"]
107
+ obj_files = src_files.ext('.o').map { |f| File.join(out_dir, f.sub(/^#{@ext_dir}\//, '')) }
108
+ ld = src_files.detect { |f| f =~ /\.cpp$/ } ? cxx : cc
109
+
110
+ src_files.each do |src|
111
+ obj_file = File.join(out_dir, src.sub(/\.(c|cpp)$/, '.o').sub(/^#{@ext_dir}\//, ''))
112
+ if src =~ /\.c$/
113
+ file obj_file => [ src, File.dirname(obj_file) ] do |t|
114
+ sh "#{cc} #{cflags} -o #{t.name} -c #{t.prerequisites[0]}"
115
+ end
116
+
117
+ else
118
+ file obj_file => [ src, File.dirname(obj_file) ] do |t|
119
+ sh "#{cxx} #{cxxflags} -o #{t.name} -c #{t.prerequisites[0]}"
120
+ end
121
+ end
122
+
123
+ CLEAN.include(obj_file)
124
+ end
125
+
126
+ desc "Build dynamic library"
127
+ file lib_name => obj_files do |t|
128
+ sh "#{ld} #{so_flags} -o #{t.name} #{t.prerequisites.join(' ')} #{ld_flags} #{libs}"
129
+ end
130
+ CLEAN.include(lib_name)
131
+
132
+ @exports.each do |e|
133
+ desc "Export #{e[:rb_file]}"
134
+ file e[:header] => [ e[:rb_file] ] do |t|
135
+ ruby "-I#{File.join(File.dirname(__FILE__), 'fake_ffi')} #{File.join(File.dirname(__FILE__), 'exporter.rb')} #{t.prerequisites[0]} #{t.name}"
136
+ end
137
+
138
+ obj_files.each { |o| file o => [ e[:header] ] }
139
+ CLEAN.include(e[:header])
140
+
141
+ desc "Export API headers"
142
+ task :api_headers => [ e[:header] ]
143
+ end
144
+
145
+ task :default => [ lib_name ]
146
+ task :package => [ :api_headers ]
147
+ end
148
+
149
+ def try_header(header, paths)
150
+ main = <<-C_FILE
151
+ #include <#{header}>
152
+ int main(int argc, char **argv) { return 0; }
153
+ C_FILE
154
+
155
+ if paths.empty? && try_compile(main)
156
+ @headers << header
157
+ return true
158
+ end
159
+
160
+ paths.each do |path|
161
+ if try_compile(main, "-I#{path}")
162
+ @include_paths << path
163
+ @headers << header
164
+ return true
165
+ end
166
+ end
167
+ false
168
+ end
169
+
170
+
171
+ def try_library(libname, options = {})
172
+ func = options[:function] || 'main'
173
+ paths = options[:paths] || ''
174
+ main = <<-C_FILE
175
+ #{(options[:headers] || []).map {|h| "#include <#{h}>"}.join('\n')}
176
+ extern int #{func}();
177
+ int main() { return #{func}(); }
178
+ C_FILE
179
+
180
+ if paths.empty? && try_compile(main)
181
+ @libraries << libname
182
+ return true
183
+ end
184
+
185
+ paths.each do |path|
186
+ if try_compile(main, "-L#{path}", "-l#{libname}")
187
+ @library_paths << path
188
+ @libraries << libname
189
+ end
190
+ end
191
+ end
192
+
193
+ def try_compile(src, *opts)
194
+ Dir.mktmpdir do |dir|
195
+ path = File.join(dir, 'ffi-test.c')
196
+ File.open(path, 'w') do |f|
197
+ f << src
198
+ end
199
+ begin
200
+ return system "#{cc} #{opts.join(' ')} -o #{File.join(dir, 'ffi-test')} #{path} >& /dev/null"
201
+ rescue
202
+ return false
203
+ end
204
+ end
205
+ end
206
+
207
+ def cc
208
+ @cc ||= (ENV['CC'] || RbConfig::CONFIG['CC'] || 'cc')
209
+ end
210
+
211
+ def cxx
212
+ @cxx ||= (ENV['CXX'] || RbConfig::CONFIG['CXX'] || 'c++')
213
+ end
214
+ end
215
+ end
216
+ end
@@ -0,0 +1,49 @@
1
+ require 'rake'
2
+ require 'rake/tasklib'
3
+ require 'rake/clean'
4
+
5
+ module FFI
6
+ module Compiler
7
+ class ExportTask < Rake::TaskLib
8
+
9
+ def initialize(rb_dir, out_dir, options = {})
10
+ @rb_dir = rb_dir
11
+ @out_dir = out_dir
12
+ @gem_spec = options[:gem_spec]
13
+ @exports = []
14
+
15
+ if block_given?
16
+ yield self
17
+ define_tasks!
18
+ end
19
+ end
20
+
21
+ def export(rb_file)
22
+ @exports << { :rb_file => File.join(@rb_dir, rb_file), :header => File.join(@out_dir, File.basename(rb_file).sub(/\.rb$/, '.h')) }
23
+ end
24
+
25
+ def export_all
26
+ Dir["#@rb_dir/**/*rb"].each do |rb_file|
27
+ @exports << { :rb_file => rb_file, :header => File.join(@out_dir, File.basename(rb_file).sub(/\.rb$/, '.h')) }
28
+ end
29
+ end
30
+
31
+ private
32
+ def define_tasks!
33
+ @exports.each do |e|
34
+ file e[:header] => [ e[:rb_file] ] do |t|
35
+ ruby "-I#{File.join(File.dirname(__FILE__), 'fake_ffi')} #{File.join(File.dirname(__FILE__), 'exporter.rb')} #{t.prerequisites[0]} #{t.name}"
36
+ end
37
+ CLEAN.include(e[:header])
38
+
39
+ desc "Export API headers"
40
+ task :api_headers => [ e[:header] ]
41
+ @gem_spec.files << e[:header] unless @gem_spec.nil?
42
+ end
43
+
44
+ task :gem => [ :api_headers ] unless @gem_spec.nil?
45
+ end
46
+
47
+ end
48
+ end
49
+ end
@@ -0,0 +1,4 @@
1
+ require 'ffi'
2
+
3
+ load ARGV[0]
4
+ FFI.exporter.dump(ARGV[1])
@@ -0,0 +1,8 @@
1
+ module FFI
2
+ module Compiler
3
+ module Loader
4
+ def self.find(*args)
5
+ end
6
+ end
7
+ end
8
+ end
@@ -0,0 +1,170 @@
1
+ module FFI
2
+
3
+ def self.exporter=(exporter)
4
+ @@exporter = exporter
5
+ end
6
+
7
+ def self.exporter
8
+ @@exporter
9
+ end
10
+
11
+ class Type
12
+ attr_reader :name
13
+ def initialize(name)
14
+ @name = name
15
+ end
16
+ end
17
+
18
+ class StructByReference < Type
19
+ def initialize(struct_class)
20
+ super("struct #{struct_class.to_s.gsub('::', '_')} *")
21
+ end
22
+ end
23
+
24
+ class StructByValue < Type
25
+ def initialize(struct_class)
26
+ super("struct #{struct_class.to_s.gsub('::', '_')}")
27
+ end
28
+ end
29
+
30
+ PrimitiveTypes = {
31
+ :char => 'char',
32
+ :uchar => 'unsigned char',
33
+ :short => 'short',
34
+ :ushort => 'unsigned short',
35
+ :int => 'int',
36
+ :uint => 'unsigned int',
37
+ :long => 'long',
38
+ :ulong => 'unsigned long',
39
+ :float => 'float',
40
+ :double => 'double',
41
+ :pointer => 'void *',
42
+ :string => 'const char *',
43
+ }
44
+
45
+ TypeMap = {}
46
+ def self.find_type(type)
47
+ return type if type.is_a?(Type)
48
+
49
+ t = TypeMap[type]
50
+ return t unless t.nil?
51
+
52
+ if PrimitiveTypes.has_key?(type)
53
+ return TypeMap[type] = Type.new(PrimitiveTypes[type])
54
+ end
55
+ raise TypeError.new("cannot resolve type #{type}")
56
+ end
57
+
58
+ class Exporter
59
+ attr_reader :mod, :functions
60
+
61
+ def initialize(mod)
62
+ @mod = mod
63
+ @functions = []
64
+ @structs = []
65
+ end
66
+
67
+ def attach(mname, fname, result_type, param_types)
68
+ @functions << { mname: mname, fname: fname, result_type: result_type, params: param_types.dup }
69
+ end
70
+
71
+ def struct(name, fields)
72
+ @structs << { name: name, fields: fields.dup }
73
+ end
74
+
75
+ def dump(out_file)
76
+ File.open(out_file, 'w') do |f|
77
+ guard = File.basename(out_file).upcase.gsub('.', '_').gsub('/', '_')
78
+ f.puts <<-HEADER
79
+ #ifndef #{guard}
80
+ #define #{guard} 1
81
+
82
+ #ifndef RBFFI_EXPORT
83
+ # ifdef __cplusplus
84
+ # define RBFFI_EXPORT extern "C"
85
+ # else
86
+ # define RBFFI_EXPORT
87
+ # endif
88
+ #endif
89
+
90
+ HEADER
91
+
92
+ @structs.each do |s|
93
+ f.puts "struct #{s[:name].gsub('::', '_')} {"
94
+ s[:fields].each do |field|
95
+ f.puts "#{' ' * 4}#{field[:type].name} #{field[:name].to_s};"
96
+ end
97
+ f.puts '};'
98
+ f.puts
99
+ end
100
+ @functions.each do |fn|
101
+ param_string = fn[:params].empty? ? 'void' : fn[:params].map(&:name).join(', ')
102
+ f.puts "RBFFI_EXPORT #{fn[:result_type].name} #{fn[:fname]}(#{param_string});"
103
+ end
104
+ f.puts <<-EPILOG
105
+
106
+ #endif /* #{guard} */
107
+ EPILOG
108
+ end
109
+ end
110
+
111
+ end
112
+
113
+ module Library
114
+ def self.extended(mod)
115
+ FFI.exporter = Exporter.new(mod)
116
+ end
117
+
118
+ def attach_function(*args)
119
+ FFI.exporter.attach(args[0], args[0], find_type(args[2]), args[1].map { |t| find_type(t) })
120
+ end
121
+
122
+ def ffi_lib(*args)
123
+
124
+ end
125
+
126
+ TypeMap = {}
127
+ def find_type(type)
128
+ t = TypeMap[type]
129
+ return t unless t.nil?
130
+
131
+ if type.is_a?(Class) && type < Struct
132
+ return TypeMap[type] = StructByReference.new(type)
133
+ end
134
+
135
+ TypeMap[type] = FFI.find_type(type)
136
+ end
137
+ end
138
+
139
+ class Struct
140
+ def self.layout(*args)
141
+ fields = []
142
+ i = 0
143
+ while i < args.length
144
+ fields << { name: args[i], type: find_type(args[i+1]) }
145
+ i += 2
146
+ end
147
+ FFI.exporter.struct(self.to_s, fields)
148
+ end
149
+
150
+ TypeMap = {}
151
+ def self.find_type(type)
152
+ t = TypeMap[type]
153
+ return t unless t.nil?
154
+
155
+ if type.is_a?(Class) && type < Struct
156
+ return TypeMap[type] = StructByValue.new(type)
157
+ end
158
+
159
+ TypeMap[type] = FFI.find_type(type)
160
+ end
161
+
162
+ def self.by_value
163
+ StructByValue.new(self)
164
+ end
165
+
166
+ def self.by_ref
167
+ StructByReference.new(self)
168
+ end
169
+ end
170
+ end
@@ -1,14 +1,15 @@
1
1
  require 'pathname'
2
2
  require 'ffi'
3
+ require_relative 'platform'
3
4
 
4
5
  module FFI
5
6
  module Compiler
6
7
  module Loader
7
8
  def self.find(name, start_path = nil)
8
- library = FFI.map_library_name(name)
9
+ library = Platform.system.map_library_name(name)
9
10
  root = false
10
11
  Pathname.new(start_path || File.dirname(caller[0].split(/:/)[0])).ascend do |path|
11
- Dir.glob("#{path}/**/#{library}") do |f|
12
+ Dir.glob("#{path}/**/{#{FFI::Platform::ARCH}-#{FFI::Platform::OS}/#{library},#{library}}") do |f|
12
13
  return f
13
14
  end
14
15
 
@@ -0,0 +1,29 @@
1
+ module FFI::Compiler
2
+ class Platform
3
+ LIBSUFFIX = FFI::Platform.mac? ? 'bundle' : FFI::Platform::LIBSUFFIX
4
+
5
+ def self.system
6
+ @@system ||= Platform.new
7
+ end
8
+
9
+ def map_library_name(name)
10
+ "#{FFI::Platform::LIBPREFIX}#{name}.#{LIBSUFFIX}"
11
+ end
12
+
13
+ def arch
14
+ FFI::Platform::ARCH
15
+ end
16
+
17
+ def os
18
+ FFI::Platform::OS
19
+ end
20
+
21
+ def name
22
+ FFI::Platform.name
23
+ end
24
+
25
+ def mac?
26
+ FFI::Platform.mac?
27
+ end
28
+ end
29
+ end
@@ -1,167 +1,15 @@
1
+ require 'rake'
1
2
  require 'rake/tasklib'
2
3
  require 'rake/clean'
3
4
  require 'ffi'
4
5
  require 'tmpdir'
5
6
  require 'rbconfig'
7
+ require_relative 'compile_task'
6
8
 
7
9
  module FFI
8
- class Compiler
9
- DEFAULT_CFLAGS = %w(-fexceptions -O -fno-omit-frame-pointer -fno-strict-aliasing)
10
- DEFAULT_LDFLAGS = %w(-fexceptions)
11
-
12
- class Task < Rake::TaskLib
13
- attr_reader :cflags, :cxxflags, :ldflags, :libs
14
-
15
- def initialize(name)
16
- @name = File.basename(name)
17
- @defines = []
18
- @include_paths = []
19
- @library_paths = []
20
- @libraries = []
21
- @headers = []
22
- @functions = []
23
- @cflags = DEFAULT_CFLAGS.dup
24
- @cxxflags = DEFAULT_CFLAGS.dup
25
- @ldflags = DEFAULT_LDFLAGS.dup
26
- @libs = []
27
-
28
- yield self if block_given?
29
- define_task!
30
- end
31
-
32
- def have_func?(func)
33
- main = <<-C_FILE
34
- extern void #{func}();
35
- int main(int argc, char **argv) { #{func}(); return 0; }
36
- C_FILE
37
-
38
- if try_compile(main)
39
- @functions << func
40
- return true
41
- end
42
- false
43
- end
44
-
45
- def have_header?(header, *paths)
46
- try_header(header, @include_paths) || try_header(header, paths)
47
- end
48
-
49
- def have_library?(libname, *paths)
50
- try_library(libname, @library_paths) || try_library(libname, paths)
51
- end
52
-
53
- private
54
- def define_task!
55
- pic_flags = %w(-fPIC)
56
- so_flags = []
57
-
58
- if FFI::Platform.mac?
59
- pic_flags = []
60
- so_flags << '-dynamiclib'
61
-
62
- elsif FFI::Platform.name =~ /linux/
63
- so_flags << "-shared -Wl,-soname,#{lib_name}"
64
-
65
- else
66
- so_flags << '-shared'
67
- end
68
- so_flags = so_flags.join(' ')
69
-
70
- lib_name = FFI.map_library_name(@name)
71
-
72
- iflags = @include_paths.uniq.map { |p| "-I#{p}" }
73
- defines = @functions.uniq.map { |f| "-DHAVE_#{f.upcase}=1" }
74
- defines << @headers.uniq.map { |h| "-DHAVE_#{h.upcase.sub(/\./, '_')}=1" }
75
-
76
- cflags = (@cflags + pic_flags + iflags + defines).join(' ')
77
- cxxflags = (@cxxflags + @cflags + pic_flags + iflags + defines).join(' ')
78
- ld_flags = (@library_paths.map { |path| "-L#{path}" } + @ldflags).join(' ')
79
- libs = (@libraries.map { |l| "-l#{l}" } + @libs).join(' ')
80
-
81
- src_files = FileList['*.{c,cpp}']
82
- obj_files = src_files.ext '.o'
83
- ld = src_files.detect { |f| f =~ /\.cpp$/ } ? cxx : cc
84
-
85
- CLEAN.include(obj_files)
86
-
87
- rule '.o' => '.c' do |t|
88
- sh "#{cc} #{cflags} -o #{t.name} -c #{t.source}"
89
- end
90
-
91
- rule '.o' => '.cpp' do |t|
92
- sh "#{cxx} #{cxxflags} -o #{t.name} -c #{t.source}"
93
- end
94
-
95
- desc "Build dynamic library"
96
- file lib_name => obj_files do |t|
97
- sh "#{ld} #{so_flags} -o #{t.name} #{t.prerequisites.join(' ')} #{ld_flags} #{libs}"
98
- end
99
- CLEAN.include(lib_name)
100
-
101
- task :default => [ lib_name ]
102
- end
103
-
104
- def try_header(header, paths)
105
- main = <<-C_FILE
106
- #include <#{header}>
107
- int main(int argc, char **argv) { return 0; }
108
- C_FILE
109
-
110
- if paths.empty? && try_compile(main)
111
- @headers << header
112
- return true
113
- end
114
-
115
- paths.each do |path|
116
- if try_compile(main, "-I#{path}")
117
- @include_paths << path
118
- @headers << header
119
- return true
120
- end
121
- end
122
- false
123
- end
124
-
125
-
126
- def try_library(libname, paths)
127
- main = <<-C_FILE
128
- int main(int argc, char **argv) { return 0; }
129
- C_FILE
130
-
131
- if paths.empty? && try_compile(main)
132
- @libraries << libname
133
- return true
134
- end
135
-
136
- paths.each do |path|
137
- if try_compile(main, "-L#{path}", "-l#{libname}")
138
- @library_paths << path
139
- @libraries << libname
140
- end
141
- end
142
- end
143
-
144
- def try_compile(src, *opts)
145
- Dir.mktmpdir do |dir|
146
- path = File.join(dir, 'ffi-test.c')
147
- File.open(path, 'w') do |f|
148
- f << src
149
- end
150
- begin
151
- return system "#{cc} #{opts.join(' ')} -o #{File.join(dir, 'ffi-test')} #{path} >& /dev/null"
152
- rescue
153
- return false
154
- end
155
- end
156
- end
157
-
158
- def cc
159
- @cc ||= (ENV['CC'] || RbConfig::CONFIG['CC'] || 'cc')
160
- end
161
-
162
- def cxx
163
- @cxx ||= (ENV['CXX'] || RbConfig::CONFIG['CXX'] || 'c++')
164
- end
10
+ module Compiler
11
+ class Task < CompileTask
12
+ warn "#{self} is deprecated"
165
13
  end
166
14
  end
167
15
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ffi-compiler
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.3
4
+ version: 0.1.0
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2013-01-19 00:00:00.000000000 Z
12
+ date: 2013-01-28 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: rake
@@ -69,7 +69,13 @@ files:
69
69
  - README.md
70
70
  - Rakefile
71
71
  - LICENSE
72
+ - lib/ffi-compiler/compile_task.rb
73
+ - lib/ffi-compiler/export_task.rb
74
+ - lib/ffi-compiler/exporter.rb
75
+ - lib/ffi-compiler/fake_ffi/ffi-compiler/loader.rb
76
+ - lib/ffi-compiler/fake_ffi/ffi.rb
72
77
  - lib/ffi-compiler/loader.rb
78
+ - lib/ffi-compiler/platform.rb
73
79
  - lib/ffi-compiler/task.rb
74
80
  homepage: http://wiki.github.com/ffi/ffi
75
81
  licenses: