main: more flexible FDTD setup
Signed-off-by: Thorsten Liebig <Thorsten.Liebig@gmx.de>pull/14/head
parent
1eca3dd23a
commit
6140b07c47
|
@ -20,7 +20,6 @@
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <fstream>
|
#include <fstream>
|
||||||
#include "fparser.hh"
|
#include "fparser.hh"
|
||||||
#include "tinyxml.h"
|
|
||||||
#include "excitation.h"
|
#include "excitation.h"
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
@ -32,8 +31,7 @@ Excitation::Excitation()
|
||||||
|
|
||||||
this->Reset(0);
|
this->Reset(0);
|
||||||
|
|
||||||
m_Excite_Elem = NULL;
|
m_Excit_Type = Excitation::UNDEFINED;
|
||||||
m_Excit_Type = -1;
|
|
||||||
m_SignalPeriod = 0;
|
m_SignalPeriod = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -55,27 +53,44 @@ void Excitation::Reset( double timestep )
|
||||||
m_foi = 0;
|
m_foi = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Excitation::setupExcitation( TiXmlElement* Excite)
|
bool Excitation::SetupGaussianPulse(double f0, double fc)
|
||||||
{
|
{
|
||||||
if (!Excite)
|
m_Excit_Type = Excitation::GaissianPulse;
|
||||||
{
|
m_f0 = f0;
|
||||||
cerr << "Excitation::setupExcitation: Error, can't read openEMS excitation settings... " << endl;
|
m_fc = fc;
|
||||||
return false;
|
m_f_max = f0+fc;
|
||||||
}
|
|
||||||
|
|
||||||
m_Excite_Elem = Excite;
|
|
||||||
|
|
||||||
double f0=0;
|
|
||||||
m_Excite_Elem->QueryIntAttribute("Type",&m_Excit_Type);
|
|
||||||
m_SignalPeriod = 0;
|
m_SignalPeriod = 0;
|
||||||
switch (m_Excit_Type)
|
|
||||||
{
|
|
||||||
case 1: // sinusoidal excite
|
|
||||||
m_Excite_Elem->QueryDoubleAttribute("f0",&f0);
|
|
||||||
m_SignalPeriod = 1/f0;
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
return true;
|
|
||||||
|
bool Excitation::SetupSinusoidal(double f0)
|
||||||
|
{
|
||||||
|
m_Excit_Type = Excitation::Sinusoidal;
|
||||||
|
m_f0 = f0;
|
||||||
|
m_f_max = f0;
|
||||||
|
m_SignalPeriod = 1/f0;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Excitation::SetupDiracPulse(double fmax)
|
||||||
|
{
|
||||||
|
m_Excit_Type = Excitation::DiracPulse;
|
||||||
|
m_SignalPeriod = 0;
|
||||||
|
m_f_max = fmax;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Excitation::SetupStepExcite(double fmax)
|
||||||
|
{
|
||||||
|
m_Excit_Type = Excitation::Step;
|
||||||
|
m_SignalPeriod = 0;
|
||||||
|
m_f_max = fmax;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Excitation::SetupCustomExcite(string str, double f0, double fmax)
|
||||||
|
{
|
||||||
|
m_Excit_Type = Excitation::CustomExcite;
|
||||||
|
m_CustomExc_Str = str;
|
||||||
|
m_f0 = f0;
|
||||||
|
m_SignalPeriod = 0;
|
||||||
|
m_f_max = fmax;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Excitation::buildExcitationSignal(unsigned int maxTS)
|
bool Excitation::buildExcitationSignal(unsigned int maxTS)
|
||||||
|
@ -86,32 +101,26 @@ bool Excitation::buildExcitationSignal(unsigned int maxTS)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
double f0=0;
|
|
||||||
double fc=0;
|
|
||||||
switch (m_Excit_Type)
|
switch (m_Excit_Type)
|
||||||
{
|
{
|
||||||
case 0:
|
case Excitation::GaissianPulse:
|
||||||
m_Excite_Elem->QueryDoubleAttribute("f0",&f0);
|
CalcGaussianPulsExcitation(m_f0,m_fc,maxTS);
|
||||||
m_Excite_Elem->QueryDoubleAttribute("fc",&fc);
|
|
||||||
CalcGaussianPulsExcitation(f0,fc,maxTS);
|
|
||||||
break;
|
break;
|
||||||
case 1:
|
case Excitation::Sinusoidal:
|
||||||
m_Excite_Elem->QueryDoubleAttribute("f0",&f0);
|
CalcSinusExcitation(m_f0,maxTS);
|
||||||
CalcSinusExcitation(f0,maxTS);
|
|
||||||
break;
|
break;
|
||||||
case 2:
|
case Excitation::DiracPulse:
|
||||||
CalcDiracPulsExcitation();
|
CalcDiracPulsExcitation();
|
||||||
break;
|
break;
|
||||||
case 3:
|
case Excitation::Step:
|
||||||
CalcStepExcitation();
|
CalcStepExcitation();
|
||||||
break;
|
break;
|
||||||
case 10:
|
case Excitation::CustomExcite:
|
||||||
m_Excite_Elem->QueryDoubleAttribute("f0",&f0);
|
CalcCustomExcitation(m_f0,maxTS,m_CustomExc_Str);
|
||||||
CalcCustomExcitation(f0,maxTS,m_Excite_Elem->Attribute("Function"));
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
cerr << "Excitation::buildExcitationSignal: Unknown excitation type: \"" << m_Excit_Type<< "\" !!" << endl;
|
cerr << "Excitation::buildExcitationSignal: Unknown excitation type: \"" << m_Excit_Type<< "\" !!" << endl;
|
||||||
m_Excit_Type = -1;
|
m_Excit_Type = Excitation::UNDEFINED;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -22,17 +22,25 @@
|
||||||
#include <string>
|
#include <string>
|
||||||
#include "tools/constants.h"
|
#include "tools/constants.h"
|
||||||
|
|
||||||
class TiXmlElement;
|
|
||||||
|
|
||||||
class Excitation
|
class Excitation
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
enum ExciteTypes {UNDEFINED=-1, GaissianPulse=0, Sinusoidal=1, DiracPulse=2, Step=3, CustomExcite=10};
|
||||||
Excitation();
|
Excitation();
|
||||||
virtual ~Excitation();
|
virtual ~Excitation();
|
||||||
|
|
||||||
virtual void Reset( double timestep );
|
virtual void Reset( double timestep );
|
||||||
|
|
||||||
bool setupExcitation(TiXmlElement* Excite);
|
bool SetupGaussianPulse(double f0, double fc);
|
||||||
|
bool SetupSinusoidal(double f0);
|
||||||
|
bool SetupDiracPulse(double fmax);
|
||||||
|
bool SetupStepExcite(double fmax);
|
||||||
|
bool SetupCustomExcite(std::string str, double f0, double fmax);
|
||||||
|
|
||||||
|
double GetCenterFreq() {return m_f0;}
|
||||||
|
double GetCutOffFreq() {return m_fc;}
|
||||||
|
double GetMaxFreq() {return m_f_max;}
|
||||||
|
|
||||||
bool buildExcitationSignal(unsigned int maxTS);
|
bool buildExcitationSignal(unsigned int maxTS);
|
||||||
|
|
||||||
//! Get the excitation timestep with the (first) max amplitude
|
//! Get the excitation timestep with the (first) max amplitude
|
||||||
|
@ -72,15 +80,21 @@ protected:
|
||||||
double dT;
|
double dT;
|
||||||
unsigned int m_nyquistTS;
|
unsigned int m_nyquistTS;
|
||||||
double m_SignalPeriod;
|
double m_SignalPeriod;
|
||||||
int m_Excit_Type;
|
ExciteTypes m_Excit_Type;
|
||||||
|
|
||||||
TiXmlElement* m_Excite_Elem;
|
|
||||||
|
|
||||||
//Excitation time-signal
|
//Excitation time-signal
|
||||||
unsigned int Length;
|
unsigned int Length;
|
||||||
FDTD_FLOAT* Signal_volt;
|
FDTD_FLOAT* Signal_volt;
|
||||||
FDTD_FLOAT* Signal_curr;
|
FDTD_FLOAT* Signal_curr;
|
||||||
|
|
||||||
|
// center frequency
|
||||||
|
double m_f0;
|
||||||
|
|
||||||
|
// cutoff-frequency (Gaussian pulse only)
|
||||||
|
double m_fc;
|
||||||
|
|
||||||
|
std::string m_CustomExc_Str;
|
||||||
|
|
||||||
// max frequency
|
// max frequency
|
||||||
double m_f_max;
|
double m_f_max;
|
||||||
// frequency of interest
|
// frequency of interest
|
||||||
|
|
3
main.cpp
3
main.cpp
|
@ -101,7 +101,8 @@ int main(int argc, char *argv[])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int EC = FDTD.SetupFDTD(argv[1]);
|
int EC = FDTD.ParseFDTDSetup(argv[1]);
|
||||||
|
EC = FDTD.SetupFDTD();
|
||||||
if (EC) return EC;
|
if (EC) return EC;
|
||||||
FDTD.RunFDTD();
|
FDTD.RunFDTD();
|
||||||
|
|
||||||
|
|
305
openems.cpp
305
openems.cpp
|
@ -84,6 +84,18 @@ openEMS::openEMS()
|
||||||
|
|
||||||
m_Abort = false;
|
m_Abort = false;
|
||||||
m_Exc = 0;
|
m_Exc = 0;
|
||||||
|
|
||||||
|
m_TS_method=3;
|
||||||
|
m_TS=0;
|
||||||
|
m_TS_fac=1.0;
|
||||||
|
m_maxTime=0.0;
|
||||||
|
|
||||||
|
for (int n=0;n<6;++n)
|
||||||
|
{
|
||||||
|
m_BC_type[n] = 0;
|
||||||
|
m_PML_size[n] = 8;
|
||||||
|
m_Mur_v_ph[n] = 0;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
openEMS::~openEMS()
|
openEMS::~openEMS()
|
||||||
|
@ -233,78 +245,28 @@ string openEMS::GetExtLibsInfo()
|
||||||
return str.str();
|
return str.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool openEMS::SetupBoundaryConditions(TiXmlElement* BC)
|
bool openEMS::SetupBoundaryConditions()
|
||||||
{
|
{
|
||||||
int EC; //error code of tinyxml
|
FDTD_Op->SetBoundaryCondition(m_BC_type); //operator only knows about PEC and PMC, everything else is defined by extensions (see below)
|
||||||
int bounds[6] = {0,0,0,0,0,0}; //default boundary cond. (PEC)
|
|
||||||
unsigned int pml_size[6] = {8,8,8,8,8,8}; //default pml size
|
|
||||||
string s_bc;
|
|
||||||
const char* tmp = BC->Attribute("PML_Grading");
|
|
||||||
string pml_gradFunc;
|
|
||||||
if (tmp)
|
|
||||||
pml_gradFunc = string(tmp);
|
|
||||||
|
|
||||||
string bound_names[] = {"xmin","xmax","ymin","ymax","zmin","zmax"};
|
|
||||||
|
|
||||||
for (int n=0; n<6; ++n)
|
|
||||||
{
|
|
||||||
EC = BC->QueryIntAttribute(bound_names[n].c_str(),&bounds[n]);
|
|
||||||
if (EC==TIXML_SUCCESS)
|
|
||||||
continue;
|
|
||||||
if (EC==TIXML_WRONG_TYPE)
|
|
||||||
{
|
|
||||||
tmp = BC->Attribute(bound_names[n].c_str());
|
|
||||||
if (tmp)
|
|
||||||
s_bc = string(tmp);
|
|
||||||
if (s_bc=="PEC")
|
|
||||||
bounds[n] = 0;
|
|
||||||
else if (s_bc=="PMC")
|
|
||||||
bounds[n] = 1;
|
|
||||||
else if (s_bc=="MUR")
|
|
||||||
bounds[n] = 2;
|
|
||||||
else if (strncmp(s_bc.c_str(),"PML_=",4)==0)
|
|
||||||
{
|
|
||||||
bounds[n] = 3;
|
|
||||||
pml_size[n] = atoi(s_bc.c_str()+4);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
cerr << "openEMS::SetupBoundaryConditions: Warning, boundary condition for \"" << bound_names[n] << "\" unknown... set to PEC " << endl;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
cerr << "openEMS::SetupBoundaryConditions: Warning, boundary condition for \"" << bound_names[n] << "\" not found... set to PEC " << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
FDTD_Op->SetBoundaryCondition(bounds); //operator only knows about PEC and PMC, everything else is defined by extensions (see below)
|
|
||||||
|
|
||||||
/**************************** create all operator/engine extensions here !!!! **********************************/
|
/**************************** create all operator/engine extensions here !!!! **********************************/
|
||||||
//Mur-ABC, defined as extension to the operator
|
|
||||||
double mur_v_ph = 0;
|
|
||||||
//read general mur phase velocity
|
|
||||||
if (BC->QueryDoubleAttribute("MUR_PhaseVelocity",&mur_v_ph) != TIXML_SUCCESS)
|
|
||||||
mur_v_ph = -1;
|
|
||||||
string mur_v_ph_names[6] = {"MUR_PhaseVelocity_xmin", "MUR_PhaseVelocity_xmax", "MUR_PhaseVelocity_ymin", "MUR_PhaseVelocity_ymax", "MUR_PhaseVelocity_zmin", "MUR_PhaseVelocity_zmax"};
|
|
||||||
for (int n=0; n<6; ++n)
|
for (int n=0; n<6; ++n)
|
||||||
{
|
{
|
||||||
FDTD_Op->SetBCSize(n, 0);
|
FDTD_Op->SetBCSize(n, 0);
|
||||||
if (bounds[n]==2) //Mur-ABC
|
if (m_BC_type[n]==2) //Mur-ABC
|
||||||
{
|
{
|
||||||
FDTD_Op->SetBCSize(n, 1);
|
FDTD_Op->SetBCSize(n, 1);
|
||||||
Operator_Ext_Mur_ABC* op_ext_mur = new Operator_Ext_Mur_ABC(FDTD_Op);
|
Operator_Ext_Mur_ABC* op_ext_mur = new Operator_Ext_Mur_ABC(FDTD_Op);
|
||||||
op_ext_mur->SetDirection(n/2,n%2);
|
op_ext_mur->SetDirection(n/2,n%2);
|
||||||
double v_ph = 0;
|
op_ext_mur->SetPhaseVelocity(m_Mur_v_ph[n]);
|
||||||
//read special mur phase velocity or assign general phase velocity
|
|
||||||
if (BC->QueryDoubleAttribute(mur_v_ph_names[n].c_str(),&v_ph) == TIXML_SUCCESS)
|
|
||||||
op_ext_mur->SetPhaseVelocity(v_ph);
|
|
||||||
else if (mur_v_ph>0)
|
|
||||||
op_ext_mur->SetPhaseVelocity(mur_v_ph);
|
|
||||||
FDTD_Op->AddExtension(op_ext_mur);
|
FDTD_Op->AddExtension(op_ext_mur);
|
||||||
}
|
}
|
||||||
if (bounds[n]==3)
|
if (m_BC_type[n]==3)
|
||||||
FDTD_Op->SetBCSize(n, pml_size[n]);
|
FDTD_Op->SetBCSize(n, m_PML_size[n]);
|
||||||
}
|
}
|
||||||
|
|
||||||
//create the upml
|
//create the upml
|
||||||
Operator_Ext_UPML::Create_UPML(FDTD_Op,bounds,pml_size,pml_gradFunc);
|
Operator_Ext_UPML::Create_UPML(FDTD_Op, m_BC_type, m_PML_size, string());
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -556,15 +518,19 @@ bool openEMS::SetupMaterialStorages()
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool openEMS::SetupOperator(TiXmlElement* FDTD_Opts)
|
void openEMS::SetupCylinderMultiGrid(std::string val)
|
||||||
|
{
|
||||||
|
m_CC_MultiGrid.clear();
|
||||||
|
m_CC_MultiGrid = SplitString2Double(val,',');
|
||||||
|
}
|
||||||
|
|
||||||
|
bool openEMS::SetupOperator()
|
||||||
{
|
{
|
||||||
if (CylinderCoords)
|
if (CylinderCoords)
|
||||||
{
|
{
|
||||||
const char* radii = FDTD_Opts->Attribute("MultiGrid");
|
if (m_CC_MultiGrid.size()>0)
|
||||||
if (radii)
|
|
||||||
{
|
{
|
||||||
string rad(radii);
|
FDTD_Op = Operator_CylinderMultiGrid::New(m_CC_MultiGrid, m_engine_numThreads);
|
||||||
FDTD_Op = Operator_CylinderMultiGrid::New(SplitString2Double(rad,','),m_engine_numThreads);
|
|
||||||
if (FDTD_Op==NULL)
|
if (FDTD_Op==NULL)
|
||||||
FDTD_Op = Operator_Cylinder::New(m_engine_numThreads);
|
FDTD_Op = Operator_Cylinder::New(m_engine_numThreads);
|
||||||
}
|
}
|
||||||
|
@ -590,19 +556,35 @@ bool openEMS::SetupOperator(TiXmlElement* FDTD_Opts)
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void openEMS::Set_BC_Type(int idx, int type)
|
||||||
int openEMS::SetupFDTD(const char* file)
|
{
|
||||||
|
if ((idx<0) || (idx>5))
|
||||||
|
return;
|
||||||
|
m_BC_type[idx] = type;
|
||||||
|
}
|
||||||
|
|
||||||
|
void openEMS::Set_BC_PML(int idx, unsigned int size)
|
||||||
|
{
|
||||||
|
if ((idx<0) || (idx>5))
|
||||||
|
return;
|
||||||
|
m_BC_type[idx] = 3;
|
||||||
|
m_PML_size[idx] = size;
|
||||||
|
}
|
||||||
|
|
||||||
|
void openEMS::Set_Mur_PhaseVel(int idx, double val)
|
||||||
|
{
|
||||||
|
if ((idx<0) || (idx>5))
|
||||||
|
return;
|
||||||
|
m_Mur_v_ph[idx] = val;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool openEMS::ParseFDTDSetup(std::string file)
|
||||||
{
|
{
|
||||||
if (file==NULL) return -1;
|
|
||||||
Reset();
|
Reset();
|
||||||
|
|
||||||
if (g_settings.GetVerboseLevel()>0)
|
if (g_settings.GetVerboseLevel()>0)
|
||||||
cout << "Read openEMS xml file: " << file << " ..." << endl;
|
cout << "Read openEMS xml file: " << file << " ..." << endl;
|
||||||
|
|
||||||
timeval startTime;
|
|
||||||
gettimeofday(&startTime,NULL);
|
|
||||||
|
|
||||||
|
|
||||||
TiXmlDocument doc(file);
|
TiXmlDocument doc(file);
|
||||||
if (!doc.LoadFile())
|
if (!doc.LoadFile())
|
||||||
{
|
{
|
||||||
|
@ -629,22 +611,35 @@ int openEMS::SetupFDTD(const char* file)
|
||||||
double dhelp=0;
|
double dhelp=0;
|
||||||
FDTD_Opts->QueryDoubleAttribute("NumberOfTimesteps",&dhelp);
|
FDTD_Opts->QueryDoubleAttribute("NumberOfTimesteps",&dhelp);
|
||||||
if (dhelp<0)
|
if (dhelp<0)
|
||||||
NrTS=0;
|
this->SetNumberOfTimeSteps(0);
|
||||||
else
|
else
|
||||||
NrTS = (unsigned int)dhelp;
|
this->SetNumberOfTimeSteps((unsigned int)dhelp);
|
||||||
|
|
||||||
int ihelp = 0;
|
int ihelp = 0;
|
||||||
FDTD_Opts->QueryIntAttribute("CylinderCoords",&ihelp);
|
FDTD_Opts->QueryIntAttribute("CylinderCoords",&ihelp);
|
||||||
if (ihelp==1)
|
if (ihelp==1)
|
||||||
CylinderCoords = true;
|
this->SetCylinderCoords(true);
|
||||||
|
const char* cchelp = FDTD_Opts->Attribute("MultiGrid");
|
||||||
|
if (cchelp!=NULL)
|
||||||
|
this->SetupCylinderMultiGrid(string(cchelp));
|
||||||
|
|
||||||
FDTD_Opts->QueryDoubleAttribute("endCriteria",&endCrit);
|
dhelp = 0;
|
||||||
if (endCrit==0)
|
FDTD_Opts->QueryDoubleAttribute("endCriteria",&dhelp);
|
||||||
endCrit=1e-6;
|
if (dhelp==0)
|
||||||
|
this->SetEndCriteria(1e-6);
|
||||||
|
else
|
||||||
|
this->SetEndCriteria(dhelp);
|
||||||
|
|
||||||
FDTD_Opts->QueryIntAttribute("OverSampling",&m_OverSampling);
|
ihelp = 0;
|
||||||
if (m_OverSampling<2)
|
FDTD_Opts->QueryIntAttribute("OverSampling",&ihelp);
|
||||||
m_OverSampling=2;
|
if (ihelp<2)
|
||||||
|
this->SetOverSampling(2);
|
||||||
|
else
|
||||||
|
this->SetOverSampling(ihelp);
|
||||||
|
|
||||||
|
// check for cell constant material averaging
|
||||||
|
if (FDTD_Opts->QueryIntAttribute("CellConstantMaterial",&ihelp)==TIXML_SUCCESS)
|
||||||
|
this->SetCellConstantMaterial(ihelp==1);
|
||||||
|
|
||||||
TiXmlElement* BC = FDTD_Opts->FirstChildElement("BoundaryCond");
|
TiXmlElement* BC = FDTD_Opts->FirstChildElement("BoundaryCond");
|
||||||
if (BC==NULL)
|
if (BC==NULL)
|
||||||
|
@ -653,16 +648,122 @@ int openEMS::SetupFDTD(const char* file)
|
||||||
exit(-3);
|
exit(-3);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// const char* tmp = BC->Attribute("PML_Grading");
|
||||||
|
// string pml_gradFunc;
|
||||||
|
// if (tmp)
|
||||||
|
// pml_gradFunc = string(tmp);
|
||||||
|
|
||||||
|
string bound_names[] = {"xmin","xmax","ymin","ymax","zmin","zmax"};
|
||||||
|
|
||||||
|
for (int n=0; n<6; ++n)
|
||||||
|
{
|
||||||
|
int EC = BC->QueryIntAttribute(bound_names[n].c_str(),&ihelp);
|
||||||
|
if (EC==TIXML_SUCCESS)
|
||||||
|
this->Set_BC_Type(n, ihelp);
|
||||||
|
continue;
|
||||||
|
if (EC==TIXML_WRONG_TYPE)
|
||||||
|
{
|
||||||
|
string s_bc;
|
||||||
|
const char* tmp = BC->Attribute(bound_names[n].c_str());
|
||||||
|
if (tmp)
|
||||||
|
s_bc = string(tmp);
|
||||||
|
if (s_bc=="PEC")
|
||||||
|
this->Set_BC_Type(n, 0);
|
||||||
|
else if (s_bc=="PMC")
|
||||||
|
this->Set_BC_Type(n, 1);
|
||||||
|
else if (s_bc=="MUR")
|
||||||
|
this->Set_BC_Type(n, 2);
|
||||||
|
else if (strncmp(s_bc.c_str(),"PML_=",4)==0)
|
||||||
|
this->Set_BC_PML(n, atoi(s_bc.c_str()+4));
|
||||||
|
else
|
||||||
|
cerr << "openEMS::SetupBoundaryConditions: Warning, boundary condition for \"" << bound_names[n] << "\" unknown... set to PEC " << endl;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
cerr << "openEMS::SetupBoundaryConditions: Warning, boundary condition for \"" << bound_names[n] << "\" not found... set to PEC " << endl;
|
||||||
|
}
|
||||||
|
|
||||||
|
//read general mur phase velocity
|
||||||
|
if (BC->QueryDoubleAttribute("MUR_PhaseVelocity",&dhelp) != TIXML_SUCCESS)
|
||||||
|
for (int n=0;n<6;++n)
|
||||||
|
this->Set_Mur_PhaseVel(n, dhelp);
|
||||||
|
|
||||||
|
string mur_v_ph_names[6] = {"MUR_PhaseVelocity_xmin", "MUR_PhaseVelocity_xmax", "MUR_PhaseVelocity_ymin", "MUR_PhaseVelocity_ymax", "MUR_PhaseVelocity_zmin", "MUR_PhaseVelocity_zmax"};
|
||||||
|
for (int n=0; n<6; ++n)
|
||||||
|
if (BC->QueryDoubleAttribute(mur_v_ph_names[n].c_str(),&dhelp) == TIXML_SUCCESS)
|
||||||
|
this->Set_Mur_PhaseVel(n, dhelp);
|
||||||
|
|
||||||
if (g_settings.GetVerboseLevel()>0)
|
if (g_settings.GetVerboseLevel()>0)
|
||||||
cout << "Read Geometry..." << endl;
|
cout << "Read Geometry..." << endl;
|
||||||
m_CSX = new ContinuousStructure();
|
ContinuousStructure* csx = new ContinuousStructure();
|
||||||
string EC(m_CSX->ReadFromXML(openEMSxml));
|
string EC(csx->ReadFromXML(openEMSxml));
|
||||||
if (EC.empty()==false)
|
if (EC.empty()==false)
|
||||||
{
|
|
||||||
cerr << EC << endl;
|
cerr << EC << endl;
|
||||||
// return(-2);
|
this->SetCSX(csx);
|
||||||
|
|
||||||
|
TiXmlElement* m_Excite_Elem = FDTD_Opts->FirstChildElement("Excitation");
|
||||||
|
if (!m_Excite_Elem)
|
||||||
|
{
|
||||||
|
cerr << "Excitation::setupExcitation: Error, can't read openEMS excitation settings... " << endl;
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Excitation* exc = this->InitExcitation();
|
||||||
|
double f0=0, fc=0, f_max=0;
|
||||||
|
ihelp = -1;
|
||||||
|
m_Excite_Elem->QueryIntAttribute("Type",&ihelp);
|
||||||
|
switch (ihelp)
|
||||||
|
{
|
||||||
|
case Excitation::GaissianPulse:
|
||||||
|
m_Excite_Elem->QueryDoubleAttribute("f0",&f0);
|
||||||
|
m_Excite_Elem->QueryDoubleAttribute("fc",&fc);
|
||||||
|
exc->SetupGaussianPulse(f0, fc);
|
||||||
|
break;
|
||||||
|
case Excitation::Sinusoidal: // sinusoidal excite
|
||||||
|
m_Excite_Elem->QueryDoubleAttribute("f0",&f0);
|
||||||
|
exc->SetupSinusoidal(f0);
|
||||||
|
break;
|
||||||
|
case Excitation::DiracPulse:
|
||||||
|
FDTD_Opts->QueryDoubleAttribute("f_max",&f_max);
|
||||||
|
exc->SetupDiracPulse(f_max);
|
||||||
|
break;
|
||||||
|
case Excitation::Step:
|
||||||
|
FDTD_Opts->QueryDoubleAttribute("f_max",&f_max);
|
||||||
|
exc->SetupStepExcite(f_max);
|
||||||
|
break;
|
||||||
|
case Excitation::CustomExcite:
|
||||||
|
m_Excite_Elem->QueryDoubleAttribute("f0",&f0);
|
||||||
|
FDTD_Opts->QueryDoubleAttribute("f_max",&f_max);
|
||||||
|
exc->SetupCustomExcite(m_Excite_Elem->Attribute("Function"), f0, f_max);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (FDTD_Opts->QueryIntAttribute("TimeStepMethod",&ihelp)==TIXML_SUCCESS)
|
||||||
|
this->SetTimeStepMethod(ihelp);
|
||||||
|
if (FDTD_Opts->QueryDoubleAttribute("TimeStep",&dhelp)==TIXML_SUCCESS)
|
||||||
|
this->SetTimeStep(dhelp);
|
||||||
|
if (FDTD_Opts->QueryDoubleAttribute("TimeStepFactor",&dhelp)==TIXML_SUCCESS)
|
||||||
|
this->SetTimeStepFactor(dhelp);
|
||||||
|
}
|
||||||
|
|
||||||
|
Excitation* openEMS::InitExcitation()
|
||||||
|
{
|
||||||
|
delete m_Exc;
|
||||||
|
m_Exc = new Excitation();
|
||||||
|
return m_Exc;
|
||||||
|
}
|
||||||
|
|
||||||
|
void openEMS::SetCSX(ContinuousStructure* csx)
|
||||||
|
{
|
||||||
|
delete m_CSX;
|
||||||
|
m_CSX = csx;
|
||||||
|
}
|
||||||
|
|
||||||
|
int openEMS::SetupFDTD()
|
||||||
|
{
|
||||||
|
|
||||||
|
timeval startTime;
|
||||||
|
gettimeofday(&startTime,NULL);
|
||||||
|
|
||||||
if (g_settings.GetVerboseLevel()>2)
|
if (g_settings.GetVerboseLevel()>2)
|
||||||
m_CSX->ShowPropertyStatus(cerr);
|
m_CSX->ShowPropertyStatus(cerr);
|
||||||
|
|
||||||
|
@ -677,15 +778,12 @@ int openEMS::SetupFDTD(const char* file)
|
||||||
m_CSX->Write2XML("debugCSX.xml");
|
m_CSX->Write2XML("debugCSX.xml");
|
||||||
|
|
||||||
//*************** setup operator ************//
|
//*************** setup operator ************//
|
||||||
if (SetupOperator(FDTD_Opts)==false)
|
if (SetupOperator()==false)
|
||||||
return 2;
|
return 2;
|
||||||
|
|
||||||
// default material averaging is quarter cell averaging
|
// default material averaging is quarter cell averaging
|
||||||
FDTD_Op->SetQuarterCellMaterialAvg();
|
FDTD_Op->SetQuarterCellMaterialAvg();
|
||||||
|
|
||||||
// check for cell constant material averaging
|
|
||||||
if (FDTD_Opts->QueryIntAttribute("CellConstantMaterial",&ihelp)==TIXML_SUCCESS)
|
|
||||||
m_CellConstantMaterial=(ihelp==1);
|
|
||||||
if (m_CellConstantMaterial)
|
if (m_CellConstantMaterial)
|
||||||
{
|
{
|
||||||
FDTD_Op->SetCellConstantMaterial();
|
FDTD_Op->SetCellConstantMaterial();
|
||||||
|
@ -693,9 +791,6 @@ int openEMS::SetupFDTD(const char* file)
|
||||||
cout << "Enabling constant cell material assumption." << endl;
|
cout << "Enabling constant cell material assumption." << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
m_Exc = new Excitation();
|
|
||||||
if (!m_Exc->setupExcitation(FDTD_Opts->FirstChildElement("Excitation")))
|
|
||||||
exit(2);
|
|
||||||
FDTD_Op->SetExcitationSignal(m_Exc);
|
FDTD_Op->SetExcitationSignal(m_Exc);
|
||||||
FDTD_Op->AddExtension(new Operator_Ext_Excitation(FDTD_Op));
|
FDTD_Op->AddExtension(new Operator_Ext_Excitation(FDTD_Op));
|
||||||
if (!CylinderCoords)
|
if (!CylinderCoords)
|
||||||
|
@ -703,19 +798,14 @@ int openEMS::SetupFDTD(const char* file)
|
||||||
|
|
||||||
if (FDTD_Op->SetGeometryCSX(m_CSX)==false) return(2);
|
if (FDTD_Op->SetGeometryCSX(m_CSX)==false) return(2);
|
||||||
|
|
||||||
SetupBoundaryConditions(BC);
|
SetupBoundaryConditions();
|
||||||
|
|
||||||
int TS_method=0;
|
FDTD_Op->SetTimeStepMethod(m_TS_method);
|
||||||
if (FDTD_Opts->QueryIntAttribute("TimeStepMethod",&TS_method)==TIXML_SUCCESS)
|
|
||||||
FDTD_Op->SetTimeStepMethod(TS_method);
|
|
||||||
|
|
||||||
double timestep=0;
|
if (m_TS>0)
|
||||||
FDTD_Opts->QueryDoubleAttribute("TimeStep",×tep);
|
FDTD_Op->SetTimestep(m_TS);
|
||||||
if (timestep)
|
if (m_TS_fac<1)
|
||||||
FDTD_Op->SetTimestep(timestep);
|
FDTD_Op->SetTimestepFactor(m_TS_fac);
|
||||||
double timestepfactor=0;
|
|
||||||
if (FDTD_Opts->QueryDoubleAttribute("TimeStepFactor",×tepfactor)==TIXML_SUCCESS)
|
|
||||||
FDTD_Op->SetTimestepFactor(timestepfactor);
|
|
||||||
|
|
||||||
// Is a steady state detection requested
|
// Is a steady state detection requested
|
||||||
Operator_Ext_SteadyState* Op_Ext_SSD = NULL;
|
Operator_Ext_SteadyState* Op_Ext_SSD = NULL;
|
||||||
|
@ -751,14 +841,7 @@ int openEMS::SetupFDTD(const char* file)
|
||||||
if ((m_CSX->GetQtyPropertyType(CSProperties::LORENTZMATERIAL)>0) || (m_CSX->GetQtyPropertyType(CSProperties::DEBYEMATERIAL)>0))
|
if ((m_CSX->GetQtyPropertyType(CSProperties::LORENTZMATERIAL)>0) || (m_CSX->GetQtyPropertyType(CSProperties::DEBYEMATERIAL)>0))
|
||||||
FDTD_Op->AddExtension(new Operator_Ext_LorentzMaterial(FDTD_Op));
|
FDTD_Op->AddExtension(new Operator_Ext_LorentzMaterial(FDTD_Op));
|
||||||
if (m_CSX->GetQtyPropertyType(CSProperties::CONDUCTINGSHEET)>0)
|
if (m_CSX->GetQtyPropertyType(CSProperties::CONDUCTINGSHEET)>0)
|
||||||
{
|
FDTD_Op->AddExtension(new Operator_Ext_ConductingSheet(FDTD_Op, m_Exc->GetMaxFreq()));
|
||||||
double f_max=0;
|
|
||||||
FDTD_Opts->QueryDoubleAttribute("f_max",&f_max);
|
|
||||||
if (f_max>0)
|
|
||||||
FDTD_Op->AddExtension(new Operator_Ext_ConductingSheet(FDTD_Op,f_max));
|
|
||||||
else
|
|
||||||
cerr << __func__ << ": Error, max. frequency is <=0, disabling conducting sheet material..." << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
//check all properties to request material storage during operator creation...
|
//check all properties to request material storage during operator creation...
|
||||||
SetupMaterialStorages();
|
SetupMaterialStorages();
|
||||||
|
@ -781,10 +864,8 @@ int openEMS::SetupFDTD(const char* file)
|
||||||
FDTD_Op->SetMaterialStoreFlags(2,false);
|
FDTD_Op->SetMaterialStoreFlags(2,false);
|
||||||
FDTD_Op->SetMaterialStoreFlags(3,false);
|
FDTD_Op->SetMaterialStoreFlags(3,false);
|
||||||
|
|
||||||
double maxTime=0;
|
unsigned int maxTime_TS = (unsigned int)(m_maxTime/FDTD_Op->GetTimestep());
|
||||||
FDTD_Opts->QueryDoubleAttribute("MaxTime",&maxTime);
|
if ((m_maxTime>0) && (maxTime_TS<NrTS))
|
||||||
unsigned int maxTime_TS = (unsigned int)(maxTime/FDTD_Op->GetTimestep());
|
|
||||||
if ((maxTime_TS>0) && (maxTime_TS<NrTS))
|
|
||||||
NrTS = maxTime_TS;
|
NrTS = maxTime_TS;
|
||||||
|
|
||||||
if (!m_Exc->buildExcitationSignal(NrTS))
|
if (!m_Exc->buildExcitationSignal(NrTS))
|
||||||
|
|
37
openems.h
37
openems.h
|
@ -21,6 +21,7 @@
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
#include <sys/time.h>
|
#include <sys/time.h>
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
#define __OPENEMS_STAT_FILE__ "openEMS_stats.txt"
|
#define __OPENEMS_STAT_FILE__ "openEMS_stats.txt"
|
||||||
#define __OPENEMS_RUN_STAT_FILE__ "openEMS_run_stats.txt"
|
#define __OPENEMS_RUN_STAT_FILE__ "openEMS_run_stats.txt"
|
||||||
|
@ -46,19 +47,35 @@ public:
|
||||||
|
|
||||||
virtual bool parseCommandLineArgument( const char *argv );
|
virtual bool parseCommandLineArgument( const char *argv );
|
||||||
|
|
||||||
int SetupFDTD(const char* file);
|
bool ParseFDTDSetup(std::string file);
|
||||||
|
int SetupFDTD();
|
||||||
virtual void RunFDTD();
|
virtual void RunFDTD();
|
||||||
|
|
||||||
void Reset();
|
void Reset();
|
||||||
|
|
||||||
|
void SetNumberOfTimeSteps(unsigned int val) {NrTS=val;}
|
||||||
void SetEnableDumps(bool val) {Enable_Dumps=val;}
|
void SetEnableDumps(bool val) {Enable_Dumps=val;}
|
||||||
void SetEndCriteria(double val) {endCrit=val;}
|
void SetEndCriteria(double val) {endCrit=val;}
|
||||||
|
void SetOverSampling(int val) {m_OverSampling=val;}
|
||||||
|
void SetCellConstantMaterial(bool val) {m_CellConstantMaterial=val;}
|
||||||
|
|
||||||
|
void SetCylinderCoords(bool val) {CylinderCoords=val;}
|
||||||
|
void SetupCylinderMultiGrid(std::vector<double> val) {m_CC_MultiGrid=val;}
|
||||||
|
void SetupCylinderMultiGrid(std::string val);
|
||||||
|
|
||||||
|
void SetTimeStepMethod(int val) {m_TS_method=val;}
|
||||||
|
void SetTimeStep(double val) {m_TS=val;}
|
||||||
|
void SetTimeStepFactor(double val) {m_TS_fac=val;}
|
||||||
|
void SetMaxTime(double val) {m_maxTime=val;}
|
||||||
|
|
||||||
void DebugMaterial() {DebugMat=true;}
|
void DebugMaterial() {DebugMat=true;}
|
||||||
void DebugOperator() {DebugOp=true;}
|
void DebugOperator() {DebugOp=true;}
|
||||||
void DebugBox() {m_debugBox=true;}
|
void DebugBox() {m_debugBox=true;}
|
||||||
|
|
||||||
|
void Set_BC_Type(int idx, int type);
|
||||||
|
void Set_BC_PML(int idx, unsigned int size);
|
||||||
|
void Set_Mur_PhaseVel(int idx, double val);
|
||||||
|
|
||||||
//! Get informations about external libs used by openEMS
|
//! Get informations about external libs used by openEMS
|
||||||
static std::string GetExtLibsInfo();
|
static std::string GetExtLibsInfo();
|
||||||
|
|
||||||
|
@ -67,15 +84,24 @@ public:
|
||||||
//! Check for abort conditions
|
//! Check for abort conditions
|
||||||
bool CheckAbortCond();
|
bool CheckAbortCond();
|
||||||
|
|
||||||
|
Excitation* InitExcitation();
|
||||||
|
|
||||||
|
void SetCSX(ContinuousStructure* csx);
|
||||||
|
|
||||||
Engine_Interface_FDTD* NewEngineInterface(int multigridlevel = 0);
|
Engine_Interface_FDTD* NewEngineInterface(int multigridlevel = 0);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
bool CylinderCoords;
|
bool CylinderCoords;
|
||||||
|
std::vector<double> m_CC_MultiGrid;
|
||||||
|
|
||||||
ContinuousStructure* m_CSX;
|
ContinuousStructure* m_CSX;
|
||||||
|
|
||||||
//! Number of Timesteps
|
//! Number of Timesteps
|
||||||
unsigned int NrTS;
|
unsigned int NrTS;
|
||||||
|
int m_TS_method;
|
||||||
|
double m_TS;
|
||||||
|
double m_TS_fac;
|
||||||
|
double m_maxTime;
|
||||||
|
|
||||||
// some command line flags
|
// some command line flags
|
||||||
bool Enable_Dumps;
|
bool Enable_Dumps;
|
||||||
|
@ -106,10 +132,13 @@ protected:
|
||||||
unsigned int m_engine_numThreads;
|
unsigned int m_engine_numThreads;
|
||||||
|
|
||||||
//! Setup an operator matching the requested engine
|
//! Setup an operator matching the requested engine
|
||||||
virtual bool SetupOperator(TiXmlElement* FDTD_Opts);
|
virtual bool SetupOperator();
|
||||||
|
|
||||||
//! Read boundary conditions from xml element and apply to FDTD operator
|
//! Read boundary conditions from xml element and apply to FDTD operator
|
||||||
bool SetupBoundaryConditions(TiXmlElement* BC);
|
bool SetupBoundaryConditions();
|
||||||
|
int m_BC_type[6];
|
||||||
|
unsigned int m_PML_size[6];
|
||||||
|
double m_Mur_v_ph[6];
|
||||||
|
|
||||||
//! Check whether or not the FDTD-Operator has to store material data.
|
//! Check whether or not the FDTD-Operator has to store material data.
|
||||||
bool SetupMaterialStorages();
|
bool SetupMaterialStorages();
|
||||||
|
|
Loading…
Reference in New Issue