From: curt Date: Fri, 13 Jul 2001 05:15:29 +0000 (+0000) Subject: Nuked the segfault on exit bug everyone was seeing. The material lib could X-Git-Url: https://git.mxchange.org/?a=commitdiff_plain;h=dae9b63a14a9e0855eeda9cbe7fbd95326420f0b;p=flightgear.git Nuked the segfault on exit bug everyone was seeing. The material lib could have multiple ptrs to individual entries (aliases) but the destructor was trying to delete every ptr so it would delete already freed memory for aliases. I implimented a simple ref counting scheme (similar to the plib mechanism) to track references to material lib entries and only "delete" them when the last reference is removed. --- diff --git a/src/Objects/matlib.cxx b/src/Objects/matlib.cxx index 7103d976e..9d110bd69 100644 --- a/src/Objects/matlib.cxx +++ b/src/Objects/matlib.cxx @@ -72,18 +72,6 @@ static bool local_file_exists( const string& path ) { } else { return true; } - -#if 0 - cout << path << " "; - FILE *fp = fopen( path.c_str(), "r" ); - if ( fp == NULL ) { - cout << " doesn't exist\n"; - return false; - } else { - cout << " exists\n"; - return true; - } -#endif } @@ -123,6 +111,7 @@ bool FGMaterialLib::load( const string& mpath ) { FGNewMat *m = matlib[src_mat]; if ( m != NULL ) { matlib[dst_mat] = m; + m->ref(); } else { SG_LOG( SG_GENERAL, SG_ALERT, "Bad material alias pointing to nonexistant material" ); @@ -139,6 +128,7 @@ bool FGMaterialLib::load( const string& mpath ) { // create a pointer to a heap allocated copy of the structure FGNewMat *m = new FGNewMat; *m = tmp; + m->ref(); // build the ssgSimpleState SGPath tex_path( globals->get_fg_root() ); @@ -277,9 +267,9 @@ FGMaterialLib::~FGMaterialLib ( void ) { // Free up all the material entries first for ( material_map_iterator it = begin(); it != end(); it++ ) { FGNewMat *slot = it->second; - if ( slot != NULL ) { + slot->deRef(); + if ( slot->getRef() <= 0 ) { delete slot; - it->second = NULL; } } } diff --git a/src/Objects/newmat.cxx b/src/Objects/newmat.cxx index 2fa702d61..451b344ef 100644 --- a/src/Objects/newmat.cxx +++ b/src/Objects/newmat.cxx @@ -43,6 +43,7 @@ FGNewMat::FGNewMat ( void ) { wrapu = wrapv = 1; mipmap = 1; light_coverage = -1.0; + refcount = 0; } @@ -67,6 +68,7 @@ FGNewMat::FGNewMat ( const string &mat_name, const string &tex_name ) specular[0] = specular[1] = specular[2] = specular[3] = 1.0; emission[0] = emission[1] = emission[2] = emission[3] = 1.0; light_coverage = -1.0; + refcount = 0; } diff --git a/src/Objects/newmat.hxx b/src/Objects/newmat.hxx index acd9169be..72a92ecc3 100644 --- a/src/Objects/newmat.hxx +++ b/src/Objects/newmat.hxx @@ -92,6 +92,10 @@ private: // true if texture loading deferred, and not yet loaded bool texture_loaded; + // ref count so we can properly delete if we have multiple + // pointers to this record + int refcount; + public: // Constructor @@ -144,6 +148,10 @@ public: inline ssgStateSelector *get_state() const { return state; } + inline void ref() { refcount++; } + inline void deRef() { refcount--; } + inline int getRef() const { return refcount; } + void dump_info(); };