【问题标题】:What parts of the codebase are making binaries large?代码库的哪些部分使二进制文件变大了?
【发布时间】:2019-03-15 00:39:23
【问题描述】:

我已经为模拟器构建了一些代码,现在正尝试使用 TI 的免费工具链交叉编译到具有 64kb nvram 的目标。编译器声称我的代码超出 ROM 大约 34kb:

(...) msp430-elf/bin/ld: region `ROM' overflowed by 33716 bytes

另一行说它无法将.text 字段放入其分配的空间。我不敢相信我的添加总共是 34kb,更不用说导致二进制文件溢出这个数量了。

  • 我的代码添加到项目中的 .o 文件仅占项目总数的一小部分(1.9MB 中的 200kb),而且我已经取出了项目中的大量组件。
  • 我已经向编译器传递了-Os -s 标志。
  • 新代码包含大约 100 个字符的字符串字面量。
  • 我的代码使用了很多math.h函数(实际上它是唯一做浮点运算的部分),调用strtod,调用sprintf

是否有任何工具或方法可以分解导致二进制文件如此大的原因?

【问题讨论】:

  • 看看链接器生成的地图文件,它应该会告诉你你需要的一切。
  • 我想看看你自己的答案,你是如何解决这个问题的;)
  • 在映射文件中查找不可见的(即编译器/链接器将它们放在那里,而不是您)例程,以查找不需要的“pc”内容,例如进程退出处理程序、异常处理程序、除零处理程序。

标签: c embedded cross-compiling microcontroller


【解决方案1】:

GNU binutils 有一些工具可以帮助您确定每个符号或每个目标文件的大小。

查看size 例如:https://manpages.debian.org/jessie/binutils/size.1.en.html

nm也值得一试,因为它可以显示目标代码中每个符号的大小:https://manpages.debian.org/jessie/binutils/nm.1.en.html

仔细检查sizenm 的输出会让您直观地了解哪些内容占用了很多空间,哪些内容不占用空间。

知道printfsprintf 和许多更复杂的库函数通常会占用相当多的额外 ROM。

与使用硬浮点相比,使用软浮点的浮点支持也会使代码膨胀,即使用软件仿真与硬件指令来处理浮点。

有时编译器会增加惊人的膨胀量:)

【讨论】:

    【解决方案2】:

    我曾经也遇到过小型 MSP430 控制器的内存问题。 如果可能有负值或使用浮点,TI 工具链会将大型库链接到您的二进制文件中。就我而言,它大约占总内存使用量的 10% - 20%。

    TI 的免费 Code composer Studio 确实提供了非常强大的内存可视化(查看 -> 内存分配)

    对我帮助很大的是更改链接器设置中的初始化模型和其他优化选项。我目前没有使用 MSP430 控制器,所以我不能再告诉你细节了。

    【讨论】:

      【解决方案3】:

      还有 AMAP,一个用于查看 .map 文件的小而简单的 gui:http://www.sikorskiy.net/prj/amap/

      如果有一个类似 kdirstat 的工具可以让您直观地比较符号大小,那就太好了。

      虽然不是直接回答这个问题,但我最终还是使用了 Voidware 的 CORDIC 实现来避免使用 <math.h> 中的大型函数:https://github.com/enthdegree/cordic_wrapped

      【讨论】:

        猜你喜欢
        • 2012-10-25
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2023-03-20
        • 1970-01-01
        • 1970-01-01
        • 2019-01-26
        • 1970-01-01
        相关资源
        最近更新 更多