moved code_block functions to vm

db4
Phil Dawes 2009-08-17 21:37:07 +01:00
parent fdabc9a5d8
commit 0097e76a82
2 changed files with 235 additions and 46 deletions

247
vm/code_block.cpp Normal file → Executable file
View File

@ -3,27 +3,47 @@
namespace factor
{
static relocation_type relocation_type_of(relocation_entry r)
relocation_type factorvm::relocation_type_of(relocation_entry r)
{
return (relocation_type)((r & 0xf0000000) >> 28);
}
static relocation_class relocation_class_of(relocation_entry r)
relocation_type relocation_type_of(relocation_entry r)
{
return vm->relocation_type_of(r);
}
relocation_class factorvm::relocation_class_of(relocation_entry r)
{
return (relocation_class)((r & 0x0f000000) >> 24);
}
static cell relocation_offset_of(relocation_entry r)
relocation_class relocation_class_of(relocation_entry r)
{
return vm->relocation_class_of(r);
}
cell factorvm::relocation_offset_of(relocation_entry r)
{
return (r & 0x00ffffff);
}
void flush_icache_for(code_block *block)
cell relocation_offset_of(relocation_entry r)
{
return vm->relocation_offset_of(r);
}
void factorvm::flush_icache_for(code_block *block)
{
flush_icache((cell)block,block->size);
}
static int number_of_parameters(relocation_type type)
void flush_icache_for(code_block *block)
{
return vm->flush_icache_for(block);
}
int factorvm::number_of_parameters(relocation_type type)
{
switch(type)
{
@ -47,7 +67,12 @@ static int number_of_parameters(relocation_type type)
}
}
void *object_xt(cell obj)
int number_of_parameters(relocation_type type)
{
return vm->number_of_parameters(type);
}
void *factorvm::object_xt(cell obj)
{
switch(tagged<object>(obj).type())
{
@ -61,7 +86,12 @@ void *object_xt(cell obj)
}
}
static void *xt_pic(word *w, cell tagged_quot)
void *object_xt(cell obj)
{
return vm->object_xt(obj);
}
void *factorvm::xt_pic(word *w, cell tagged_quot)
{
if(tagged_quot == F || max_pic_size == 0)
return w->xt;
@ -75,25 +105,45 @@ static void *xt_pic(word *w, cell tagged_quot)
}
}
void *word_xt_pic(word *w)
void *xt_pic(word *w, cell tagged_quot)
{
return vm->xt_pic(w,tagged_quot);
}
void *factorvm::word_xt_pic(word *w)
{
return xt_pic(w,w->pic_def);
}
void *word_xt_pic_tail(word *w)
void *word_xt_pic(word *w)
{
return vm->word_xt_pic(w);
}
void *factorvm::word_xt_pic_tail(word *w)
{
return xt_pic(w,w->pic_tail_def);
}
void *word_xt_pic_tail(word *w)
{
return vm->word_xt_pic_tail(w);
}
/* References to undefined symbols are patched up to call this function on
image load */
void undefined_symbol()
void factorvm::undefined_symbol()
{
general_error(ERROR_UNDEFINED_SYMBOL,F,F,NULL);
}
void undefined_symbol()
{
return vm->undefined_symbol();
}
/* Look up an external library symbol referenced by a compiled code block */
void *get_rel_symbol(array *literals, cell index)
void *factorvm::get_rel_symbol(array *literals, cell index)
{
cell symbol = array_nth(literals,index);
cell library = array_nth(literals,index + 1);
@ -101,7 +151,7 @@ void *get_rel_symbol(array *literals, cell index)
dll *d = (library == F ? NULL : untag<dll>(library));
if(d != NULL && !d->dll)
return (void *)undefined_symbol;
return (void *)factor::undefined_symbol;
switch(tagged<object>(symbol).type())
{
@ -114,7 +164,7 @@ void *get_rel_symbol(array *literals, cell index)
return sym;
else
{
return (void *)undefined_symbol;
return (void *)factor::undefined_symbol;
}
}
case ARRAY_TYPE:
@ -129,15 +179,20 @@ void *get_rel_symbol(array *literals, cell index)
if(sym)
return sym;
}
return (void *)undefined_symbol;
return (void *)factor::undefined_symbol;
}
default:
critical_error("Bad symbol specifier",symbol);
return (void *)undefined_symbol;
return (void *)factor::undefined_symbol;
}
}
cell compute_relocation(relocation_entry rel, cell index, code_block *compiled)
void *get_rel_symbol(array *literals, cell index)
{
return vm->get_rel_symbol(literals,index);
}
cell factorvm::compute_relocation(relocation_entry rel, cell index, code_block *compiled)
{
array *literals = untag<array>(compiled->literals);
cell offset = relocation_offset_of(rel) + (cell)compiled->xt();
@ -179,7 +234,12 @@ cell compute_relocation(relocation_entry rel, cell index, code_block *compiled)
#undef ARG
}
void iterate_relocations(code_block *compiled, relocation_iterator iter)
cell compute_relocation(relocation_entry rel, cell index, code_block *compiled)
{
return vm->compute_relocation(rel,index,compiled);
}
void factorvm::iterate_relocations(code_block *compiled, relocation_iterator iter)
{
if(compiled->relocation != F)
{
@ -197,15 +257,25 @@ void iterate_relocations(code_block *compiled, relocation_iterator iter)
}
}
void iterate_relocations(code_block *compiled, relocation_iterator iter)
{
return vm->iterate_relocations(compiled,iter);
}
/* Store a 32-bit value into a PowerPC LIS/ORI sequence */
static void store_address_2_2(cell *ptr, cell value)
void factorvm::store_address_2_2(cell *ptr, cell value)
{
ptr[-1] = ((ptr[-1] & ~0xffff) | ((value >> 16) & 0xffff));
ptr[ 0] = ((ptr[ 0] & ~0xffff) | (value & 0xffff));
}
void store_address_2_2(cell *ptr, cell value)
{
return vm->store_address_2_2(ptr,value);
}
/* Store a value into a bitfield of a PowerPC instruction */
static void store_address_masked(cell *ptr, fixnum value, cell mask, fixnum shift)
void factorvm::store_address_masked(cell *ptr, fixnum value, cell mask, fixnum shift)
{
/* This is unaccurate but good enough */
fixnum test = (fixnum)mask >> 1;
@ -215,8 +285,13 @@ static void store_address_masked(cell *ptr, fixnum value, cell mask, fixnum shif
*ptr = ((*ptr & ~mask) | ((value >> shift) & mask));
}
void store_address_masked(cell *ptr, fixnum value, cell mask, fixnum shift)
{
return vm->store_address_masked(ptr,value,mask,shift);
}
/* Perform a fixup on a code block */
void store_address_in_code_block(cell klass, cell offset, fixnum absolute_value)
void factorvm::store_address_in_code_block(cell klass, cell offset, fixnum absolute_value)
{
fixnum relative_value = absolute_value - offset;
@ -261,7 +336,12 @@ void store_address_in_code_block(cell klass, cell offset, fixnum absolute_value)
}
}
void update_literal_references_step(relocation_entry rel, cell index, code_block *compiled)
void store_address_in_code_block(cell klass, cell offset, fixnum absolute_value)
{
return vm->store_address_in_code_block(klass,offset,absolute_value);
}
void factorvm::update_literal_references_step(relocation_entry rel, cell index, code_block *compiled)
{
if(relocation_type_of(rel) == RT_IMMEDIATE)
{
@ -272,19 +352,29 @@ void update_literal_references_step(relocation_entry rel, cell index, code_block
}
}
void update_literal_references_step(relocation_entry rel, cell index, code_block *compiled)
{
return vm->update_literal_references_step(rel,index,compiled);
}
/* Update pointers to literals from compiled code. */
void update_literal_references(code_block *compiled)
void factorvm::update_literal_references(code_block *compiled)
{
if(!compiled->needs_fixup)
{
iterate_relocations(compiled,update_literal_references_step);
iterate_relocations(compiled,factor::update_literal_references_step);
flush_icache_for(compiled);
}
}
void update_literal_references(code_block *compiled)
{
return vm->update_literal_references(compiled);
}
/* Copy all literals referenced from a code block to newspace. Only for
aging and nursery collections */
void copy_literal_references(code_block *compiled)
void factorvm::copy_literal_references(code_block *compiled)
{
if(collecting_gen >= compiled->last_scan)
{
@ -307,8 +397,13 @@ void copy_literal_references(code_block *compiled)
}
}
void copy_literal_references(code_block *compiled)
{
return vm->copy_literal_references(compiled);
}
/* Compute an address to store at a relocation */
void relocate_code_block_step(relocation_entry rel, cell index, code_block *compiled)
void factorvm::relocate_code_block_step(relocation_entry rel, cell index, code_block *compiled)
{
#ifdef FACTOR_DEBUG
tagged<array>(compiled->literals).untag_check();
@ -320,18 +415,28 @@ void relocate_code_block_step(relocation_entry rel, cell index, code_block *comp
compute_relocation(rel,index,compiled));
}
void update_word_references_step(relocation_entry rel, cell index, code_block *compiled)
void relocate_code_block_step(relocation_entry rel, cell index, code_block *compiled)
{
return vm->relocate_code_block_step(rel,index,compiled);
}
void factorvm::update_word_references_step(relocation_entry rel, cell index, code_block *compiled)
{
relocation_type type = relocation_type_of(rel);
if(type == RT_XT || type == RT_XT_PIC || type == RT_XT_PIC_TAIL)
relocate_code_block_step(rel,index,compiled);
}
void update_word_references_step(relocation_entry rel, cell index, code_block *compiled)
{
return vm->update_word_references_step(rel,index,compiled);
}
/* Relocate new code blocks completely; updating references to literals,
dlsyms, and words. For all other words in the code heap, we only need
to update references to other words, without worrying about literals
or dlsyms. */
void update_word_references(code_block *compiled)
void factorvm::update_word_references(code_block *compiled)
{
if(compiled->needs_fixup)
relocate_code_block(compiled);
@ -346,30 +451,45 @@ void update_word_references(code_block *compiled)
heap_free(&code,compiled);
else
{
iterate_relocations(compiled,update_word_references_step);
iterate_relocations(compiled,factor::update_word_references_step);
flush_icache_for(compiled);
}
}
void update_literal_and_word_references(code_block *compiled)
void update_word_references(code_block *compiled)
{
return vm->update_word_references(compiled);
}
void factorvm::update_literal_and_word_references(code_block *compiled)
{
update_literal_references(compiled);
update_word_references(compiled);
}
static void check_code_address(cell address)
void update_literal_and_word_references(code_block *compiled)
{
return vm->update_literal_and_word_references(compiled);
}
void factorvm::check_code_address(cell address)
{
#ifdef FACTOR_DEBUG
assert(address >= code.seg->start && address < code.seg->end);
#endif
}
void check_code_address(cell address)
{
return vm->check_code_address(address);
}
/* Update references to words. This is done after a new code block
is added to the heap. */
/* Mark all literals referenced from a word XT. Only for tenured
collections */
void mark_code_block(code_block *compiled)
void factorvm::mark_code_block(code_block *compiled)
{
check_code_address((cell)compiled);
@ -379,24 +499,39 @@ void mark_code_block(code_block *compiled)
copy_handle(&compiled->relocation);
}
void mark_stack_frame_step(stack_frame *frame)
void mark_code_block(code_block *compiled)
{
return vm->mark_code_block(compiled);
}
void factorvm::mark_stack_frame_step(stack_frame *frame)
{
mark_code_block(frame_code(frame));
}
void mark_stack_frame_step(stack_frame *frame)
{
return vm->mark_stack_frame_step(frame);
}
/* Mark code blocks executing in currently active stack frames. */
void mark_active_blocks(context *stacks)
void factorvm::mark_active_blocks(context *stacks)
{
if(collecting_gen == data->tenured())
{
cell top = (cell)stacks->callstack_top;
cell bottom = (cell)stacks->callstack_bottom;
iterate_callstack(top,bottom,mark_stack_frame_step);
iterate_callstack(top,bottom,factor::mark_stack_frame_step);
}
}
void mark_object_code_block(object *object)
void mark_active_blocks(context *stacks)
{
return vm->mark_active_blocks(stacks);
}
void factorvm::mark_object_code_block(object *object)
{
switch(object->h.hi_tag())
{
@ -419,23 +554,33 @@ void mark_object_code_block(object *object)
case CALLSTACK_TYPE:
{
callstack *stack = (callstack *)object;
iterate_callstack_object(stack,mark_stack_frame_step);
iterate_callstack_object(stack,factor::mark_stack_frame_step);
break;
}
}
}
void mark_object_code_block(object *object)
{
return vm->mark_object_code_block(object);
}
/* Perform all fixups on a code block */
void relocate_code_block(code_block *compiled)
void factorvm::relocate_code_block(code_block *compiled)
{
compiled->last_scan = data->nursery();
compiled->needs_fixup = false;
iterate_relocations(compiled,relocate_code_block_step);
iterate_relocations(compiled,factor::relocate_code_block_step);
flush_icache_for(compiled);
}
void relocate_code_block(code_block *compiled)
{
return vm->relocate_code_block(compiled);
}
/* Fixup labels. This is done at compile time, not image load time */
void fixup_labels(array *labels, code_block *compiled)
void factorvm::fixup_labels(array *labels, code_block *compiled)
{
cell i;
cell size = array_capacity(labels);
@ -452,8 +597,13 @@ void fixup_labels(array *labels, code_block *compiled)
}
}
void fixup_labels(array *labels, code_block *compiled)
{
return vm->fixup_labels(labels,compiled);
}
/* Might GC */
code_block *allot_code_block(cell size)
code_block *factorvm::allot_code_block(cell size)
{
heap_block *block = heap_allot(&code,size + sizeof(code_block));
@ -480,13 +630,13 @@ code_block *allot_code_block(cell size)
return (code_block *)block;
}
code_block *allot_code_block(cell size)
{
return vm->allot_code_block(size);
}
/* Might GC */
code_block *add_code_block(
cell type,
cell code_,
cell labels_,
cell relocation_,
cell literals_)
code_block *factorvm::add_code_block(cell type,cell code_,cell labels_,cell relocation_,cell literals_)
{
gc_root<byte_array> code(code_);
gc_root<object> labels(labels_);
@ -522,4 +672,9 @@ code_block *add_code_block(
return compiled;
}
code_block *add_code_block(cell type,cell code_,cell labels_,cell relocation_,cell literals_)
{
return vm->add_code_block(type,code_,labels_,relocation_,literals_);
}
}

View File

@ -348,6 +348,40 @@ struct factorvm {
cell heap_size(heap *heap);
cell compute_heap_forwarding(heap *heap, unordered_map<heap_block *,char *> &forwarding);
void compact_heap(heap *heap, unordered_map<heap_block *,char *> &forwarding);
//code_block
relocation_type relocation_type_of(relocation_entry r);
relocation_class relocation_class_of(relocation_entry r);
cell relocation_offset_of(relocation_entry r);
void flush_icache_for(code_block *block);
int number_of_parameters(relocation_type type);
void *object_xt(cell obj);
void *xt_pic(word *w, cell tagged_quot);
void *word_xt_pic(word *w);
void *word_xt_pic_tail(word *w);
void undefined_symbol();
void *get_rel_symbol(array *literals, cell index);
cell compute_relocation(relocation_entry rel, cell index, code_block *compiled);
void iterate_relocations(code_block *compiled, relocation_iterator iter);
void store_address_2_2(cell *ptr, cell value);
void store_address_masked(cell *ptr, fixnum value, cell mask, fixnum shift);
void store_address_in_code_block(cell klass, cell offset, fixnum absolute_value);
void update_literal_references_step(relocation_entry rel, cell index, code_block *compiled);
void update_literal_references(code_block *compiled);
void copy_literal_references(code_block *compiled);
void relocate_code_block_step(relocation_entry rel, cell index, code_block *compiled);
void update_word_references_step(relocation_entry rel, cell index, code_block *compiled);
void update_word_references(code_block *compiled);
void update_literal_and_word_references(code_block *compiled);
void check_code_address(cell address);
void mark_code_block(code_block *compiled);
void mark_stack_frame_step(stack_frame *frame);
void mark_active_blocks(context *stacks);
void mark_object_code_block(object *object);
void relocate_code_block(code_block *compiled);
void fixup_labels(array *labels, code_block *compiled);
code_block *allot_code_block(cell size);
code_block *add_code_block(cell type,cell code_,cell labels_,cell relocation_,cell literals_);
// next method here: