我正在编译库,我需要隐藏尽可能多的信息 在二进制文件中(不显示使用的方法)。我正在使用 strip 等工具 这样做,但在生成的库上运行字符串工具时, 我一直在寻找包含某些类名称的符号。 有关的类是使用虚方法的类。
让我们来说明问题。
我想编译以下程序并隐藏类 A 和 二进制文件中 B :
namespace test {
class A {
public:
virtual void foo() {};
};
class B: public A {
};
}
int main(int argc, char **argv) {
test::B b;
b.foo();
return 0;
}
我用g ++编译它:
$ g++ --version
g++ (Ubuntu 5.4.0-6ubuntu1~16.04.4) 5.4.0 20160609
$ g++ main.cpp
如果我查找与 test 命名空间相关的所有符号,我会得到以下结果:
$strings a.out | grep test
N4test1BE
N4test1AE
_ZN4test1AC2Ev
_ZN4test1A3fooEv
_ZTVN4test1BE
_ZN4test1BC1Ev
_ZTIN4test1BE
_ZTVN4test1AE
_ZTSN4test1AE
_ZTIN4test1AE
_ZN4test1AC1Ev
_ZTSN4test1BE
_ZN4test1BC2Ev
我知道以 _Z 开头的符号与 不同的类方法(即使我不确定它们之间的区别 _ZN , _ZTV , _ZTI 和 _ZTS )。但我不知道两者是什么 符号 N4test1BE 和 N4test1AE 。
如果我删除所有符号:
$ strip --strip-all --discard-all a.out
$ strings a.out | grep test
N4test1BE
N4test1AE
我无法删除两个符号。
有人可以帮我理解它们是什么以及如何从二进制文件中删除它们吗?
我的直觉是它与 VTable 有关,但我真的不知道它是如何工作的。
提前致谢!
答案 0 :(得分:0)
这些字符串来自运行时类型信息(RTTI)。具体来说,它们使typeid(obj).name()
能够返回识别名称。
如果您不需要,可以使用-fno-rtti
将其关闭。请注意,某些标准C ++功能需要RTTI。当禁用它时,你得到的不仅仅是C ++,你可能需要调整一些代码来保持它的正常运行。