如何从 Android NDK .so 文件中去除符号?

Myr*_*ria 7 android debug-symbols android-ndk

如何从 Android.so原生代码库中剥离符号?

我有一个.so在十六进制编辑器中清晰可见的数千个符号。IDA Pro 根据可执行文件中的符号自动使用适当的符号进行反汇编。

但是,如果我要求nm转储符号表,它会说没有。 strip并且objcopy也没有效果。

C:\AndroidProject.apk\lib\armeabi-v7a>arm-linux-androideabi-strings.exe libMeow.so | findstr _ZN11SecretClass14SecretFunctionERKS_
_ZN11SecretClass14SecretFunctionERKS_

C:\AndroidProject.apk\lib\armeabi-v7a>arm-linux-androideabi-nm.exe libMeow.so
arm-linux-androideabi-nm.exe: libMeow.so: no symbols

C:\AndroidProject.apk\lib\armeabi-v7a>copy /y libMeow.so libMeow-test.so
        1 file(s) copied.

C:\AndroidProject.apk\lib\armeabi-v7a>sha1sum libMeow.so libMeow-test.so
0a36701ba44b4cfb31e6f6506349493d5466cd70 *libMeow.so
0a36701ba44b4cfb31e6f6506349493d5466cd70 *libMeow-test.so

C:\AndroidProject.apk\lib\armeabi-v7a>arm-linux-androideabi-strip.exe libMeow-test.so

C:\AndroidProject.apk\lib\armeabi-v7a>sha1sum libMeow.so libMeow-test.so
0a36701ba44b4cfb31e6f6506349493d5466cd70 *libMeow.so
0a36701ba44b4cfb31e6f6506349493d5466cd70 *libMeow-test.so

C:\AndroidProject.apk\lib\armeabi-v7a>arm-linux-androideabi-strip.exe -g libMeow-test.so

C:\AndroidProject.apk\lib\armeabi-v7a>sha1sum libMeow.so libMeow-test.so
0a36701ba44b4cfb31e6f6506349493d5466cd70 *libMeow.so
0a36701ba44b4cfb31e6f6506349493d5466cd70 *libMeow-test.so
Run Code Online (Sandbox Code Playgroud)

名称已更改以保护有罪的人。

mst*_*sjo 8

由于.so是一个将动态加载的共享库,因此它需要有一定数量的外部可用符号。要查看这些,请使用nm -D libMeow.so. Strip 不会删除这些,否则会使库无法使用。

由于某些功能需要从外部加载,因此您不能只删除所有动态符号,因为那样没有人能够与.so. 如果你.so是一个 JNI 库,你需要让 JNI 入口点函数在外部可见,而如果它是另一个.so链接的共享库,你至少需要让你的库的公共接口可见。

要隐藏内部符号,您可以阅读https://gcc.gnu.org/wiki/Visibility以获取完整故事。粗略地说,您的选择是:

  • 用于__attribute__ ((visibility ("hidden")))您不希望在库外可见的每个符号。(这可能是相当多的,而且要追踪每一个都需要做很多工作。)
  • Build with -fvisibility=hidden,它在每个外部符号上隐式设置它,并添加__attribute__ ((visibility ("default")))您实际需要导出的那些(可能更少)
  • 使用“版本脚本”来限制要导出到选择列表的功能。链接时,通过-Wl,-version-script -Wl,mylib.ver

对于版本脚本案例,mylib.ver应如下所示:

{ global:
PublicFunction1;
PublicFunction2;
local: *; };
Run Code Online (Sandbox Code Playgroud)

  • 您还应该考虑“-fvisibility-inlines-hidden”,因为您提到了可见性。如果链接到其他库,`-Wl,--exclude-libs,ALL` 是必须的。没有`-Wl,--exclude-libs,ALL`,即使使用`-fvisibility=hidden -fvisibility-inlines-hidden`,我们的共享对象也会重新导出数百个符号。另请参阅[如何将 gcc -fvisibility 选项应用于静态库中的符号?](/sf/ask/155551371/) (2认同)
  • 另一组可能有助于减少大小和符号的选项是编译器标志“-ffunction-sections -fdata-sections”和链接器标志“-Wl,--gc-sections”。 (2认同)