如何在 MacO 中真正剥离二进制文件

发布于 2024-08-15 14:23:25 字数 1341 浏览 8 评论 0原文

MacOs 10.6,如​​果我有一个文件“unwanted.c”,其中包含:

class secret_thing {
public:
secret_thing() {}
void revealing_method_name() {}
};

main()
{
    secret_thing obj;
    obj.revealing_method_name();
}

现在我这样做:

$ g++ unwanted.c -o unwanted
$ strip unwanted
$ nm unwanted | grep secret
0000000100000eb8 T __ZN12secret_thing21revealing_method_nameEv 
0000000100000eae T __ZN12secret_thingC1Ev

如果我像大多数人在编写 C++ 代码时所做的那样,将秘密类的接口和实现分开,那么在剥离的可执行文件。遗憾的是,我收到了一个包含数千行代码的现有代码库,但这不是我的选择之一。

我尝试过 -fno-rtti,作为一个疯狂的猜测,但这并没有解决任何问题。我向谷歌诸神祈祷,发现了很多关于脱衣舞俱乐部的参考资料,但没有任何有用的链接。我浏览了 mac 上的 strip、g++ 和 ld 的手册页,没有明显的东西可以尝试,尽管“private externs”这个短语很有趣,但我不知道该怎么做。

[ 更新 ] 可悲的是,我尝试做一个小例子却出现了问题。这是一个更复杂的示例,它更接近真正的问题,如果构建优化,它仍然包含不需要的符号。

我对不好的例子表示歉意。事实证明,找到最小的实际问题是很困难的。不过,非常感谢您的答案,每个答案都让我接近解决方案。

class base {
public:
    virtual int revealing_method_name() = 0;
    virtual ~base() {};
};

class secret_thing : public base {
public:
    int revealing_method_name() { return 0; };
};

class other_thing : public base {
public:
    int revealing_method_name() { return 1; };
};

int main(int argc, char**)
{
    base *object = 0;
    if( argc > 1 ) object = new secret_thing;
    else object = new other_thing;

    return object->revealing_method_name();
}

MacOs 10.6, if I have a file "unwanted.c" which contains:

class secret_thing {
public:
secret_thing() {}
void revealing_method_name() {}
};

main()
{
    secret_thing obj;
    obj.revealing_method_name();
}

Now I do:

$ g++ unwanted.c -o unwanted
$ strip unwanted
$ nm unwanted | grep secret
0000000100000eb8 T __ZN12secret_thing21revealing_method_nameEv 
0000000100000eae T __ZN12secret_thingC1Ev

If I split out the interface and implementation of the secret class, as most people do when writing C++ code, then there are no unwanted symbols in the stripped executable. Sadly, I am handed an existing code base of many thousand lines of code and this isn't one of my choices.

I have tried -fno-rtti, as a wild guess, and that didn't fix anything. I have prayed to the Google gods and found many references to strip clubs, but no helpful links. I have skimmed the man pages for strip, g++, and ld on the mac, and there were no obvious things to try, though the phrase "private externs" was intriguing, I couldn't figure out what to do about that.

[ update ]
Sadly, there turns out to be a problem with my attempt to make a small example. Here is a more complicated example, which is closer to what the real problem is, which still has unwanted symbols if it is built optimized.

I apologize for the bad examples. It turns out to be hard to find the smallest actual problem. Many thanks for the answers, though, each answer pushes me close to a solution.

class base {
public:
    virtual int revealing_method_name() = 0;
    virtual ~base() {};
};

class secret_thing : public base {
public:
    int revealing_method_name() { return 0; };
};

class other_thing : public base {
public:
    int revealing_method_name() { return 1; };
};

int main(int argc, char**)
{
    base *object = 0;
    if( argc > 1 ) object = new secret_thing;
    else object = new other_thing;

    return object->revealing_method_name();
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

空心↖ 2024-08-22 14:23:25

使用以下编译行,我成功地从可执行文件中删除符号:

$ g++ -Xlinker -unexported_symbol -Xlinker "*" -o executable file.cpp
$ strip executable

给定最新的示例文件,结果是:

$ nm executable
                 U __ZTVN10__cxxabiv117__class_type_infoE
                 U __ZTVN10__cxxabiv120__si_class_type_infoE
                 U __ZdlPv
                 U __Znwm
                 U ___cxa_pure_virtual
                 U ___gxx_personality_v0
0000000100000000 A __mh_execute_header
                 U _exit
                 U dyld_stub_binder

Using the following compile line I successfully strip the symbols from the executable:

$ g++ -Xlinker -unexported_symbol -Xlinker "*" -o executable file.cpp
$ strip executable

Given the latest sample file, this results in:

$ nm executable
                 U __ZTVN10__cxxabiv117__class_type_infoE
                 U __ZTVN10__cxxabiv120__si_class_type_infoE
                 U __ZdlPv
                 U __Znwm
                 U ___cxa_pure_virtual
                 U ___gxx_personality_v0
0000000100000000 A __mh_execute_header
                 U _exit
                 U dyld_stub_binder
花海 2024-08-22 14:23:25

这似乎按预期工作......:

$ strip unwanted
$ nm unwanted | grep secret | cut -f 3 -d ' ' > /tmp/remove
$ strip -R /tmp/remove unwanted

This seems to work as desired...:

$ strip unwanted
$ nm unwanted | grep secret | cut -f 3 -d ' ' > /tmp/remove
$ strip -R /tmp/remove unwanted
拿命拼未来 2024-08-22 14:23:25

听起来您真正想要的不是删除可执行文件,而是混淆其符号表。我不确定,但也许类似 this 会有所帮助。至少,“C++ 符号表混淆器”可能是更好的 Google 搜索字符串。

It sounds like what you really want isn't to strip the executable, but to obfuscate its symbol table. I'm not sure, but perhaps something like this would be helpful. At least, "C++ symbol table obfuscator" is probably a better Google search string..

欲拥i 2024-08-22 14:23:25

鉴于您发布的示例代码,添加“-O”优化标志会导致编译后 nm 不显示这些符号。

Given the example code you’ve posted, adding the ‘-O’ optimisation flag results in those symbols not being shown by nm after compilation.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文