从 Ruby 访问 C 项目上的 dll 函数

access dll function on C project from Ruby

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

谢谢。

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

我将在 OSX 上给你一个例子,但你也可以在 Windows 上找到等效的例子。

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

#ifndef __HELLO__
#define __HELLO__

extern void say_hello(void); 

#endif

并且您想从 ruby 程序中调用 say_hello run.rb:

# 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.

中的名字

那么你必须 运行 ruby extconf.rb 才能生成 Makefile。

ruby extconf.rb    
creating Makefile

然后您必须键入 make,这将根据库编译 _wrap.c 文件(在我的例子中是 .bundle,在您的例子中是 .DLL)。

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

现在您必须键入 make install(或 sudo make install on Unix/Osx)

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!

我将在此处粘贴到用于生成库 hello.bundle

.c 文件下方
#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