Android APP embed v8的错误汇总
Android APP embed v8的过程(请参见编译和嵌入v8至Android APP),非常艰难,会出现各种各样的错误,此文对此进行总结,便于问题的记录和后续查询和分析。遇到的问题大致分为2类:
- 在Ubuntu 16.04系统下,编译v8的时候,环境的配置、各种参数的设置问题,这最终会影响到生成的库(分static library和shared library两种情形)是否正确。这里定义叫编译v8库的问题。
- 利用Android studio将生成的v8的静态库或者分享库通过NDK嵌入到Android APP时候的各种编译错误或者参数配置问题。此类问题定义为embed v8 in Android APP问题。
解决问题的思路:
- 得到问题的信息,然后在网上搜索,查询是否已有他人的经验可用,比如Stack Overflow和其他网站;
- 在v8的官方wiki页面,找到问题反馈途径(其中,mailing list较常用):
- 结合已有的知识储备,通过实际分析v8构建和相关工具链的机制来修改参数,不断尝试。
编译v8库的问题
- How to build v8 use gnu-libstdc++ instead of llvm-libc++?
tools/dev/v8gen.py android.arm.release -- use_sysroot=false use_glib=false use_custom_libcxx=false
embed v8 in Android APP问题
Note:目前已实现嵌入v8到Android APP并进一步实现基于v8和OpenGL的javascript游戏引擎。请参见我的Github 示例V8Android和SunGameEngine
利用v8的最新分支编译成静态库,然后在AS里面gradle打包,CMake构建时出现下面错误:
Build command failed. Error while executing process /usr/local/v8/v8/third_party/android_tools/sdk/cmake/3.6.4111459/bin/cmake with arguments {--build /mnt/share/V8Wrapper/app/.externalNativeBuild/cmake/debug/armeabi-v7a --target native-lib} [1/1] Linking CXX shared library ../../../../build/intermediates/cmake/debug/obj/armeabi-v7a/libnative-lib.so FAILED: : && /usr/local/v8/v8/third_party/android_ndk/toolchains/llvm/prebuilt/linux-x86_64/bin/clang++ --target=armv7-none-linux-androideabi --gcc-toolchain=/usr/local/v8/v8/third_party/android_ndk/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64 --sysroot=/usr/local/v8/v8/third_party/android_ndk/sysroot -fPIC -isystem /usr/local/v8/v8/third_party/android_ndk/sysroot/usr/include/arm-linux-androideabi -D__ANDROID_API__=16 -g -DANDROID -ffunction-sections -funwind-tables -fstack-protector-strong -no-canonical-prefixes -march=armv7-a -mfloat-abi=softfp -mfpu=vfpv3-d16 -fno-integrated-as -mthumb -Wa,--noexecstack -Wformat -Werror=format-security -std=c++11 -std=c++11 -frtti -fexceptions -O0 -fno-limit-debug-info -Wl,--exclude-libs,libgcc.a -Wl,--exclude-libs,libatomic.a --sysroot /usr/local/v8/v8/third_party/android_ndk/platforms/android-16/arch-arm -Wl,--build-id -Wl,--warn-shared-textrel -Wl,--fatal-warnings -Wl,--fix-cortex-a8 -Wl,--exclude-libs,libunwind.a -L/usr/local/v8/v8/third_party/android_ndk/sources/cxx-stl/llvm-libc++/libs/armeabi-v7a -Wl,--no-undefined -Wl,-z,noexecstack -Qunused-arguments -Wl,-z,relro -Wl,-z,now -shared -Wl,-soname,libnative-lib.so -o ../../../../build/intermediates/cmake/debug/obj/armeabi-v7a/libnative-lib.so CMakeFiles/native-lib.dir/src/main/cpp/native-lib.cpp.o /usr/local/v8/v8/third_party/android_ndk/platforms/android-16/arch-arm/usr/lib/liblog.so ../../../../src/main/cpp/libs/libv8_base.a ../../../../src/main/cpp/libs/libv8_libplatform.a ../../../../src/main/cpp/libs/libv8_libbase.a ../../../../src/main/cpp/libs/libv8_nosnapshot.a ../../../../src/main/cpp/libs/libv8_libsampler.a -latomic -lm "/usr/local/v8/v8/third_party/android_ndk/sources/cxx-stl/llvm-libc++/libs/armeabi-v7a/libc++.a" && : ../../src/isolate.cc:0: error: undefined reference to 'vtable for v8::internal::SetupIsolateDelegate' /usr/local/v8/v8/third_party/android_ndk/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/lib/gcc/arm-linux-androideabi/4.9.x/../../../../arm-linux-androideabi/bin/ld: the vtable symbol may be undefined because the class is missing its key function clang++: error: linker command failed with exit code 1 (use -v to see invocation) ninja: build stopped: subcommand failed.
原因:链接时使用的是libv8_nosnapshot.a库,该库并没有包含
v8::internal::SetupIsolateDelegate
的相关定义。该问题的讨论可以参考v8 mail list的帖子:https://groups.google.com/forum/#!starred/v8-users/hjNr1F6lLgg解决办法:目前有两种办法:
(该办法已验证OK)采用libv8_snapshot.a库替代libv8_nosnapshot.a库。同时在C++源代码的前面加上部分内部空间声明(否则构建apk的时候CMake会报错,找不到这几个函数定义):
1
2
3
4
5
6
7
8
9
10
11
12/**
* Must stub in case external snapshot files are used.
*/
namespace v8::internal {
void ReadNatives() {}
void DisposeNatives() {}
void SetNativesFromFile(v8::StartupData *s) {}
void SetSnapshotFromFile(v8::StartupData *s) {}
}(该办法目前未亲自验证)成功编译v8之后,生成的include目录下并未包含
setup-isolate.h
头文件,而v8::internal::SetupIsolateDelegate
的相关定义在该头文件中。从v8源码的src子目录中找到setup-isolate.h
头文件,并将其添加到Android studio工程的CMakeLists.txt
文件对应的cpp源码段落中。可参考https://groups.google.com/forum/#!starred/v8-users/hjNr1F6lLgg
附录和链接
- http://v8-users.narkive.com/eqwIR5SF/building-v8
- https://medium.com/@hyperandroid/compile-v8-for-arm-7-df45372f9d4e
- https://medium.com/@hyperandroid/android-v8-embedding-guide-f64173f7958b
- https://bugs.chromium.org/p/chromium/issues/detail?id=738056
- https://github.com/lorinbeer/vatedroid
- https://www.jianshu.com/p/f25e36da63dc
- https://blog.piasy.com/2017/09/03/Use-WebRTC-Static-Library/#buildgradle
- https://blog.csdn.net/Kaitiren/article/details/23255195
- https://github.com/social-games/CompiledV8
- https://github.com/social-games/V8Tutorial