【问题标题】:CGO library build to JS WASM fileCGO 库构建到 JS WASM 文件
【发布时间】:2019-07-23 13:54:59
【问题描述】:

我想使用从 Golang 构建的 webassembly 库编写 JS 脚本。 但是我需要使用C库并通过CGO使用它。

简而言之,我的代码如下所示(只是加载 C 库的示例):

package main

/*
#include <stdlib.h>
*/
import "C"

func main() {
    println("Hello")
}

但是当我想按照教程中的命令构建它时,我遇到了错误。

命令:

GOARCH=wasm GOOS=js go build -o lib.wasm test.go

输出:

can't load package: package main: build constraints exclude all Go files in [Project path]

所以我的问题更多的是是否有可能构建这样的东西。

谢谢。

【问题讨论】:

    标签: go webassembly cgo


    【解决方案1】:

    不会飞:GOARCH=wasm GOOS=js 基本上使 Go 编译器从 Go 源代码生成 wasm 字节码换句话说,Go 代码被编译为 WASM 字节码和 WASM API 调用,而不是特定于 CPU 的机器代码和对特定操作系统内核的系统调用。

    另一方面,cgo 是一种将编译 C 代码与编译 Go 代码链接 的方法。为了编译使用cgo 的程序,go 工具链调用一个真正的 C 编译器(大部分时间是gcc),它编译 C 部分。

    编译后的 C 代码和 WASM 字节码存在于不同的宇宙中,彼此不知道。理论上,像 gcc 这样的 C 编译器可以支持 WASM——就像 go 现在一样——但是 IIRC 既不是这种情况,也不是 Go 的 WASM 后端被教导以某种方式处理这种情况。

    总而言之,使用cgo 的最典型案例是与已经存在的用 C 编写的库进行交互(或公开与 C 兼容的 API),并且大多数此类库通常对环境做出深刻的假设它们在其中运行——通常是与 POSIX 兼容的操作系统(带有一组系统调用来处理文件和套接字 I/O 等)。

    因此,如果您很少需要链接“纯”C 库(该库执行纯数据处理并且不以任何方式与底层操作系统通信),则可以查看C-to-Go 源代码翻译器。

    【讨论】:

    • 我注意到 GCC 的 WASM 后端 might materialize, eventually
    • 呃,Web 汇编的全部意义在于您可以将 C 等本地语言编译到其中。有很多用例将 Go WASM 链接到 C WASM 库。要将 Go 作为一种 WASM 语言认真对待,这是应该做的事情。 llvmllgo 前端很可能首先发生。
    • @Zv_oDD,请冷静下来并尝试重新阅读问题(以及我的答案)。如果我们要从问题中充实最低限度,那就是“为什么 Go 编译器不能将我的 C 代码编译(或转译或其他)到 WASM 目标?”。我的回答的本质是 Go 编译器只编译 Go 代码,并且在 C 编译器的帮助下,对使编译的 Go 代码与 C 互操作的支持有限。说得尽可能简单:Go 编译器不编译 C。
    • @Zv_oDD,所以你的抱怨被误导了:WASM 应该由任何更高级别的编程语言生成这一事实是无可争议的,但是 Go 工具链从 Go 源代码而不是 C 生成 WASM。一些工具,理论上,可能会以某种方式将各种 HLL 的编译器生成的 WASM“对象”“粘合在一起”,但只要我们谈论的是 Go 工具,它还没有出现——基本上应该不是 cgo 而是 @ 987654334@ 或类似的。从 Go 工具链中要求也能够将 C 编译为 WASM 有点牵强——不管你是否不喜欢这个。
    • github.com/therecipe/qt 使用 cgo 为 Qt 创建 Go 绑定。它成功编译为 WASM 并在浏览器中运行。这向我表明,OP 所追求的目标是可能的。
    猜你喜欢
    • 2019-11-27
    • 2021-11-12
    • 2020-03-10
    • 2021-11-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-11-05
    • 2022-08-22
    相关资源
    最近更新 更多