embedded - ARM 上的堆分析

标签 embedded profiling arm heap-memory

我正在基于 Freescale MX51 的 Linux 2.6.35 主板上开发一个 GUI 密集型 C++ 应用程序。 我想执行堆分析。

不幸的是,我发现的所有堆分析工具要么侵入性太强,要么表面上在 ARM 上不起作用。我尝试过的具体工具:

  • Valgrind Massif :由于平台的 CPU 较弱,因此无法在我的平台上运行。 Massif 引入的 80% CPU 时间开销导致我的应用程序出现一系列无法​​补偿的问题。
  • gperftools (以前称为 Google 性能工具)tcmalloc:这个相当非侵入性的、基于库的 libc malloc() 替代品的所有功能都可以在我的目标上工作除了堆分析器。换句话说,线程缓存分配器可以工作,但分析器却不能。我将在下面为任何好奇的人解释分析器的故障模式。

任何人都可以建议一套用于在 ARM 平台上执行 C++ 堆分析的替代工具吗?理想的输出最终将是一个有向分配图,类似于 gperftools 的 tcmalloc 输出。资源利用率低是必须的——我的平台资源高度受限。

<小时/>

gperftools的tcmalloc失败模式解释:

我仅为那些好奇的人提供此信息;我不期望得到回应。我看到类似于下面的 gperftools 问题 #407 的内容,但在 ARM 而不是 x86 上除外。 具体来说,我总是收到消息“未找到 Hook 分配器框架,返回空跟踪”。我花了一些时间调试这个问题,看起来,当动态链接 tcmalloc 库时,我的应用程序和动态库之间边界处的帧指针为空 - 堆栈无法在动态库的调用“上方”行走。

gperftools 问题#407:https://github.com/gperftools/gperftools/issues/410

stackoverflow 用户在 ARM 上看到类似问题:Missing frames on shared libraries on ARM

最佳答案

堆。实现这些目标的方法有很多,但我只遇到过嵌入式领域中重要的 3 种主要类型:

  1. 链表堆。每个分配都在“已使用”列表中进行跟踪。一旦被释放,它们就会被放入“自由”列表中。释放时,相邻的空闲内存块被“连接”成更大的 block 。分配可以是任意大小。每个分配和释放都是 O(N) 操作,因为它必须遍历空闲列表来为您提供一 block 内存,并将空闲 block 分解为接近您要求的大小,同时将剩余 block 保留在空闲列表中。由于每次分配的开销不断增加,该系统无法在较小的系统上单独使用。如果不采取措施尽量减少内存碎片,随着时间的推移,这也往往会导致内存碎片。

  2. 固定大小(单位)堆。您将堆分成相同大小(较小)的部分。这会浪费一点内存,具体取决于 block 有多大(以及您创建的不同大小的固定分配器堆的数量),但 alloc 和 free 都是 O(1) 时间操作。无需搜索,无需加入。这种风格通常与第一种风格结合用于“小对象分配”,因为我使用过的引擎 95% 的分配都低于设定大小(例如 256 字节)。这样,您可以使用单位堆进行小型分配,以获得巨大的速度和最小的内存损失,同时使用列表堆进行较大的分配。也没有外部内存碎片。

  3. 可重定位内存堆。您给出的不是内存指针,而是句柄。这样,您可以在需要时在幕后更改内存指针以删除碎片或其他内容。高开销。 @$$ 商非常痛苦,因为它很容易被滥用并让指针到处晃动。还增加了每次内存取消引用的开销。但想提一下。

有一些基本模式。您可以在野外找到使用它们的各种库,并且还具有有关分配数量、碎片和其他有用统计信息的内置统计信息。真正推出自己的产品也不难,尽管我不推荐它用于满足好奇心之外的任何事情,因为在没有可用的 malloc 的情况下进行调试确实很痛苦。添加线程支持也非常简单,但同样,下载现成的解决方案是更好的选择。

上述信息适用于所有平台,无论是 ARM 还是其他平台,尽管我的大部分经验都是在低级别 ARM 上,因此上述信息针对您的平台进行了实际测试。希望这有帮助!

关于embedded - ARM 上的堆分析,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11514500/

相关文章:

c - 当使用 -Wmissing-prototypes 时,如何抑制 GCC 对中断例程没有原型(prototype)的警告?

python - 如何使用Python-CAN查看CAN网络的错误帧

java - NetBeans Profiler 上的 byte[] 和 char[]

linux - 什么时候在内核中创建 kallsyms?

x86 - 将低级 x86 优化代码移植到 ARM Cortex-A8 架构

c++ - 编译时数据段太大

c++ - 结构位打包和 LSB/MSB 歧义 C++

iphone - iOS 设备中的低级循环计数器

java - GRPC 服务器响应延迟

linux - 用于 arm-linux-gcc 的 C/C++ 目标的简单 makefile