NGSPICE as a singleton
One cannot call ngSpice_Init() twice without unloading the dll. When calling ngSpice_Init, we pass a pointer to a NGSPICE instance and thus it cannot be changed. When any of the callback function is called with a stale pointer everything crashes.
This commit is contained in:
parent
bcfce68daa
commit
2a6b8f153b
|
@ -45,7 +45,6 @@ NGSPICE::~NGSPICE()
|
|||
|
||||
void NGSPICE::Init()
|
||||
{
|
||||
init();
|
||||
Command( "reset" );
|
||||
}
|
||||
|
||||
|
|
|
@ -109,6 +109,19 @@ SIM_PLOT_FRAME::SIM_PLOT_FRAME( KIWAY* aKiway, wxWindow* aParent )
|
|||
if( m_schematicFrame == NULL )
|
||||
throw std::runtime_error( "There is no schematic window" );
|
||||
|
||||
m_simulator = SPICE_SIMULATOR::CreateInstance( "ngspice" );
|
||||
|
||||
if( !m_simulator )
|
||||
{
|
||||
throw std::runtime_error( "Could not create simulator instance" );
|
||||
return;
|
||||
}
|
||||
|
||||
m_simulator->Init();
|
||||
|
||||
m_reporter = new SIM_THREAD_REPORTER( this );
|
||||
m_simulator->SetReporter( m_reporter );
|
||||
|
||||
updateNetlistExporter();
|
||||
|
||||
Connect( wxEVT_CLOSE_WINDOW, wxCloseEventHandler( SIM_PLOT_FRAME::onClose ), NULL, this );
|
||||
|
@ -145,12 +158,13 @@ SIM_PLOT_FRAME::SIM_PLOT_FRAME( KIWAY* aKiway, wxWindow* aParent )
|
|||
|
||||
m_toolBar->Realize();
|
||||
m_plotNotebook->SetPageText( 0, _( "Welcome!" ) );
|
||||
m_simulator.reset( SPICE_SIMULATOR::CreateInstance( "ngspice" ) );
|
||||
}
|
||||
|
||||
|
||||
SIM_PLOT_FRAME::~SIM_PLOT_FRAME()
|
||||
{
|
||||
delete m_simulator;
|
||||
delete m_reporter;
|
||||
}
|
||||
|
||||
|
||||
|
@ -159,12 +173,6 @@ void SIM_PLOT_FRAME::StartSimulation()
|
|||
STRING_FORMATTER formatter;
|
||||
SIM_PLOT_PANEL* plotPanel = CurrentPlot();
|
||||
|
||||
if( !m_simulator )
|
||||
{
|
||||
DisplayError( this, wxT( "Could not create simulator instance" ) );
|
||||
return;
|
||||
}
|
||||
|
||||
m_simConsole->Clear();
|
||||
updateNetlistExporter();
|
||||
|
||||
|
@ -183,8 +191,6 @@ void SIM_PLOT_FRAME::StartSimulation()
|
|||
return;
|
||||
}
|
||||
|
||||
m_simulator->SetReporter( new SIM_THREAD_REPORTER( this ) );
|
||||
m_simulator->Init();
|
||||
m_simulator->LoadNetlist( formatter.GetString() );
|
||||
updateTuners();
|
||||
applyTuners();
|
||||
|
@ -194,7 +200,6 @@ void SIM_PLOT_FRAME::StartSimulation()
|
|||
|
||||
void SIM_PLOT_FRAME::StopSimulation()
|
||||
{
|
||||
if( m_simulator )
|
||||
m_simulator->Stop();
|
||||
}
|
||||
|
||||
|
@ -367,9 +372,6 @@ void SIM_PLOT_FRAME::updateNetlistExporter()
|
|||
|
||||
bool SIM_PLOT_FRAME::updatePlot( const TRACE_DESC& aDescriptor, SIM_PLOT_PANEL* aPanel )
|
||||
{
|
||||
if( !m_simulator )
|
||||
return false;
|
||||
|
||||
SIM_TYPE simType = m_exporter->GetSimType();
|
||||
wxString spiceVector = m_exporter->GetSpiceVector( aDescriptor.GetName(),
|
||||
aDescriptor.GetType(), aDescriptor.GetParam() );
|
||||
|
@ -494,6 +496,7 @@ void SIM_PLOT_FRAME::applyTuners()
|
|||
/// @todo no ngspice hardcoding
|
||||
std::string command( "alter @" + tuner->GetSpiceName()
|
||||
+ "=" + tuner->GetValue().ToSpiceString() );
|
||||
|
||||
m_simulator->Command( command );
|
||||
}
|
||||
}
|
||||
|
@ -1015,9 +1018,6 @@ void SIM_PLOT_FRAME::onSimFinished( wxCommandEvent& aEvent )
|
|||
|
||||
void SIM_PLOT_FRAME::onSimUpdate( wxCommandEvent& aEvent )
|
||||
{
|
||||
if( !m_simulator )
|
||||
return;
|
||||
|
||||
if( IsSimulationRunning() )
|
||||
StopSimulation();
|
||||
|
||||
|
|
|
@ -48,6 +48,7 @@ class SCH_COMPONENT;
|
|||
class SPICE_SIMULATOR;
|
||||
class NETLIST_EXPORTER_PSPICE_SIM;
|
||||
class SIM_PLOT_PANEL;
|
||||
class SIM_THREAD_REPORTER;
|
||||
class TUNER_SLIDER;
|
||||
|
||||
///> Trace descriptor class
|
||||
|
@ -271,7 +272,8 @@ private:
|
|||
|
||||
SCH_EDIT_FRAME* m_schematicFrame;
|
||||
std::unique_ptr<NETLIST_EXPORTER_PSPICE_SIM> m_exporter;
|
||||
std::unique_ptr<SPICE_SIMULATOR> m_simulator;
|
||||
SPICE_SIMULATOR* m_simulator;
|
||||
SIM_THREAD_REPORTER* m_reporter;
|
||||
|
||||
typedef std::map<wxString, TRACE_DESC> TRACE_MAP;
|
||||
|
||||
|
|
|
@ -30,7 +30,12 @@ SPICE_SIMULATOR* SPICE_SIMULATOR::CreateInstance( const std::string& )
|
|||
{
|
||||
try
|
||||
{
|
||||
return new NGSPICE;
|
||||
static NGSPICE* ngspiceInstance = nullptr;
|
||||
|
||||
if( !ngspiceInstance )
|
||||
ngspiceInstance = new NGSPICE;
|
||||
|
||||
return ngspiceInstance;
|
||||
}
|
||||
catch( std::exception& e )
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue