【问题标题】:Ada Task Declaration Causes Memory LeakAda 任务声明导致内存泄漏
【发布时间】:2012-03-03 21:09:19
【问题描述】:

我有以下 Ada 小程序:

procedure Leaky_Main is 
   task Beer;
   task body Beer is 
   begin 
      null;
   end Beer;
begin 
   null;
end Leaky_Main;

所有都相当基本,但是当我这样编译时:

gnatmake -g -gnatwI leaky_main.adb

并像这样通过 Valgrind 运行它:

valgrind --tool=memcheck -v --leak-check=full --read-var-info=yes --leak-check=full --show-reachable=yes ./leaky_main

我收到以下错误摘要:

==2882== 2,104 bytes in 1 blocks are still reachable in loss record 1 of 1
==2882==    at 0x4028876: malloc (vg_replace_malloc.c:236)
==2882==    by 0x42AD3B8: __gnat_malloc (in /usr/lib/i386-linux-gnu/libgnat-4.4.so.1)
==2882==    by 0x40615FF: system__task_primitives__operations__new_atcb (in /usr/lib/i386-linux-gnu/libgnarl-4.4.so.1)
==2882==    by 0x406433C: system__tasking__initialize (in /usr/lib/i386-linux-gnu/libgnarl-4.4.so.1)
==2882==    by 0x4063C86: system__tasking__initialization__init_rts (in /usr/lib/i386-linux-gnu/libgnarl-4.4.so.1)
==2882==    by 0x4063DA6: system__tasking__initialization___elabb (in /usr/lib/i386-linux-gnu/libgnarl-4.4.so.1)
==2882==    by 0x8049ADA: adainit (b~leaky_main.adb:142)
==2882==    by 0x8049B7C: main (b~leaky_main.adb:189)
==2882== 
==2882== LEAK SUMMARY:
==2882==    definitely lost: 0 bytes in 0 blocks
==2882==    indirectly lost: 0 bytes in 0 blocks
==2882==      possibly lost: 0 bytes in 0 blocks
==2882==    still reachable: 2,104 bytes in 1 blocks
==2882==         suppressed: 0 bytes in 0 blocks
==2882== 
==2882== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 21 from 6)
--2882-- 
--2882-- used_suppression:     21 U1004-ARM-_dl_relocate_object
==2882== 
==2882== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 21 from 6)

有谁知道为什么这被报告为错误? 我相当确定没有实际泄漏,但我想知道它为什么/如何发生。

谢谢,

【问题讨论】:

  • 哪里出错了? 0 个错误,0 个字节丢失...
  • @oenone :“仍然可以访问:1 个块中的 2,104 个字节”
  • 问题出在哪里?内存仍然可以访问。这没有错误,也没有这样报告。
  • 当内存在程序终止后可以访问时,这是一个泄漏,这是一个问题。正如西蒙指出的那样,这可能是由于一个已知的错误。
  • 我认为这不是问题。这可能并不理想,但操作系统无论如何都会释放进程使用的所有内存。

标签: memory-leaks valgrind ada


【解决方案1】:

有问题的分配看起来是任务控制块 (TCB)。这必须在任务完成后保留,以便您可以说

if Beer’Terminated then
   ...

所以我认为这可能是 valgrind 进行检查时的人工制品。

我只在分配任务的地方遇到过这种情况;必须等到’Terminated 变为True 才能释放任务,或者 GNAT 很高兴地释放了堆栈但默默地没有释放 TCB,从而导致像你这样的真正泄漏。 AdaCore 最近修复了这个问题(我没有参考,它在他们的开发者日志中)。

【讨论】:

  • 谢谢西蒙,这看起来是一个合理的解释。我会为 valgrind 写一个抑制来处理它:)
  • 有趣。谢谢你的信息。
【解决方案2】:

您应该使用 deleaker 进行调试。我更喜欢)

【讨论】:

  • 与 Ada 开发无关。
猜你喜欢
  • 2015-08-22
  • 1970-01-01
  • 2011-08-16
  • 1970-01-01
  • 2015-07-06
  • 2014-06-07
  • 2013-11-20
  • 2011-10-28
  • 2016-01-18
相关资源
最近更新 更多