emscripten 提供了比较完整的工具链,包含了对于make 以及cmake 等工具的支持,以下是一个简单的c 代码转换为 wasm的demo
同时基于cmake 进行项目管理
参考项目
- 项目结构
├── CMakeLists.txt
├── README.md
├── app.js
└── src
├── add.c
├── add.h
└── app.c
- 代码简单说明
CMakeLists.txt cmake 定义
cmake_minimum_required(VERSION 3.20.0)
project(emccdemo)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_EXECUTABLE_SUFFIX .js)
set(TD_LINKER_FLAGS "-Wl,--gc-sections -Wl,--exclude-libs,ALL")
# 编译为可执行任务
add_executable(myadd src/add.c)
# 构建参数相关的,方便构建模块
target_link_libraries(myadd "-s MODULARIZE=1 -s EXPORTED_RUNTIME_METHODS=ccall")
src/add.h src/add.c 主要是一个标准的c 代码,同时集成了emscripten 方便暴露c 方法为wasm 方法
src/add.h
#ifndef ADD_H
#define ADD_H
int add(int a, int b);
int dalongdemoadd(int a, int b);
#endif
src/add.c
#include <emscripten.h>
#include "add.h"
// 属性,确保编译的时候可以暴露为wasm 方法
EMSCRIPTEN_KEEPALIVE
int add(int a,int b) {
return a+b;
}
// 属性,确保编译的时候可以暴露为wasm 方法
EMSCRIPTEN_KEEPALIVE
int dalongdemoadd(int a, int b) {
return a+b;
}
构建
为了方便构建使用了docker
- 启动docker
docker run -it -v $PWD:/src emscripten/emsdk:3.1.47 sh
- 构建
mkdir build
cd build emcmake cmake ..
make
- 效果
nodejs 代码访问wasm 模块
- app.js
基于以上的配置参数以及构建myadd 会是一个标准的node commonjs 模块,可以nodejs 使用
如下
代码
const app = require("./build/myadd")
app().then((instance) => {
console.log(instance._dalongdemoadd(1,3)); // direct calling works
})
- 效果
说明
以上是一个简单的试用,实际上emscripten 提供了不少强大的功能,对于c/c++ 周边的应用到wasm 是一个首选方案,社区已经有不少项目就是基于
emscripten 编译为wasm(opencv,fffmpeg。。。)
参考资料
https://emscripten.org/
https://github.com/rongfengliang/emscripten_basic_learning
https://emscripten.org/docs/porting/connecting_cpp_and_javascript/Interacting-with-code.html