在PHP程序中使用Rust扩展的方法

木白
木白
发布时间:2026-10-13 | 5人浏览过
原创

本文详细介绍如何将Rust代码编译为静态库,并通过C语言桥接封装为PHP扩展。流程涵盖Rust FFI接口定义、C头文件生成、使用ext_skel建立PHP扩展骨架、修改config.m4完成链接,以及解决返回值生命周期引发的段错误问题。

编写Rust静态库与C接口

首先需要编写Rust代码并将其编译为静态库(.a)。关键步骤是使用 #[no_mangle] 保留函数名以便外部调用,并使用 extern "C" 声明ABI兼容性。

// hello_from_rust.rs
#![crate_type = "staticlib"]

extern crate libc;
use std::ffi::CStr;

#[no_mangle]
pub extern "C" fn hello_from_rust(name: *const libc::c_char) {
    let buf_name = unsafe { CStr::from_ptr(name).to_bytes() };
    let str_name = String::from_utf8(buf_name.to_vec()).unwrap();
    println!("Hello from Rust, {}", str_name);
}

使用rustc编译该文件:
rustc --crate-type staticlib hello_from_rust.rs
生成后你会得到一个 libhello_from_rust.a 文件。同时请注意编译器提示需要链接的本地系统库(如 -lSystem -lpthread -lc -lm)。

为C语言创建头文件

为了在C和后续的PHP扩展中调用该函数,需要编写对应的C头文件(hello_from_rust.h):

// hello_from_rust.h
#ifndef __HELLO
#define __HELLO
void hello_from_rust(const char *name);
#endif

构建PHP扩展骨架

PHP提供 ext_skel 脚本用于自动生成扩展基础结构。在PHP源码的 ext/ 目录下运行:

./ext_skel --extname=hello_from_rust

生成的目录结构通常包含 config.m4、hello_from_rust.c、php_hello_from_rust.h 等文件。此时需要将之前生成的 libhello_from_rust.a 和 hello_from_rust.h 复制到该扩展目录中。

配置链接并修改C代码

编辑 config.m4 以指示编译系统如何链接静态库:

PHP_ARG_WITH(hello_from_rust, for hello_from_rust support,
[ --with-hello_from_rust    Include hello_from_rust support])
 
if test "$PHP_HELLO_FROM_RUST" != "no"; then
 PHP_SUBST(HELLO_FROM_RUST_SHARED_LIBADD)
 PHP_ADD_LIBRARY_WITH_PATH(hello_from_rust, ., HELLO_FROM_RUST_SHARED_LIBADD)
 PHP_NEW_EXTENSION(hello_from_rust, hello_from_rust.c, $ext_shared)
fi

在 hello_from_rust.c 中包含头文件并调用函数。注意初始测试版可能因Rust的 println! 或字符串生命周期管理导致段错误(Segfault),建议先确保基础调用通顺。

编译安装与测试

按标准顺序执行编译指令:

$ phpize
$ ./configure --with-hello_from_rust
$ make install

若遇到权限不足可尝试加 sudo。安装成功后可通过命令行验证:
$ php hello_from_rust.php

排错:处理段错误与返回值生命周期

如果在调用过程中出现 Segmentation fault: 11,通常是因为Rust中的临时字符串变量在返回给C时已被销毁。解决方法是调整Rust接口,使其返回由C/C++管理生命周期的指针,或者在C层做好内存拷贝。修正后的Rust签名示例如下:

pub extern "C" fn hello_from_rust(name: *const libc::c_char) -> *const libc::c_char {
    // 逻辑... 确保返回指针的有效性或使用CString管理
}
以上就是在PHP程序中使用Rust扩展的详细内容,更多关于PHP RUST扩展开发资料请关注本站其它相关文章!
相关标签:

本站声明

本文内容仅供参考,不代表本站观点。转载或引用请注明出处。如发现内容问题,请通过联系我们页面反馈。

Python 相关产品和应用

全部下载

专题列表