Skip to content

Commit

Permalink
Background Fields: Fix Restart GUARD
Browse files Browse the repository at this point in the history
Simplify the logic of restarting fields:
- do not add the already contained fields in
  `movingWindowCheck` again
- spares us the substraction we had before
- GUARDS are not part of the checkpoint data,
  which is cumbersome for the "outer" GUARDS
  of our global domain
- we need to add the background field ONLY in those
  to generate a valid restart field
  • Loading branch information
ax3l committed Jul 17, 2017
1 parent ad39d1a commit 494865e
Show file tree
Hide file tree
Showing 2 changed files with 50 additions and 37 deletions.
81 changes: 47 additions & 34 deletions include/picongpu/simulationControl/MySimulation.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -421,6 +421,10 @@ class MySimulation : public SimulationHelper<simDim>
GridController<simDim> &gc = Environment<simDim>::get().GridController();
gc.setStateAfterSlides(0);

DataConnector &dc = Environment<>::get().DataConnector();
auto fieldE = dc.get< FieldE >( FieldE::getName(), true );
auto fieldB = dc.get< FieldB >( FieldB::getName(), true );

/* fill all objects registed in DataConnector */
if (initialiserController)
{
Expand All @@ -442,6 +446,20 @@ class MySimulation : public SimulationHelper<simDim>

initialiserController->restart((uint32_t)this->restartStep, this->restartDirectory);
step = this->restartStep;

/** restore background fields in GUARD
*
* loads the outer GUARDS of the global domain for absorbing/open boundary condtions
*
* @todo as soon as we add GUARD fields to the checkpoint data, e.g. for PML boundary
* conditions, this section needs to be removed
*/
cellwiseOperation::CellwiseOperation< GUARD > guardBGField( *cellDescription );
namespace nvfct = pmacc::nvidia::functors;
guardBGField( fieldE, nvfct::Add(), FieldBackgroundE( fieldE->getUnit() ),
step, FieldBackgroundE::InfluenceParticlePusher );
guardBGField( fieldB, nvfct::Add(), FieldBackgroundB( fieldB->getUnit() ),
step, FieldBackgroundB::InfluenceParticlePusher );
}
else
{
Expand All @@ -455,25 +473,7 @@ class MySimulation : public SimulationHelper<simDim>
Environment<>::get().MemoryInfo().getMemoryInfo(&freeGpuMem);
log<picLog::MEMORY > ("free mem after all particles are initialized %1% MiB") % (freeGpuMem / 1024 / 1024);

/** a background field for the particle pusher might be added at the
beginning of a simulation in movingWindowCheck()
At restarts the external fields are already added and will be
double-counted, so we remove it in advance. */
DataConnector &dc = Environment<>::get().DataConnector();
auto fieldE = dc.get< FieldE >( FieldE::getName(), true );
auto fieldB = dc.get< FieldB >( FieldB::getName(), true );

if( this->restartRequested )
{
namespace nvfct = pmacc::nvidia::functors;

(*pushBGField)( fieldE, nvfct::Sub(), FieldBackgroundE(fieldE->getUnit()),
step, FieldBackgroundE::InfluenceParticlePusher);
(*pushBGField)( fieldB, nvfct::Sub(), FieldBackgroundB(fieldB->getUnit()),
step, FieldBackgroundB::InfluenceParticlePusher);
}

// communicate all fields
// generate valid GUARDS (overwrite)
EventTask eRfieldE = fieldE->asyncCommunication(__getTransactionEvent());
__setTransactionEvent(eRfieldE);
EventTask eRfieldB = fieldB->asyncCommunication(__getTransactionEvent());
Expand Down Expand Up @@ -648,26 +648,39 @@ class MySimulation : public SimulationHelper<simDim>
slide(currentStep);
}

/** add background field: the movingWindowCheck is just at the start
* of a time step before all the plugins are called (and the step
* itself is performed for this time step).
* Hence the background field is visible for all plugins
* in between the time steps.
/* do not double-add background field on restarts
* (contained in checkpoint data)
*/
namespace nvfct = pmacc::nvidia::functors;
bool addBgFields = true;
if( this->restartRequested )
{
if( this->restartStep == int32_t(currentStep) )
addBgFields = false;
}

DataConnector &dc = Environment<>::get().DataConnector();
if( addBgFields )
{
/** add background field: the movingWindowCheck is just at the start
* of a time step before all the plugins are called (and the step
* itself is performed for this time step).
* Hence the background field is visible for all plugins
* in between the time steps.
*/
namespace nvfct = pmacc::nvidia::functors;

auto fieldE = dc.get< FieldE >( FieldE::getName(), true );
auto fieldB = dc.get< FieldB >( FieldB::getName(), true );
DataConnector &dc = Environment<>::get().DataConnector();

(*pushBGField)( fieldE, nvfct::Add(), FieldBackgroundE(fieldE->getUnit()),
currentStep, FieldBackgroundE::InfluenceParticlePusher );
(*pushBGField)( fieldB, nvfct::Add(), FieldBackgroundB(fieldB->getUnit()),
currentStep, FieldBackgroundB::InfluenceParticlePusher );
auto fieldE = dc.get< FieldE >( FieldE::getName(), true );
auto fieldB = dc.get< FieldB >( FieldB::getName(), true );

dc.releaseData( FieldE::getName() );
dc.releaseData( FieldB::getName() );
(*pushBGField)( fieldE, nvfct::Add(), FieldBackgroundE(fieldE->getUnit()),
currentStep, FieldBackgroundE::InfluenceParticlePusher );
(*pushBGField)( fieldB, nvfct::Add(), FieldBackgroundB(fieldB->getUnit()),
currentStep, FieldBackgroundB::InfluenceParticlePusher );

dc.releaseData( FieldE::getName() );
dc.releaseData( FieldB::getName() );
}
}

virtual void resetAll(uint32_t currentStep)
Expand Down
6 changes: 3 additions & 3 deletions include/pmacc/simulationControl/SimulationHelper.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -231,7 +231,6 @@ class SimulationHelper : public IPlugin
TimeIntervall tSimCalculation;
TimeIntervall tRound;
double roundAvg = 0.0;
Environment<>::get().SimulationDescription().setCurrentStep( currentStep );

/* Since in the main loop movingWindow is called always before the dump, we also call it here for consistency.
* This becomes only important, if movingWindowCheck does more than merely checking for a slide.
Expand Down Expand Up @@ -261,13 +260,14 @@ class SimulationHelper : public IPlugin
tRound.toggleEnd();
roundAvg += tRound.getInterval();

/* NEXT TIMESTEP STARTS HERE */
currentStep++;
Environment<>::get().SimulationDescription().setCurrentStep( currentStep );
/*output after a round*/
/* output times after a round */
dumpTimes(tSimCalculation, tRound, roundAvg, currentStep);

movingWindowCheck(currentStep);
/*dump after simulated step*/
/* dump at the beginning of the simulated step */
dumpOneStep(currentStep);
}

Expand Down

0 comments on commit 494865e

Please sign in to comment.