【问题标题】:Detect the bounds of the stack of the current thread检测当前线程的栈边界
【发布时间】:2011-01-09 06:32:34
【问题描述】:

我正在编写一个半准确的垃圾收集器,我想知道是否有一种方法可以准确地检测给定线程的系统分配堆栈的边界。

我需要这个,所以我可以扫描堆栈的根(指针),我目前的方法是在进入新线程和进入 main() 时保存堆栈指针,然后在每个线程再次保存它时使用全局锁启动垃圾回收。

(我知道从长远来看这种方法并不理想,因为它会导致不必要的锁定,但现在在基础知识成熟之前它是可以接受的)

但我真的很想有一种更“安全”的方式来检测边界,因为根很容易“逃脱”这种机制(取决于线程实现——pthreads 易于管理,但不是OpenMP 或 Grand Central Dispatch 也是如此)。

如果有一种可移植的方式来做到这一点,那就更棒了,但我不认为会是这样。我目前正在使用 Mac OS X 10.6,但欢迎任何平台的答案。

【问题讨论】:

    标签: multithreading garbage-collection parallel-processing


    【解决方案1】:

    您可以使用 VM 机制对堆栈末端进行写保护,并扩展 VM 写陷阱。然后你就会知道堆栈页面中堆栈的边界。

    但我不确定我是否理解反对简单地检查现有线程的 SP 的当前值,* 如果你做出“大堆栈”假设 * 通常由小-number-of-threads 并行社区。​​p>

    请参阅this SO article,了解有关您没有“大筹码”的世界模型的讨论。然后你不能构建一个简单地扫描“堆栈”的 GC,因为它是按需分配的堆(例如,函数入口)。 现在您需要扫描所有可能处于活动状态的堆栈段。

    【讨论】:

    • 感谢您的意见。您使用虚拟内存写入陷阱的建议很聪明,但您可能是对的,它是不必要的。此外,它仅在增加堆栈时起作用,而不是在所需堆栈空间减少时不起作用,这使得它不适合 GC 目的(因为它会泄漏大量未使用的根)。我最担心的是线程实现会对堆栈的布局和大小做出不同的假设,但很可能我的担心是没有根据的。
    • 线程实现没有太多选择,给定线性地址空间。每个线程都必须启动,具有一些固定大小的最大线性堆栈量。 Linux 和 MS 都这样做,通常(预)分配 1Mb(在目标文件中设置为默认值),但任何线程分叉都可以指定数量。我发现有趣的情况是预分配很小,并且函数调用相对于调用者的堆栈不连续地分配 new 线性堆栈帧段。然后对“the”堆栈进行简单的线性扫描就行不通了,因为有很多片段。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-05-25
    • 2010-11-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多