From ac0f49a9290d5c496f764936e701cdb8d7f0927d Mon Sep 17 00:00:00 2001 From: mfranz Date: Tue, 1 May 2007 17:03:50 +0000 Subject: [PATCH] remove util.cxx workaround for listener-call-at-exit-segfault, and make NasalSys.cxx more robust instead. The reason for the crash was that during fgfs shutdown destroyed subsystems (GENERAL group) still need Nasal access (for AI Model destruction listeners), but at that point globals->get_subsystem() can't even deliver the "nasal" subsystem (INIT group). One way to solve that problem would have been to replace globals->get_subsystem("nasal") by globals->get_subsystem_mgr()->get_group(SGSubsystemMgr::INIT)->get_subsystem("nasal"), but Andy decided to store a pointer to the active "nasal" subsysten in NasalSys.cxx instead, as the "nasal" subsystem needs to be accessed in every single Nasal extension function, and multiple "nasal" subsystems are out of the question, anyway. --- src/Main/util.cxx | 14 +------------- src/Scripting/NasalSys.cxx | 27 +++++++++++++-------------- 2 files changed, 14 insertions(+), 27 deletions(-) diff --git a/src/Main/util.cxx b/src/Main/util.cxx index 056b9c4ed..c6efd7b0a 100644 --- a/src/Main/util.cxx +++ b/src/Main/util.cxx @@ -107,18 +107,6 @@ fgSetupWind (double min_hdg, double max_hdg, double speed, double gust) void fgExit (int status) { - // remove subsystems first, which need access to other subsystems in their - // destructors (e.g. "nasal") - SGSubsystem *sub; - - sub = globals->get_subsystem("ai_model"); - globals->get_subsystem_mgr()->get_group(SGSubsystemMgr::GENERAL)->remove_subsystem("ai_model"); - delete sub; - - sub = globals->get_subsystem("submodel_mgr"); - globals->get_subsystem_mgr()->get_group(SGSubsystemMgr::GENERAL)->remove_subsystem("submodel_mgr"); - delete sub; - #ifdef OSG_LIBRARY_STATIC osgDB::Registry::instance( true); #endif @@ -133,7 +121,7 @@ double fgGetLowPass (double current, double target, double timeratio) { if ( timeratio < 0.0 ) { - if ( timeratio < -1.0 ) { + if ( timeratio < -1.0 ) { // time went backwards; kill the filter current = target; } else { diff --git a/src/Scripting/NasalSys.cxx b/src/Scripting/NasalSys.cxx index 70eb70002..81effe1e5 100644 --- a/src/Scripting/NasalSys.cxx +++ b/src/Scripting/NasalSys.cxx @@ -22,6 +22,9 @@ #include "NasalSys.hxx" +static FGNasalSys* nasalSys = 0; + + // Read and return file contents in a single buffer. Note use of // stat() to get the file size. This is a win32 function, believe it // or not. :) Note the REALLY IMPORTANT use of the "b" flag to fopen. @@ -52,6 +55,7 @@ static char* readfile(const char* file, int* lenOut) FGNasalSys::FGNasalSys() { + nasalSys = this; _context = 0; _globals = naNil(); _gcHash = naNil(); @@ -82,6 +86,7 @@ naRef FGNasalSys::call(naRef code, naRef locals) FGNasalSys::~FGNasalSys() { + nasalSys = 0; map::iterator it, end = _listener.end(); for(it = _listener.begin(); it != end; ++it) delete it->second; @@ -254,8 +259,7 @@ static naRef f_fgcommand(naContext c, naRef me, int argc, naRef* args) // FGNasalSys::setTimer(). See there for docs. static naRef f_settimer(naContext c, naRef me, int argc, naRef* args) { - FGNasalSys* nasal = (FGNasalSys*)globals->get_subsystem("nasal"); - nasal->setTimer(argc, args); + nasalSys->setTimer(argc, args); return naNil(); } @@ -263,24 +267,21 @@ static naRef f_settimer(naContext c, naRef me, int argc, naRef* args) // FGNasalSys::setListener(). See there for docs. static naRef f_setlistener(naContext c, naRef me, int argc, naRef* args) { - FGNasalSys* nasal = (FGNasalSys*)globals->get_subsystem("nasal"); - return nasal->setListener(c, argc, args); + return nasalSys->setListener(c, argc, args); } // removelistener(int) extension function. Falls through to // FGNasalSys::removeListener(). See there for docs. static naRef f_removelistener(naContext c, naRef me, int argc, naRef* args) { - FGNasalSys* nasal = (FGNasalSys*)globals->get_subsystem("nasal"); - return nasal->removeListener(c, argc, args); + return nasalSys->removeListener(c, argc, args); } // Returns a ghost handle to the argument to the currently executing // command static naRef f_cmdarg(naContext c, naRef me, int argc, naRef* args) { - FGNasalSys* nasal = (FGNasalSys*)globals->get_subsystem("nasal"); - return nasal->cmdArgGhost(); + return nasalSys->cmdArgGhost(); } // Sets up a property interpolation. The first argument is either a @@ -777,8 +778,7 @@ void FGNasalModelData::modelLoaded(const string& path, SGPropertyNode *prop, _module = path; const char *s = load ? load->getStringValue() : ""; - FGNasalSys *nas = (FGNasalSys *)globals->get_subsystem("nasal"); - nas->createModule(_module.c_str(), _module.c_str(), s, strlen(s), _props); + nasalSys->createModule(_module.c_str(), _module.c_str(), s, strlen(s), _props); } FGNasalModelData::~FGNasalModelData() @@ -786,8 +786,7 @@ FGNasalModelData::~FGNasalModelData() if(_module.empty()) return; - FGNasalSys *nas = (FGNasalSys *)globals->get_subsystem("nasal"); - if(!nas) { + if(!nasalSys) { SG_LOG(SG_NASAL, SG_ALERT, "Trying to run an script " "without Nasal subsystem present."); return; @@ -795,9 +794,9 @@ FGNasalModelData::~FGNasalModelData() if(_unload) { const char *s = _unload->getStringValue(); - nas->createModule(_module.c_str(), _module.c_str(), s, strlen(s), _props); + nasalSys->createModule(_module.c_str(), _module.c_str(), s, strlen(s), _props); } - nas->deleteModule(_module.c_str()); + nasalSys->deleteModule(_module.c_str()); }