llc --version 可直接列出已注册目标,包括名称、描述及是否默认启用;具体目标取决于 llc 编译时启用的后端,如 vcpkg install llvm[target-arm] 后才支持 arm。

llc --version 能直接列出已注册目标
最简单的方法就是运行 llc(LLVM 的代码生成器)并加 --version 参数。它会打印出当前二进制中所有已注册的目标,包括名称、描述和是否默认启用:
llc --version
输出里你会看到类似这样的行:
Registered Targets: x86 - 32-bit X86: Pentium-Pro and above x86-64 - 64-bit X86: EM64T and AMD64 arm - ARM architecture aarch64 - AArch64 (little-endian) riscv32 - 32-bit RISC-V riscv64 - 64-bit RISC-V
注意:这里列出的目标,只取决于你当前安装的 llc 是怎么编译出来的——比如用 vcpkg install llvm 默认不带 target-arm,那 arm 就不会出现;而 vcpkg install llvm[target-arm] 后再跑 llc --version 才能看到。
TargetRegistry::lookupTarget 需要运行时调用
如果你在 C++ 代码里写 Pass 或自定义工具,想通过 API 查找目标,得用 TargetRegistry::lookupTarget。它不返回“所有目标列表”,而是按名字查单个目标:
std::string Error;
const Target *TheTarget = TargetRegistry::lookupTarget("aarch64", Error);
if (!TheTarget) {
errs() << "Target lookup failed: " << Error << "\n";
}常见错误现象:
-
Error为空但TheTarget是nullptr:说明该目标没被链接进你的可执行文件(比如没 linkLLVMARMAsmPrinter等后端库) -
Error提示no such target:名字拼错,或大小写不匹配(aarch64≠AArch64) - 链接时报
undefined reference to `llvm::InitializeARMTargetInfo()':漏掉初始化函数调用
必须确保对应目标的初始化函数被调用,例如:
InitializeARMTarget(); InitializeARMTargetMC(); InitializeARMTargetAsmPrinter();
这些函数通常在 llvm/Support/TargetSelect.h 里声明,不同目标前缀不同(ARM、AARCH64、RISCV 等)。
vcpkg install llvm[target-*] 决定哪些目标能被 lookupTarget 找到
用 vcpkg 安装 LLVM 时,目标是否可用,完全由你显式指定的 features 控制:
-
vcpkg install llvm→ 只含默认目标(通常是x86和x86-64) -
vcpkg install llvm[target-arm]→ 加入 ARM 支持,lookupTarget("arm")才可能成功 -
vcpkg install llvm[target-all]→ 全部后端,体积大、编译慢,但最省心
如果你用的是自己从源码构建的 LLVM,那就要在 cmake 时打开对应选项,比如:
-DLLVM_TARGETS_TO_BUILD="ARM;AArch64;RISCV"
否则即使代码里写了 InitializeARMTarget(),链接也会失败——因为对应目标的 object 文件根本没被编译出来。
为什么 TargetRegistry 不提供 getAllTargets?
LLVM 没有暴露类似 TargetRegistry::getAllTargets() 的接口,根本原因是:目标不是“自动发现”的,而是靠静态注册机制驱动的。
每个目标子目录(如 lib/Target/ARM/)里都有一个 ARMTargetInfo.cpp,里面调用了 RegisterTarget 宏,把目标注册进全局 registry。但这个过程发生在链接期,且只对实际被引用的目标生效。没有被链接的目标代码,其注册逻辑根本不会进入最终二进制。
所以,“查找可用目标”本质上是个构建+链接问题,而不是运行时反射问题。想确认某个目标是否存在,最可靠的方式还是先确保它被构建并链接进来,再用 llc --version 或 lookupTarget 验证。

















