25 using namespace basis;
45 static bool __global_program_is_dying =
false;
51 class gremlin_object_record
54 root_object *c_object;
60 static_memory_gremlin::static_memory_gremlin()
65 c_show_debugging(false)
72 __global_program_is_dying =
true;
75 #ifdef DEBUG_STATIC_MEMORY_GREMLIN
77 printf(
"SMG: beginning static object shutdown...\n");
80 #ifndef SKIP_STATIC_CLEANUP
82 while (c_top_index > 0) {
85 int zapped_index = c_top_index - 1;
86 gremlin_object_record *ptr = c_pointers[zapped_index];
94 #ifdef DEBUG_STATIC_MEMORY_GREMLIN
96 printf((
astring(
"SMG: deleting ") + ptr->c_object->instance_name()
97 +
" called " + ptr->c_name
98 +
a_sprintf(
" at index %d.\n", zapped_index) ).s());
100 WHACK(ptr->c_object);
105 delete [] c_pointers;
113 static mutex __global_synch_mem;
114 return __global_synch_mem;
117 int static_memory_gremlin::locate(
const char *unique_name)
120 for (
int i = 0; i < c_top_index; i++) {
121 if (!strcmp(c_pointers[i]->c_name, unique_name))
return i;
123 return common::NOT_FOUND;
129 int indy = locate(unique_name);
131 return c_pointers[indy]->c_object;
137 for (
int i = 0; i < c_top_index; i++) {
138 if (ptr == c_pointers[i]->c_object)
139 return c_pointers[i]->c_name;
147 int indy = locate(unique_name);
150 #ifdef DEBUG_STATIC_MEMORY_GREMLIN
151 if (c_show_debugging)
152 printf((
astring(
"SMG: cleaning out old object ")
153 + c_pointers[indy]->c_object->instance_name()
154 +
" called " + c_pointers[indy]->c_name
155 +
" in favor of object " + to_put->instance_name()
156 +
" called " + unique_name
157 +
a_sprintf(
" at index %d.\n", indy)).s());
159 WHACK(c_pointers[indy]->c_object);
160 c_pointers[indy]->c_object = to_put;
163 #ifdef DEBUG_STATIC_MEMORY_GREMLIN
164 if (c_show_debugging)
165 printf((
astring(
"SMG: storing ") + to_put->instance_name()
166 +
" called " + unique_name
167 +
a_sprintf(
" at index %d.\n", c_top_index)).s());
170 c_pointers[c_top_index] =
new gremlin_object_record;
171 c_pointers[c_top_index]->c_object = to_put;
172 c_pointers[c_top_index]->c_name = unique_name;
180 if (!c_pointers || (c_top_index + 1 >= c_actual_size) ) {
182 #ifdef DEBUG_STATIC_MEMORY_GREMLIN
183 if (c_show_debugging)
184 printf(
a_sprintf(
"SMG: adding space for top at %d.\n", c_top_index).s());
187 typedef gremlin_object_record *base_ptr;
188 gremlin_object_record **new_ptr =
new base_ptr[c_actual_size];
190 throw "error: static_memory_gremlin::ensure_space_exists: failed to allocate memory for pointer list";
192 for (
int i = 0; i < c_actual_size; i++) new_ptr[i] =
NULL_POINTER;
194 new_ptr[j] = c_pointers[j];
195 if (c_pointers)
delete [] c_pointers;
196 c_pointers = new_ptr;
208 static bool _initted =
false;
213 #ifdef DEBUG_STATIC_MEMORY_GREMLIN
214 printf(
"%s: initializing HOOPLE_GLOBALS now.\n",
_global_argv[0]);
217 #ifdef ENABLE_MEMORY_HOOK
223 #ifdef ENABLE_CALLSTACK_TRACKING
228 FUNCDEF(
"HOOPLE_GLOBALS remainder");
245 return *_internal_gremlin;
int full_trace_size() const
this returns an estimated number of bytes needed for the full_trace().
a_sprintf is a specialization of astring that provides printf style support.
Provides a dynamically resizable ASCII character string.
auto_synchronizer simplifies concurrent code by automatically unlocking.
Holds onto memory chunks that are allocated globally within the program.
bool put(const char *unique_name, basis::root_object *ptr)
adds a "ptr" to the set of static objects under the "unique_name".
basis::root_object * get(const char *unique_name)
locates the pointer held for the "unique_name", if any.
static bool __program_is_dying()
Reports whether the program is shutting down currently.
static static_memory_gremlin & __hoople_globals()
Holds onto objects that have been allocated in a program-wide scope.
void ensure_space_exists()
static basis::mutex & __memory_gremlin_synchronizer()
private object for static_memory_gremlin's use only.
const char * find(const basis::root_object *ptr)
locates the name for "ptr" in our objects.
#define NULL_POINTER
The value representing a pointer to nothing.
#define FUNCDEF(func_in)
FUNCDEF sets the name of a function (and plugs it into the callstack).
#define program_wide_memories()
Implements an application lock to ensure only one is running at once.
callstack_tracker & thread_wide_stack_trace()
the single instance of callstack_tracker.
The guards collection helps in testing preconditions and reporting errors.
void WHACK(contents *&ptr)
deletion with clearing of the pointer.
bool non_negative(const type &a)
non_negative returns true if "a" is greater than or equal to zero.
bool negative(const type &a)
negative returns true if "a" is less than zero.
A dynamic container class that holds any kind of object via pointers.
const int SMG_CHUNKING_FACTOR