我在尝试使用 Android NDK 23 (23.1.7779620) 构建一个简单的 C++ 库时感到非常困惑。我正在使用 CMake,这是一个非常简单的程序:
# CMakeLists.txt
cmake_minimum_required(VERSION 3.14)
project(mf)
add_library(mf lib.cpp)
// lib.hpp
#pragma once
#include <string>
std::string foo(std::string);
// lib.cpp
#include "lib.hpp"
std::string foo(std::string str) {
return std::string{"test"} + str;
}
这是构建的命令行:
cmake -G Ninja -DCMAKE_BUILD_TYPE=Release -DBUILD_SHARED_LIBS=ON -DANDROID_STL=c++_shared -DANDROID_ABI=arm64-v8a -DANDROID_PLATFORM=android-29 -DCMAKE_TOOLCHAIN_FILE=${ANDROID_NDK}/build/cmake/android.toolchain.cmake ..
cmake --build . -v
- 第一个问题是我期望链接到
libc++.so
并不是libc++_shared.so
。它们之间有什么区别?我读本文 https://developer.android.com/ndk/guides/cpp-support。但仍然没有解释之间的区别libc++
and libc++_shared
- 第二个问题更糟糕,看来我正在使用 libstdc++!
- 第三点,我认为clang的c++实现是在命名空间下的
std::__1
但我找不到类似的东西。
我知道使用 libc++_shared 因为这个命令:
$ readelf -d libmf.so
Dynamic section at offset 0x76e0 contains 26 entries:
Tag Type Name/Value
0x0000000000000001 (NEEDED) Shared library: [libm.so]
0x0000000000000001 (NEEDED) Shared library: [libc++_shared.so]
0x0000000000000001 (NEEDED) Shared library: [libdl.so]
0x0000000000000001 (NEEDED) Shared library: [libc.so]
0x000000000000000e (SONAME) Library soname: [libmf.so]
运行 nm 似乎我正在使用来自libstdc++
:
$ nm -gDC libmf.so | grep '__ndk1'
0000000000003af0 T foo(std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char> >)
U std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char> >::append(char const*, unsigned long)
$ nm -gDC libmf.so | grep '__1'
$
Update
在这篇文章中解释了之间的区别libc++.so
and libc++_shared.so