我目前正在研究世代垃圾收集器。这意味着只有最近的对象被遍历,幸存的对象(=从已知的根可到达)被提升到老一代。当对象指向相同或老一代的其他对象时,这可以正常工作。但是,当较旧的对象指向较新的对象时,并且由于仅遍历较新的对象,指向的对象将被错误地收集。为避免这种情况,此类对象在每个 GC 阶段都会被显式标记和遍历。
显然,这样的“父”对象是可变的,因为通过构造不可变的对象总是指向现有对象。因此,要成为“父对象”,必须在提升后修改对象,使其指向更新的对象。
为了知道老一代的哪些对象指向了年轻一代,我正在寻找一种透明地监控内存变化的方法。为此,我使用内存保护和信号/异常处理。内存页面设置为只读,这会导致在写入时引发信号/异常,在这种情况下,我将内存保护设置回读写并将地址记录在某处以进行进一步处理,并返回负责的代码异常恢复正常。这样,当 GC 触发时,我知道在哪里寻找潜在的父母进行遍历。
在 Linux 上,我使用 mprotect/SIGSEGV 信号处理的组合。在 Windows 上,我打算使用 VirtualProtect,但没有发现 SIGSEGV 处理的等效项。所以我的问题:
你会如何在 Windows 上做到这一点?异常处理 API 似乎相当混乱。
有没有更好的方法来知道哪些内存区域被修改了,这样我就不必做所有这些簿记了?
我的代码是用纯 C 编写的。目前我需要调用者代码来显式地标记修改过的对象,但这很乏味且容易出错,所以我正在寻找一种透明的方式来做到这一点。
在此先感谢,弗雷德