00001 // Copyright (C) Calum Grant 2008 00002 00003 namespace dynamic 00004 { 00005 namespace internal 00006 { 00008 DYNAMIC_API void * apartment_malloc(std::size_t bytes); 00009 00011 DYNAMIC_API void apartment_free(void *p); 00012 00014 DYNAMIC_API void apartment_defrag(); 00015 } 00016 00017 namespace gc 00018 { 00019 class gc_object; 00020 00022 00023 class garbage_collector 00024 { 00025 public: 00026 virtual ~garbage_collector(); 00027 00029 virtual gc_object * chain()=0; 00030 00032 virtual void mark_reachable(gc_object*)=0; 00033 00035 virtual void collect()=0; 00036 00038 virtual int object_count()=0; 00039 00041 virtual void on_add_object()=0; 00042 00044 virtual void try_idle_gc()=0; 00045 00047 00051 virtual void disable()=0; 00052 00054 virtual void enable()=0; 00055 00057 virtual void set_min_objects(int)=0; 00058 00060 00062 virtual void set_idle_gc_factor(int)=0; 00063 00065 00067 virtual void set_gc_factor(int)=0; 00068 }; 00069 00070 00072 00075 DYNAMIC_API garbage_collector & global_gc(); 00076 00078 00079 garbage_collector * create_gc(); 00080 00082 00083 class DYNAMIC_API gc_object 00084 { 00086 gc_object * next, *prev; 00087 00089 unsigned root_ref_count : 31; 00090 00092 bool marked : 1; 00093 00094 public: 00096 00097 void link(); 00098 00100 void link_to(gc_object*); 00101 00103 void unlink(); 00104 00106 gc_object * next_gc_object() const 00107 { 00108 return next; 00109 } 00110 00111 public: 00113 void * operator new(std::size_t s) 00114 { 00115 return internal::apartment_malloc(s); 00116 } 00117 00119 void operator delete(void * p) 00120 { 00121 return internal::apartment_free(p); 00122 } 00123 00125 gc_object(const gc_object&) : root_ref_count(0) 00126 { 00127 link(); 00128 } 00129 00131 gc_object & operator=(const gc_object&) 00132 { 00133 return *this; 00134 } 00135 00137 gc_object(int) : root_ref_count(1) 00138 { 00139 next = prev = this; 00140 } 00141 00143 gc_object() : root_ref_count(0) 00144 { 00145 link(); 00146 } 00147 00149 00150 virtual ~gc_object() 00151 { 00152 unlink(); 00153 } 00154 00156 virtual void finalize() { } 00157 00159 virtual void mark() { marked = true; } 00160 00162 virtual void mark_children(garbage_collector &) =0; 00163 00165 bool is_marked() const 00166 { 00167 return marked; 00168 } 00169 00171 virtual void init_mark() 00172 { 00173 marked = root_ref_count!=0; 00174 } 00175 00177 void add_root_ref() 00178 { 00179 ++root_ref_count; 00180 } 00181 00183 void release_root_ref() { --root_ref_count; } 00184 }; 00185 00186 00188 00193 template<typename T> 00194 class root_ref 00195 { 00196 T * object; 00197 public: 00198 typedef T value_type; 00199 00201 root_ref(T * t) : object(t) 00202 { 00203 object->add_root_ref(); 00204 } 00205 00207 root_ref(const root_ref & other) : object(other.object) 00208 { 00209 object->add_root_ref(); 00210 } 00211 00213 ~root_ref() 00214 { 00215 object->release_root_ref(); 00216 } 00217 00219 root_ref & operator=(root_ref other) 00220 { 00221 swap(other); 00222 return *this; 00223 } 00224 00226 T * operator->() const 00227 { 00228 return object; 00229 } 00230 00232 T & operator*() const 00233 { 00234 return *object; 00235 } 00236 00238 T * get() const 00239 { 00240 return object; 00241 } 00242 00244 void swap(root_ref & other) 00245 { 00246 std::swap(object, other.object); 00247 } 00248 }; 00249 } 00250 }
1.5.7.1