Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/ruby/25.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何编译Ruby扩展_Ruby_Gem_Rake_Rakefile - Fatal编程技术网

如何编译Ruby扩展

如何编译Ruby扩展,ruby,gem,rake,rakefile,Ruby,Gem,Rake,Rakefile,我在ext/Q/flagvalue.c中有一个简单的扩展 我的ext/Q/extconfig.rb如下所示: require 'mkmf' create_makefile('Q/flagvalue') Rakefile中的任务设置如下: Rake::ExtensionTask.new("Q") do |extension| extension.lib_dir = 'lib/Q' end 当我rake build时,我得到以下输出: mkdir -p tmp/x86_64-linux/Q/

我在ext/Q/flagvalue.c中有一个简单的扩展

我的ext/Q/extconfig.rb如下所示:

require 'mkmf'
create_makefile('Q/flagvalue')
Rakefile中的任务设置如下:

Rake::ExtensionTask.new("Q") do |extension|
  extension.lib_dir = 'lib/Q'
end
当我
rake build
时,我得到以下输出:

mkdir -p tmp/x86_64-linux/Q/1.9.3 cd tmp/x86_64-linux/Q/1.9.3 /usr/local/rvm/rubies/ruby-1.9.3-p286/bin/ruby -I. ../../../../ext/Q/extconf.rb creating Makefile cd - cd tmp/x86_64-linux/Q/1.9.3 make compiling ../../../../ext/Q/flagvalue.c linking shared-object Q/flagvalue.so cd - install -c tmp/x86_64-linux/Q/1.9.3/Q.so lib/Q/Q.so rake aborted! No such file or directory - tmp/x86_64-linux/Q/1.9.3/Q.so mkdir-ptmp/x86_64-linux/Q/1.9.3 cd tmp/x86_64-linux/Q/1.9.3 /usr/local/rvm/rubies/ruby-1.9.3-p286/bin/ruby-I../../../../../../ext/Q/extconf.rb 创建Makefile 光盘- cd tmp/x86_64-linux/Q/1.9.3 制作 编译../../../../../ext/Q/flagvalue.c 链接共享对象Q/flagvalue.so 光盘- 安装-c tmp/x86_64-linux/Q/1.9.3/Q.so lib/Q/Q.so 雷克流产了! 没有这样的文件或目录-tmp/x86_64-linux/Q/1.9.3/Q.so
因此,似乎编译器编译并链接了flagvalue。因此安装程序尝试安装不存在的Q.So…此错误来自何处,我可以做些什么?

在您的
Rakefile
中尝试此操作:

Rake::ExtensionTask.new 'flagvalue' do |extension|
  extension.ext_dir = 'ext/Q'
  extension.lib_dir = 'lib/Q'
end
这确实需要一些重复,因为Rake任务不知道您在
extconf
中指定了什么作为目标(也就是说,它不知道
Q
目录),所以您必须再次指定。这也意味着在项目中任务在
tmp
目录下创建的结构中不会有
Q
目录,但这可能不是问题。

好的,经过一些挖掘(以及一些模糊的猜测:-Δ)我找到了解决方案:

我刚从gemspec(来源)获得了一些代码,这是如此:

s.executables   = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
这种方法的问题是,您必须在您的存储库中已经有了编译二进制文件的权限。正确的方法是从ext目录中获取*.c文件并将其重命名为*.c,如下所示:

s.executables   = s.files.grep(%r{^ext/.*c$}).map{ |f| File.basename(f, '.c') + '.so'}
s.bindir        = 'bin'
并且还将bindir添加到
Rakefile
的扩展任务中,并使其从规范中获取文件:

spec = Gem::Specification.load('Q.gemspec')
spec.executables.each do |f|
  Rake::ExtensionTask.new('Q', spec) do |ext|
    ext.name    = f.gsub(/\.so$/,'')
    ext.tmp_dir = 'tmp'
    ext.lib_dir = 'bin'
  end
end
:-Δ