从Ruby访问C项目的dll函数

时间:2018-01-30 22:11:36

标签: c ruby dll ffi fiddle

我有一个用C编写的控制硬件设备的项目。我试图从Ruby应用程序访问我的项目中的DLL函数,以便从Ruby Web应用程序控制硬件。我没有使用FFI和Fiddle加载dll项目文件。有没有人有一个我可以用来分享类似案例的例子?

感谢。

1 个答案:

答案 0 :(得分:1)

我建议使用SWIG(http://swig.org

我会给你一个关于OSX的例子,但你也可以在Windows上找到相同的例子。

假设您有一个库(在我的情况下为hello.bundle或在您的情况下为hello.DLL),并带有此头文件hello.h

#ifndef __HELLO__
#define __HELLO__

extern void say_hello(void); 

#endif

你想从像run.rb这样的红宝石程序中调用say_hello

# file: run.rb
require 'hello'

# Call a c function
Hello.say_hello

(注意模块名称是大写的)

你要做的就是创建一个像这样的文件hello.i

%module hello
 %{
 #include "hello.h"
 %}

 // Parse the original header file
 %include "hello.h"

然后运行命令:

swig -ruby hello.i

这将生成一个文件.c,它是一个包装器,将作为ruby环境的包装器模块安装:hello_wrap.c

然后您需要使用以下内容创建文件extconf.rb

require 'mkmf'
create_makefile('hello')

注意这里“hello”是文件.i中我们模块的名称。

然后你必须运行将生成Makefile的ruby extconf.rb

ruby extconf.rb    
creating Makefile

然后你必须输入make来编译针对库的_wrap.c文件(在我的例子中是.bundle,在你的情况下.DLL)。

make
compiling hello_wrap.c
linking shared-object hello.bundle

现在你必须输入make install(或在Unix / Osx上安装sudo make install)

sudo make install
Password:
/usr/bin/install -c -m 0755 hello.bundle /Library/Ruby/Site/2.3.0/universal-darwin17

然后你可以运行你的程序run.rb

ruby run.rb 
Hello, world!

我将粘贴到用于生成库的.c文件下面hello.bundle

#include <stdio.h>
#include "hello.h"

void say_hello(void) {
    printf("Hello, world!\n");
    return;
}

如果您将此文件与其.h文件一起保留,Makefile将为您构建库

make
compiling hello.c
compiling hello_wrap.c
linking shared-object hello.bundle