]> gitweb.factorcode.org Git - factor.git/commitdiff
vm: more code cleanups
authorSlava Pestov <slava@slava-pestovs-macbook-pro.local>
Wed, 7 Oct 2009 13:33:54 +0000 (08:33 -0500)
committerSlava Pestov <slava@slava-pestovs-macbook-pro.local>
Wed, 7 Oct 2009 13:33:54 +0000 (08:33 -0500)
16 files changed:
vm/code_heap.cpp
vm/code_heap.hpp
vm/contexts.cpp
vm/data_gc.cpp
vm/data_gc.hpp
vm/data_heap.cpp
vm/data_heap.hpp
vm/errors.cpp
vm/errors.hpp
vm/heap.cpp
vm/heap.hpp
vm/image.cpp
vm/os-unix.cpp
vm/os-windows.cpp
vm/segments.hpp
vm/vm.hpp

index 6cb952cd36b7c86227077942a0b224120fb73928..f07639d9bb8fcde61e21d4bcbac72631804dc245 100755 (executable)
@@ -3,12 +3,12 @@
 namespace factor
 {
 
-code_heap::code_heap(factor_vm *myvm, cell size) : heap(myvm,size) {}
+code_heap::code_heap(bool secure_gc, cell size) : heap(secure_gc,size) {}
 
 void code_heap::write_barrier(code_block *compiled)
 {
-       remembered_set[compiled] = myvm->data->nursery();
-       youngest_referenced_generation = myvm->data->nursery();
+       remembered_set[compiled] = nursery_gen;
+       youngest_referenced_generation = nursery_gen;
 }
 
 bool code_heap::needs_fixup_p(code_block *compiled)
@@ -26,7 +26,7 @@ void code_heap::code_heap_free(code_block *compiled)
 /* Allocate a code heap during startup */
 void factor_vm::init_code_heap(cell size)
 {
-       code = new code_heap(this,size);
+       code = new code_heap(secure_gc,size);
 }
 
 bool factor_vm::in_code_heap_p(cell ptr)
@@ -228,7 +228,7 @@ critical here */
 void factor_vm::compact_code_heap()
 {
        /* Free all unreachable code blocks, don't trace contexts */
-       garbage_collection(data->tenured(),false,false,0);
+       garbage_collection(tenured_gen,false,false,0);
 
        /* Figure out where the code heap blocks are going to end up */
        cell size = code->compute_heap_forwarding();
index 1ac72e82184030714c5d8ba70c6fb0ce2fac7e91..feea7da307815c07dacbfbe7811ea3daa1301e33 100755 (executable)
@@ -13,7 +13,7 @@ struct code_heap : heap {
        /* Minimum value in the above map. */
        cell youngest_referenced_generation;
 
-       explicit code_heap(factor_vm *myvm, cell size);
+       explicit code_heap(bool secure_gc, cell size);
        void write_barrier(code_block *compiled);
        bool needs_fixup_p(code_block *compiled);
        void code_heap_free(code_block *compiled);
index 2b7a55d49115c12ddd744c52f61cfb3f2869e6d2..78dc2ccd3fd013ebe461f4ea0d4a0652d5b944f9 100644 (file)
@@ -44,8 +44,8 @@ context *factor_vm::alloc_context()
        else
        {
                new_context = new context;
-               new_context->datastack_region = new segment(this,ds_size);
-               new_context->retainstack_region = new segment(this,rs_size);
+               new_context->datastack_region = new segment(ds_size);
+               new_context->retainstack_region = new segment(rs_size);
        }
 
        return new_context;
index 1b12bddaf3afef89ed2b2513cbb3d907f5ee25d6..0fa5e1b07f9a9ce007bb585cd243d15e934a1e48 100755 (executable)
@@ -5,7 +5,7 @@ namespace factor
 
 void factor_vm::init_data_gc()
 {
-       code->youngest_referenced_generation = data->nursery();
+       code->youngest_referenced_generation = nursery_gen;
 }
 
 gc_state::gc_state(data_heap *data_, bool growing_data_heap_, cell collecting_gen_) :
@@ -71,7 +71,7 @@ template<typename Strategy> object *factor_vm::promote_object(object *untagged,
        object *newpointer = strategy.allot(size);
        if(!newpointer) longjmp(current_gc->gc_unwind,1);
 
-       gc_stats *s = &stats[current_gc->collecting_gen];
+       generation_stats *s = &stats.generations[current_gc->collecting_gen];
        s->object_count++;
        s->bytes_copied += size;
 
@@ -91,7 +91,7 @@ template<typename Strategy> void factor_vm::trace_card(card *ptr, cell gen, cell
 
        strategy.copy_reachable_objects(card_scan,&card_end);
 
-       cards_scanned++;
+       stats.cards_scanned++;
 }
 
 template<typename Strategy> void factor_vm::trace_card_deck(card_deck *deck, cell gen, card mask, card unmask, Strategy &strategy)
@@ -122,7 +122,7 @@ template<typename Strategy> void factor_vm::trace_card_deck(card_deck *deck, cel
                }
        }
 
-       decks_scanned++;
+       stats.decks_scanned++;
 }
 
 /* Trace all objects referenced from marked cards */
@@ -142,11 +142,11 @@ template<typename Strategy> void factor_vm::trace_generation_cards(cell gen, Str
                /* after the collection, no old->nursery pointers remain
                anywhere, but old->aging pointers might remain in tenured
                space */
-               if(gen == data->tenured())
+               if(gen == tenured_gen)
                        unmask = card_points_to_nursery;
                /* after the collection, all cards in aging space can be
                cleared */
-               else if(gen == data->aging())
+               else if(gen == aging_gen)
                        unmask = card_mark_mask;
                else
                {
@@ -201,7 +201,7 @@ template<typename Strategy> void factor_vm::trace_cards(Strategy &strategy)
        for(i = current_gc->collecting_gen + 1; i < gen_count; i++)
                trace_generation_cards(i,strategy);
 
-       card_scan_time += (current_micros() - start);
+       stats.card_scan_time += (current_micros() - start);
 }
 
 /* Copy all tagged pointers in a range of memory */
@@ -353,7 +353,7 @@ template<typename Strategy> void factor_vm::trace_code_heap_roots(Strategy &stra
                                trace_literal_references(iter->first,strategy);
                }
 
-               code_heap_scans++;
+               stats.code_heap_scans++;
        }
 }
 
@@ -385,7 +385,7 @@ void factor_vm::free_unmarked_code_blocks()
        literal_and_word_reference_updater updater(this);
        code->free_unmarked(updater);
        code->remembered_set.clear();
-       code->youngest_referenced_generation = data->tenured();
+       code->youngest_referenced_generation = tenured_gen;
 }
 
 void factor_vm::update_dirty_code_blocks()
@@ -429,7 +429,11 @@ template<typename Strategy> Strategy &copying_collector<Strategy>::strategy()
 template<typename Strategy> object *copying_collector<Strategy>::allot(cell size)
 {
        if(newspace->here + size <= newspace->end)
-               return myvm->allot_zone(newspace,size);
+       {
+               object *obj = newspace->allot(size);
+               myvm->allot_barrier(obj);
+               return obj;
+       }
        else
                return NULL;
 }
@@ -478,7 +482,7 @@ struct aging_collector : copying_collector<aging_collector>
 
        explicit aging_collector(factor_vm *myvm_, zone *newspace_) :
                copying_collector<aging_collector>(myvm_,newspace_),
-               tenured(&myvm->data->generations[myvm->data->tenured()]) {}
+               tenured(&myvm->data->generations[tenured_gen]) {}
 
        bool should_copy_p(object *untagged)
        {
@@ -532,7 +536,7 @@ struct tenured_collector : copying_collector<tenured_collector>
 
 void factor_vm::collect_nursery()
 {
-       nursery_collector collector(this,&data->generations[data->aging()]);
+       nursery_collector collector(this,&data->generations[aging_gen]);
 
        trace_roots(collector);
        trace_contexts(collector);
@@ -546,10 +550,10 @@ void factor_vm::collect_nursery()
 
 void factor_vm::collect_aging()
 {
-       std::swap(data->generations[data->aging()],data->semispaces[data->aging()]);
-       reset_generation(data->aging());
+       std::swap(data->generations[aging_gen],data->semispaces[aging_gen]);
+       reset_generation(aging_gen);
 
-       aging_collector collector(this,&data->generations[data->aging()]);
+       aging_collector collector(this,&data->generations[aging_gen]);
 
        trace_roots(collector);
        trace_contexts(collector);
@@ -563,7 +567,7 @@ void factor_vm::collect_aging()
 
 void factor_vm::collect_aging_again()
 {
-       aging_again_collector collector(this,&data->generations[data->tenured()]);
+       aging_again_collector collector(this,&data->generations[tenured_gen]);
 
        trace_roots(collector);
        trace_contexts(collector);
@@ -572,7 +576,7 @@ void factor_vm::collect_aging_again()
        collector.go();
        update_dirty_code_blocks();
 
-       reset_generation(data->aging());
+       reset_generation(aging_gen);
        nursery.here = nursery.start;
 }
 
@@ -585,18 +589,18 @@ void factor_vm::collect_tenured(cell requested_bytes, bool trace_contexts_)
        }
        else
        {
-               std::swap(data->generations[data->tenured()],data->semispaces[data->tenured()]);
-               reset_generation(data->tenured());
+               std::swap(data->generations[tenured_gen],data->semispaces[tenured_gen]);
+               reset_generation(tenured_gen);
        }
 
-       tenured_collector collector(this,&data->generations[data->tenured()]);
+       tenured_collector collector(this,&data->generations[tenured_gen]);
 
         trace_roots(collector);
         if(trace_contexts_) trace_contexts(collector);
         collector.go();
         free_unmarked_code_blocks();
 
-       reset_generation(data->aging());
+       reset_generation(aging_gen);
        nursery.here = nursery.start;
 
        if(current_gc->growing_data_heap)
@@ -605,7 +609,7 @@ void factor_vm::collect_tenured(cell requested_bytes, bool trace_contexts_)
 
 void factor_vm::record_gc_stats()
 {
-       gc_stats *s = &stats[current_gc->collecting_gen];
+       generation_stats *s = &stats.generations[current_gc->collecting_gen];
 
        cell gc_elapsed = (current_micros() - current_gc->start_time);
        s->collections++;
@@ -673,7 +677,7 @@ void factor_vm::garbage_collection(cell collecting_gen_, bool growing_data_heap_
 
 void factor_vm::gc()
 {
-       garbage_collection(data->tenured(),false,true,0);
+       garbage_collection(tenured_gen,false,true,0);
 }
 
 void factor_vm::primitive_gc()
@@ -690,7 +694,7 @@ void factor_vm::primitive_gc_stats()
 
        for(i = 0; i < gen_count; i++)
        {
-               gc_stats *s = &stats[i];
+               generation_stats *s = &stats.generations[i];
                result.add(allot_cell(s->collections));
                result.add(tag<bignum>(long_long_to_bignum(s->gc_time)));
                result.add(tag<bignum>(long_long_to_bignum(s->max_gc_time)));
@@ -702,10 +706,10 @@ void factor_vm::primitive_gc_stats()
        }
 
        result.add(tag<bignum>(ulong_long_to_bignum(total_gc_time)));
-       result.add(tag<bignum>(ulong_long_to_bignum(cards_scanned)));
-       result.add(tag<bignum>(ulong_long_to_bignum(decks_scanned)));
-       result.add(tag<bignum>(ulong_long_to_bignum(card_scan_time)));
-       result.add(allot_cell(code_heap_scans));
+       result.add(tag<bignum>(ulong_long_to_bignum(stats.cards_scanned)));
+       result.add(tag<bignum>(ulong_long_to_bignum(stats.decks_scanned)));
+       result.add(tag<bignum>(ulong_long_to_bignum(stats.card_scan_time)));
+       result.add(allot_cell(stats.code_heap_scans));
 
        result.trim();
        dpush(result.elements.value());
@@ -713,13 +717,7 @@ void factor_vm::primitive_gc_stats()
 
 void factor_vm::clear_gc_stats()
 {
-       for(cell i = 0; i < gen_count; i++)
-               memset(&stats[i],0,sizeof(gc_stats));
-
-       cards_scanned = 0;
-       decks_scanned = 0;
-       card_scan_time = 0;
-       code_heap_scans = 0;
+       memset(&stats,0,sizeof(gc_stats));
 }
 
 void factor_vm::primitive_clear_gc_stats()
@@ -763,7 +761,7 @@ void factor_vm::inline_gc(cell *gc_roots_base, cell gc_roots_size)
        for(cell i = 0; i < gc_roots_size; i++)
                gc_locals.push_back((cell)&gc_roots_base[i]);
 
-       garbage_collection(data->nursery(),false,true,0);
+       garbage_collection(nursery_gen,false,true,0);
 
        for(cell i = 0; i < gc_roots_size; i++)
                gc_locals.pop_back();
@@ -775,15 +773,6 @@ VM_C_API void inline_gc(cell *gc_roots_base, cell gc_roots_size, factor_vm *myvm
        VM_PTR->inline_gc(gc_roots_base,gc_roots_size);
 }
 
-inline object *factor_vm::allot_zone(zone *z, cell a)
-{
-       cell h = z->here;
-       z->here = h + align8(a);
-       object *obj = (object *)h;
-       allot_barrier(obj);
-       return obj;
-}
-
 /*
  * It is up to the caller to fill in the object's fields in a meaningful
  * fashion!
@@ -801,33 +790,32 @@ object *factor_vm::allot_object(header header, cell size)
        {
                /* If there is insufficient room, collect the nursery */
                if(nursery.here + size > nursery.end)
-                       garbage_collection(data->nursery(),false,true,0);
+                       garbage_collection(nursery_gen,false,true,0);
 
-               cell h = nursery.here;
-               nursery.here = h + align8(size);
-               obj = (object *)h;
+               obj = nursery.allot(size);
        }
        /* If the object is bigger than the nursery, allocate it in
        tenured space */
        else
        {
-               zone *tenured = &data->generations[data->tenured()];
+               zone *tenured = &data->generations[tenured_gen];
 
                /* If tenured space does not have enough room, collect */
                if(tenured->here + size > tenured->end)
                {
                        gc();
-                       tenured = &data->generations[data->tenured()];
+                       tenured = &data->generations[tenured_gen];
                }
 
                /* If it still won't fit, grow the heap */
                if(tenured->here + size > tenured->end)
                {
-                       garbage_collection(data->tenured(),true,true,size);
-                       tenured = &data->generations[data->tenured()];
+                       garbage_collection(tenured_gen,true,true,size);
+                       tenured = &data->generations[tenured_gen];
                }
 
-               obj = allot_zone(tenured,size);
+               obj = tenured->allot(size);
+               allot_barrier(obj);
 
                /* Allows initialization code to store old->new pointers
                without hitting the write barrier in the common case of
index c8b7b479c274b6187041cc13ff42466360461fe3..04a9682ae589f19e7d62c165bd409b391684afbb 100755 (executable)
@@ -2,7 +2,7 @@ namespace factor
 {
 
 /* statistics */
-struct gc_stats {
+struct generation_stats {
        cell collections;
        u64 gc_time;
        u64 max_gc_time;
@@ -10,6 +10,14 @@ struct gc_stats {
        u64 bytes_copied;
 };
 
+struct gc_stats {
+       generation_stats generations[gen_count];
+       u64 cards_scanned;
+       u64 decks_scanned;
+       u64 card_scan_time;
+       cell code_heap_scans;
+};
+
 struct gc_state {
        /* The data heap we're collecting */
        data_heap *data;
@@ -35,17 +43,17 @@ struct gc_state {
 
        inline bool collecting_nursery_p()
        {
-               return collecting_gen == data->nursery();
+               return collecting_gen == nursery_gen;
        }
 
        inline bool collecting_aging_p()
        {
-               return collecting_gen == data->aging();
+               return collecting_gen == aging_gen;
        }
 
        inline bool collecting_tenured_p()
        {
-               return collecting_gen == data->tenured();
+               return collecting_gen == tenured_gen;
        }
 
        inline bool collecting_accumulation_gen_p()
index d5cfbb449dc505d67fbbb853458b511b7faa198e..5ccde31f37949edc5fe6fe8ad5d1b3506888afe8 100755 (executable)
@@ -25,7 +25,7 @@ data_heap::data_heap(factor_vm *myvm, cell young_size_, cell aging_size_, cell t
 
        total_size += deck_size;
 
-       seg = new segment(myvm,total_size);
+       seg = new segment(total_size);
 
        generations = new zone[gen_count];
        semispaces = new zone[gen_count];
@@ -43,17 +43,17 @@ data_heap::data_heap(factor_vm *myvm, cell young_size_, cell aging_size_, cell t
 
        cell alloter = align(seg->start,deck_size);
 
-       alloter = generations[tenured()].init_zone(tenured_size,alloter);
-       alloter = semispaces[tenured()].init_zone(tenured_size,alloter);
+       alloter = generations[tenured_gen].init_zone(tenured_size,alloter);
+       alloter = semispaces[tenured_gen].init_zone(tenured_size,alloter);
 
-       alloter = generations[aging()].init_zone(aging_size,alloter);
-       alloter = semispaces[aging()].init_zone(aging_size,alloter);
+       alloter = generations[aging_gen].init_zone(aging_size,alloter);
+       alloter = semispaces[aging_gen].init_zone(aging_size,alloter);
 
-       alloter = generations[nursery()].init_zone(young_size,alloter);
-       alloter = semispaces[nursery()].init_zone(0,alloter);
+       alloter = generations[nursery_gen].init_zone(young_size,alloter);
+       alloter = semispaces[nursery_gen].init_zone(0,alloter);
 
        if(seg->end - alloter > deck_size)
-               myvm->critical_error("Bug in alloc_data_heap",alloter);
+               critical_error("Bug in alloc_data_heap",alloter);
 }
 
 data_heap *factor_vm::grow_data_heap(data_heap *data, cell requested_bytes)
@@ -103,7 +103,7 @@ void factor_vm::clear_allot_markers(cell gen)
 their allocation pointers and cards reset. */
 void factor_vm::reset_generation(cell gen)
 {
-       assert(gen != data->nursery());
+       assert(gen != nursery_gen);
 
        zone *z = &data->generations[gen];
        z->here = z->start;
@@ -117,11 +117,11 @@ void factor_vm::reset_generation(cell gen)
 void factor_vm::set_data_heap(data_heap *data_)
 {
        data = data_;
-       nursery = data->generations[data->nursery()];
+       nursery = data->generations[nursery_gen];
        nursery.here = nursery.start;
        init_card_decks();
-       reset_generation(data->aging());
-       reset_generation(data->tenured());
+       reset_generation(aging_gen);
+       reset_generation(tenured_gen);
 }
 
 void factor_vm::init_data_heap(cell young_size, cell aging_size, cell tenured_size, bool secure_gc_)
@@ -234,7 +234,7 @@ void factor_vm::primitive_data_room()
        cell gen;
        for(gen = 0; gen < gen_count; gen++)
        {
-               zone *z = (gen == data->nursery() ? &nursery : &data->generations[gen]);
+               zone *z = (gen == nursery_gen ? &nursery : &data->generations[gen]);
                a.add(tag_fixnum((z->end - z->here) >> 10));
                a.add(tag_fixnum((z->size) >> 10));
        }
@@ -246,7 +246,7 @@ void factor_vm::primitive_data_room()
 /* Disables GC and activates next-object ( -- obj ) primitive */
 void factor_vm::begin_scan()
 {
-       heap_scan_ptr = data->generations[data->tenured()].start;
+       heap_scan_ptr = data->generations[tenured_gen].start;
        gc_off = true;
 }
 
@@ -265,7 +265,7 @@ cell factor_vm::next_object()
        if(!gc_off)
                general_error(ERROR_HEAP_SCAN,F,F,NULL);
 
-       if(heap_scan_ptr >= data->generations[data->tenured()].here)
+       if(heap_scan_ptr >= data->generations[tenured_gen].here)
                return F;
 
        object *obj = (object *)heap_scan_ptr;
index c4e8fe0d7b573966dd5789871ae80e1f99392ba6..cd53d66768f6cace0bae4626f1b661f151a201c2 100755 (executable)
@@ -9,7 +9,7 @@ struct zone {
        cell here;
        cell size;
        cell end;
-       
+
        cell init_zone(cell size_, cell start_)
        {
                size = size_;
@@ -17,11 +17,18 @@ struct zone {
                end = start_ + size_;
                return end;
        }
-       
+
        inline bool contains_p(object *pointer)
        {
                return ((cell)pointer - start) < size;
        }
+
+       inline object *allot(cell size)
+       {
+               cell h = here;
+               here = h + align8(size);
+               return (object *)h;
+       }
 };
 
 struct data_heap {
@@ -43,19 +50,13 @@ struct data_heap {
        char *decks;
        char *decks_end;
        
-       /* the 0th generation is where new objects are allocated. */
-       cell nursery() { return 0; }
-       
-       /* where objects hang around */
-       cell aging() { return 1; }
-       
-       /* the oldest generation */
-       cell tenured() { return 2; }
-       
        explicit data_heap(factor_vm *myvm, cell young_size, cell aging_size, cell tenured_size);
        ~data_heap();
 };
 
+static const cell nursery_gen = 0;
+static const cell aging_gen = 1;
+static const cell tenured_gen = 2;
 static const cell gen_count = 3;
 
 }
index 2435ac1c331eb187f48ddf9ee214cd1a05e55a7e..fc79603e67e92bfcd120d0905775ebafc15d21b5 100755 (executable)
@@ -3,26 +3,26 @@
 namespace factor
 {
 
-void factor_vm::out_of_memory()
-{
-       print_string("Out of memory\n\n");
-       dump_generations();
-       exit(1);
-}
-
-void fatal_error(const char* msg, cell tagged)
+void fatal_error(const char *msg, cell tagged)
 {
        print_string("fatal_error: "); print_string(msg);
        print_string(": "); print_cell_hex(tagged); nl();
        exit(1);
 }
 
-void factor_vm::critical_error(const char* msg, cell tagged)
+void critical_error(const char *msg, cell tagged)
 {
        print_string("You have triggered a bug in Factor. Please report.\n");
        print_string("critical_error: "); print_string(msg);
        print_string(": "); print_cell_hex(tagged); nl();
-       factorbug();
+       SIGNAL_VM_PTR()->factorbug();
+}
+
+void out_of_memory()
+{
+       print_string("Out of memory\n\n");
+       SIGNAL_VM_PTR()->dump_generations();
+       exit(1);
 }
 
 void factor_vm::throw_error(cell error, stack_frame *callstack_top)
index b837381005f5acc9b1731d89e8536aee49e4f4c5..c1ea2e19071231722304bb3c28c8a1366d6208ef 100755 (executable)
@@ -23,7 +23,9 @@ enum vm_error_type
        ERROR_FP_TRAP,
 };
 
-void fatal_error(const char* msg, cell tagged);
+void fatal_error(const char *msg, cell tagged);
+void critical_error(const char *msg, cell tagged);
+void out_of_memory();
 void memory_signal_handler_impl();
 void fp_signal_handler_impl();
 void misc_signal_handler_impl();
index 0f2f2fda1f901d6d0dd5543dfdea7006972a46e2..8c2d7d9ef5118048d7cbecbe6bb1907f29c5a840 100644 (file)
@@ -11,10 +11,9 @@ void heap::clear_free_list()
        memset(&free,0,sizeof(heap_free_list));
 }
 
-heap::heap(factor_vm *myvm_, cell size)
+heap::heap(bool secure_gc_, cell size) : secure_gc(secure_gc_)
 {
-       myvm = myvm_;
-       seg = new segment(myvm,align_page(size));
+       seg = new segment(align_page(size));
        if(!seg) fatal_error("Out of memory in new_heap",size);
        clear_free_list();
 }
@@ -85,7 +84,7 @@ void heap::build_free_list(cell size)
 void heap::assert_free_block(free_heap_block *block)
 {
        if(block->type() != FREE_BLOCK_TYPE)
-               myvm->critical_error("Invalid block in free list",(cell)block);
+               critical_error("Invalid block in free list",(cell)block);
 }
 
 free_heap_block *heap::find_free_block(cell size)
@@ -263,7 +262,7 @@ void heap::compact_heap()
 
 heap_block *heap::free_allocated(heap_block *prev, heap_block *scan)
 {
-       if(myvm->secure_gc)
+       if(secure_gc)
                memset(scan + 1,0,scan->size() - sizeof(heap_block));
 
        if(prev && prev->type() == FREE_BLOCK_TYPE)
index 07ed6bc2912eb4276d4c224fa73fe735289259a8..52d3f98ba54e769ee0b7df3825265b54d13eb547 100644 (file)
@@ -10,12 +10,12 @@ struct heap_free_list {
 };
 
 struct heap {
-       factor_vm *myvm;
+       bool secure_gc;
        segment *seg;
        heap_free_list free;
        unordered_map<heap_block *, char *> forwarding;
 
-       explicit heap(factor_vm *myvm, cell size);
+       explicit heap(bool secure_gc_, cell size);
 
        inline heap_block *next_block(heap_block *block)
        {
index 90afaa82f2909295ccfeff7925c010af7754adae..5af87905062a74a7244514895e6e2658fd54ea02 100755 (executable)
@@ -28,7 +28,7 @@ void factor_vm::load_data_heap(FILE *file, image_header *h, vm_parameters *p)
 
        clear_gc_stats();
 
-       zone *tenured = &data->generations[data->tenured()];
+       zone *tenured = &data->generations[tenured_gen];
 
        fixnum bytes_read = fread((void*)tenured->start,1,h->data_size,file);
 
@@ -85,7 +85,7 @@ bool factor_vm::save_image(const vm_char *filename)
                return false;
        }
 
-       zone *tenured = &data->generations[data->tenured()];
+       zone *tenured = &data->generations[tenured_gen];
 
        h.magic = image_magic;
        h.version = image_version;
@@ -156,7 +156,7 @@ void factor_vm::data_fixup(cell *cell)
        if(immediate_p(*cell))
                return;
 
-       zone *tenured = &data->generations[data->tenured()];
+       zone *tenured = &data->generations[tenured_gen];
        *cell += (tenured->start - data_relocation_base);
 }
 
@@ -280,7 +280,7 @@ void factor_vm::relocate_data()
        data_fixup(&bignum_pos_one);
        data_fixup(&bignum_neg_one);
 
-       zone *tenured = &data->generations[data->tenured()];
+       zone *tenured = &data->generations[tenured_gen];
 
        for(relocating = tenured->start;
                relocating < tenured->here;
index d17dedf29901661adb9616227b3c73280b743a47..e792483e0de65e2aee5f139289d4cf17e62cdfc5 100644 (file)
@@ -83,9 +83,8 @@ void factor_vm::primitive_existsp()
        box_boolean(stat(path,&sb) >= 0);
 }
 
-segment::segment(factor_vm *myvm_, cell size_)
+segment::segment(cell size_)
 {
-       myvm = myvm_;
        size = size_;
 
        int pagesize = getpagesize();
@@ -94,8 +93,7 @@ segment::segment(factor_vm *myvm_, cell size_)
                PROT_READ | PROT_WRITE | PROT_EXEC,
                MAP_ANON | MAP_PRIVATE,-1,0);
 
-       if(array == (char*)-1)
-               myvm->out_of_memory();
+       if(array == (char*)-1) out_of_memory();
 
        if(mprotect(array,pagesize,PROT_NONE) == -1)
                fatal_error("Cannot protect low guard page",(cell)array);
index 0dfaecab697cf54242b9c3cfba519d7a388edc58..48ddeffcb6d3d501e4e15a92a3ec3130ea07c012 100755 (executable)
@@ -96,9 +96,8 @@ void factor_vm::primitive_existsp()
        box_boolean(windows_stat(path));
 }
 
-segment::segment(factor_vm *myvm_, cell size_)
+segment::segment(cell size_)
 {
-       myvm = myvm_;
        size = size_;
 
        char *mem;
@@ -106,7 +105,7 @@ segment::segment(factor_vm *myvm_, cell size_)
 
        if((mem = (char *)VirtualAlloc(NULL, getpagesize() * 2 + size,
                MEM_COMMIT, PAGE_EXECUTE_READWRITE)) == 0)
-               myvm->out_of_memory();
+               out_of_memory();
 
        if (!VirtualProtect(mem, getpagesize(), PAGE_NOACCESS, &ignore))
                fatal_error("Cannot allocate low guard page", (cell)mem);
index 6b2e6c69d45be1e9ed08c68dd67b9b0a5c6d52cc..6ff21709746673aaf9d45c3fd36ea3d1bf61f40b 100644 (file)
@@ -9,12 +9,11 @@ inline cell align_page(cell a)
 /* segments set up guard pages to check for under/overflow.
 size must be a multiple of the page size */
 struct segment {
-       factor_vm *myvm;
        cell start;
        cell size;
        cell end;
 
-       explicit segment(factor_vm *myvm, cell size);
+       explicit segment(cell size);
        ~segment();
 };
 
index 2ddb991b29d56855c1630c322a458a8b02172eaf..772f8bcfdbfa6baba565524569d01cb33997017b 100755 (executable)
--- a/vm/vm.hpp
+++ b/vm/vm.hpp
@@ -4,16 +4,97 @@ namespace factor
 struct factor_vm
 {
        // First five fields accessed directly by assembler. See vm.factor
+
+       /* Current stacks */
        context *stack_chain;
-       zone nursery; /* new objects are allocated here */
+       
+       /* New objects are allocated here */
+       zone nursery;
+
+       /* Add this to a shifted address to compute write barrier offsets */
        cell cards_offset;
        cell decks_offset;
-       cell userenv[USER_ENV]; /* TAGGED user environment data; see getenv/setenv prims */
 
-       // contexts
+       /* TAGGED user environment data; see getenv/setenv prims */
+       cell userenv[USER_ENV];
+
+       /* Data stack and retain stack sizes */
        cell ds_size, rs_size;
+
+       /* Pooling unused contexts to make callbacks cheaper */
        context *unused_contexts;
 
+       /* Canonical T object. It's just a word */
+       cell T;
+
+       /* Is call counting enabled? */
+       bool profiling_p;
+
+       /* Global variables used to pass fault handler state from signal handler to
+          user-space */
+       cell signal_number;
+       cell signal_fault_addr;
+       unsigned int signal_fpu_status;
+       stack_frame *signal_callstack_top;
+
+       /* Zeroes out deallocated memory; set by the -securegc command line argument */
+       bool secure_gc;
+
+       /* A heap walk allows useful things to be done, like finding all
+          references to an object for debugging purposes. */
+       cell heap_scan_ptr;
+
+       /* GC is off during heap walking */
+       bool gc_off;
+
+       /* Data heap */
+       data_heap *data;
+
+       /* Where we store object start offsets in cards */
+       cell allot_markers_offset;
+
+       /* Only set if we're performing a GC */
+       gc_state *current_gc;
+
+       /* Statistics */
+       gc_stats stats;
+
+       /* Code heap */
+       code_heap *code;
+
+       /* If a runtime function needs to call another function which potentially
+          allocates memory, it must wrap any local variable references to Factor
+          objects in gc_root instances */
+       std::vector<cell> gc_locals;
+       std::vector<cell> gc_bignums;
+
+       /* Debugger */
+       bool fep_disabled;
+       bool full_output;
+
+       /* Canonical bignums */
+       cell bignum_zero;
+       cell bignum_pos_one;
+       cell bignum_neg_one;
+
+       /* Only used during image loading */
+       cell code_relocation_base;
+       cell data_relocation_base;
+
+       /* Method dispatch statistics */
+       cell megamorphic_cache_hits;
+       cell megamorphic_cache_misses;
+
+       cell cold_call_to_ic_transitions;
+       cell ic_to_pic_transitions;
+       cell pic_to_mega_transitions;
+       /* Indexed by PIC_TAG, PIC_HI_TAG, PIC_TUPLE, PIC_HI_TAG_TUPLE */
+       cell pic_counts[4];
+
+       /* Number of entries in a polymorphic inline cache */
+       cell max_pic_size;
+
+       // contexts
        void reset_datastack();
        void reset_retainstack();
        void fix_stacks();
@@ -32,9 +113,6 @@ struct factor_vm
        void primitive_check_datastack();
 
        // run
-       /* Canonical T object. It's just a word */
-       cell T;
-
        void primitive_getenv();
        void primitive_setenv();
        void primitive_exit();
@@ -46,23 +124,12 @@ struct factor_vm
        void primitive_clone();
 
        // profiler
-       bool profiling_p;
-
        void init_profiler();
        code_block *compile_profiling_stub(cell word_);
        void set_profiling(bool profiling);
        void primitive_profiling();
 
        // errors
-       /* Global variables used to pass fault handler state from signal handler to
-          user-space */
-       cell signal_number;
-       cell signal_fault_addr;
-       unsigned int signal_fpu_status;
-       stack_frame *signal_callstack_top;
-
-       void out_of_memory();
-       void critical_error(const char* msg, cell tagged);
        void throw_error(cell error, stack_frame *callstack_top);
        void not_implemented_error();
        bool in_page(cell fault, cell area, cell area_size, int offset);
@@ -142,13 +209,6 @@ struct factor_vm
        bignum *digit_stream_to_bignum(unsigned int n_digits, unsigned int (*producer)(unsigned int, factor_vm *), unsigned int radix, int negative_p);
 
        //data_heap
-       bool secure_gc;  /* Set by the -securegc command line argument */
-       bool gc_off; /* GC is off during heap walking */
-       data_heap *data;
-       /* A heap walk allows useful things to be done, like finding all
-          references to an object for debugging purposes. */
-       cell heap_scan_ptr;
-
        void init_card_decks();
        data_heap *grow_data_heap(data_heap *data, cell requested_bytes);
        void clear_cards(cell gen);
@@ -173,8 +233,6 @@ struct factor_vm
        cell object_size(cell tagged);
 
        //write barrier
-       cell allot_markers_offset;
-
        inline card *addr_to_card(cell a)
        {
                return (card*)(((cell)(a) >> card_bits) + cards_offset);
@@ -227,15 +285,6 @@ struct factor_vm
        }
 
        // data_gc
-       /* used during garbage collection only */
-       gc_state *current_gc;
-       /* statistics */
-       gc_stats stats[gen_count];
-       u64 cards_scanned;
-       u64 decks_scanned;
-       u64 card_scan_time;
-       cell code_heap_scans;
-
        void init_data_gc();
        template<typename Strategy> object *resolve_forwarding(object *untagged, Strategy &strategy);
        template<typename Strategy> void trace_handle(cell *handle, Strategy &strategy);
@@ -269,7 +318,6 @@ struct factor_vm
        void clear_gc_stats();
        void primitive_become();
        void inline_gc(cell *gc_roots_base, cell gc_roots_size);
-       inline object *allot_zone(zone *z, cell a);
        object *allot_object(header header, cell size);
        void primitive_clear_gc_stats();
 
@@ -301,22 +349,12 @@ struct factor_vm
        #endif
        }
 
-       // local roots
-       /* If a runtime function needs to call another function which potentially
-          allocates memory, it must wrap any local variable references to Factor
-          objects in gc_root instances */
-       std::vector<cell> gc_locals;
-       std::vector<cell> gc_bignums;
-
        // generic arrays
        template<typename Array> Array *allot_array_internal(cell capacity);
        template<typename Array> bool reallot_array_in_place_p(Array *array, cell capacity);
        template<typename Array> Array *reallot_array(Array *array_, cell capacity);
 
        //debug
-       bool fep_disabled;
-       bool full_output;
-
        void print_chars(string* str);
        void print_word(word* word, cell nesting);
        void print_factor_string(string* str);
@@ -389,10 +427,6 @@ struct factor_vm
        void primitive_wrapper();
 
        //math
-       cell bignum_zero;
-       cell bignum_pos_one;
-       cell bignum_neg_one;
-
        void primitive_bignum_to_fixnum();
        void primitive_float_to_fixnum();
        void primitive_fixnum_divint();
@@ -519,8 +553,6 @@ struct factor_vm
        code_block *add_code_block(cell type, cell code_, cell labels_, cell owner_, cell relocation_, cell literals_);
 
        //code_heap
-       code_heap *code;
-
        inline void check_code_pointer(cell ptr)
        {
        #ifdef FACTOR_DEBUG
@@ -554,9 +586,6 @@ struct factor_vm
        }
 
        //image
-       cell code_relocation_base;
-       cell data_relocation_base;
-
        void init_objects(image_header *h);
        void load_data_heap(FILE *file, image_header *h, vm_parameters *p);
        void load_code_heap(FILE *file, image_header *h, vm_parameters *p);
@@ -646,9 +675,6 @@ struct factor_vm
        void primitive_quot_compiled_p();
 
        //dispatch
-       cell megamorphic_cache_hits;
-       cell megamorphic_cache_misses;
-
        cell search_lookup_alist(cell table, cell klass);
        cell search_lookup_hash(cell table, cell klass, cell hashcode);
        cell nth_superclass(tuple_layout *layout, fixnum echelon);
@@ -666,12 +692,6 @@ struct factor_vm
        void primitive_dispatch_stats();
 
        //inline cache
-       cell max_pic_size;
-       cell cold_call_to_ic_transitions;
-       cell ic_to_pic_transitions;
-       cell pic_to_mega_transitions;
-       cell pic_counts[4];  /* PIC_TAG, PIC_HI_TAG, PIC_TUPLE, PIC_HI_TAG_TUPLE */
-
        void init_inline_caching(int max_size);
        void deallocate_inline_cache(cell return_address);
        cell determine_inline_cache_type(array *cache_entries);