VM: change lot of visitation objects to use cool lambda functions instead
parent
fce5d4353a
commit
365b39e0cc
|
@ -108,20 +108,11 @@ code_block* callback_heap::add(cell owner, cell return_rewind) {
|
|||
return stub;
|
||||
}
|
||||
|
||||
struct callback_updater {
|
||||
callback_heap* callbacks;
|
||||
|
||||
explicit callback_updater(callback_heap* callbacks)
|
||||
: callbacks(callbacks) {}
|
||||
|
||||
void operator()(code_block* stub, cell size) {
|
||||
callbacks->update(stub);
|
||||
}
|
||||
};
|
||||
|
||||
void callback_heap::update() {
|
||||
callback_updater updater(this);
|
||||
allocator->iterate(updater);
|
||||
auto callback_updater = [&](code_block* stub, cell size) {
|
||||
update(stub);
|
||||
};
|
||||
allocator->iterate(callback_updater);
|
||||
}
|
||||
|
||||
/* Allocates memory (add(), allot_alien())*/
|
||||
|
|
59
vm/image.cpp
59
vm/image.cpp
|
@ -77,21 +77,14 @@ struct startup_fixup {
|
|||
cell size(code_block* compiled) { return compiled->size(*this); }
|
||||
};
|
||||
|
||||
struct start_object_updater {
|
||||
factor_vm* parent;
|
||||
startup_fixup fixup;
|
||||
slot_visitor<startup_fixup> visitor;
|
||||
|
||||
start_object_updater(factor_vm* parent, startup_fixup fixup)
|
||||
: parent(parent),
|
||||
fixup(fixup),
|
||||
visitor(slot_visitor<startup_fixup>(parent, fixup)) { }
|
||||
|
||||
void operator()(object* obj, cell size) {
|
||||
parent->data->tenured->starts.record_object_start_offset(obj);
|
||||
void factor_vm::fixup_data(cell data_offset, cell code_offset) {
|
||||
startup_fixup fixup(data_offset, code_offset);
|
||||
slot_visitor<startup_fixup> visitor(this, fixup);
|
||||
visitor.visit_all_roots();
|
||||
|
||||
auto start_object_updater = [&](object *obj, cell size) {
|
||||
data->tenured->starts.record_object_start_offset(obj);
|
||||
visitor.visit_slots(obj);
|
||||
|
||||
switch (obj->type()) {
|
||||
case ALIEN_TYPE: {
|
||||
|
||||
|
@ -100,11 +93,11 @@ struct start_object_updater {
|
|||
if (to_boolean(ptr->base))
|
||||
ptr->update_address();
|
||||
else
|
||||
ptr->expired = parent->true_object;
|
||||
ptr->expired = true_object;
|
||||
break;
|
||||
}
|
||||
case DLL_TYPE: {
|
||||
parent->ffi_dlopen((dll*)obj);
|
||||
ffi_dlopen((dll*)obj);
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
|
@ -112,16 +105,8 @@ struct start_object_updater {
|
|||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
void factor_vm::fixup_data(cell data_offset, cell code_offset) {
|
||||
startup_fixup fixup(data_offset, code_offset);
|
||||
slot_visitor<startup_fixup> visitor(this, fixup);
|
||||
visitor.visit_all_roots();
|
||||
|
||||
start_object_updater updater(this, fixup);
|
||||
data->tenured->iterate(updater, fixup);
|
||||
};
|
||||
data->tenured->iterate(start_object_updater, fixup);
|
||||
}
|
||||
|
||||
struct startup_code_block_relocation_visitor {
|
||||
|
@ -169,25 +154,15 @@ struct startup_code_block_relocation_visitor {
|
|||
}
|
||||
};
|
||||
|
||||
struct startup_code_block_updater {
|
||||
factor_vm* parent;
|
||||
startup_fixup fixup;
|
||||
|
||||
startup_code_block_updater(factor_vm* parent, startup_fixup fixup)
|
||||
: parent(parent), fixup(fixup) {}
|
||||
|
||||
void operator()(code_block* compiled, cell size) {
|
||||
slot_visitor<startup_fixup> visitor(parent, fixup);
|
||||
visitor.visit_code_block_objects(compiled);
|
||||
|
||||
startup_code_block_relocation_visitor code_visitor(parent, fixup);
|
||||
compiled->each_instruction_operand(code_visitor);
|
||||
}
|
||||
};
|
||||
|
||||
void factor_vm::fixup_code(cell data_offset, cell code_offset) {
|
||||
startup_fixup fixup(data_offset, code_offset);
|
||||
startup_code_block_updater updater(this, fixup);
|
||||
auto updater = [&](code_block* compiled, cell size) {
|
||||
slot_visitor<startup_fixup> visitor(this, fixup);
|
||||
visitor.visit_code_block_objects(compiled);
|
||||
|
||||
startup_code_block_relocation_visitor code_visitor(this, fixup);
|
||||
compiled->each_instruction_operand(code_visitor);
|
||||
};
|
||||
code->allocator->iterate(updater, fixup);
|
||||
}
|
||||
|
||||
|
|
|
@ -87,37 +87,6 @@ struct slot_become_fixup : no_fixup {
|
|||
}
|
||||
};
|
||||
|
||||
struct object_become_visitor {
|
||||
slot_visitor<slot_become_fixup>* visitor;
|
||||
|
||||
explicit object_become_visitor(slot_visitor<slot_become_fixup>* visitor)
|
||||
: visitor(visitor) {}
|
||||
|
||||
void operator()(object* obj) { visitor->visit_slots(obj); }
|
||||
};
|
||||
|
||||
struct code_block_become_visitor {
|
||||
slot_visitor<slot_become_fixup>* visitor;
|
||||
|
||||
explicit code_block_become_visitor(
|
||||
slot_visitor<slot_become_fixup>* visitor) : visitor(visitor) {}
|
||||
|
||||
void operator()(code_block* compiled, cell size) {
|
||||
visitor->visit_code_block_objects(compiled);
|
||||
visitor->visit_embedded_literals(compiled);
|
||||
}
|
||||
};
|
||||
|
||||
struct code_block_write_barrier_visitor {
|
||||
code_heap* code;
|
||||
|
||||
explicit code_block_write_barrier_visitor(code_heap* code) : code(code) {}
|
||||
|
||||
void operator()(code_block* compiled, cell size) {
|
||||
code->write_barrier(compiled);
|
||||
}
|
||||
};
|
||||
|
||||
/* classes.tuple uses this to reshape tuples; tools.deploy.shaker uses this
|
||||
to coalesce equal but distinct quotations and wrappers. */
|
||||
/* Calls gc */
|
||||
|
@ -147,11 +116,16 @@ void factor_vm::primitive_become() {
|
|||
slot_become_fixup(&become_map));
|
||||
visitor.visit_all_roots();
|
||||
|
||||
object_become_visitor object_visitor(&visitor);
|
||||
each_object(object_visitor);
|
||||
auto object_become_visitor = [&](object* obj) {
|
||||
visitor.visit_slots(obj);
|
||||
};
|
||||
each_object(object_become_visitor);
|
||||
|
||||
code_block_become_visitor code_block_visitor(&visitor);
|
||||
each_code_block(code_block_visitor);
|
||||
auto code_block_become_visitor = [&](code_block* compiled, cell size) {
|
||||
visitor.visit_code_block_objects(compiled);
|
||||
visitor.visit_embedded_literals(compiled);
|
||||
};
|
||||
each_code_block(code_block_become_visitor);
|
||||
}
|
||||
|
||||
/* Since we may have introduced old->new references, need to revisit
|
||||
|
@ -159,7 +133,9 @@ void factor_vm::primitive_become() {
|
|||
data->mark_all_cards();
|
||||
|
||||
{
|
||||
code_block_write_barrier_visitor code_block_visitor(code);
|
||||
auto code_block_visitor = [&](code_block* compiled, cell size) {
|
||||
code->write_barrier(compiled);
|
||||
};
|
||||
each_code_block(code_block_visitor);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -188,19 +188,11 @@ template <typename Fixup> void slot_visitor<Fixup>::visit_data_roots() {
|
|||
}
|
||||
}
|
||||
|
||||
template <typename Fixup> struct callback_slot_visitor {
|
||||
slot_visitor<Fixup>* visitor;
|
||||
|
||||
callback_slot_visitor(slot_visitor<Fixup>* visitor) : visitor(visitor) {}
|
||||
|
||||
void operator()(code_block* stub, cell size) {
|
||||
visitor->visit_handle(&stub->owner);
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Fixup> void slot_visitor<Fixup>::visit_callback_roots() {
|
||||
callback_slot_visitor<Fixup> callback_visitor(this);
|
||||
parent->callbacks->allocator->iterate(callback_visitor);
|
||||
auto callback_slot_visitor = [&](code_block* stub, cell size) {
|
||||
visit_handle(&stub->owner);
|
||||
};
|
||||
parent->callbacks->allocator->iterate(callback_slot_visitor);
|
||||
}
|
||||
|
||||
template <typename Fixup>
|
||||
|
@ -381,18 +373,6 @@ template <typename Fixup> void slot_visitor<Fixup>::visit_contexts() {
|
|||
}
|
||||
}
|
||||
|
||||
template <typename Fixup> struct literal_references_visitor {
|
||||
slot_visitor<Fixup>* visitor;
|
||||
|
||||
explicit literal_references_visitor(slot_visitor<Fixup>* visitor)
|
||||
: visitor(visitor) {}
|
||||
|
||||
void operator()(instruction_operand op) {
|
||||
if (op.rel_type() == RT_LITERAL)
|
||||
op.store_value(visitor->visit_pointer(op.load_value()));
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Fixup>
|
||||
void slot_visitor<Fixup>::visit_code_block_objects(code_block* compiled) {
|
||||
visit_handle(&compiled->owner);
|
||||
|
@ -402,10 +382,14 @@ void slot_visitor<Fixup>::visit_code_block_objects(code_block* compiled) {
|
|||
|
||||
template <typename Fixup>
|
||||
void slot_visitor<Fixup>::visit_embedded_literals(code_block* compiled) {
|
||||
if (!parent->code->uninitialized_p(compiled)) {
|
||||
literal_references_visitor<Fixup> visitor(this);
|
||||
compiled->each_instruction_operand(visitor);
|
||||
}
|
||||
if (parent->code->uninitialized_p(compiled))
|
||||
return;
|
||||
|
||||
auto update_literal_refs = [&](instruction_operand op) {
|
||||
if (op.rel_type() == RT_LITERAL)
|
||||
op.store_value(visit_pointer(op.load_value()));
|
||||
};
|
||||
compiled->each_instruction_operand(update_literal_refs);
|
||||
}
|
||||
|
||||
template <typename Fixup> struct call_frame_code_block_visitor {
|
||||
|
@ -465,25 +449,18 @@ void slot_visitor<Fixup>::visit_uninitialized_code_blocks() {
|
|||
parent->code->uninitialized_blocks = new_uninitialized_blocks;
|
||||
}
|
||||
|
||||
template <typename Fixup> struct embedded_code_pointers_visitor {
|
||||
Fixup fixup;
|
||||
|
||||
explicit embedded_code_pointers_visitor(Fixup fixup) : fixup(fixup) {}
|
||||
|
||||
void operator()(instruction_operand op) {
|
||||
relocation_type type = op.rel_type();
|
||||
if (type == RT_ENTRY_POINT || type == RT_ENTRY_POINT_PIC ||
|
||||
type == RT_ENTRY_POINT_PIC_TAIL)
|
||||
op.store_code_block(fixup.fixup_code(op.load_code_block()));
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Fixup>
|
||||
void slot_visitor<Fixup>::visit_embedded_code_pointers(code_block* compiled) {
|
||||
if (!parent->code->uninitialized_p(compiled)) {
|
||||
embedded_code_pointers_visitor<Fixup> operand_visitor(fixup);
|
||||
compiled->each_instruction_operand(operand_visitor);
|
||||
}
|
||||
if (parent->code->uninitialized_p(compiled))
|
||||
return;
|
||||
auto update_code_block_refs = [&](instruction_operand op){
|
||||
relocation_type type = op.rel_type();
|
||||
if (type == RT_ENTRY_POINT ||
|
||||
type == RT_ENTRY_POINT_PIC ||
|
||||
type == RT_ENTRY_POINT_PIC_TAIL)
|
||||
op.store_code_block(fixup.fixup_code(op.load_code_block()));
|
||||
};
|
||||
compiled->each_instruction_operand(update_code_block_refs);
|
||||
}
|
||||
|
||||
template <typename Fixup>
|
||||
|
@ -500,7 +477,6 @@ template <typename Fixup>
|
|||
void slot_visitor<Fixup>::visit_mark_stack(std::vector<cell>* mark_stack) {
|
||||
while (!mark_stack->empty()) {
|
||||
cell ptr = mark_stack->back();
|
||||
// TJaba
|
||||
mark_stack->pop_back();
|
||||
|
||||
if (ptr & 1) {
|
||||
|
|
Loading…
Reference in New Issue