Visual Studio Android 将程序集文件构建到应用程序中

Visual Studio Android building assembly files into app

我们有一个 Visual Studio Android 解决方案,其中包含一个静态库项目,其中包含以汇编实现的功能。喜欢:

my.S -> libMine.a -> libMyApp.so

为了编译,已经跳过了一些环节(如下)。然后,主应用程序共享库项目的 linking 失败(在我们关心的两种体系结构上 - x64 和 arm64),未定义对 [the] 程序集 [文件] 中实现的函数的引用。

Visual Studio(或其跨平台移动开发/Android 插件)似乎无法正确处理程序集文件项目项 - 被视为 C/C++编译器文件,它会在第一个点字符处出错(即在 .text 中); Microsoft 宏汇编器是 "not supported on this platform"。所以我研究了设置自定义构建步骤,使用以下命令:

$(ClangToolExe) %(FullPath) --target=$(ClangTarget) -g -o $(IntDir)%(FileName).o

这将预处理、编译和 link - 但是错误的 linker: 而不是针对特定 Android 工具链的那个,它将用于我的 MinGW 安装无法识别仿真模式 - 无论如何,那不是我的 NDK 工具链的位置。

我们现在可以跳过对象的 linking(将 -c 添加到上述命令)。令我们沮丧的是,生成的目标文件仍然没有添加到静态库中,正如 {Rest of the toolchain path}ar t libMine.a 所确认的那样。事实上,该库将为我们的函数提供未定义的符号,如 {Rest of the toolchain path}objdump -t libMine.a.

所示

让我们手动将目标文件添加到生成的库中,作为 post 构建步骤。命令:

$(ToolChainPrebuiltPath){Rest of the toolchain path}ar.exe ru $(TargetPath) $(IntDir)my.o

objdump -t libMine.a 现在将显示我们已获得符号。然而,还有 *UND*efined 对。

快进:

我做错了什么?我该如何解决那些未定义的引用?

似乎奏效的是:

1,确保程序集文件的扩展名是 .S,即大写 S。这是我发现的少数几个文件名大小写 [=28] 的例子之一=].

2、配置项目,使程序集文件用clang.exe {full/path/to/assembly.S, i.e. %(FullPath)} -c --target=$(ClangTarget) -g -o $(IntDir)%(FileName).o构建。对于VS Android,我们需要单独指定构建输出,也就是$(IntDir)%(FileName).o部分重新来一遍

3、运行 ar 作为 post 构建命令:{correct toolchain}/ar.exe rus $(TargetPath) {output from assembly compilation}每个程序集文件.

此解决方案缺少的一件事是检测 [缺少] 更改,这意味着将在每次编译时重建程序集文件,以及依赖它的所有内容。