处理 OCaml 项目中的 C 代码依赖项

问题描述

我正在使用 ocamlbuild 构建我的 OCaml 项目,该项目使用外部 C 库“cstub”。我在网上找到了一个很好的解决方案,可以在 http://l-lang.blogspot.com/2012/08/incorporating-c-code-in-ocaml-project.html 中使用 ocamlbuild 将 C 库包含在编译过程中(将 pdep ["link";] "linkdep" (fun param -> [param]);添加myocamlbuild.ml)。

但是,我的C库本身有一个外部的ASM依赖,上面的解决方案无法捕获它。它无法与 ASM 函数链接,因为它没有与 ASM 文件一起编译。因此,我的问题是:在编译 C 程序时,有没有办法调整上面给出的建议以添加对 ASM 文件支持?例如,是否有额外的参数要添加pdep 命令中以支持额外的编译功能

在此先非常感谢您!

解决方法

所有构建相关问题的默认序言。如果您有该选项,请考虑使用 dune。 OCamlBuild 即将退休,所以不要期望太多的帮助或好的现代文档。话虽如此,我明白这并不总是一种选择,我自己在我的主要项目中使用 ocamlbuild

因此,您添加到 ocamlbuild 插件中的 pdep 规则采用了一个参数,例如,

<*.native>: linkdep(toto_c.o)

toto_c.o(或括号之间的任何内容)作为 param 传递,您需要将其转换为路径列表,因此如果您的 asm 文件编译为 foo.o,你可以把它写成

<*.native>: linkdep(toto_c.o,foo.o)

并且您的 pdep 规则应该是

pdep ["link"] "linkdep" (String.split_at_char ',')

如果您希望 ocamlbuild 从文件 foo.o 构建 foo.s,您还需要编写组装文件的规则,(ocamlbuild -documentation 将向您显示 {{1 }},我没有找到 ocamlbuild 模式的任何规则)。

完全未经测试,但规则应该是这样的,

*.s -> *.o

然后将其添加到 let asm_rule () = let deps = ["%.s"] and prod = "%.o" in let action env _ = let src = env "%.s" and obj = env "%.o" in let tags = tags_of_pathname src ++ "compile" in Cmd (S [Sh "as"; T tags; P src; A "-o"; Px obj]) in rule "asm: s -> o" ~deps ~prod action 阶段的 dispatch 上,例如,

Before_rules