VM: use a free_list_allocator for the callbacks, that way they can
individually be freeddb4
							parent
							
								
									4015565cf6
								
							
						
					
					
						commit
						85dade6914
					
				| 
						 | 
					@ -6,7 +6,7 @@ callback_heap::callback_heap(cell size, factor_vm* parent) {
 | 
				
			||||||
  seg = new segment(size, true);
 | 
					  seg = new segment(size, true);
 | 
				
			||||||
  if (!seg)
 | 
					  if (!seg)
 | 
				
			||||||
    fatal_error("Out of memory in callback_heap constructor", size);
 | 
					    fatal_error("Out of memory in callback_heap constructor", size);
 | 
				
			||||||
  allocator = new bump_allocator<code_block>(size, seg->start);
 | 
					  allocator = new free_list_allocator<code_block>(size, seg->start);
 | 
				
			||||||
  this->parent = parent;
 | 
					  this->parent = parent;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -65,19 +65,20 @@ void callback_heap::update(code_block* stub) {
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
code_block* callback_heap::add(cell owner, cell return_rewind) {
 | 
					code_block* callback_heap::add(cell owner, cell return_rewind) {
 | 
				
			||||||
 | 
					  std::cout << "callback_heap::add" << std::endl;
 | 
				
			||||||
  tagged<array> code_template(parent->special_objects[CALLBACK_STUB]);
 | 
					  tagged<array> code_template(parent->special_objects[CALLBACK_STUB]);
 | 
				
			||||||
  tagged<byte_array> insns(array_nth(code_template.untagged(), 1));
 | 
					  tagged<byte_array> insns(array_nth(code_template.untagged(), 1));
 | 
				
			||||||
  cell size = array_capacity(insns.untagged());
 | 
					  cell size = array_capacity(insns.untagged());
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  cell bump = align(size + sizeof(code_block), data_alignment);
 | 
					  cell bump = align(size + sizeof(code_block), data_alignment);
 | 
				
			||||||
  if (allocator->here + bump > allocator->end) {
 | 
					  code_block* stub = allocator->allot(bump);
 | 
				
			||||||
 | 
					  if (!stub) {
 | 
				
			||||||
    parent->general_error(ERROR_CALLBACK_SPACE_OVERFLOW,
 | 
					    parent->general_error(ERROR_CALLBACK_SPACE_OVERFLOW,
 | 
				
			||||||
                          false_object,
 | 
					                          false_object,
 | 
				
			||||||
                          false_object);
 | 
					                          false_object);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  code_block* stub = allocator->allot(bump);
 | 
					  stub->header = bump & ~7;
 | 
				
			||||||
  stub->header = bump | 1;
 | 
					 | 
				
			||||||
  stub->owner = owner;
 | 
					  stub->owner = owner;
 | 
				
			||||||
  stub->parameters = false_object;
 | 
					  stub->parameters = false_object;
 | 
				
			||||||
  stub->relocation = false_object;
 | 
					  stub->relocation = false_object;
 | 
				
			||||||
| 
						 | 
					@ -114,14 +115,14 @@ struct callback_updater {
 | 
				
			||||||
  explicit callback_updater(callback_heap* callbacks)
 | 
					  explicit callback_updater(callback_heap* callbacks)
 | 
				
			||||||
      : callbacks(callbacks) {}
 | 
					      : callbacks(callbacks) {}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  void operator()(object* stub) {
 | 
					  void operator()(code_block* stub, cell size) {
 | 
				
			||||||
    callbacks->update((code_block*)stub);
 | 
					    callbacks->update(stub);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void callback_heap::update() {
 | 
					void callback_heap::update() {
 | 
				
			||||||
  callback_updater updater(this);
 | 
					  callback_updater updater(this);
 | 
				
			||||||
  parent->each_object(allocator, updater);
 | 
					  allocator->iterate(updater);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/* Allocates memory */
 | 
					/* Allocates memory */
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -25,7 +25,7 @@ from the callback heap in the previous session when the image was saved. */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct callback_heap {
 | 
					struct callback_heap {
 | 
				
			||||||
  segment* seg;
 | 
					  segment* seg;
 | 
				
			||||||
  bump_allocator<code_block>* allocator;
 | 
					  free_list_allocator<code_block>* allocator;
 | 
				
			||||||
  factor_vm* parent;
 | 
					  factor_vm* parent;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  callback_heap(cell size, factor_vm* parent);
 | 
					  callback_heap(cell size, factor_vm* parent);
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -199,22 +199,18 @@ template <typename Fixup> void slot_visitor<Fixup>::visit_bignum_roots() {
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
template <typename Fixup> struct callback_slot_visitor {
 | 
					template <typename Fixup> struct callback_slot_visitor {
 | 
				
			||||||
  callback_heap* callbacks;
 | 
					 | 
				
			||||||
  slot_visitor<Fixup>* visitor;
 | 
					  slot_visitor<Fixup>* visitor;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  callback_slot_visitor(callback_heap* callbacks,
 | 
					  callback_slot_visitor(slot_visitor<Fixup>* visitor) : visitor(visitor) {}
 | 
				
			||||||
                        slot_visitor<Fixup>* visitor)
 | 
					 | 
				
			||||||
      : callbacks(callbacks), visitor(visitor) {}
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
  void operator()(object* stub) {
 | 
					  void operator()(code_block* stub, cell size) {
 | 
				
			||||||
    code_block *block = (code_block*)stub;
 | 
					    visitor->visit_handle(&stub->owner);
 | 
				
			||||||
    visitor->visit_handle(&block->owner);
 | 
					 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
template <typename Fixup> void slot_visitor<Fixup>::visit_callback_roots() {
 | 
					template <typename Fixup> void slot_visitor<Fixup>::visit_callback_roots() {
 | 
				
			||||||
  callback_slot_visitor<Fixup> callback_visitor(parent->callbacks, this);
 | 
					  callback_slot_visitor<Fixup> callback_visitor(this);
 | 
				
			||||||
  parent->each_object(parent->callbacks->allocator, callback_visitor);
 | 
					  parent->callbacks->allocator->iterate(callback_visitor);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
template <typename Fixup>
 | 
					template <typename Fixup>
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in New Issue