Different object files generated when cross compiling V8 7.3 for Android ARM (vs V8 7.2)

190 views
Skip to first unread message

Darin Dimitrov

unread,
Feb 11, 2019, 8:13:59 AM2/11/19
to v8-users
I am trying to cross compile V8 for Android (ARM) on an Ubuntu host using the latest NDK 19:

gn gen outgn/arm-release --args="is_debug=false symbol_level=0 target_cpu=\"arm\" v8_target_cpu=\"arm\" target_os=\"android\""

ninja
-C outgn/arm-release v8_libplatform

And then I try to inspect the exported symbols from the resulting object file:

nm -C outgn/arm-release/obj/v8_libplatform/default-platform.o | grep "v8::platform::DefaultPlatform::DefaultPlatform"

outputs the following when building V8 7.2.502.25:

00000001 T v8::platform::DefaultPlatform::DefaultPlatform(v8::platform::IdleTaskSupport, std::__ndk1::unique_ptr<v8::TracingController, std::__ndk1::default_delete<v8::TracingController> >)

and the following when building V8 7.3.492.10:

00000001 T v8::platform::DefaultPlatform::DefaultPlatform(v8::platform::IdleTaskSupport, std::__1::unique_ptr<v8::TracingController, std::__1::default_delete<v8::TracingController> >)

Notice the "std::__ndk1" vs "std::__1". It looks like some different STL is used in 7.3.

As a result I am getting errors when I try to link against "libv8_libplatform.a" in Android studio:

error: undefined reference to 'v8::platform::DefaultPlatform::DefaultPlatform(v8::platform::IdleTaskSupport, std::__ndk1::unique_ptr<v8::TracingController, std::__ndk1::default_delete<v8::TracingController> >)'

Do you know what might have changed in the compilation process of V8 between those two versions that would result in such behavior? And is it possible to somehow control this using some build flags?

Darin Dimitrov

unread,
Feb 11, 2019, 11:09:49 AM2/11/19
to v8-users
I was able to bisect the issue to the following commit in which the V8 DEPS were updated: https://chromium.googlesource.com/v8/v8/+/843535b893968a89f98b295cd7b1b265ca2927c1

Darin Dimitrov

unread,
Feb 12, 2019, 11:05:19 AM2/12/19
to v8-users
Further narrowing this down.

In V8 7.2, libc++ is taken from the NDK: 

-isystem../../third_party/android_ndk/sources/cxx-stl/llvm-libc++/include
-isystem../../third_party/android_ndk/sources/cxx-stl/llvm-libc++abi/include

whereas in V8 7.3, a different libc++ is used:

-isystem../../buildtools/third_party/libc++/trunk/include
-isystem../../buildtools/third_party/libc++abi/trunk/include

And the difference between the two versions is that the one from the NDK defines the following std namespace override:

#ifndef _LIBCPP_ABI_NAMESPACE
# define _LIBCPP_ABI_NAMESPACE _LIBCPP_CONCAT(__ndk,_LIBCPP_ABI_VERSION)
#endif

while the custom one uses this:

#ifndef _LIBCPP_ABI_NAMESPACE
# define _LIBCPP_ABI_NAMESPACE _LIBCPP_CONCAT(__,_LIBCPP_ABI_VERSION)
#endif

So the question is, what would be the proper gn arguments to link against libc++ from the NDK?

I have tried setting use_custom_libcxx=false but in this case no -isystem is specified and the build fails as it cannot find some common includes such as <memory> and <functional>.

Tom Anderson

unread,
Feb 12, 2019, 3:15:04 PM2/12/19
to v8-users
Usually C++ objects should not be passed over library boundaries.  In this case though, the issue could be fixed by adding a wrapper for v8::platform::DefaultPlatform::DefaultPlatform() that takes a C-style pointer instead of a unique_ptr.

I'm also not sure if v8_libplatform is meant to be redistributed in this way, though the V8 team can say for sure.

Darin Dimitrov

unread,
Feb 13, 2019, 2:24:34 AM2/13/19
to v8-users
Tom, thanks for the reply. The DefaultPlatform method was just an example. Looking at the public API in v8.h there are quite a lot of references to C++ objects from the standard library and I am getting tons of those similar linker errors. That's what made me think that I must be doing something wrong.

I managed to successfully compile and link if I manually modify _LIBCPP_ABI_NAMESPACE in the "third_party/libc++/trunk/include/__config" include file. But I feel that it should somehow be possible to specify the libc++ location when building v8 so that it uses the one from the NDK.

Darin Dimitrov

unread,
Feb 20, 2019, 4:41:58 AM2/20/19
to v8-users
Turns out that V8 is building against a custom STL passing the _LIBCPP_ABI_UNSTABLE flag. So in order to build my final executable I had to use this same STL instead of the default libc++_static.a library provided by the NDK.

张小明

unread,
Jul 10, 2019, 4:01:20 AM7/10/19
to v8-users
It seems 7.5.288.22 didn't fix this issue. Do somebody know if there is a plan to fix it?

Jean-Claude Monnin

unread,
Jun 15, 2020, 10:53:55 PM6/15/20
to v8-u...@googlegroups.com
I'm facing the same issue. I built v8 for Android, and when linking `libv8_monolith.a` in my app using NDK, there are link errors. The app and the other third-party libs use the NDK libc++ expecting the `std::__ndk1` namespace, but v8 is expecting `std::__1`.

I couldn't find a way to tell the v8 build system to use the libc++ from the NDK. Is there really no way to use the default libc++ from NDK when compiling v8?

In case the only solution is to use the libc++ version imposed by v8 everywhere (like Darin Dimitrov did), how is it done?
I'm couldn't find an appropriate lib to link in `buildtools/third_party/libc++`. I could find some `libc++_static.a` in the v8 source tree, but they are in `third_party/android_ndk/` and they use `std::__ndk1` (see [1] and [2]).

Any advice of how to correctly use v8 with NDK is appreciated.
The official documentation helps to get v8 compiled standalone (https://v8.dev/docs/cross-compile-arm), but the difficult part starts when trying linking it with other libs and code.

I tried with both 7.3-lkgr and 8.3-lkgr v8 versions.


--------------------------
[1]: Searching for `libc++_static.a` in the v8 source tree

find . -name libc++_static.a
./third_party/android_ndk/toolchains/llvm/prebuilt/linux-x86_64/sysroot/usr/lib/i686-linux-android/libc++_static.a
./third_party/android_ndk/toolchains/llvm/prebuilt/linux-x86_64/sysroot/usr/lib/aarch64-linux-android/libc++_static.a
./third_party/android_ndk/toolchains/llvm/prebuilt/linux-x86_64/sysroot/usr/lib/x86_64-linux-android/libc++_static.a
./third_party/android_ndk/toolchains/llvm/prebuilt/linux-x86_64/sysroot/usr/lib/arm-linux-androideabi/libc++_static.a
./third_party/android_ndk/sources/cxx-stl/llvm-libc++/libs/armeabi-v7a/libc++_static.a
./third_party/android_ndk/sources/cxx-stl/llvm-libc++/libs/arm64-v8a/libc++_static.a
./third_party/android_ndk/sources/cxx-stl/llvm-libc++/libs/x86_64/libc++_static.a
./third_party/android_ndk/sources/cxx-stl/llvm-libc++/libs/x86/libc++_static.a

[2]: checking the demangled names used in the static library

~/Android/Sdk/ndk/21.3.6528147/toolchains/aarch64-linux-android-4.9/prebuilt/linux-x86_64/bin/aarch64-linux-android-nm --demangle third_party/android_ndk/toolchains/llvm/prebuilt/linux-x86_64/sysroot/usr/lib/i686-linux-android/libc++_static.a | grep string
00000000 W std::__ndk1::__basic_string_common<true>::__throw_length_error() const
....
--
--
v8-users mailing list
---
You received this message because you are subscribed to the Google Groups "v8-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to v8-users+u...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Jean-Claude Monnin

unread,
Jun 17, 2020, 2:15:24 AM6/17/20
to v8-users
I was able to get it running by defining `use_custom_libcxx=false`.

In hindsight it's rather straightforward. It doesn't work on 7.3, but it works fine on 8.3.
I have read in a couple of places that `use_custom_libcxx=false` is not supported on Android. It looks like this information is outdated if using a recent version of v8.

Himanshu Bansla

unread,
Sep 1, 2020, 12:12:09 PM9/1/20
to v8-users
Hi, I was also trying to cross-compile v8 7.6 for android ARM on ubuntu machine: 
 gn gen out.gn/android.arm64.release -vv --args="is_debug=false is_component_build=false v8_use_snapshot=true v8_static_library=true v8_use_external_startup_data=false v8_enable_i18n_support=true v8_monolithic=true use_custom_libcxx=false target_cpu=\"arm64\""
Running nm --demangle on the v8's static library(v8_monolith.a)  which is created by building v8 has symbols as std::__cxx11  which should be std::__ndk.  Any idea what else can i try ? I even tried with v8 8.3 but didnot get any help. What would be the proper gn arguments to link against libc++ from the NDK ?

Reply all
Reply to author
Forward
0 new messages