(svn r4486) - NewGRF: Create and use a memory pool to manage sprite groups. This

reduces the amount of house keeping we do and the chance of memory 
leaks.
This commit is contained in:
2006-04-20 20:51:57 +00:00
parent fe6dadad7b
commit 92d8af75db
7 changed files with 96 additions and 142 deletions

View File

@@ -97,74 +97,3 @@ byte RandomizedSpriteGroupTriggeredBits(const RandomizedSpriteGroup *rsg,
return (rsg->num_groups - 1) << rsg->lowest_randbit;
}
/**
* Traverse a sprite group and release its and its child's memory.
* A group is only released if its reference count is zero.
* We pass a pointer to a pointer so that the original reference can be set to NULL.
* @param group_ptr Pointer to sprite group reference.
*/
void UnloadSpriteGroup(SpriteGroup **group_ptr)
{
SpriteGroup *group;
int i;
assert(group_ptr != NULL);
assert(*group_ptr != NULL);
group = *group_ptr;
*group_ptr = NULL; // Remove this reference.
group->ref_count--;
if (group->ref_count > 0) {
DEBUG(grf, 6)("UnloadSpriteGroup: Group at `%p' (type %d) has %d reference(s) left.", group, group->type, group->ref_count);
return; // Still some references left, so don't clear up.
}
DEBUG(grf, 6)("UnloadSpriteGroup: Releasing group at `%p'.", group);
switch (group->type) {
case SGT_REAL:
{
RealSpriteGroup *rsg = &group->g.real;
for (i = 0; i < rsg->loading_count; i++) {
if (rsg->loading[i] != NULL) UnloadSpriteGroup(&rsg->loading[i]);
}
for (i = 0; i < rsg->loaded_count; i++) {
if (rsg->loaded[i] != NULL) UnloadSpriteGroup(&rsg->loaded[i]);
}
free(group->g.real.loaded);
free(group->g.real.loading);
free(group);
return;
}
case SGT_DETERMINISTIC:
{
DeterministicSpriteGroup *dsg = &group->g.determ;
for (i = 0; i < group->g.determ.num_ranges; i++) {
if (dsg->ranges[i].group != NULL) UnloadSpriteGroup(&dsg->ranges[i].group);
}
if (dsg->default_group != NULL) UnloadSpriteGroup(&dsg->default_group);
free(group->g.determ.ranges);
free(group);
return;
}
case SGT_RANDOMIZED:
{
for (i = 0; i < group->g.random.num_groups; i++) {
if (group->g.random.groups[i] != NULL) UnloadSpriteGroup(&group->g.random.groups[i]);
}
free(group->g.random.groups);
free(group);
return;
}
case SGT_CALLBACK:
case SGT_RESULT:
free(group);
return;
}
DEBUG(grf, 1)("Unable to remove unknown sprite group type `0x%x'.", group->type);
}