Beispiel #1
0
FGFDMExec::~FGFDMExec()
{
  try {
    Unbind();
    DeAllocate();

    if (IdFDM == 0) { // Meaning this is no child FDM
      if(Root != 0) {
         if(StandAlone)
            delete Root;
         Root = 0;
      }
      if(FDMctr != 0) {
         delete FDMctr;
         FDMctr = 0;
      }
    }
  } catch ( string msg ) {
    cout << "Caught error: " << msg << endl;
  }

  for (unsigned int i=1; i<ChildFDMList.size(); i++) delete ChildFDMList[i]->exec;
  ChildFDMList.clear();

  PropertyCatalog.clear();

  if (FDMctr > 0) (*FDMctr)--;

  Debug(1);
}
Beispiel #2
0
//  Reduce the size of this, retaining data from the original array
//  for valid indices of the new array.
bool AMatrix_base::Shrink(const int NumRows, const int NumCols) {

    bool result = false;
    int i, j;

    if ((NumRows < m_NumRows) || (NumCols < m_NumCols)) {
        if (NumRows > 0 && NumCols > 0) {
            //  
            AMatrix_base tmpMatrix(NumRows, NumCols);
            for (i = 0; i < NumRows; ++i) {
                for (j = 0; j < NumCols; ++j) {
                    tmpMatrix.m_Array[i][j] = m_Array[i][j];
                    if (i == 0) {
                        tmpMatrix.m_ColumnFlags[j] = m_ColumnFlags[j];
                    }
                }
            }
            DeAllocate();
            Allocate(NumRows, NumCols);
            for (i = 0; i < NumRows; ++i) {
                for (j = 0; j < NumCols; ++j) {
                    m_Array[i][j] = tmpMatrix.m_Array[i][j];
                    if (i == 0) {
                        m_ColumnFlags[j] = tmpMatrix.m_ColumnFlags[j];
                    }
                }
            }
            result = true;
        }
    }
    return result;
}
Beispiel #3
0
void AMatrix_base::MakeArrayBigger(const int RowIndex, const int ColIndex) {
//-------------------------------------------------------------
// if m_Array is big enough, return true.
// if m_Array is too small, make it bigger and return false.
//-------------------------------------------------------------
  // make an array that's big enough (don't let either dimension shrink)
  int  NumRows = Max(m_NumRows, RowIndex+1);
  int  NumCols = Max(m_NumCols, ColIndex+1);
  AMatrix_base  NewMatrix(NumRows, NumCols);

  // copy old array into new array
  NewMatrix.SlowCopy(*this);

  // free the old array
  DeAllocate();

  // save new array in place of old array
  m_Array = NewMatrix.m_Array;
  m_ColumnFlags = NewMatrix.m_ColumnFlags;
  m_NumRows = NewMatrix.m_NumRows;
  m_NumCols = NewMatrix.m_NumCols;

  // pretend new array has been freed
  // (so that new array isn't freed when leaving this routine)
  NewMatrix.m_Array = NULL;
  NewMatrix.m_ColumnFlags = NULL;
  NewMatrix.m_NumRows = 0;
  NewMatrix.m_NumCols = 0;
}
Beispiel #4
0
void AMatrix_base::Copy(const AMatrix_base& Matrix) {
//--------------------------------------------
// copy Matrix to this one
//--------------------------------------------
  DeAllocate();
  Allocate(Matrix.m_NumRows, Matrix.m_NumCols);
  memcpy(m_Array, Matrix.m_Array, m_NumRows*m_NumCols*sizeof(double));
  memcpy(m_ColumnFlags, Matrix.m_ColumnFlags, m_NumCols*sizeof(bool));
}
Beispiel #5
0
 cchar& operator=(const char* psz)
 {
     if (psz != pchar) { // ensure we aren't copying over ourselves
         if (pchar != NULL)
             DeAllocate();
         if (psz != NULL) {
             Allocate(strlen(psz) + 1);
             strcpy (pchar, psz);
         } else {
             pchar = NULL;
         }
     }
     return *this;
 }
Beispiel #6
0
bool FGFDMExec::LoadModel(const string& model, bool addModelToPath)
{
  string token;
  string aircraftCfgFileName;
  Element* element = 0L;
  bool result = false; // initialize result to false, indicating input file not yet read

  modelName = model; // Set the class modelName attribute

  if( AircraftPath.empty() || EnginePath.empty() || SystemsPath.empty()) {
    cerr << "Error: attempted to load aircraft with undefined ";
    cerr << "aircraft, engine, and system paths" << endl;
    return false;
  }

  FullAircraftPath = AircraftPath;
  if (addModelToPath) FullAircraftPath += "/" + model;
  aircraftCfgFileName = FullAircraftPath + "/" + model + ".xml";

  if (modelLoaded) {
    DeAllocate();
    Allocate();
  }

  int saved_debug_lvl = debug_lvl;

  document = LoadXMLDocument(aircraftCfgFileName); // "document" is a class member
  if (document) {
    if (IsChild) debug_lvl = 0;

    ReadPrologue(document);

    if (IsChild) debug_lvl = saved_debug_lvl;

    // Process the fileheader element in the aircraft config file. This element is OPTIONAL.
    element = document->FindElement("fileheader");
    if (element) {
      result = ReadFileHeader(element);
      if (!result) {
        cerr << endl << "Aircraft fileheader element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
    }

    if (IsChild) debug_lvl = 0;

    // Process the metrics element. This element is REQUIRED.
    element = document->FindElement("metrics");
    if (element) {
      result = ((FGAircraft*)Models[eAircraft])->Load(element);
      if (!result) {
        cerr << endl << "Aircraft metrics element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
    } else {
      cerr << endl << "No metrics element was found in the aircraft config file." << endl;
      return false;
    }

    // Process the mass_balance element. This element is REQUIRED.
    element = document->FindElement("mass_balance");
    if (element) {
      result = ((FGMassBalance*)Models[eMassBalance])->Load(element);
      if (!result) {
        cerr << endl << "Aircraft mass_balance element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
    } else {
      cerr << endl << "No mass_balance element was found in the aircraft config file." << endl;
      return false;
    }

    // Process the ground_reactions element. This element is REQUIRED.
    element = document->FindElement("ground_reactions");
    if (element) {
      result = ((FGGroundReactions*)Models[eGroundReactions])->Load(element);
      if (!result) {
        cerr << endl << "Aircraft ground_reactions element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
      ((FGFCS*)Models[eSystems])->AddGear(((FGGroundReactions*)Models[eGroundReactions])->GetNumGearUnits());
    } else {
      cerr << endl << "No ground_reactions element was found in the aircraft config file." << endl;
      return false;
    }

    // Process the external_reactions element. This element is OPTIONAL.
    element = document->FindElement("external_reactions");
    if (element) {
      result = ((FGExternalReactions*)Models[eExternalReactions])->Load(element);
      if (!result) {
        cerr << endl << "Aircraft external_reactions element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
    }

    // Process the buoyant_forces element. This element is OPTIONAL.
    element = document->FindElement("buoyant_forces");
    if (element) {
      result = ((FGBuoyantForces*)Models[eBuoyantForces])->Load(element);
      if (!result) {
        cerr << endl << "Aircraft buoyant_forces element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
    }

    // Process the propulsion element. This element is OPTIONAL.
    element = document->FindElement("propulsion");
    if (element) {
      result = ((FGPropulsion*)Models[ePropulsion])->Load(element);
      if (!result) {
        cerr << endl << "Aircraft propulsion element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
      for (unsigned int i=0; i<((FGPropulsion*)Models[ePropulsion])->GetNumEngines(); i++)
        ((FGFCS*)Models[eSystems])->AddThrottle();
    }

    // Process the system element[s]. This element is OPTIONAL, and there may be more than one.
    element = document->FindElement("system");
    while (element) {
      result = ((FGFCS*)Models[eSystems])->Load(element, FGFCS::stSystem);
      if (!result) {
        cerr << endl << "Aircraft system element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
      element = document->FindNextElement("system");
    }

    // Process the autopilot element. This element is OPTIONAL.
    element = document->FindElement("autopilot");
    if (element) {
      result = ((FGFCS*)Models[eSystems])->Load(element, FGFCS::stAutoPilot);
      if (!result) {
        cerr << endl << "Aircraft autopilot element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
    }

    // Process the flight_control element. This element is OPTIONAL.
    element = document->FindElement("flight_control");
    if (element) {
      result = ((FGFCS*)Models[eSystems])->Load(element, FGFCS::stFCS);
      if (!result) {
        cerr << endl << "Aircraft flight_control element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
    }

    // Process the aerodynamics element. This element is OPTIONAL, but almost always expected.
    element = document->FindElement("aerodynamics");
    if (element) {
      result = ((FGAerodynamics*)Models[eAerodynamics])->Load(element);
      if (!result) {
        cerr << endl << "Aircraft aerodynamics element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
    } else {
      cerr << endl << "No expected aerodynamics element was found in the aircraft config file." << endl;
    }

    // Process the input element. This element is OPTIONAL.
    element = document->FindElement("input");
    if (element) {
      result = ((FGInput*)Models[eInput])->Load(element);
      if (!result) {
        cerr << endl << "Aircraft input element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
    }

    // Process the output element[s]. This element is OPTIONAL, and there may be more than one.
    unsigned int idx=0;
    typedef double (FGOutput::*iOPMF)(void) const;
    typedef int (FGFDMExec::*iOPV)(void) const;
    element = document->FindElement("output");
    while (element) {
      if (debug_lvl > 0) cout << endl << "  Output data set: " << idx << "  ";
      FGOutput* Output = new FGOutput(this);
      Output->InitModel();
      Schedule(Output);
      result = Output->Load(element);
      if (!result) {
        cerr << endl << "Aircraft output element has problems in file " << aircraftCfgFileName << endl;
        return result;
      } else {
        Outputs.push_back(Output);
        string outputProp = CreateIndexedPropertyName("simulation/output",idx);
        instance->Tie(outputProp+"/log_rate_hz", Output, (iOPMF)0, &FGOutput::SetRate, false);
        instance->Tie("simulation/force-output", this, (iOPV)0, &FGFDMExec::ForceOutput, false);
        idx++;
      }
      element = document->FindNextElement("output");
    }

    // Lastly, process the child element. This element is OPTIONAL - and NOT YET SUPPORTED.
    element = document->FindElement("child");
    if (element) {
      result = ReadChild(element);
      if (!result) {
        cerr << endl << "Aircraft child element has problems in file " << aircraftCfgFileName << endl;
        return result;
      }
    }

    // Since all vehicle characteristics have been loaded, place the values in the Inputs
    // structure for the FGModel-derived classes.
    LoadModelConstants();

    modelLoaded = true;

    if (debug_lvl > 0) {
      LoadInputs(eMassBalance); // Update all input mass properties for the report.
      Models[eMassBalance]->Run(false);  // Update all mass properties for the report.
      ((FGMassBalance*)Models[eMassBalance])->GetMassPropertiesReport();

      cout << endl << fgblue << highint
           << "End of vehicle configuration loading." << endl
           << "-------------------------------------------------------------------------------"
           << reset << endl;
    }

    if (IsChild) debug_lvl = saved_debug_lvl;

  } else {
    cerr << fgred
         << "  JSBSim failed to open the configuration file: " << aircraftCfgFileName
         << fgdef << endl;
  }

  for (unsigned int i=0; i< Models.size(); i++) LoadInputs(i);

  if (result) {
    struct PropertyCatalogStructure masterPCS;
    masterPCS.base_string = "";
    masterPCS.node = (FGPropertyManager*)Root;
    BuildPropertyCatalog(&masterPCS);
  }

  return result;
}
Beispiel #7
0
 ~cchar()
 {
     if (pchar != NULL)
         DeAllocate();
 }