40#include <boost/format.hpp> 
   78    NekDouble totalTime = 0.0, predictorTime = 0.0, fineSolveTime = 0.0,
 
   79              coarseSolveTime = 0.0, fasTime = 0.0;
 
   88    m_comm->GetTimeComm()->Block();
 
  108        for (
size_t timeLevel = 
m_nTimeLevel - 1; timeLevel > 0; timeLevel--)
 
  114        predictorTime += timer.
Elapsed().count();
 
  115        totalTime += timer.
Elapsed().count();
 
  119        int convergenceCurr = 0;
 
  129                m_comm->GetSpaceComm()->GetRank() == 0)
 
  131                std::cout << 
"Iteration " << k + 1 << std::endl << std::flush;
 
  138            fineSolveTime += timer.
Elapsed().count();
 
  139            totalTime += timer.
Elapsed().count();
 
  143            for (
size_t timeLevel = 0; timeLevel < 
m_nTimeLevel - 1;
 
  170            fasTime += timer.
Elapsed().count();
 
  171            totalTime += timer.
Elapsed().count();
 
  176                                     ->UpdateFirstQuadratureSolutionVector(),
 
  179            totalTime += timer.
Elapsed().count();
 
  183            coarseSolveTime += timer.
Elapsed().count();
 
  184            totalTime += timer.
Elapsed().count();
 
  189                               ->UpdateLastQuadratureSolutionVector(),
 
  192            totalTime += timer.
Elapsed().count();
 
  196            for (
size_t timeLevel = 
m_nTimeLevel - 1; timeLevel > 0;
 
  210                if (timeLevel - 1 != 0)
 
  216            fasTime += timer.
Elapsed().count();
 
  217            totalTime += timer.
Elapsed().count();
 
  228        totalTime += timer.
Elapsed().count();
 
  233            m_comm->GetSpaceComm()->GetRank() == 0)
 
  235            std::cout << 
"Total Computation Time : " << totalTime << 
"s" 
  238            std::cout << 
" - Predictor Time = " << predictorTime << 
"s" 
  241            std::cout << 
" - Coarse Solve Time = " << coarseSolveTime << 
"s" 
  244            std::cout << 
" - Fine Solve Time = " << fineSolveTime << 
"s" 
  247            std::cout << 
" - FAS Correction Time = " << fasTime << 
"s" 
  254    m_comm->GetTimeComm()->Block();
 
  259        m_comm->GetSpaceComm()->GetRank() == 0)
 
  261        std::cout << 
"Total Computation Time : " << totalTime << 
"s" 
  264        std::cout << 
" - Predictor Time = " << predictorTime << 
"s" << std::endl
 
  266        std::cout << 
" - Coarse Solve Time = " << coarseSolveTime << 
"s" 
  269        std::cout << 
" - Fine Solve Time = " << fineSolveTime << 
"s" 
  272        std::cout << 
" - FAS Correction Time = " << fasTime << 
"s" << std::endl
 
  283    for (
size_t timeLevel = 0; timeLevel < 
m_nTimeLevel; timeLevel++)
 
  287            "Total number of steps should be divisible by number of chunks.");
 
  290                 "All SDC levels should have the same timestep");
 
  293                 "All SDC levels should have the same timestep");
 
  297    if (
m_EqSys[0]->GetCheckpointSteps())
 
  300                 "number of IO_CheckSteps should divide number of steps " 
  304    if (
m_EqSys[0]->GetInfoSteps())
 
  307                 "number of IO_InfoSteps should divide number of steps " 
  320    for (
size_t timeLevel = 0; timeLevel < 
m_nTimeLevel; timeLevel++)
 
  324            std::dynamic_pointer_cast<LibUtilities::TimeIntegrationSchemeSDC>(
 
  325                m_EqSys[timeLevel]->GetTimeIntegrationScheme());
 
  329                 "Should only be run with a SDC method");
 
  333        for (
size_t i = 0; i < 
m_nVar; ++i)
 
  335            fields[i] = 
m_EqSys[timeLevel]->UpdatePhysField(i);
 
  342            m_EqSys[timeLevel]->GetTimeIntegrationSchemeOperators());
 
  347    for (
size_t timeLevel = 0; timeLevel < 
m_nTimeLevel; timeLevel++)
 
  357    for (
size_t timeLevel = 0; timeLevel < 
m_nTimeLevel - 1; timeLevel++)
 
  364        for (
size_t n = 0; n < 
m_QuadPts[timeLevel + 1]; ++n)
 
  376            for (
size_t i = 0; i < 
m_nVar; ++i)
 
  401    for (
size_t timeLevel = 0; timeLevel < 
m_nTimeLevel - 1; timeLevel++)
 
  417        size_t i0 = 
m_SDCSolver[timeLevel]->HasFirstQuadrature() ? 0 : 1;
 
  418        size_t j0 = 
m_SDCSolver[timeLevel + 1]->HasFirstQuadrature() ? 0 : 1;
 
  421        for (
size_t i = i0; i < 
m_QuadPts[timeLevel]; ++i)
 
  423            for (
size_t j = j0; j < 
m_QuadPts[timeLevel + 1]; ++j)
 
  426                    (ImatFtoC->GetPtr())[(i - i0) *
 
  437        for (
size_t j = j0; j < 
m_QuadPts[timeLevel + 1]; ++j)
 
  439            for (
size_t i = i0; i < 
m_QuadPts[timeLevel]; ++i)
 
  443                         ->GetPtr())[(j - j0) * (
m_QuadPts[timeLevel] - i0) +
 
  466    const size_t timeLevel, 
const size_t index)
 
  468    for (
size_t n = 0; n < 
m_QuadPts[timeLevel]; ++n)
 
  472            for (
size_t i = 0; i < 
m_nVar; ++i)
 
  476                    m_SDCSolver[timeLevel]->GetSolutionVector()[index][i], 1,
 
  477                    m_SDCSolver[timeLevel]->UpdateSolutionVector()[n][i], 1);
 
  480                    m_SDCSolver[timeLevel]->GetResidualVector()[index][i], 1,
 
  481                    m_SDCSolver[timeLevel]->UpdateResidualVector()[n][i], 1);
 
  510    for (
size_t k = 0; k < niter; k++)
 
  550                               const size_t fineLevel, 
SDCarray &out,
 
  554    for (
size_t n = 0; n < 
m_QuadPts[coarseLevel]; ++n)
 
  557                    m_EqSys[fineLevel]->UpdateFields(), in[n],
 
  562    for (
size_t n = 0; n < 
m_QuadPts[fineLevel]; ++n)
 
  566            for (
size_t i = 0; i < 
m_nVar; ++i)
 
  569                            m_storage[fineLevel][0][i], 1, out[n][i], 1);
 
  570                for (
size_t k = 1; k < 
m_QuadPts[coarseLevel]; ++k)
 
  572                    size_t index = k * 
m_QuadPts[fineLevel] + n;
 
  575                                 m_storage[fineLevel][k][i], 1, out[n][i], 1,
 
  588    size_t coarseLevel = timeLevel;
 
  589    size_t fineLevel   = timeLevel - 1;
 
  592                fineLevel, 
m_SDCSolver[fineLevel]->UpdateSolutionVector(),
 
  601    size_t coarseLevel = timeLevel;
 
  602    size_t fineLevel   = timeLevel - 1;
 
  605                fineLevel, 
m_SDCSolver[fineLevel]->UpdateResidualVector(),
 
  613                            const size_t coarseLevel, 
SDCarray &out)
 
  616    for (
size_t n = 0; n < 
m_QuadPts[coarseLevel]; ++n)
 
  618        for (
size_t i = 0; i < 
m_nVar; ++i)
 
  622            for (
size_t k = 1; k < 
m_QuadPts[fineLevel]; ++k)
 
  624                size_t index = k * 
m_QuadPts[coarseLevel] + n;
 
  626                             in[k][i], 1, 
m_storage[fineLevel][n][i], 1,
 
  633    for (
size_t n = 0; n < 
m_QuadPts[coarseLevel]; ++n)
 
  636                    m_EqSys[coarseLevel]->UpdateFields(),
 
  646    size_t fineLevel   = timeLevel;
 
  647    size_t coarseLevel = timeLevel + 1;
 
  650             coarseLevel, 
m_SDCSolver[coarseLevel]->UpdateSolutionVector());
 
  652    for (
size_t n = 0; n < 
m_QuadPts[coarseLevel]; ++n)
 
  664    size_t fineLevel   = timeLevel;
 
  665    size_t coarseLevel = timeLevel + 1;
 
  671        for (
size_t n = 0; n < 
m_QuadPts[coarseLevel]; ++n)
 
  684    size_t fineLevel   = timeLevel - 1;
 
  685    size_t coarseLevel = timeLevel;
 
  692                 m_SDCSolver[coarseLevel]->UpdateFAScorrectionVector());
 
  696                 m_SDCSolver[fineLevel]->GetIntegratedResidualVector(),
 
  703            fineLevel, 
m_SDCSolver[fineLevel]->GetIntegratedResidualVector(),
 
  704            coarseLevel, 
m_SDCSolver[coarseLevel]->UpdateFAScorrectionVector());
 
  708    for (
size_t n = 0; n < 
m_QuadPts[coarseLevel]; ++n)
 
  710        for (
size_t i = 0; i < 
m_nVar; ++i)
 
  716                    m_SDCSolver[coarseLevel]->GetFAScorrectionVector()[n][i], 1,
 
  718                    m_SDCSolver[coarseLevel]->UpdateFAScorrectionVector()[n][i],
 
  724                m_SDCSolver[coarseLevel]->GetFAScorrectionVector()[n][i], 1,
 
  725                m_SDCSolver[coarseLevel]->GetIntegratedResidualVector()[n][i],
 
  726                1, 
m_SDCSolver[coarseLevel]->UpdateFAScorrectionVector()[n][i],
 
  737                           const size_t fineLevel,
 
  746                    m_EqSys[coarseLevel]->UpdateFields(), out,
 
  748        for (
size_t i = 0; i < 
m_nVar; ++i)
 
  757                    m_EqSys[fineLevel]->UpdateFields(),
 
  759        for (
size_t i = 0; i < 
m_nVar; ++i)
 
  762                        out[i], 1, out[i], 1);
 
  772    size_t fineLevel   = timeLevel;
 
  773    size_t coarseLevel = timeLevel + 1;
 
  776            fineLevel, 
m_SDCSolver[fineLevel]->UpdateSolutionVector()[0],
 
  785    size_t fineLevel   = timeLevel;
 
  786    size_t coarseLevel = timeLevel + 1;
 
  789            fineLevel, 
m_SDCSolver[fineLevel]->UpdateResidualVector()[0],
 
  797                           const SDCarray &in, 
const size_t fineLevel,
 
  802    for (
size_t n = 0; n < 
m_QuadPts[coarseLevel]; ++n)
 
  806            for (
size_t i = 0; i < 
m_nVar; ++i)
 
  814            for (
size_t i = 0; i < 
m_nVar; ++i)
 
  823    for (
size_t n = 0; n < 
m_QuadPts[coarseLevel]; ++n)
 
  826                    m_EqSys[fineLevel]->UpdateFields(),
 
  831    for (
size_t n = 0; n < 
m_QuadPts[fineLevel]; ++n)
 
  835            for (
size_t i = 0; i < 
m_nVar; ++i)
 
  837                for (
size_t k = 0; k < 
m_QuadPts[coarseLevel]; ++k)
 
  839                    size_t index = k * 
m_QuadPts[fineLevel] + n;
 
  842                                 m_storage[fineLevel][k][i], 1, out[n][i], 1,
 
  855    size_t coarseLevel = timeLevel + 1;
 
  856    size_t fineLevel   = timeLevel;
 
  859            m_SDCSolver[coarseLevel]->GetSolutionVector(), fineLevel,
 
  860            m_SDCSolver[fineLevel]->UpdateSolutionVector(), 
false);
 
  868    size_t coarseLevel = timeLevel + 1;
 
  869    size_t fineLevel   = timeLevel;
 
  874        for (
size_t n = 1; n < 
m_QuadPts[fineLevel]; ++n)
 
  883                m_SDCSolver[coarseLevel]->GetResidualVector(), fineLevel,
 
  884                m_SDCSolver[fineLevel]->UpdateResidualVector(), 
false);
 
  897        for (
size_t timeLevel = 0; timeLevel < 
m_nTimeLevel - 1; timeLevel++)
 
  900                        m_EqSys[timeLevel + 1]->UpdateFields(),
 
  902                        m_SDCSolver[timeLevel + 1]->UpdateSolutionVector()[0]);
 
  907    for (
size_t timeLevel = 0; timeLevel < 
m_nTimeLevel; timeLevel++)
 
  909        for (
size_t i = 0; i < 
m_nVar; ++i)
 
  911            m_comm->GetTimeComm()->Bcast(
 
  912                m_SDCSolver[timeLevel]->UpdateSolutionVector()[0][i],
 
  924    for (
size_t i = 0; i < 
m_nVar; ++i)
 
  928            m_SDCSolver[timeLevel]->GetSolutionVector()[0][i], 1,
 
  930                ->GetIntegratedResidualVector()[
m_QuadPts[timeLevel] - 1][i],
 
  932        m_EqSys[timeLevel]->CopyToPhysField(
 
  934                   ->GetSolutionVector()[
m_QuadPts[timeLevel] - 1][i]);
 
  945    size_t timeLevel = 0;
 
  947        m_EqSys[timeLevel]->GetSession()->DefinesParameter(
"IO_CheckSteps")
 
  948            ? 
m_EqSys[timeLevel]->GetSession()->GetParameter(
"IO_CheckSteps")
 
  950    IOChkStep                  = IOChkStep ? IOChkStep : 
m_nsteps[timeLevel];
 
  951    static std::string dirname = 
m_session->GetSessionName() + 
".pit";
 
  953    if ((step + 1) % IOChkStep == 0)
 
  956        size_t nchk = (step + 1) / IOChkStep;
 
  959        if (!fs::is_directory(dirname))
 
  961            fs::create_directory(dirname);
 
  967            m_SDCSolver[timeLevel]->UpdateLastQuadratureSolutionVector());
 
  970        std::string filename = dirname + 
"/" + 
m_session->GetSessionName() +
 
  971                               "_" + std::to_string(nchk) + 
".fld";
 
  974        m_EqSys[timeLevel]->SetTime(time);
 
  977        m_EqSys[timeLevel]->WriteFld(filename);
 
#define ASSERTL0(condition, msg)
 
tKey RegisterCreatorFunction(tKey idKey, CreatorFunction classCreator, std::string pDesc="")
Register a class with the factory.
 
Defines a specification for a set of points.
 
static std::string RegisterEnumValue(std::string pEnum, std::string pString, int pEnumValue)
Registers an enumeration value.
 
LibUtilities::SessionReaderSharedPtr m_session
Session reader object.
 
LibUtilities::CommSharedPtr m_comm
Communication object.
 
void RestrictResidual(const size_t timeLevel)
 
void UpdateFirstQuadrature(const size_t timeLevel)
 
void InitialiseSDCScheme(void)
 
void AssertParameters(void)
 
void RestrictSolution(const size_t timeLevel)
 
Array< OneD, Array< OneD, NekDouble > > m_ImatFtoC
 
Array< OneD, Array< OneD, NekDouble > > m_ImatCtoF
 
void Restrict(const size_t fineLevel, const SDCarray &in, const size_t coarseLevel, SDCarray &out)
 
void ResidualEval(const NekDouble time, const size_t timeLevel, const size_t n)
 
static std::string className
Name of the class.
 
void InterpolateResidual(const size_t timeLevel)
 
void CorrectSolution(const size_t timeLevel)
 
void EvaluateSDCResidualNorm(const size_t timeLevel)
 
void IntegratedResidualEval(const size_t timeLevel)
 
void RunSweep(const NekDouble time, const size_t timeLevel, const bool update=false)
 
static DriverSharedPtr create(const LibUtilities::SessionReaderSharedPtr &pSession, const SpatialDomains::MeshGraphSharedPtr &pGraph)
Creates an instance of this class.
 
void Interpolate(const size_t coarseLevel, const SDCarray &in, const size_t fineLevel, SDCarray &out, bool forced)
 
void ComputeFASCorrection(const size_t timeLevel)
 
Array< OneD, SDCarray > m_solutionRest
 
void CorrectInitialResidual(const size_t timeLevel)
 
SOLVER_UTILS_EXPORT void v_Execute(std::ostream &out=std::cout) override
Virtual function for solve implementation.
 
void WriteOutput(const size_t step, const NekDouble time)
 
void CorrectInitialSolution(const size_t timeLevel)
 
Array< OneD, std::shared_ptr< LibUtilities::TimeIntegrationSchemeSDC > > m_SDCSolver
 
Array< OneD, SDCarray > m_correction
 
SOLVER_UTILS_EXPORT void v_InitObject(std::ostream &out=std::cout) override
Virtual function for initialisation implementation.
 
Array< OneD, SDCarray > m_storage
 
Array< OneD, SDCarray > m_integralRest
 
void Correct(const size_t coarseLevel, const Array< OneD, Array< OneD, NekDouble > > &in, const size_t fineLevel, Array< OneD, Array< OneD, NekDouble > > &out, bool forced)
 
Array< OneD, SDCarray > m_residualRest
 
void InterpolateSolution(const size_t timeLevel)
 
void PropagateQuadratureSolutionAndResidual(const size_t timeLevel, const size_t index)
 
SOLVER_UTILS_EXPORT DriverPFASST(const LibUtilities::SessionReaderSharedPtr pSession, const SpatialDomains::MeshGraphSharedPtr pGraph)
Constructor.
 
static std::string driverLookupId
 
void CorrectResidual(const size_t timeLevel)
 
Array< OneD, size_t > m_QuadPts
 
bool IsNotInitialCondition(const size_t n)
 
void ApplyWindowing(void)
 
void SetTimeInterpolator(void)
 
Base class for the development of parallel-in-time solvers.
 
size_t m_numChunks
Number of time chunks.
 
NekDouble m_totalTime
Total time integration interval.
 
NekDouble vL2ErrorMax(void)
 
Array< OneD, NekDouble > m_vL2Errors
Storage for parallel-in-time iteration.
 
void UpdateFieldCoeffs(const size_t timeLevel, const Array< OneD, const Array< OneD, NekDouble > > &in=NullNekDoubleArrayOfArray)
 
NekDouble m_chunkTime
Time integration interval per chunk.
 
void SendToNextProc(Array< OneD, Array< OneD, NekDouble > > &array, int &convergence)
 
size_t m_nTimeLevel
Number of time levels.
 
size_t m_iterMaxPIT
Maximum number of parallel-in-time iteration.
 
void PrintErrorNorm(const size_t timeLevel, const bool normalized)
 
Array< OneD, size_t > m_nsteps
Number of time steps for each time level.
 
void InitialiseEqSystem(bool turnoff_output)
 
SOLVER_UTILS_EXPORT void v_InitObject(std::ostream &out=std::cout) override
Virtual function for initialisation implementation.
 
Array< OneD, NekDouble > m_vLinfErrors
 
void EvaluateExactSolution(const size_t timeLevel, const NekDouble &time)
 
void GetParametersFromSession(void)
 
void RecvFromPreviousProc(Array< OneD, Array< OneD, NekDouble > > &array, int &convergence)
 
Array< OneD, std::shared_ptr< UnsteadySystem > > m_EqSys
Equation system to solve.
 
void PrintHeader(const std::string &title, const char c)
 
NekDouble m_tolerPIT
ParallelInTime tolerance.
 
size_t m_chunkRank
Rank in time.
 
void PrintSolverInfo(std::ostream &out=std::cout)
 
size_t m_nVar
Number of variables.
 
Array< OneD, size_t > m_npts
Number of dof for each time level.
 
Array< OneD, Array< OneD, NekDouble > > m_exactsoln
 
void SolutionConvergenceSummary(const size_t timeLevel)
 
NekDouble m_time
Local time.
 
Array< OneD, NekDouble > m_timestep
Time step for each time level.
 
void CopySolutionVector(const Array< OneD, const Array< OneD, NekDouble > > &in, Array< OneD, Array< OneD, NekDouble > > &out)
 
PointsManagerT & PointsManager(void)
 
std::shared_ptr< SessionReader > SessionReaderSharedPtr
 
DriverFactory & GetDriverFactory()
 
Array< OneD, Array< OneD, Array< OneD, NekDouble > > > SDCarray
 
std::shared_ptr< MeshGraph > MeshGraphSharedPtr
 
std::vector< double > w(NPUPPER)
 
std::shared_ptr< DNekMat > DNekMatSharedPtr
 
void Svtvp(int n, const T alpha, const T *x, const int incx, const T *y, const int incy, T *z, const int incz)
Svtvp (scalar times vector plus vector): z = alpha*x + y.
 
void Vadd(int n, const T *x, const int incx, const T *y, const int incy, T *z, const int incz)
Add vector z = x+y.
 
void Smul(int n, const T alpha, const T *x, const int incx, T *y, const int incy)
Scalar multiply y = alpha*x.
 
void Zero(int n, T *x, const int incx)
Zero vector.
 
void Vcopy(int n, const T *x, const int incx, T *y, const int incy)
 
void Vsub(int n, const T *x, const int incx, const T *y, const int incy, T *z, const int incz)
Subtract vector z = x-y.