distcc分布式编译:将.c通过socket发送到其他电脑,其他电脑把.c编译成.o,然后再发送回来,在本地进行连接。
icu:需要先编译host程序,然后使用host程序产生一些文件,再交叉编译出target程序。
出错信息:
distcc[7063] ERROR: compile (null) on localhost failed
make[1]: *** [/disk6/jenkins/workspace/Yunos-4.0-SCM-TestBuild/host/out/platforms/phone.sc9832.sprd.eng.arm/host/obj/EXECUTABLE/LINKED/pkgdata] Error 1
/disk6/jenkins/workspace/Yunos-4.0-SCM-TestBuild/host/out/platforms/phone.sc9832.sprd.eng.arm/host/obj/SHARED_LIBRARY/LINKED/libicuuc.so: undefined reference to `__cxa_throw_bad_array_new_length'
collect2: ld returned 1 exit status
distcc[7026] ERROR: compile (null) on localhost failed
make[1]: *** [/disk6/jenkins/workspace/Yunos-4.0-SCM-TestBuild/host/out/platforms/phone.sc9832.sprd.eng.arm/host/obj/EXECUTABLE/LINKED/gennorm2] Error 1
/disk6/jenkins/workspace/Yunos-4.0-SCM-TestBuild/host/out/platforms/phone.sc9832.sprd.eng.arm/host/obj/SHARED_LIBRARY/LINKED/libicuuc.so: undefined reference to `__cxa_throw_bad_array_new_length'
collect2: ld returned 1 exit status本地编译时没有出现过这个问题,分布式编译时,偶现这个问题,icu的host程序编译失败,提示找不到符号__cxa_throw_bad_array_new_length。
先看__cxa_throw_bad_array_new_length是哪里来的:
交叉编译arm工具链(gcc4.9, glibc2.20)上面:
shuyin.wsy@10-101-175-19:/disk7/shuyin.wsy/codebase_host/prebuilts/gcc/linux-x86/arm/arm-linux-gnueabi-4.9-glibc-2.20/sysroot/usr/lib$ objdump -C -T libstdc++.so.6 | grep __cxa_throw_bad_array_new_length
0004dae4 g DF .text 00000048 CXXABI_1.3.8 __cxa_throw_bad_array_new_length
交叉编译x86工具链(gcc4.9, glibc2.20)上面:
shuyin.wsy@10-101-175-19:/disk7/shuyin.wsy/codebase_host/prebuilts/gcc/linux-x86/x86/i686-linux-gnu-4.9-glibc-2.20/sysroot/usr/lib$ objdump -T -C libstdc++.so.6 | grep __cxa_throw_bad_array_new_length
000488f0 g DF .text00000036 CXXABI_1.3.8 __cxa_throw_bad_array_new_length
服务器(gcc4.6, glibc2.15)上面:
shuyin.wsy@10-101-175-19:/usr/lib/i386-linux-gnu$ objdump -C -T libstdc++.so.6 | grep __cxa_throw_bad_array_new_length
shuyin.wsy@10-101-175-19:/usr/lib/i386-linux-gnu$
可以确定,__cxa_throw_bad_array_new_length是比较新的glibc里面编译出来的libstdc++里面的。
推测是分布式编译icu的host程序时,电脑A(比如gcc4.6, glibc2.15)将.c文件发送到电脑B(比如gcc4.6,glibc2.20),电脑B编译出.o(包括了对__cxa_throw_bad_array_new_length函数的调用,undefined ref),并发送给电脑A。电脑A进行连接.so或者.exe时,由于自身的glibc版本低(glibc2.15 < glibc2.20,且glibc2.15的libstdc++中没有__cxa_throw_bad_array_new_length的定义),所以找不到__cxa_throw_bad_array_new_length函数。
验证.o中是否调用了__cxa_throw_bad_array_new_length函数:
yunos.mk:
LOCAL_PATH:=$(call my-dir)
include $(CLEAR_VARS)
LOCAL_CFLAGS_REMOVED:= -fexceptions
LOCAL_SRC_FILES:= main.cpp
LOCAL_MODULE:= treewei_test
LOCAL_CFLAGS+=-g -std=c++0x
LOCAL_LDFLAGS+= -lstdc++
include $(BUILD_EXECUTABLE)main.cpp:
#include
#include
void * f(int i)
{
return new int[i];
}
int main(int argc, char* argv[])
{ f(-1);
return 1;
}
得到一个target的.o文件,可以看到__cxa_throw_bad_array_new_length里面包括了__cxa_throw_bad_array_new_length函数的调用:
shuyin.wsy@10-101-175-19:/disk7/shuyin.wsy/codebase_host/out/platforms/phone.sc9832.sprd.eng.arm/target/obj/EXECUTABLE/treewei_test_intermediates$ nm main.o
00000000 r $d
00000000 r $d
00000000 r $d
00000000 r $d
00000010 N $d
00000000 t $t
00000000 t $t
00000001 T _Z1fi
U _Znaj
U __aeabi_unwind_cpp_pr1
U __cxa_throw_bad_array_new_length
00000001 T main