gpt4 book ai didi

c++ - 添加虚拟析构函数膨胀代码大小

转载 作者:塔克拉玛干 更新时间:2023-11-03 02:21:15 25 4
gpt4 key购买 nike

我正在使用最新可用的 arm-none-eabi-gcc 6.3 在 arm cortex m3 上使用 c++。我制作了一个虚拟类并创建了该类的全局对象:

class B
{};

class A : B
{
public:
A()
{
RCC->APB2ENR |= RCC_APB2ENR_IOPCEN;
GPIOC->CRH = 1;
GPIOC->ODR |= 1<<8;
}

virtual void foo()
{}

virtual ~A()
{}
};

A a;

int main(void) { while(1); }

此代码编译为 1620 字节。如果我删除虚拟 dtor,它会编译为 1304 字节。这是一个明显的区别。

我查看了程序集和 .map 文件,发现如果我使用虚拟 dtor,许多不同的运行时函数会链接到我的二进制文件。有 malloc 和 free 以及 _static_initialization_and_destruction 等等。

奇怪的是:我不明白他们怎么称呼? Main 是这样调用的:

 8000260:   d3f9        bcc.n   8000256 <FillZerobss>
8000262: f000 f89f bl 80003a4 <SystemInit>
8000266: f000 f957 bl 8000518 <__libc_init_array>
800026a: f000 f865 bl 8000338 <main>
800026e: 4770 bx lr

从 main 返回后(顺便说一句,这从来没有发生过)执行就停留在 bx lr 上,它不断跳转到相同的地址。

所以我看不到调用静态对象取消初始化的路径。为什么不将其优化为无法访问的代码?

我这样编译: arm-none-eabi-g++ -c -fmessage-length=0 -mcpu=cortex-m3 -mthumb -fdata-sections -ffunction-sections -fno-rtti -fno-exceptions -fno-threadsafe-statics并像这样链接 arm-none-eabi-g++ -mcpu=cortex-m3 -mthumb --specs=nosys.specs --specs=nano.specs -Wl,--gc-sections -T "${ProjDirPath}/src/Startup/STM32F100XB_FLASH.ld" -ffreestanding

我尝试添加 -fno-use-cxa-atexit 或制作一个虚拟 __cxa_atexit - 它确实使二进制稍微变小了(这比完全没有效果更奇怪)。

有没有办法完全禁止销毁静态对象?

更新:

  • 添加 -Os 使代码缩小但有/没有虚拟 dtor 仍然存在差异(1244 对 1040 字节)所以问题仍然存在。
  • 这是使用 -S with dtor 编译的输出, without dtor

最佳答案

如果不进行全程序优化,就不清楚析构函数实际上是不可达的。可能有另一个带有构造函数的翻译单元生成一个线程,该线程稍后调用 exit 函数。

关于c++ - 添加虚拟析构函数膨胀代码大小,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45243551/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com