3 /* A tool to debug write barriers. Call check_data_heap() to ensure that all
4 cards that should be marked are actually marked. */
14 inline generation generation_of(factor_vm* parent, object* obj) {
15 if (parent->data->nursery->contains_p(obj))
16 return nursery_generation;
17 else if (parent->data->aging->contains_p(obj))
18 return aging_generation;
19 else if (parent->data->tenured->contains_p(obj))
20 return tenured_generation;
22 critical_error("Bad object", (cell) obj);
23 return (generation) - 1;
32 slot_checker(factor_vm* parent, object* obj, generation gen)
33 : parent(parent), obj(obj), gen(gen) {}
35 void check_write_barrier(cell* slot_ptr, generation target, char mask) {
36 cell object_card_pointer = parent->cards_offset + ((cell) obj >> card_bits);
37 cell slot_card_pointer =
38 parent->cards_offset + ((cell) slot_ptr >> card_bits);
39 char slot_card_value = *(char*)slot_card_pointer;
40 if ((slot_card_value & mask) != mask) {
41 std::cout << "card not marked" << std::endl;
42 std::cout << "source generation: " << gen << std::endl;
43 std::cout << "target generation: " << target << std::endl;
44 std::cout << "object: 0x" << std::hex << (cell)
45 obj << std::dec << std::endl;
46 std::cout << "object type: " << obj->type() << std::endl;
47 std::cout << "slot pointer: 0x" << std::hex << (cell)
48 slot_ptr << std::dec << std::endl;
49 std::cout << "slot value: 0x" << std::hex << *slot_ptr << std::dec
51 std::cout << "card of object: 0x" << std::hex << object_card_pointer
52 << std::dec << std::endl;
53 std::cout << "card of slot: 0x" << std::hex << slot_card_pointer
54 << std::dec << std::endl;
55 std::cout << std::endl;
60 void operator()(cell* slot_ptr) {
61 if (!immediate_p(*slot_ptr)) {
62 generation target = generation_of(parent, untag<object>(*slot_ptr));
64 case nursery_generation:
66 case aging_generation:
67 if (target == nursery_generation)
68 check_write_barrier(slot_ptr, target, card_points_to_nursery);
70 case tenured_generation:
71 if (target == nursery_generation)
72 check_write_barrier(slot_ptr, target, card_points_to_nursery);
73 else if (target == aging_generation)
74 check_write_barrier(slot_ptr, target, card_points_to_aging);
81 struct object_checker {
84 explicit object_checker(factor_vm* parent) : parent(parent) {}
86 void operator()(object* obj) {
87 slot_checker checker(parent, obj, generation_of(parent, obj));
88 obj->each_slot(checker);
92 void factor_vm::check_data_heap() {
93 object_checker checker(this);