HotSpot Stop-and-Copy GC

rednaxelafx的Cheney算法的伪代码。如果不用forwarding的话,维护一个旧地址到新地址的映射也可以。

其中重点部分:

 1 void Heap::collect() {
 2   // The from-space contains objects, and the to-space is empty now.
 3 
 4   address scanned = _to_space->bottom();
 5   
 6   // scavenge objects directly referenced by the root set
 7   foreach (Object** slot in ROOTS) {
 8     process_reference(slot);
 9   }
10 
11   // breadth-first scanning of object graph
12   while (scanned < _to_space->top()) {
13     Object* parent_obj = (Object*) scanned;
14     foreach (Object** slot in parent_obj->obejct_fields()) {
15       process_reference(slot);
16       // note: _to_space->top() moves if any object is newly copied
17       //       into to-space.
18     }
19     scanned += parent_obj->size();
20   }
21 
22   // Now all live objects will have been evacuated into the to-space,
23   // and we don't need the data in the from-space anymore.
24 
25   swap_spaces();
26 }

Cheney算法的简单优雅之处来自它通过隐式队列来实现广度优先遍历,但它的缺点之一却也在此:广度优先的拷贝顺序使得GC后对象的空间局部性(memory locality)变差了。但是如果要改为真的深度优先顺序就会需要一个栈,无论是隐式(通常意味着递归调用)或者是显式。 

HotSpot Seial GC => rednaxelafx的Cheney算法伪代码 
* saved mark => scanned 
* FastScanClosure => process_reference() 
* GenCollectedHeap::gen_process_strong_roots()、SharedHeap::process_strong_roots() => 遍历根集合的循环逻辑 
* FastEvacuateFollowersClosure => 遍历扫描队列的循环 
* oopDesc::oop_iterate() => 遍历对象的引用类型字段的循环,Object::object_fields() 
* DefNewGeneration::copy_to_survivor_space() => 拷贝对象的逻辑,Heap::evacuate() 

ParalleScavenge总体过程虽然也是这样,但是因为多线程模型细节复杂很多。除strong reference之外,其他的soft,weak,phantom等reference也要处理。

rednaxelafx的完整回答

http://hllvm.group.iteye.com/group/topic/39376

其他Cheney算法的概述

https://en.wikipedia.org/wiki/Cheney%27s_algorithm

http://www.cs.umd.edu/class/fall2002/cmsc631/cheney/cheney.html

posted @ 2017-02-23 23:15  陈清扬  阅读(252)  评论(0编辑  收藏  举报