Clang有一个非常酷的扩展,名为 阻止 将真正的lambda函数机制引入C语言中。与block相比,gcc的嵌套函数相当有限。然而,试图编译一个微不足道的程序时 c.c
:
#include <stdio.h>int main() { void (^hello)(void) = ^(void) { printf("Hello, block!\n"); }; hello(); return 0;}。
与 clang -fblocks c.c
,我得到了
usrbinld.gold: tmpcc-NZ7tqa.o: in function __block_literal_global:c.c(.rodata+0x10): error: undefined reference to '_NSConcreteGlobalBlock'clang: error: linker command failed with exit code 1 (use -v to see invocation)
看来我应该用 clang -fblocks c.c -lBlocksRuntime
但后来我发现
usrbinld.gold: error: cannot find -lBlocksRuntime(其余同上)
有什么提示吗?
在Ubuntu Linux上。
sudo apt-get install llvm
sudo apt-get install clang
sudo apt-get install libblocksruntime-dev
test.c
:
#include <stdio.h>
int main() {
void (^hello)(void) = ^(void) {
printf("Hello, block!\n");
};
hello();
return 0;
}
编译。
clang test.c -fblocks -lBlocksRuntime -o test
./test
Hello, block!
可以正常工作。
从 在使用block的clang程序中,你需要链接哪些库? 至少在2010年初,似乎还没有简单的方法来解决这个问题。
技术背景信息。
块本身是语言特性,但它们也需要一些运行时支持。因此,要么编译器必须提供一个运行时库,并将其静态地链接到构建产品中,要么系统必须提供这样一个运行时库,构建产品可以与之链接。
在macOS中,block运行时是libSystem的一部分,由于macOS中所有的可执行库和动态库都是针对libSystem链接的,所以它们都有block支持。
在 Linux 系统中,如果这种运行时支持被认为是系统或语言的核心特性,通常会被添加到 libC 库中(大多数情况下是 glibc),然而由于 gcc 目前根本不支持块,而且块是否会成为一个正式的 C 特性也是未知数,因此 Linux 系统默认不提供块的运行时支持。
clang本身确实提供了一个不受目标影响的块运行时,作为 编译器运行时库但它是可选的,而且许多Linux系统似乎并不包含在他们的clang安装包中。这就是为什么这个项目 blockruntime 已经创建了,它建立了clang块运行时支持作为一个自己的库,你可以静态地链接到你的项目中或动态地安装到你的系统中。这个 源码 在GitHub上提供。
根据您的Linux发行版,可能存在一个即用型安装包。请注意,blockruntime不能只为Linux编译,它也可以为FreeBSD或Windows(MinGWMingw-w64)编译,如果你不想使用Apple提供的运行时,甚至可以为Mac编译。理论上它应该可以移植到任何clang原生支持的平台。